通过WIFI(不用数据线)连接Android手机调试

通过WIFI(不用数据线)连接Android手机调试

本文主要介绍WIFI 链接手机调试,这里详细介绍了WIFI 链接Android手机实现调试的过程,有需要的小伙伴可以参考下

Android开发中少不了真机调试,总用数据线插插拔拔的还是不方便也不稳定,其实可以实现WIFI的方式连接android手机。

       1. 当然首先要打开WIFI,手机要和电脑在同一局域网内。

       2. 在手机上安装AdbWireless(Google Play上需搜一下就有),注意手机是需要root过的。

       3. 安装完毕后在手机上启动AdbWireless,按屏幕中央的大按钮激活无线连接:

如何通过WIFI连接(不用数据线)Android手机调试

       4. 按照屏幕提示,在电脑上从Android SDK\platform-tools目录中找到adb(Android Debug Bridge),命令行输入如下命令即可完成连接:

       adb connect xx.xx.xx.xx

通过WIFI(不用数据线)连接Android手机调试

 

如何通过WIFI连接(不用数据线)Android手机调试

       5. 现在再回到Eclipse里启动调试,发现到手机的连接已经成功建立:

如何通过WIFI连接(不用数据线)Android手机调试

 

以上就是Android 利用WIFI 链接调试的资料,后续继续补充,希望能帮到有需要的朋友。

 



在PowerManager的API文档中,给出了一个关机/重启接口:
public void reboot (String reason)

对于这个接口的描述很简单,就是几句话。
接口的作用就是重启设备,而且,就算重启成功了也没有返回值。
需要包含REBOOT权限,也就是android.permission.REBOOT
唯一参数reason代表需要的特定重启模式,比如recovery,当然也可以为null。

一、上层空间 
1.frameworks/base/core/java/android/os/PowerManager.java

/**
* Reboot the device. Will not return if the reboot is
* successful. Requires the {@link android.Manifest.permission#REBOOT}
* permission.
*
* @param reason code to pass to the kernel (e.g., "recovery") to
* request special boot modes, or null.
*/
public void reboot(String reason)
{
try {
mService.reboot(reason);
} catch (RemoteException e) {
}
}

mService为IPowerManager Binder接口服务。

**
* {@hide}
*/
public PowerManager(IPowerManager service, Handler handler)
{
mService = service;
mHandler = handler;
}

 

2.frameworks/base/core/java/android/os/IPowerManager.aidl

interface IPowerManager
{
...
void reboot(String reason);
...
}

3.frameworks/base/services/java/com/android/server/PowerManagerService.java

 

/**
* Reboot the device immediately, passing 'reason' (may be null)
* to the underlying __reboot system call. Should not return.
*/
public void reboot(String reason)
{
mContext.enforceCallingOrSelfPermission(android.Manifest.permission.REBOOT, null);

if (mHandler == null || !ActivityManagerNative.isSystemReady()) {
throw new IllegalStateException("Too early to call reboot()");
}

final String finalReason = reason;
Runnable runnable = new Runnable() {
public void run() {
synchronized (this) {
ShutdownThread.reboot(getUiContext(), finalReason, false);
}

}
};
// ShutdownThread must run on a looper capable of displaying the UI.
mHandler.post(runnable);

// PowerManager.reboot() is documented not to return so just wait for the inevitable.
synchronized (runnable) {
while (true) {
try {
runnable.wait();
} catch (InterruptedException e) {
}
}
}
}

4.frameworks/base/services/java/com/android/server/pm/ShutdownThread.java

 

