busybox/util-linux/hwclock.c
<<
>>
Prefs
   1/* vi: set sw=4 ts=4: */
   2/*
   3 * Mini hwclock implementation for busybox
   4 *
   5 * Copyright (C) 2002 Robert Griebl <griebl@gmx.de>
   6 *
   7 * Licensed under GPLv2 or later, see file LICENSE in this tarball for details.
   8*/
   9
  10#include <sys/utsname.h>
  11#include "libbb.h"
  12#include "rtc_.h"
  13
  14#if ENABLE_FEATURE_HWCLOCK_LONG_OPTIONS
  15# ifndef _GNU_SOURCE
  16#  define _GNU_SOURCE
  17# endif
  18#endif
  19
  20static const char *rtcname;
  21
  22static time_t read_rtc(int utc)
  23{
  24        time_t ret;
  25        int fd;
  26
  27        fd = rtc_xopen(&rtcname, O_RDONLY);
  28        ret = rtc_read_time(fd, utc);
  29        close(fd);
  30
  31        return ret;
  32}
  33
  34static void write_rtc(time_t t, int utc)
  35{
  36        struct tm tm;
  37        int rtc = rtc_xopen(&rtcname, O_WRONLY);
  38
  39        if (utc)
  40                gmtime_r(&t, &tm);
  41        else
  42                localtime_r(&t, &tm);
  43        tm.tm_isdst = 0;
  44
  45        xioctl(rtc, RTC_SET_TIME, &tm);
  46
  47        close(rtc);
  48}
  49
  50static void show_clock(int utc)
  51{
  52        //struct tm *ptm;
  53        time_t t;
  54        char *cp;
  55
  56        t = read_rtc(utc);
  57        //ptm = localtime(&t);  /* Sets 'tzname[]' */
  58
  59        cp = ctime(&t);
  60        if (cp[0])
  61                cp[strlen(cp) - 1] = '\0';
  62
  63        //printf("%s  %.6f seconds %s\n", cp, 0.0, utc ? "" : (ptm->tm_isdst ? tzname[1] : tzname[0]));
  64        printf("%s  0.000000 seconds\n", cp);
  65}
  66
  67static void to_sys_clock(int utc)
  68{
  69        struct timeval tv;
  70        const struct timezone tz = { timezone/60 - 60*daylight, 0 };
  71
  72        tv.tv_sec = read_rtc(utc);
  73        tv.tv_usec = 0;
  74        if (settimeofday(&tv, &tz))
  75                bb_perror_msg_and_die("settimeofday() failed");
  76}
  77
  78static void from_sys_clock(int utc)
  79{
  80        struct timeval tv;
  81
  82        gettimeofday(&tv, NULL);
  83        //if (gettimeofday(&tv, NULL))
  84        //      bb_perror_msg_and_die("gettimeofday() failed");
  85        write_rtc(tv.tv_sec, utc);
  86}
  87
  88#define HWCLOCK_OPT_LOCALTIME   0x01
  89#define HWCLOCK_OPT_UTC         0x02
  90#define HWCLOCK_OPT_SHOW        0x04
  91#define HWCLOCK_OPT_HCTOSYS     0x08
  92#define HWCLOCK_OPT_SYSTOHC     0x10
  93#define HWCLOCK_OPT_RTCFILE     0x20
  94
  95int hwclock_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
  96int hwclock_main(int argc UNUSED_PARAM, char **argv)
  97{
  98        unsigned opt;
  99        int utc;
 100
 101#if ENABLE_FEATURE_HWCLOCK_LONG_OPTIONS
 102        static const char hwclock_longopts[] ALIGN1 =
 103                "localtime\0" No_argument "l"
 104                "utc\0"       No_argument "u"
 105                "show\0"      No_argument "r"
 106                "hctosys\0"   No_argument "s"
 107                "systohc\0"   No_argument "w"
 108                "file\0"      Required_argument "f"
 109                ;
 110        applet_long_options = hwclock_longopts;
 111#endif
 112        opt_complementary = "r--ws:w--rs:s--wr:l--u:u--l";
 113        opt = getopt32(argv, "lurswf:", &rtcname);
 114
 115        /* If -u or -l wasn't given check if we are using utc */
 116        if (opt & (HWCLOCK_OPT_UTC | HWCLOCK_OPT_LOCALTIME))
 117                utc = (opt & HWCLOCK_OPT_UTC);
 118        else
 119                utc = rtc_adjtime_is_utc();
 120
 121        if (opt & HWCLOCK_OPT_HCTOSYS)
 122                to_sys_clock(utc);
 123        else if (opt & HWCLOCK_OPT_SYSTOHC)
 124                from_sys_clock(utc);
 125        else
 126                /* default HWCLOCK_OPT_SHOW */
 127                show_clock(utc);
 128
 129        return 0;
 130}
 131