]> git.ipfire.org Git - thirdparty/util-linux.git/blob - clock/cmos.c
Imported from util-linux-2.9v tarball.
[thirdparty/util-linux.git] / clock / cmos.c
1 /*
2 * i386 CMOS starts out with 14 bytes clock data
3 * alpha has something similar, but with details
4 * depending on the machine type.
5 *
6 * byte 0: seconds (0-59)
7 * byte 2: minutes (0-59)
8 * byte 4: hours (0-23 in 24hr mode,
9 * 1-12 in 12hr mode, with high bit unset/set if am/pm)
10 * byte 6: weekday (1-7, Sunday=1)
11 * byte 7: day of the month (1-31)
12 * byte 8: month (1-12)
13 * byte 9: year (0-99)
14 * Numbers are stored in BCD/binary if bit 2 of byte 11 is unset/set
15 * The clock is in 12hr/24hr mode if bit 1 of byte 11 is unset/set
16 * The clock is undefined (being updated) if bit 7 of byte 10 is set.
17 * The clock is frozen (to be updated) by setting bit 7 of byte 11
18 * Bit 7 of byte 14 indicates whether the CMOS clock is reliable:
19 * it is 1 if RTC power has been good since this bit was last read;
20 * it is 0 when the battery is dead and system power has been off.
21 *
22 * Avoid setting the RTC clock within 2 seconds of the day rollover
23 * that starts a new month or enters daylight saving time.
24 *
25 * The century situation is messy:
26 * Usually byte 50 (0x32) gives the century (in BCD, so 19 or 20 hex),
27 * but IBM PS/2 has (part of) a checksum there and uses byte 55 (0x37).
28 * Sometimes byte 127 (0x7f) or Bank 1, byte 0x48 gives the century.
29 * The original RTC will not access any century byte; some modern
30 * versions will. If a modern RTC or BIOS increments the century byte
31 * it may go from 0x19 to 0x20, but in some buggy cases 0x1a is produced.
32 */
33
34 /*
35 * A struct tm has int fields
36 * tm_sec (0-59, 60 or 61 only for leap seconds)
37 * tm_min (0-59)
38 * tm_hour (0-23)
39 * tm_mday (1-31)
40 * tm_mon (0-11)
41 * tm_year (number of years since 1900)
42 * tm_wday (0-6, 0=Sunday)
43 * tm_yday (0-365)
44 * tm_isdst (>0: yes, 0: no, <0: unknown)
45 */
46
47 #include <unistd.h> /* for geteuid() */
48 #include <fcntl.h> /* for O_RDWR */
49
50 #include "nls.h"
51
52 #if defined(__i386__) || defined(__alpha__)
53 #include <asm/io.h> /* for inb, outb */
54 #else
55 void outb(int a, int b){}
56 int inb(int c){ return 0; }
57 #endif
58
59 #include "clock.h"
60
61 #define BCD_TO_BIN(val) ((val)=((val)&15) + ((val)>>4)*10)
62 #define BIN_TO_BCD(val) ((val)=(((val)/10)<<4) + (val)%10)
63
64 #define TM_EPOCH 1900
65 int cmos_epoch = 1900; /* 1980 for an alpha in ARC console time */
66 /* One also sees 1952 (Digital Unix?)
67 and 1958 (ALPHA_PRE_V1_2_SRM_CONSOLE) */
68
69 /* Martin Ostermann writes:
70 The problem with the Jensen is twofold: First, it has the clock at a
71 different address. Secondly, it has a distinction beween "local" and
72 normal bus addresses. The local ones pertain to the hardware integrated
73 into the chipset, like serial/parallel ports and of course, the RTC.
74 Those need to be addressed differently. This is handled fine in the kernel,
75 and it's not a problem, since this usually gets totally optimized by the
76 compile. But the i/o routines of (g)libc lack this support so far.
77 The result of this is, that the old clock program worked only on the
78 Jensen when USE_DEV_PORT was defined, but not with the normal inb/outb
79 functions.
80 */
81 int use_dev_port = 0; /* 1 for Jensen */
82 int dev_port_fd;
83 unsigned short clock_ctl_addr = 0x70; /* 0x170 for Jensen */
84 unsigned short clock_data_addr = 0x71; /* 0x171 for Jensen */
85
86
87 int century_byte = 0; /* 0: don't access a century byte
88 50 (0x32): usual PC value
89 55 (0x37): PS/2 */
90
91 #ifdef __alpha__
92 int funkyTOY = 0; /* 1 for PC164/LX164/SX164 type alpha */
93 #endif
94
95 #ifdef __alpha
96
97 static int
98 is_in_cpuinfo(char *fmt, char *str)
99 {
100 FILE *cpuinfo;
101 char field[256];
102 char format[256];
103 int found = 0;
104
105 sprintf(format, "%s : %s", fmt, "%255s");
106
107 if ((cpuinfo = fopen ("/proc/cpuinfo", "r")) != NULL) {
108 while (!feof(cpuinfo)) {
109 if (fscanf (cpuinfo, format, field) == 1) {
110 if (strncmp(field, str, strlen(str)) == 0)
111 found = 1;
112 break;
113 }
114 fgets (field, 256, cpuinfo);
115 }
116 fclose(cpuinfo);
117 }
118 return found;
119 }
120
121 /* Set cmos_epoch, either from user options, or by asking the kernel,
122 or by looking at /proc/cpu_info */
123 void
124 set_cmos_epoch(int ARCconsole, int SRM) {
125 unsigned long epoch;
126
127 /* Believe the user */
128 if (ARCconsole)
129 cmos_epoch = 1980;
130
131 if (ARCconsole || SRM)
132 return;
133
134
135 /* If we can ask the kernel, we don't need guessing from /proc/cpuinfo */
136 if (get_epoch_rtc(&epoch, 1) == 0) {
137 cmos_epoch = epoch;
138 return;
139 }
140
141
142 /* See whether we are dealing with SRM or MILO, as they have
143 different "epoch" ideas. */
144 if (is_in_cpuinfo("system serial number", "MILO")) {
145 ARCconsole = 1;
146 if (debug) printf (_("booted from MILO\n"));
147 }
148
149 /* See whether we are dealing with a RUFFIAN aka UX, as they have REALLY
150 different TOY (TimeOfYear) format: BCD, and not an ARC-style epoch.
151 BCD is detected dynamically, but we must NOT adjust like ARC. */
152 if (ARCconsole && is_in_cpuinfo("system type", "Ruffian")) {
153 ARCconsole = 0;
154 if (debug) printf (_("Ruffian BCD clock\n"));
155 }
156
157 if (ARCconsole)
158 cmos_epoch = 1980;
159 }
160
161 void
162 set_cmos_access(int Jensen, int funky_toy) {
163
164 /* See whether we're dealing with a Jensen---it has a weird I/O
165 system. DEC was just learning how to build Alpha PCs. */
166 if (Jensen || is_in_cpuinfo("system type", "Jensen")) {
167 use_dev_port = 1;
168 clock_ctl_addr = 0x170;
169 clock_data_addr = 0x171;
170 if (debug) printf (_("clockport adjusted to 0x%x\n"), clock_ctl_addr);
171 }
172
173 /* see whether we are dealing with PC164/LX164/SX164, as they have a TOY
174 that must be accessed differently to work correctly. */
175 if (funky_toy ||
176 is_in_cpuinfo("system variation", "PC164") ||
177 is_in_cpuinfo("system variation", "LX164") ||
178 is_in_cpuinfo("system variation", "SX164")) {
179 funkyTOY = 1;
180 if (debug) printf (_("funky TOY!\n"));
181 }
182 }
183 #endif
184
185
186
187
188 #ifdef __i386__
189
190 /*
191 * Try to do CMOS access atomically, so that no other processes
192 * can get a time slice while we are reading or setting the clock.
193 * (Also, if the kernel time is synchronized with an external source,
194 * the kernel itself will fiddle with the RTC every 11 minutes.)
195 */
196
197 static unsigned long
198 atomic(const char *name, unsigned long (*op)(unsigned long),
199 unsigned long arg)
200 {
201 unsigned long v;
202 __asm__ volatile ("cli");
203 v = (*op)(arg);
204 __asm__ volatile ("sti");
205 return v;
206 }
207
208 #elif __alpha__
209
210 /*
211 * The Alpha doesn't allow user-level code to disable interrupts (for
212 * good reasons). Instead, we ensure atomic operation by performing
213 * the operation and checking whether the high 32 bits of the cycle
214 * counter changed. If they did, a context switch must have occurred
215 * and we redo the operation. As long as the operation is reasonably
216 * short, it will complete atomically, eventually.
217 */
218
219 static unsigned long
220 atomic(const char *name, unsigned long (*op)(unsigned long),
221 unsigned long arg)
222 {
223 unsigned long ts1, ts2, n, v;
224
225 for (n = 0; n < 1000; ++n) {
226 asm volatile ("rpcc %0" : "r="(ts1));
227 v = (*op)(arg);
228 asm volatile ("rpcc %0" : "r="(ts2));
229
230 if ((ts1 ^ ts2) >> 32 == 0) {
231 return v;
232 }
233 }
234 fprintf(stderr, _("%s: atomic %s failed for 1000 iterations!"), progname, name);
235 exit(1);
236 }
237
238 #else
239
240 /*
241 * Hmmh, this isn't very atomic. Maybe we should force an error
242 * instead?
243 */
244 static unsigned long
245 atomic(const char *name, unsigned long (*op)(unsigned long),
246 unsigned long arg)
247 {
248 return (*op)(arg);
249 }
250
251 #endif
252
253
254 static inline
255 unsigned long cmos_read(unsigned long reg)
256 {
257 if (use_dev_port) {
258 unsigned char v = reg | 0x80;
259 lseek(dev_port_fd, clock_ctl_addr, 0);
260 write(dev_port_fd, &v, 1);
261 lseek(dev_port_fd, clock_data_addr, 0);
262 read(dev_port_fd, &v, 1);
263 return v;
264 } else {
265 /* We only want to read CMOS data, but unfortunately
266 writing to bit 7 disables (1) or enables (0) NMI;
267 since this bit is read-only we have to guess the old status.
268 Various docs suggest that one should disable NMI while
269 reading/writing CMOS data, and enable it again afterwards.
270 This would yield the sequence
271 outb (reg | 0x80, 0x70);
272 val = inb(0x71);
273 outb (0x0d, 0x70); // 0x0d: random read-only location
274 Other docs state that "any write to 0x70 should be followed
275 by an action to 0x71 or the RTC wil be left in an unknown state".
276 Most docs say that it doesnt matter at all what one does.
277 */
278 /* bit 0x80: disable NMI while reading - should we?
279 Let us follow the kernel and not disable.
280 Called only with 0 <= reg < 128 */
281 outb (reg, clock_ctl_addr);
282 return inb (clock_data_addr);
283 }
284 }
285
286 static inline
287 unsigned long cmos_write(unsigned long reg, unsigned long val)
288 {
289 if (use_dev_port) {
290 unsigned char v = reg | 0x80;
291 lseek(dev_port_fd, clock_ctl_addr, 0);
292 write(dev_port_fd, &v, 1);
293 v = (val & 0xff);
294 lseek(dev_port_fd, clock_data_addr, 0);
295 write(dev_port_fd, &v, 1);
296 } else {
297 outb (reg, clock_ctl_addr);
298 outb (val, clock_data_addr);
299 }
300 return 0;
301 }
302
303 unsigned long cmos_set_time(unsigned long arg)
304 {
305 unsigned char save_control, save_freq_select, pmbit = 0;
306 struct tm tm = *(struct tm *) arg;
307 unsigned int century;
308
309 /*
310 * CMOS byte 10 (clock status register A) has 3 bitfields:
311 * bit 7: 1 if data invalid, update in progress (read-only bit)
312 * (this is raised 224 us before the actual update starts)
313 * 6-4 select base frequency
314 * 010: 32768 Hz time base (default)
315 * 111: reset
316 * all other combinations are manufacturer-dependent
317 * (e.g.: DS1287: 010 = start oscillator, anything else = stop)
318 * 3-0 rate selection bits for interrupt
319 * 0000 none (may stop RTC)
320 * 0001, 0010 give same frequency as 1000, 1001
321 * 0011 122 microseconds (minimum, 8192 Hz)
322 * .... each increase by 1 halves the frequency, doubles the period
323 * 1111 500 milliseconds (maximum, 2 Hz)
324 * 0110 976.562 microseconds (default 1024 Hz)
325 */
326
327 save_control = cmos_read (11); /* tell the clock it's being set */
328 cmos_write (11, (save_control | 0x80));
329 save_freq_select = cmos_read (10); /* stop and reset prescaler */
330 cmos_write (10, (save_freq_select | 0x70));
331
332 tm.tm_year += TM_EPOCH;
333 century = tm.tm_year/100;
334 tm.tm_year -= cmos_epoch;
335 tm.tm_year %= 100;
336 tm.tm_mon += 1;
337 tm.tm_wday += 1;
338
339 if (!(save_control & 0x02)) { /* 12hr mode; the default is 24hr mode */
340 if (tm.tm_hour == 0)
341 tm.tm_hour = 24;
342 if (tm.tm_hour > 12) {
343 tm.tm_hour -= 12;
344 pmbit = 0x80;
345 }
346 }
347
348 if (!(save_control & 0x04)) { /* BCD mode - the default */
349 BIN_TO_BCD(tm.tm_sec);
350 BIN_TO_BCD(tm.tm_min);
351 BIN_TO_BCD(tm.tm_hour);
352 BIN_TO_BCD(tm.tm_wday);
353 BIN_TO_BCD(tm.tm_mday);
354 BIN_TO_BCD(tm.tm_mon);
355 BIN_TO_BCD(tm.tm_year);
356 BIN_TO_BCD(century);
357 }
358
359 cmos_write (0, tm.tm_sec);
360 cmos_write (2, tm.tm_min);
361 cmos_write (4, tm.tm_hour | pmbit);
362 cmos_write (6, tm.tm_wday);
363 cmos_write (7, tm.tm_mday);
364 cmos_write (8, tm.tm_mon);
365 cmos_write (9, tm.tm_year);
366 if (century_byte)
367 cmos_write (century_byte, century);
368
369
370 /* The kernel sources, linux/arch/i386/kernel/time.c, have the
371 following comment:
372
373 The following flags have to be released exactly in this order,
374 otherwise the DS12887 (popular MC146818A clone with integrated
375 battery and quartz) will not reset the oscillator and will not
376 update precisely 500 ms later. You won't find this mentioned
377 in the Dallas Semiconductor data sheets, but who believes data
378 sheets anyway ... -- Markus Kuhn
379 */
380
381 cmos_write (11, save_control);
382 cmos_write (10, save_freq_select);
383 return 0;
384 }
385
386 static int
387 hclock_read(unsigned long reg) {
388 return atomic("clock read", cmos_read, (reg));
389 }
390
391 static void
392 hclock_set_time(const struct tm *tm) {
393 atomic("set time", cmos_set_time, (unsigned long)(tm));
394 }
395
396 static inline int
397 cmos_clock_busy() {
398 return
399 #ifdef __alpha__
400 /* poll bit 4 (UF) of Control Register C */
401 funkyTOY ? (hclock_read(12) & 0x10) :
402 #endif
403 /* poll bit 7 (UIP) of Control Register A */
404 (hclock_read(10) & 0x80);
405 }
406
407
408 static int
409 synchronize_to_clock_tick_cmos(void) {
410 int i;
411
412 /* Wait for rise. Should be within a second, but in case something
413 weird happens, we have a limit on this loop to reduce the impact
414 of this failure.
415 */
416 for (i = 0; !cmos_clock_busy(); i++)
417 if (i >= 10000000)
418 return 1;
419
420 /* Wait for fall. Should be within 2.228 ms. */
421 for (i = 0; cmos_clock_busy(); i++)
422 if (i >= 1000000)
423 return 1;
424 return 0;
425 }
426
427
428
429 static int
430 read_hardware_clock_cmos(struct tm *tm) {
431 /*----------------------------------------------------------------------------
432 Read the hardware clock and return the current time via <tm> argument.
433 Assume we have an ISA machine and read the clock directly with CPU I/O
434 instructions.
435
436 This function is not totally reliable. It takes a finite and
437 unpredictable amount of time to execute the code below. During that
438 time, the clock may change and we may even read an invalid value in
439 the middle of an update. We do a few checks to minimize this
440 possibility, but only the kernel can actually read the clock
441 properly, since it can execute code in a short and predictable
442 amount of time (by turning of interrupts).
443
444 In practice, the chance of this function returning the wrong time is
445 extremely remote.
446
447 -----------------------------------------------------------------------------*/
448 bool got_time = FALSE;
449 unsigned char status, pmbit;
450
451 status = pmbit = 0; /* just for gcc */
452
453 while (!got_time) {
454 /* Bit 7 of Byte 10 of the Hardware Clock value is the Update In Progress
455 (UIP) bit, which is on while and 244 uS before the Hardware Clock
456 updates itself. It updates the counters individually, so reading
457 them during an update would produce garbage. The update takes 2mS,
458 so we could be spinning here that long waiting for this bit to turn
459 off.
460
461 Furthermore, it is pathologically possible for us to be in this
462 code so long that even if the UIP bit is not on at first, the
463 clock has changed while we were running. We check for that too,
464 and if it happens, we start over.
465 */
466
467 if (!cmos_clock_busy()) {
468 /* No clock update in progress, go ahead and read */
469 tm->tm_sec = hclock_read(0);
470 tm->tm_min = hclock_read(2);
471 tm->tm_hour = hclock_read(4);
472 tm->tm_wday = hclock_read(6);
473 tm->tm_mday = hclock_read(7);
474 tm->tm_mon = hclock_read(8);
475 tm->tm_year = hclock_read(9);
476 status = hclock_read(11);
477 #if 0
478 if (century_byte)
479 century = hclock_read(century_byte);
480 #endif
481
482 /* Unless the clock changed while we were reading, consider this
483 a good clock read .
484 */
485 if (tm->tm_sec == hclock_read (0))
486 got_time = TRUE;
487 }
488 /* Yes, in theory we could have been running for 60 seconds and
489 the above test wouldn't work!
490 */
491 }
492
493 if (!(status & 0x04)) { /* BCD mode - the default */
494 BCD_TO_BIN(tm->tm_sec);
495 BCD_TO_BIN(tm->tm_min);
496 pmbit = (tm->tm_hour & 0x80);
497 tm->tm_hour &= 0x7f;
498 BCD_TO_BIN(tm->tm_hour);
499 BCD_TO_BIN(tm->tm_wday);
500 BCD_TO_BIN(tm->tm_mday);
501 BCD_TO_BIN(tm->tm_mon);
502 BCD_TO_BIN(tm->tm_year);
503 #if 0
504 BCD_TO_BIN(century);
505 #endif
506 }
507
508 /* We don't use the century byte of the Hardware Clock
509 since we don't know its address (usually 50 or 55).
510 Here, we follow the advice of the X/Open Base Working Group:
511 "if century is not specified, then values in the range [69-99]
512 refer to years in the twentieth century (1969 to 1999 inclusive),
513 and values in the range [00-68] refer to years in the twenty-first
514 century (2000 to 2068 inclusive)."
515 */
516
517 tm->tm_wday -= 1;
518 tm->tm_mon -= 1;
519 tm->tm_year += (cmos_epoch - TM_EPOCH);
520 if (tm->tm_year < 69)
521 tm->tm_year += 100;
522 if (pmbit) {
523 tm->tm_hour += 12;
524 if (tm->tm_hour == 24)
525 tm->tm_hour = 0;
526 }
527
528 tm->tm_isdst = -1; /* don't know whether it's daylight */
529 return 0;
530 }
531
532
533
534 static int
535 set_hardware_clock_cmos(const struct tm *new_broken_time) {
536
537 hclock_set_time(new_broken_time);
538 return 0;
539 }
540
541 static int
542 i386_iopl(const int level) {
543 #if defined(__i386__) || defined(__alpha__)
544 extern int iopl(const int level);
545 return iopl(level);
546 #else
547 return -2;
548 #endif
549 }
550
551 static int
552 get_permissions_cmos(void) {
553 int rc;
554
555 if (use_dev_port) {
556 if ((dev_port_fd = open("/dev/port", O_RDWR)) < 0) {
557 int errsv = errno;
558 fprintf(stderr, _("Cannot open /dev/port: %s"), strerror(errsv));
559 rc = 1;
560 } else
561 rc = 0;
562 } else {
563 rc = i386_iopl(3);
564 if (rc == -2) {
565 fprintf(stderr, _("I failed to get permission because I didnt try.\n"));
566 } else if (rc != 0) {
567 rc = errno;
568 fprintf(stderr, _("%s is unable to get I/O port access: "
569 "the iopl(3) call failed.\n"), progname);
570 if(rc == EPERM && geteuid())
571 fprintf(stderr, _("Probably you need root privileges.\n"));
572 }
573 }
574 return rc ? 1 : 0;
575 }
576
577 static struct clock_ops cmos = {
578 "direct I/O instructions to ISA clock",
579 get_permissions_cmos,
580 read_hardware_clock_cmos,
581 set_hardware_clock_cmos,
582 synchronize_to_clock_tick_cmos,
583 };
584
585
586 /* return &cmos if cmos clock present, NULL otherwise */
587 /* choose this construction to avoid gcc messages about unused variables */
588
589 struct clock_ops *
590 probe_for_cmos_clock(void){
591 int have_cmos =
592 #if defined(__i386__) || defined(__alpha__)
593 TRUE;
594 #else
595 FALSE;
596 #endif
597 return have_cmos ? &cmos : NULL;
598 }