/**
* Request a clean shutdown, waiting for subsystems to clean up their
* state etc. Must be called from a Looper thread in which its UI
* is shown.
*
* @param context Context used to display the shutdown progress dialog.
* @param reason code to pass to the kernel (e.g. "recovery"), or null.
* @param confirm true if user confirmation is needed before shutting down.
*/
public static void reboot(final Context context, String reason, boolean confirm) {
mReboot = true;
mRebootSafeMode = false;
mRebootReason = reason;
shutdownInner(context, confirm);
}

 这里说明是需要重启,且不是安全模式,重启参数为传递下来的reason,shutdownInner的confirm参数是用来设置是否有确认提示框的,通过reboot接口调用重启是没有的,为false。
重启的实现在run()中,因为ShutdownThread是Thread的扩展,所以run会自动运行。

 

/**
* Makes sure we handle the shutdown gracefully.
* Shuts off power regardless of radio and bluetooth state if the alloted time has passed.
*/
public void run() {
BroadcastReceiver br = new BroadcastReceiver() {
@Override public void onReceive(Context context, Intent intent) {
// We don't allow apps to cancel this, so ignore the result.
actionDone();
}
};

/*
* Write a system property in case the system_server reboots before we
* get to the actual hardware restart. If that happens, we'll retry at
* the beginning of the SystemServer startup.
*/
{
String reason = (mReboot ? "1" : "0") + (mRebootReason != null ? mRebootReason : "");
SystemProperties.set(SHUTDOWN_ACTION_PROPERTY, reason);
}

/*
* If we are rebooting into safe mode, write a system property
* indicating so.
*/
if (mRebootSafeMode) {
SystemProperties.set(REBOOT_SAFEMODE_PROPERTY, "1");
}
...
rebootOrShutdown(mReboot, mRebootReason);
}

 在重启前会将重启原因写入sys.shutdown.requested,如果没有则为空,如果是安全模式还会将persist.sys.safemode置1,之后会进行一些关机前的预处理,关闭ActivityManager以及MountService,最终调用rebootOrShutdown进行关机操作。

 

/**
* Do not call this directly. Use {@link #reboot(Context, String, boolean)}
* or {@link #shutdown(Context, boolean)} instead.
*
* @param reboot true to reboot or false to shutdown
* @param reason reason for reboot
*/
public static void rebootOrShutdown(boolean reboot, String reason) {
if (reboot) {
Log.i(TAG, "Rebooting, reason: " + reason);
try {
PowerManagerService.lowLevelReboot(reason);
} catch (Exception e) {
Log.e(TAG, "Reboot failed, will attempt shutdown instead", e);
}
} else if (SHUTDOWN_VIBRATE_MS > 0) {
// vibrate before shutting down
Vibrator vibrator = new SystemVibrator();
try {
vibrator.vibrate(SHUTDOWN_VIBRATE_MS);
} catch (Exception e) {
// Failure to vibrate shouldn't interrupt shutdown. Just log it.
Log.w(TAG, "Failed to vibrate during shutdown.", e);
}

// vibrator is asynchronous so we need to wait to avoid shutting down too soon.
try {
Thread.sleep(SHUTDOWN_VIBRATE_MS);
} catch (InterruptedException unused) {
}
}

// Shutdown power
Log.i(TAG, "Performing low-level shutdown...");
PowerManagerService.lowLevelShutdown();
}
}

如果确认重启,则调用PowerManagerService的lowLevelReboot函数,参数就是传递下来的reason,稍后分析。如果不是重启,即mReboot=false,那就是需要关机了,在shutdown函数中就能够知道。

 

/**
* Request a clean shutdown, waiting for subsystems to clean up their
* state etc. Must be called from a Looper thread in which its UI
* is shown.
*
* @param context Context used to display the shutdown progress dialog.
* @param confirm true if user confirmation is needed before shutting down.
*/
public static void shutdown(final Context context, boolean confirm) {
mReboot = false;
mRebootSafeMode = false;
shutdownInner(context, confirm);
}

 关机的时候需要震动,就是这里了SHUTDOWN_VIBRATE_MS,默认的定义是500ms。但是在代码上看,无论如何,最后都会调用一下lowLevelShutdown函数,也就是关机。逻辑上,这里可能是个问题,但是实际中,如果重启操作能够调用成功的话,整个系统都重启了,后边的代码当然不可能执行到了。

