1 /*
2  * wpa_supplicant/hostapd / OS specific functions for Win32 systems
3  * Copyright (c) 2005-2006, Jouni Malinen <j@w1.fi>
4  *
5  * This software may be distributed under the terms of the BSD license.
6  * See README for more details.
7  */
8 
9 #include "includes.h"
10 #include <time.h>
11 #include <winsock2.h>
12 #include <wincrypt.h>
13 
14 #include "os.h"
15 
16 void os_sleep(os_time_t sec, os_time_t usec)
17 {
18 	if (sec)
19 		Sleep(sec * 1000);
20 	if (usec)
21 		Sleep(usec / 1000);
22 }
23 
24 
25 int os_get_time(struct os_time *t)
26 {
27 #define EPOCHFILETIME (116444736000000000ULL)
28 	FILETIME ft;
29 	LARGE_INTEGER li;
30 	ULONGLONG tt;
31 
32 #ifdef _WIN32_WCE
33 	SYSTEMTIME st;
34 
35 	GetSystemTime(&st);
36 	SystemTimeToFileTime(&st, &ft);
37 #else /* _WIN32_WCE */
38 	GetSystemTimeAsFileTime(&ft);
39 #endif /* _WIN32_WCE */
40 	li.LowPart = ft.dwLowDateTime;
41 	li.HighPart = ft.dwHighDateTime;
42 	tt = (li.QuadPart - EPOCHFILETIME) / 10;
43 	t->sec = (os_time_t) (tt / 1000000);
44 	t->usec = (os_time_t) (tt % 1000000);
45 
46 	return 0;
47 }
48 
49 
50 int os_get_reltime(struct os_reltime *t)
51 {
52 	/* consider using performance counters or so instead */
53 	struct os_time now;
54 	int res = os_get_time(&now);
55 	t->sec = now.sec;
56 	t->usec = now.usec;
57 	return res;
58 }
59 
60 
61 int os_mktime(int year, int month, int day, int hour, int min, int sec,
62 	      os_time_t *t)
63 {
64 	struct tm tm, *tm1;
65 	time_t t_local, t1, t2;
66 	os_time_t tz_offset;
67 
68 	if (year < 1970 || month < 1 || month > 12 || day < 1 || day > 31 ||
69 	    hour < 0 || hour > 23 || min < 0 || min > 59 || sec < 0 ||
70 	    sec > 60)
71 		return -1;
72 
73 	memset(&tm, 0, sizeof(tm));
74 	tm.tm_year = year - 1900;
75 	tm.tm_mon = month - 1;
76 	tm.tm_mday = day;
77 	tm.tm_hour = hour;
78 	tm.tm_min = min;
79 	tm.tm_sec = sec;
80 
81 	t_local = mktime(&tm);
82 
83 	/* figure out offset to UTC */
84 	tm1 = localtime(&t_local);
85 	if (tm1) {
86 		t1 = mktime(tm1);
87 		tm1 = gmtime(&t_local);
88 		if (tm1) {
89 			t2 = mktime(tm1);
90 			tz_offset = t2 - t1;
91 		} else
92 			tz_offset = 0;
93 	} else
94 		tz_offset = 0;
95 
96 	*t = (os_time_t) t_local - tz_offset;
97 	return 0;
98 }
99 
100 
101 int os_gmtime(os_time_t t, struct os_tm *tm)
102 {
103 	struct tm *tm2;
104 	time_t t2 = t;
105 
106 	tm2 = gmtime(&t2);
107 	if (tm2 == NULL)
108 		return -1;
109 	tm->sec = tm2->tm_sec;
110 	tm->min = tm2->tm_min;
111 	tm->hour = tm2->tm_hour;
112 	tm->day = tm2->tm_mday;
113 	tm->month = tm2->tm_mon + 1;
114 	tm->year = tm2->tm_year + 1900;
115 	return 0;
116 }
117 
118 
119 int os_daemonize(const char *pid_file)
120 {
121 	/* TODO */
122 	return -1;
123 }
124 
125 
126 void os_daemonize_terminate(const char *pid_file)
127 {
128 }
129 
130 
131 int os_get_random(unsigned char *buf, size_t len)
132 {
133 	HCRYPTPROV prov;
134 	BOOL ret;
135 
136 	if (!CryptAcquireContext(&prov, NULL, NULL, PROV_RSA_FULL,
137 				 CRYPT_VERIFYCONTEXT))
138 		return -1;
139 
140 	ret = CryptGenRandom(prov, len, buf);
141 	CryptReleaseContext(prov, 0);
142 
143 	return ret ? 0 : -1;
144 }
145 
146 
147 unsigned long os_random(void)
148 {
149 	return rand();
150 }
151 
152 
153 char * os_rel2abs_path(const char *rel_path)
154 {
155 	return _strdup(rel_path);
156 }
157 
158 
159 int os_program_init(void)
160 {
161 #ifdef CONFIG_NATIVE_WINDOWS
162 	WSADATA wsaData;
163 	if (WSAStartup(MAKEWORD(2, 0), &wsaData)) {
164 		printf("Could not find a usable WinSock.dll\n");
165 		return -1;
166 	}
167 #endif /* CONFIG_NATIVE_WINDOWS */
168 	return 0;
169 }
170 
171 
172 void os_program_deinit(void)
173 {
174 #ifdef CONFIG_NATIVE_WINDOWS
175 	WSACleanup();
176 #endif /* CONFIG_NATIVE_WINDOWS */
177 }
178 
179 
180 int os_setenv(const char *name, const char *value, int overwrite)
181 {
182 	return -1;
183 }
184 
185 
186 int os_unsetenv(const char *name)
187 {
188 	return -1;
189 }
190 
191 
192 char * os_readfile(const char *name, size_t *len)
193 {
194 	FILE *f;
195 	char *buf;
196 
197 	f = fopen(name, "rb");
198 	if (f == NULL)
199 		return NULL;
200 
201 	fseek(f, 0, SEEK_END);
202 	*len = ftell(f);
203 	fseek(f, 0, SEEK_SET);
204 
205 	buf = malloc(*len);
206 	if (buf == NULL) {
207 		fclose(f);
208 		return NULL;
209 	}
210 
211 	fread(buf, 1, *len, f);
212 	fclose(f);
213 
214 	return buf;
215 }
216 
217 
218 void * os_zalloc(size_t size)
219 {
220 	return calloc(1, size);
221 }
222 
223 
224 size_t os_strlcpy(char *dest, const char *src, size_t siz)
225 {
226 	const char *s = src;
227 	size_t left = siz;
228 
229 	if (left) {
230 		/* Copy string up to the maximum size of the dest buffer */
231 		while (--left != 0) {
232 			if ((*dest++ = *s++) == '\0')
233 				break;
234 		}
235 	}
236 
237 	if (left == 0) {
238 		/* Not enough room for the string; force NUL-termination */
239 		if (siz != 0)
240 			*dest = '\0';
241 		while (*s++)
242 			; /* determine total src string length */
243 	}
244 
245 	return s - src - 1;
246 }
247