diff options
author | Greg Hackmann <ghackmann@google.com> | 2013-12-18 00:35:07 +0000 |
---|---|---|
committer | Android Git Automerger <android-git-automerger@android.com> | 2013-12-18 00:35:07 +0000 |
commit | 2f77ecb81366d9c269d608e33ec0a1ee9795dffe (patch) | |
tree | 7e8525f745c7f9f0b30915fdaf8deac294c4ba8a /toolbox | |
parent | ec5b104ca2ec459348f7b035fad878c65e4ec2f7 (diff) | |
parent | 796be8f1432fd02d83f2dae9dbcf11a0976df3b5 (diff) | |
download | system_core-2f77ecb81366d9c269d608e33ec0a1ee9795dffe.zip system_core-2f77ecb81366d9c269d608e33ec0a1ee9795dffe.tar.gz system_core-2f77ecb81366d9c269d608e33ec0a1ee9795dffe.tar.bz2 |
am 796be8f1: am b1a82bcb: am f1da46d2: am d27498cb: Merge "toolbox: date: use RTC subsystem on devices without /dev/alarm"
* commit '796be8f1432fd02d83f2dae9dbcf11a0976df3b5':
toolbox: date: use RTC subsystem on devices without /dev/alarm
Diffstat (limited to 'toolbox')
-rw-r--r-- | toolbox/date.c | 94 |
1 files changed, 80 insertions, 14 deletions
diff --git a/toolbox/date.c b/toolbox/date.c index fc8e4f8..ed307c0 100644 --- a/toolbox/date.c +++ b/toolbox/date.c @@ -6,15 +6,87 @@ #include <errno.h> #include <time.h> #include <linux/android_alarm.h> +#include <linux/rtc.h> #include <sys/ioctl.h> +static int settime_alarm(struct timespec *ts) { + int fd, ret; + + fd = open("/dev/alarm", O_RDWR); + if (fd < 0) + return fd; + + ret = ioctl(fd, ANDROID_ALARM_SET_RTC, &ts); + close(fd); + return ret; +} + +static int settime_alarm_tm(struct tm *tm) { + time_t t; + struct timespec ts; + + t = mktime(tm); + ts.tv_sec = t; + ts.tv_nsec = 0; + return settime_alarm(&ts); +} + +static int settime_alarm_timeval(struct timeval *tv) { + struct timespec ts; + + ts.tv_sec = tv->tv_sec; + ts.tv_nsec = tv->tv_usec * 1000; + return settime_alarm(&ts); +} + +static int settime_rtc_tm(struct tm *tm) { + int fd, ret; + struct timeval tv; + struct rtc_time rtc; + + fd = open("/dev/rtc0", O_RDWR); + if (fd < 0) + return fd; + + tv.tv_sec = mktime(tm); + tv.tv_usec = 0; + + ret = settimeofday(&tv, NULL); + if (ret < 0) + goto done; + + memset(&rtc, 0, sizeof(rtc)); + rtc.tm_sec = tm->tm_sec; + rtc.tm_min = tm->tm_min; + rtc.tm_hour = tm->tm_hour; + rtc.tm_mday = tm->tm_mday; + rtc.tm_mon = tm->tm_mon; + rtc.tm_year = tm->tm_year; + rtc.tm_wday = tm->tm_wday; + rtc.tm_yday = tm->tm_yday; + rtc.tm_isdst = tm->tm_isdst; + + ret = ioctl(fd, RTC_SET_TIME, rtc); +done: + close(fd); + return ret; +} + +static int settime_rtc_timeval(struct timeval *tv) { + struct tm tm, *err; + time_t t = tv->tv_sec; + + err = gmtime_r(&t, &tm); + if (!err) + return -1; + + return settime_rtc_tm(&tm); +} + static void settime(char *s) { struct tm tm; int day = atoi(s); int hour; - time_t t; - int fd; - struct timespec ts; while (*s && *s != '.') s++; @@ -32,12 +104,8 @@ static void settime(char *s) { tm.tm_sec = (hour % 100); tm.tm_isdst = -1; - t = mktime(&tm); - - fd = open("/dev/alarm", O_RDWR); - ts.tv_sec = t; - ts.tv_nsec = 0; - ioctl(fd, ANDROID_ALARM_SET_RTC, &ts); + if (settime_alarm_tm(&tm) < 0) + settime_rtc_tm(&tm); } int date_main(int argc, char *argv[]) @@ -115,11 +183,9 @@ int date_main(int argc, char *argv[]) //tv.tv_usec = 0; strtotimeval(argv[optind], &tv); printf("time %s -> %lu.%lu\n", argv[optind], tv.tv_sec, tv.tv_usec); - fd = open("/dev/alarm", O_RDWR); - ts.tv_sec = tv.tv_sec; - ts.tv_nsec = tv.tv_usec * 1000; - res = ioctl(fd, ANDROID_ALARM_SET_RTC, &ts); - //res = settimeofday(&tv, NULL); + res = settime_alarm_timeval(&tv); + if (res < 0) + res = settime_rtc_timeval(&tv); if(res < 0) { fprintf(stderr,"settimeofday failed %s\n", strerror(errno)); return 1; |