目光转回PowerManagerService
4.frameworks/base/services/java/com/android/server/PowerManagerService.java

 

/**
* Low-level function to reboot the device.
*
* @param reason code to pass to the kernel (e.g. "recovery"), or null.
* @throws IOException if reboot fails for some reason (eg, lack of
* permission)
*/
public static void lowLevelReboot(String reason) throws IOException {
nativeReboot(reason);
}

/**
* Low-level function turn the device off immediately, without trying
* to be clean. Most people should use
* {@link com.android.server.pm.internal.app.ShutdownThread} for a clean shutdown.
*/
public static void lowLevelShutdown() {
nativeShutdown();
}

很熟悉的字样native,是JNI调用了:

private static native void nativeShutdown();
private static native void nativeReboot(String reason) throws IOException;

5.frameworks/base/services/jni/com_android_server_PowerManagerService.cpp

 

static JNINativeMethod gPowerManagerServiceMethods[] = {
/* name, signature, funcPtr */
...
{ "nativeShutdown", "()V",
(void*) nativeShutdown },
{ "nativeReboot", "(Ljava/lang/String;)V",
(void*) nativeReboot },
...
};

这两个好哥俩的实现也是在一起的:

 

static void nativeShutdown(JNIEnv *env, jobject clazz) {
android_reboot(ANDROID_RB_POWEROFF, 0, 0);
}

static void nativeReboot(JNIEnv *env, jobject clazz, jstring reason) {
if (reason == NULL) {
android_reboot(ANDROID_RB_RESTART, 0, 0);
} else {
const char *chars = env->GetStringUTFChars(reason, NULL);
android_reboot(ANDROID_RB_RESTART2, 0, (char *) chars);
env->ReleaseStringUTFChars(reason, chars); // In case it fails.
}
jniThrowIOException(env, errno);
}

 可以看到无论是关机还是重启,都是调用android_reboot来实现的,只是参数不一样而已。

6.system/core/libcutils/android_reboot.c

 

int android_reboot(int cmd, int flags, char *arg)
{
int ret = 0;
int reason = -1;

#ifdef RECOVERY_PRE_COMMAND
if (cmd == (int) ANDROID_RB_RESTART2) {
if (arg && strlen(arg) > 0) {
char cmd[PATH_MAX];
sprintf(cmd, RECOVERY_PRE_COMMAND " %s", arg);
system(cmd);
}
}
#endif

if (!(flags & ANDROID_RB_FLAG_NO_SYNC))
sync();

if (!(flags & ANDROID_RB_FLAG_NO_REMOUNT_RO))
remount_ro();

switch (cmd) {
case ANDROID_RB_RESTART:
reason = RB_AUTOBOOT;
break;

case ANDROID_RB_POWEROFF:
ret = reboot(RB_POWER_OFF);
return ret;

case ANDROID_RB_RESTART2:
// REBOOT_MAGIC
break;

default:
return -1;
}

#ifdef RECOVERY_PRE_COMMAND_CLEAR_REASON
reason = RB_AUTOBOOT;
#endif

if (reason != -1)
ret = reboot(reason);
else
ret = __reboot(LINUX_REBOOT_MAGIC1, LINUX_REBOOT_MAGIC2,
LINUX_REBOOT_CMD_RESTART2, arg);

return ret;
}

 

http://www.jb51.net/article/79844.htm

 

 

Android应用中仿今日头条App制作ViewPager指示器

http://www.jb51.net/article/82683.htm

 

Android开发教程之shape和selector的结合使用

http://www.jb51.net/article/78539.htm

 

Android 自定义弹性ListView控件实例代码(三种方法

http://www.jb51.net/article/78249.htm

 


 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

你可能感兴趣的:(Android)