File: | src/sys/arch/amd64/stand/cdboot/../libsa/time.c |
Warning: | line 91, column 10 1st function call argument is an uninitialized value |
Press '?' to see keyboard shortcuts
Keyboard shortcuts:
1 | /* $OpenBSD: time.c,v 1.5 2014/09/23 17:59:25 brad Exp $ */ | |||
2 | ||||
3 | /* | |||
4 | * Copyright (c) 1997 Michael Shalayeff | |||
5 | * Copyright (c) 1997 Tobias Weingartner | |||
6 | * All rights reserved. | |||
7 | * | |||
8 | * Redistribution and use in source and binary forms, with or without | |||
9 | * modification, are permitted provided that the following conditions | |||
10 | * are met: | |||
11 | * 1. Redistributions of source code must retain the above copyright | |||
12 | * notice, this list of conditions and the following disclaimer. | |||
13 | * 2. Redistributions in binary form must reproduce the above copyright | |||
14 | * notice, this list of conditions and the following disclaimer in the | |||
15 | * documentation and/or other materials provided with the distribution. | |||
16 | * | |||
17 | * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR | |||
18 | * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | |||
19 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | |||
20 | * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE | |||
21 | * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | |||
22 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | |||
23 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | |||
24 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT | |||
25 | * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY | |||
26 | * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | |||
27 | * SUCH DAMAGE. | |||
28 | * | |||
29 | */ | |||
30 | ||||
31 | #include <sys/time.h> | |||
32 | #include <machine/biosvar.h> | |||
33 | #include <machine/pio.h> | |||
34 | #include "libsa.h" | |||
35 | #include "biosdev.h" | |||
36 | ||||
37 | #define isleap(y)((((y) % 4) == 0 && ((y) % 100) != 0) || ((y) % 400) == 0) ((((y) % 4) == 0 && ((y) % 100) != 0) || ((y) % 400) == 0) | |||
38 | ||||
39 | /* | |||
40 | * Convert from bcd (packed) to int | |||
41 | */ | |||
42 | static __inline u_int8_t | |||
43 | bcdtoint(u_int8_t c) | |||
44 | { | |||
45 | return ((c & 0xf0) / 8) * 5 + (c & 0x0f); | |||
46 | } | |||
47 | ||||
48 | /* | |||
49 | * Quick compute of time in seconds since the Epoch | |||
50 | */ | |||
51 | const u_short monthcount[] = { | |||
52 | 0, 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334, 365 | |||
53 | }; | |||
54 | ||||
55 | static __inline time_t | |||
56 | compute(int year, u_int8_t month, u_int8_t day, u_int8_t hour, | |||
57 | u_int8_t min, u_int8_t sec) | |||
58 | { | |||
59 | /* Number of days per month */ | |||
60 | register time_t tt; | |||
61 | ||||
62 | /* Compute days */ | |||
63 | tt = (year - 1970) * 365 + monthcount[month] + day - 1; | |||
64 | ||||
65 | /* Compute for leap year */ | |||
66 | for (month <= 2 ? year-- : 0; year >= 1970; year--) | |||
67 | if (isleap(year)((((year) % 4) == 0 && ((year) % 100) != 0) || ((year ) % 400) == 0)) | |||
68 | tt++; | |||
69 | ||||
70 | /* Plus the time */ | |||
71 | tt = sec + 60 * (min + 60 * (tt * 24 + hour)); | |||
72 | ||||
73 | return tt; | |||
74 | } | |||
75 | ||||
76 | static int | |||
77 | bios_time_date(int f, u_int8_t *b) | |||
78 | { | |||
79 | __asm volatile(DOINT(0x1a)"int $0x20+(" "0x1a" ")" "\n\t" | |||
80 | "setc %b0\n\t" | |||
81 | "movb %%ch, 0(%2)\n\t" | |||
82 | "movb %%cl, 1(%2)\n\t" | |||
83 | "movb %%dh, 2(%2)\n\t" | |||
84 | "movb %%dl, 3(%2)\n\t" | |||
85 | : "=a" (f) | |||
86 | : "0" (f), "r" (b) : "%ecx", "%edx", "cc"); | |||
87 | ||||
88 | if (f & 0xff) | |||
89 | return -1; | |||
90 | else { | |||
91 | b[0] = bcdtoint(b[0]); | |||
| ||||
92 | b[1] = bcdtoint(b[1]); | |||
93 | b[2] = bcdtoint(b[2]); | |||
94 | b[3] = bcdtoint(b[3]); | |||
95 | return 0; | |||
96 | } | |||
97 | } | |||
98 | ||||
99 | static __inline int | |||
100 | biosdate(u_int8_t *b) | |||
101 | { | |||
102 | return bios_time_date(4 << 8, b); | |||
103 | } | |||
104 | ||||
105 | static __inline int | |||
106 | biostime(u_int8_t *b) | |||
107 | { | |||
108 | return bios_time_date(2 << 8, b); | |||
109 | } | |||
110 | ||||
111 | /* | |||
112 | * Return time since epoch | |||
113 | */ | |||
114 | time_t | |||
115 | getsecs(void) | |||
116 | { | |||
117 | u_int8_t timebuf[4], datebuf[4]; | |||
118 | ||||
119 | /* Query BIOS for time & date */ | |||
120 | if (!biostime(timebuf) && !biosdate(datebuf)) { | |||
121 | #ifdef notdef | |||
122 | int dst; | |||
123 | ||||
124 | dst = timebuf[3]; | |||
125 | #endif | |||
126 | /* Convert to seconds since Epoch */ | |||
127 | return compute(datebuf[0] * 100 + datebuf[1], datebuf[2], | |||
128 | datebuf[3], timebuf[0], timebuf[1], timebuf[2]); | |||
129 | } else | |||
130 | errno = EIO5; | |||
131 | ||||
132 | return 1; | |||
133 | } | |||
134 | ||||
135 | u_int | |||
136 | sleep(u_int i) | |||
137 | { | |||
138 | register time_t t; | |||
139 | ||||
140 | /* | |||
141 | * Loop for the requested number of seconds, polling BIOS, | |||
142 | * so that it may handle interrupts. | |||
143 | */ | |||
144 | for (t = getsecs() + i; getsecs() < t; cnischar()) | |||
| ||||
145 | ; | |||
146 | ||||
147 | return 0; | |||
148 | } |