在Android系统download后第一次启动,imx6sx-sabresd 板子改时间没办法保存到RTC中,导致下一次启动后,时间依然是RTC中初始值。之后再次改时间是可以成功保存到RTC中,也不会再出现时间无法保存问题。
第一次启动改时间时打开logcat会出现下面的错误log:
11-05 00:01:36.291 508 920 D AlarmManagerService: Setting time of day to sec=1194236700
11-05 04:25:00.000 508 920 W AlarmManagerService: Unable to set rtc to 1194236700: No such device
11-05 04:25:00.026 508 508 D ConditionProviders.SCP: onReceive android.intent.action.TIME_SET
11-05 04:25:00.034 508 508 D ConditionProviders.SCP: notifyCondition condition://android/schedule?days=6.7&start=23.30&end=10.0&exitAtAlarm=false STATE_FALSE reason=!meetsSchedule
11-05 04:25:00.035 508 508 D ConditionProviders.SCP: notifyCondition condition://android/schedule?days=1.2.3.4.5&start=22.0&end=7.0&exitAtAlarm=false STATE_TRUE reason=meetsSchedule
11-05 04:25:00.037 508 508 D ConditionProviders.SCP: Scheduling evaluate for Mon Nov 05 07:00:00 GMT+00:00 2007 (1194246000000), in +2h34m59s974ms, now=Mon Nov 05 04:25:00 GMT+00:00 2007 (1194236700026)
11-05 04:25:00.062 737 768 D OpenGLRenderer: endAllActiveAnimators on 0x8bbe5200 (RippleDrawable) with handle 0x8bc67bc0
11-05 04:25:00.111 508 519 W InputMethodManagerService: Window already focused, ignoring focus gain of: com.android.internal.view.IInputMethodClient$Stub$Proxy@e5da2bf attribute=null, token = android.os.BinderProxy@ec6ec1b
11-05 04:25:00.218 921 921 I Periodic: Executing periodic callback for HOUR because the time changed
11-05 04:25:00.314 921 921 I AlarmClock: AlarmInitReceiver android.intent.action.TIME_SET
11-05 04:25:00.491 508 520 I UsageStatsService: Time changed in UsageStats by 15803 seconds
11-05 04:25:00.491 508 520 I UsageStatsService: User[0] Flushing usage stats to disk
11-05 04:25:00.583 508 520 I UsageStatsDatabase: Time changed by +4h23m23s709ms. files deleted: 0 files moved: 4
11-05 04:25:00.613 508 520 I UsageStatsService: User[0] Rollover scheduled @ 2007-11-06 04:19:47(1194322787349)
问题关键在这:AlarmManagerService: Unable to set rtc to 1194236700: No such device
而这个log是在函数static jint android_server_AlarmManagerService_setKernelTime(JNIEnv*, jobject, jlong nativeData, jlong millis)中打印的
213 ALOGD("Setting time of day to sec=%d\n", (int) tv.tv_sec);
214
215 ret = impl->setTime(&tv);
216
217 if(ret < 0) {
218 ALOGW("Unable to set rtc to %ld: %s\n", tv.tv_sec, strerror(errno));
219 ret = -1;
220 }
而这里的setTime之所以会失败是因为class AlarmImpl 私有成员变量变量rtc_id<0
134 if (rtc_id < 0) {
135 ALOGV("Not setting RTC because wall clock RTC was not found");
136 errno = ENODEV;
137 return -1;
138 }
在AlarmManagerService初始化时候调用static jlong android_server_AlarmManagerService_init(JNIEnv*, jobject)设置rtc_id (wall_clock_rtc())。wall_clock_rtc()中读取rtc设备文件成功和失败的log如下:
01-01 00:22:51.635 509 509 E AlarmManagerService: found wall clock RTC 0
01-01 00:01:15.384 508 508 W AlarmManagerService: no wall clock RTC found
242static const char rtc_sysfs[] = "/sys/class/rtc";
269static int wall_clock_rtc()
270{
271 std::unique_ptr dir(opendir(rtc_sysfs), closedir);
272 if (!dir.get()) {
273 ALOGE("failed to open %s: %s", rtc_sysfs, strerror(errno));
274 return -1;
275 }
276
277 struct dirent *dirent;
278 while (errno = 0, dirent = readdir(dir.get())) {
279 unsigned int rtc_id;
280 int matched = sscanf(dirent->d_name, "rtc%u", &rtc_id);
281
282 if (matched < 0)
283 break;
284 else if (matched != 1)
285 continue;
286
287 if (rtc_is_hctosys(rtc_id)) {
288 ALOGV("found wall clock RTC %u", rtc_id);
289 return rtc_id;
290 }
291 }
292
293 if (errno == 0)
294 ALOGW("no wall clock RTC found");
295 else
296 ALOGE("failed to enumerate RTCs: %s", strerror(errno));
297
298 return -1;
299}
可以看出这个错误log是由于系统在读取/sys/class/rtc目录下的文件时候没有任何匹配rtc%u的文件。所以问题变成了rtc driver初始化问题,而从boot log中可以看出
snvs_rtc 20cc000.snvs:snvs-rtc-lp: rtc core: registered 20cc000.snvs:snvs-r as rtc0
snvs_rtc 20cc000.snvs:snvs-rtc-lp: setting system clock to 1970-01-01 00:00:12 UTC (12)
rtc driver是有进行初始化,但是否生成相应的设备文件需要在Linux driver里面debug。
----未完待续