本文不一定对所有的Android方案有用,但是有一定的参考价值。
在Android13 Amlogic 方案的TV设备,上出现了wifi开启的情况待机关机(input keyevent 26),开机后必现wifi 关闭状态,
这里记录一下解决方法和思路。
查看Setitngs.java 确实有相关代码
Settings.Global.WIFI_SLEEP_POLICY
public static final String WIFI_SLEEP_POLICY = "wifi_sleep_policy";
/**
* Value for {@link #WIFI_SLEEP_POLICY} to use the default Wi-Fi sleep
* policy, which is to sleep shortly after the turning off
* according to the {@link #STAY_ON_WHILE_PLUGGED_IN} setting.
* @deprecated This is no longer used by the platform.
*/
@Deprecated
public static final int WIFI_SLEEP_POLICY_DEFAULT = 0;
/**
* Value for {@link #WIFI_SLEEP_POLICY} to use the default policy when
* the device is on battery, and never go to sleep when the device is
* plugged in.
* @deprecated This is no longer used by the platform.
*/
@Deprecated
public static final int WIFI_SLEEP_POLICY_NEVER_WHILE_PLUGGED = 1;
/**
* Value for {@link #WIFI_SLEEP_POLICY} to never go to sleep.
* @deprecated This is no longer used by the platform.
*/
@Deprecated
public static final int WIFI_SLEEP_POLICY_NEVER = 2;
settings 属性可通过串口指令查询。
//查询
settings get global wifi_sleep_policy
//设置
settings put global wifi_sleep_policy 0/1/2
通过查询发现 wifi_sleep_policy 默认就是 2,不会进入深度睡眠模式。
从上面代码提示看,上面wifi睡眠模式已经废弃 deprecated,平台不支持了!
所以深度睡眠属性 wifi_sleep_policy 并不管用!
从上面深度睡眠模式的注释提示内容看,有提到 according to the {@link #STAY_ON_WHILE_PLUGGED_IN} setting.
所以STAY_ON_WHILE_PLUGGED_IN 属性可能是最新的用于控制睡眠模式的属性。
查看Settings.java代码:
Settings.System.STAY_ON_WHILE_PLUGGED_IN
/**
* Whether we keep the device on while the device is plugged in.
* Supported values are:
*
* - {@code 0} to never stay on while plugged in
* - {@link BatteryManager#BATTERY_PLUGGED_AC} to stay on for AC charger
// 1
* - {@link BatteryManager#BATTERY_PLUGGED_USB} to stay on for USB charger
// 2
* - {@link BatteryManager#BATTERY_PLUGGED_WIRELESS} to stay on for wireless charger
// 4
* - {@link BatteryManager#BATTERY_PLUGGED_DOCK} to stay on for dock charger
// 8
*
* These values can be OR-ed together.
*/
@Readable
public static final String STAY_ON_WHILE_PLUGGED_IN = "stay_on_while_plugged_in";
同样可以通过串口查看并设置相关属性值:
//查询
settings get system stay_on_while_plugged_in
//设置
settings put system stay_on_while_plugged_in 4
试了一下并没有用。设备待机后开机,WiFi还是关闭。
很多问题,如果找不到参考示例,那么查看日志很大概率可以发现问题原因。
该wifi问题出现在关机时间,所以查找wifi和关机关键字的日志估计是有用的。
并不是所有Android 设备的日志都是一样,这里看的是 Android13 AML 方案上的日志.
console:/ # logcat -c; //清一下日志,然后Tv大屏操作待机
console:/ # logcat threadtime | grep -i -E "Wifi|Power"
...//找到最相关的日志
01-01 00:04:04.224 837 907 I PowerManagerService: Sleeping (uid 1000)... //关注点1
01-01 00:04:04.272 1265 1265 D DroidLogicPowerService: action: android.intent.action.SCREEN_OFF //关注点2
01-01 00:04:04.277 1265 1265 D DroidLogicPowerService: setSuspendState: 1
01-01 00:04:04.284 837 1761 I WifiService: setWifiEnabled package=com.droidlogic uid=1000 enable=false isPrivileged=true //关注点3,重点
01-01 00:04:04.287 837 1083 D WifiActiveModeWarden: Shutting down all client mode managers
...
从这里日志看到是有代码进行了关闭wifi 的操作导致,wifi 关闭的情况。
无论是wifi 开启/关闭都有这个 WifiService: setWifiEnabled 的日志,“enable=false” 说明是关闭日志的情况;
所以查看具体是哪里的流程导致关闭wifi,去除这部分代码即可解决待机会关闭wifi 的功能。
这里的 TAG 为 WifiService,并不只是WifiService.java 的打印,很多和它相关类的打印也是用这个TAG,
比如上面的显示就是WifiServiceImpl.java的打印。
这个只是最终被调用的结果,不用去分析。主要分析为什么会调用这个接口即可。
framework\base\services\core\java\com\android\server\power\PowerManagerService.java
case WAKEFULNESS_ASLEEP:
traceMethodName = "reallyGoToSleep";
Slog.i(TAG, "Sleeping (uid " + uid + ")..."); //关注的打印1
从代码看未看出哪里有和wifi调用相关。所以继续往下看。
DroidLogicPowerService 应该是 AML 方案对 PowerService 的衍生类,在里面确实看到了wifi 关闭的代码。
vendor\amlogic\common\frameworks\core\res\src\com\droidlogic\DroidLogicPowerService.java
private BroadcastReceiver mReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
String action = intent.getAction();
Log.d(TAG, "action: " + action); //关注的打印2
if (Intent.ACTION_SCREEN_ON.equals(action)) {
setSuspendState(POWER_SUSPEND_OFF);
setWifiState(context, true);
} else if (Intent.ACTION_SCREEN_OFF.equals(action)) {
setSuspendState(POWER_SUSPEND_ON);
setWifiState(context, false);
} else if (Intent.ACTION_SHUTDOWN.equals(action)) {
setSuspendState(POWER_SUSPEND_SHUTDOWN);
}
}
};
//关注点2 的打印后续会进入这里,下面就有wifi 关闭的代码
private void setWifiState(Context context, boolean state) {
if (mSystemControlManager.getPropertyBoolean("ro.vendor.platform.wifi.suspend", false) == false) {
return;
}
WifiManager wm = (WifiManager) context.getSystemService(Context.WIFI_SERVICE);
if (state) {
if (mWifiDisableWhenSuspend == true) {
wm.setWifiEnabled(true);
mWifiDisableWhenSuspend = false;
}
} else {
wm.setWifiEnabled(false); //关闭wifi
}
。。。
Log.d(TAG, "setWifiState: " + state);
}
所以在 setWifiState 方法进行处理即可,解决待机关机会关闭wifi 的问题。
也可以设置属性 ro.vendor.platform.wifi.suspend 为 false ,即可不进行wifi 开关的控制。
分析待机导致 wiif 关闭问题,这里主要靠的是看日志进行分析解决。
查看相关日志命令:
logcat threadtime | grep -i -E "Wifi|Power"
找到 setWifiEnabled 节点之前的代码,进行分析找到关闭wifi 的代码位置,进行分析处理即可。
实际情况,可能还有很多,需要具体问题。
比如wifi 在开机的时候wifi模组加载异常也可能导致wifi 开启失败;
开关wifi后,或者开机前后,可以通过命令查看wifi开启情况,确定状态是否正确:
settings get global wifi_on // 0表示关闭,1表示开启。