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