1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32#include "qemu/osdep.h"
33#include <windows.h>
34#include "qapi/error.h"
35#include "sysemu/sysemu.h"
36#include "qemu/main-loop.h"
37#include "trace.h"
38#include "qemu/sockets.h"
39#include "qemu/cutils.h"
40
41
42#include <shlobj.h>
43
44void *qemu_oom_check(void *ptr)
45{
46 if (ptr == NULL) {
47 fprintf(stderr, "Failed to allocate memory: %lu\n", GetLastError());
48 abort();
49 }
50 return ptr;
51}
52
53void *qemu_try_memalign(size_t alignment, size_t size)
54{
55 void *ptr;
56
57 if (!size) {
58 abort();
59 }
60 ptr = VirtualAlloc(NULL, size, MEM_COMMIT, PAGE_READWRITE);
61 trace_qemu_memalign(alignment, size, ptr);
62 return ptr;
63}
64
65void *qemu_memalign(size_t alignment, size_t size)
66{
67 return qemu_oom_check(qemu_try_memalign(alignment, size));
68}
69
70void *qemu_anon_ram_alloc(size_t size, uint64_t *align)
71{
72 void *ptr;
73
74
75
76
77 ptr = VirtualAlloc(NULL, size, MEM_COMMIT, PAGE_READWRITE);
78 trace_qemu_anon_ram_alloc(size, ptr);
79 return ptr;
80}
81
82void qemu_vfree(void *ptr)
83{
84 trace_qemu_vfree(ptr);
85 if (ptr) {
86 VirtualFree(ptr, 0, MEM_RELEASE);
87 }
88}
89
90void qemu_anon_ram_free(void *ptr, size_t size)
91{
92 trace_qemu_anon_ram_free(ptr, size);
93 if (ptr) {
94 VirtualFree(ptr, 0, MEM_RELEASE);
95 }
96}
97
98#ifndef CONFIG_LOCALTIME_R
99
100struct tm *gmtime_r(const time_t *timep, struct tm *result)
101{
102 struct tm *p = gmtime(timep);
103 memset(result, 0, sizeof(*result));
104 if (p) {
105 *result = *p;
106 p = result;
107 }
108 return p;
109}
110
111
112struct tm *localtime_r(const time_t *timep, struct tm *result)
113{
114 struct tm *p = localtime(timep);
115 memset(result, 0, sizeof(*result));
116 if (p) {
117 *result = *p;
118 p = result;
119 }
120 return p;
121}
122#endif
123
124void qemu_set_block(int fd)
125{
126 unsigned long opt = 0;
127 WSAEventSelect(fd, NULL, 0);
128 ioctlsocket(fd, FIONBIO, &opt);
129}
130
131void qemu_set_nonblock(int fd)
132{
133 unsigned long opt = 1;
134 ioctlsocket(fd, FIONBIO, &opt);
135 qemu_fd_register(fd);
136}
137
138int socket_set_fast_reuse(int fd)
139{
140
141
142
143
144
145 return 0;
146}
147
148
149static int socket_error(void)
150{
151 switch (WSAGetLastError()) {
152 case 0:
153 return 0;
154 case WSAEINTR:
155 return EINTR;
156 case WSAEINVAL:
157 return EINVAL;
158 case WSA_INVALID_HANDLE:
159 return EBADF;
160 case WSA_NOT_ENOUGH_MEMORY:
161 return ENOMEM;
162 case WSA_INVALID_PARAMETER:
163 return EINVAL;
164 case WSAENAMETOOLONG:
165 return ENAMETOOLONG;
166 case WSAENOTEMPTY:
167 return ENOTEMPTY;
168 case WSAEWOULDBLOCK:
169
170
171 return EAGAIN;
172 case WSAEINPROGRESS:
173 return EINPROGRESS;
174 case WSAEALREADY:
175 return EALREADY;
176 case WSAENOTSOCK:
177 return ENOTSOCK;
178 case WSAEDESTADDRREQ:
179 return EDESTADDRREQ;
180 case WSAEMSGSIZE:
181 return EMSGSIZE;
182 case WSAEPROTOTYPE:
183 return EPROTOTYPE;
184 case WSAENOPROTOOPT:
185 return ENOPROTOOPT;
186 case WSAEPROTONOSUPPORT:
187 return EPROTONOSUPPORT;
188 case WSAEOPNOTSUPP:
189 return EOPNOTSUPP;
190 case WSAEAFNOSUPPORT:
191 return EAFNOSUPPORT;
192 case WSAEADDRINUSE:
193 return EADDRINUSE;
194 case WSAEADDRNOTAVAIL:
195 return EADDRNOTAVAIL;
196 case WSAENETDOWN:
197 return ENETDOWN;
198 case WSAENETUNREACH:
199 return ENETUNREACH;
200 case WSAENETRESET:
201 return ENETRESET;
202 case WSAECONNABORTED:
203 return ECONNABORTED;
204 case WSAECONNRESET:
205 return ECONNRESET;
206 case WSAENOBUFS:
207 return ENOBUFS;
208 case WSAEISCONN:
209 return EISCONN;
210 case WSAENOTCONN:
211 return ENOTCONN;
212 case WSAETIMEDOUT:
213 return ETIMEDOUT;
214 case WSAECONNREFUSED:
215 return ECONNREFUSED;
216 case WSAELOOP:
217 return ELOOP;
218 case WSAEHOSTUNREACH:
219 return EHOSTUNREACH;
220 default:
221 return EIO;
222 }
223}
224
225int inet_aton(const char *cp, struct in_addr *ia)
226{
227 uint32_t addr = inet_addr(cp);
228 if (addr == 0xffffffff) {
229 return 0;
230 }
231 ia->s_addr = addr;
232 return 1;
233}
234
235void qemu_set_cloexec(int fd)
236{
237}
238
239
240#define _W32_FT_OFFSET (116444736000000000ULL)
241
242int qemu_gettimeofday(qemu_timeval *tp)
243{
244 union {
245 unsigned long long ns100;
246 FILETIME ft;
247 } _now;
248
249 if(tp) {
250 GetSystemTimeAsFileTime (&_now.ft);
251 tp->tv_usec=(long)((_now.ns100 / 10ULL) % 1000000ULL );
252 tp->tv_sec= (long)((_now.ns100 - _W32_FT_OFFSET) / 10000000ULL);
253 }
254
255
256 return 0;
257}
258
259int qemu_get_thread_id(void)
260{
261 return GetCurrentThreadId();
262}
263
264char *
265qemu_get_local_state_pathname(const char *relative_pathname)
266{
267 HRESULT result;
268 char base_path[MAX_PATH+1] = "";
269
270 result = SHGetFolderPath(NULL, CSIDL_COMMON_APPDATA, NULL,
271 0, base_path);
272 if (result != S_OK) {
273
274 g_critical("CSIDL_COMMON_APPDATA unavailable: %ld", (long)result);
275 abort();
276 }
277 return g_strdup_printf("%s" G_DIR_SEPARATOR_S "%s", base_path,
278 relative_pathname);
279}
280
281void qemu_set_tty_echo(int fd, bool echo)
282{
283 HANDLE handle = (HANDLE)_get_osfhandle(fd);
284 DWORD dwMode = 0;
285
286 if (handle == INVALID_HANDLE_VALUE) {
287 return;
288 }
289
290 GetConsoleMode(handle, &dwMode);
291
292 if (echo) {
293 SetConsoleMode(handle, dwMode | ENABLE_ECHO_INPUT | ENABLE_LINE_INPUT);
294 } else {
295 SetConsoleMode(handle,
296 dwMode & ~(ENABLE_ECHO_INPUT | ENABLE_LINE_INPUT));
297 }
298}
299
300static char exec_dir[PATH_MAX];
301
302void qemu_init_exec_dir(const char *argv0)
303{
304
305 char *p;
306 char buf[MAX_PATH];
307 DWORD len;
308
309 len = GetModuleFileName(NULL, buf, sizeof(buf) - 1);
310 if (len == 0) {
311 return;
312 }
313
314 buf[len] = 0;
315 p = buf + len - 1;
316 while (p != buf && *p != '\\') {
317 p--;
318 }
319 *p = 0;
320 if (access(buf, R_OK) == 0) {
321 pstrcpy(exec_dir, sizeof(exec_dir), buf);
322 }
323}
324
325char *qemu_get_exec_dir(void)
326{
327 return g_strdup(exec_dir);
328}
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362static int poll_rest(gboolean poll_msgs, HANDLE *handles, gint nhandles,
363 GPollFD *fds, guint nfds, gint timeout)
364{
365 DWORD ready;
366 GPollFD *f;
367 int recursed_result;
368
369 if (poll_msgs) {
370
371
372
373 ready = MsgWaitForMultipleObjectsEx(nhandles, handles, timeout,
374 QS_ALLINPUT, MWMO_ALERTABLE);
375
376 if (ready == WAIT_FAILED) {
377 gchar *emsg = g_win32_error_message(GetLastError());
378 g_warning("MsgWaitForMultipleObjectsEx failed: %s", emsg);
379 g_free(emsg);
380 }
381 } else if (nhandles == 0) {
382
383 if (timeout == INFINITE) {
384 ready = WAIT_FAILED;
385 } else {
386 SleepEx(timeout, TRUE);
387 ready = WAIT_TIMEOUT;
388 }
389 } else {
390
391
392
393 ready =
394 WaitForMultipleObjectsEx(nhandles, handles, FALSE, timeout, TRUE);
395 if (ready == WAIT_FAILED) {
396 gchar *emsg = g_win32_error_message(GetLastError());
397 g_warning("WaitForMultipleObjectsEx failed: %s", emsg);
398 g_free(emsg);
399 }
400 }
401
402 if (ready == WAIT_FAILED) {
403 return -1;
404 } else if (ready == WAIT_TIMEOUT || ready == WAIT_IO_COMPLETION) {
405 return 0;
406 } else if (poll_msgs && ready == WAIT_OBJECT_0 + nhandles) {
407 for (f = fds; f < &fds[nfds]; ++f) {
408 if (f->fd == G_WIN32_MSG_HANDLE && f->events & G_IO_IN) {
409 f->revents |= G_IO_IN;
410 }
411 }
412
413
414
415
416 if (timeout != 0) {
417 return 1;
418 }
419
420
421
422
423 recursed_result = poll_rest(FALSE, handles, nhandles, fds, nfds, 0);
424 return (recursed_result == -1) ? -1 : 1 + recursed_result;
425 } else if (
426
427 ready < WAIT_OBJECT_0 + nhandles) {
428 for (f = fds; f < &fds[nfds]; ++f) {
429 if ((HANDLE) f->fd == handles[ready - WAIT_OBJECT_0]) {
430 f->revents = f->events;
431 }
432 }
433
434
435
436
437 if (nhandles > 1) {
438
439 int i;
440 for (i = ready - WAIT_OBJECT_0 + 1; i < nhandles; i++) {
441 handles[i-1] = handles[i];
442 }
443 nhandles--;
444
445
446
447
448
449
450
451 if (timeout < 10) {
452 timeout = timeout + 1;
453 } else {
454 timeout = 0;
455 }
456 recursed_result = poll_rest(FALSE, handles, nhandles, fds,
457 nfds, timeout);
458 return (recursed_result == -1) ? -1 : 1 + recursed_result;
459 }
460 return 1;
461 }
462
463 return 0;
464}
465
466gint g_poll(GPollFD *fds, guint nfds, gint timeout)
467{
468 HANDLE handles[MAXIMUM_WAIT_OBJECTS];
469 gboolean poll_msgs = FALSE;
470 GPollFD *f;
471 gint nhandles = 0;
472 int retval;
473
474 for (f = fds; f < &fds[nfds]; ++f) {
475 if (f->fd == G_WIN32_MSG_HANDLE && (f->events & G_IO_IN)) {
476 poll_msgs = TRUE;
477 } else if (f->fd > 0) {
478
479
480
481
482 gint i;
483
484 for (i = 0; i < nhandles; i++) {
485 if (handles[i] == (HANDLE) f->fd) {
486 break;
487 }
488 }
489
490 if (i == nhandles) {
491 if (nhandles == MAXIMUM_WAIT_OBJECTS) {
492 g_warning("Too many handles to wait for!\n");
493 break;
494 } else {
495 handles[nhandles++] = (HANDLE) f->fd;
496 }
497 }
498 }
499 }
500
501 for (f = fds; f < &fds[nfds]; ++f) {
502 f->revents = 0;
503 }
504
505 if (timeout == -1) {
506 timeout = INFINITE;
507 }
508
509
510 if (nhandles > 1 || (nhandles > 0 && poll_msgs)) {
511
512
513
514 retval = poll_rest(poll_msgs, handles, nhandles, fds, nfds, 0);
515
516
517
518
519
520
521
522
523
524
525 if (retval == 0 && (timeout == INFINITE || timeout > 0)) {
526 retval = poll_rest(poll_msgs, handles, nhandles,
527 fds, nfds, timeout);
528 }
529 } else {
530
531
532
533 retval = poll_rest(poll_msgs, handles, nhandles, fds, nfds, timeout);
534 }
535
536 if (retval == -1) {
537 for (f = fds; f < &fds[nfds]; ++f) {
538 f->revents = 0;
539 }
540 }
541
542 return retval;
543}
544
545int getpagesize(void)
546{
547 SYSTEM_INFO system_info;
548
549 GetSystemInfo(&system_info);
550 return system_info.dwPageSize;
551}
552
553void os_mem_prealloc(int fd, char *area, size_t memory, int smp_cpus,
554 Error **errp)
555{
556 int i;
557 size_t pagesize = getpagesize();
558
559 memory = (memory + pagesize - 1) & -pagesize;
560 for (i = 0; i < memory / pagesize; i++) {
561 memset(area + pagesize * i, 0, 1);
562 }
563}
564
565
566char *qemu_get_pid_name(pid_t pid)
567{
568
569 abort();
570}
571
572
573pid_t qemu_fork(Error **errp)
574{
575 errno = ENOSYS;
576 error_setg_errno(errp, errno,
577 "cannot fork child process");
578 return -1;
579}
580
581
582#undef connect
583int qemu_connect_wrap(int sockfd, const struct sockaddr *addr,
584 socklen_t addrlen)
585{
586 int ret;
587 ret = connect(sockfd, addr, addrlen);
588 if (ret < 0) {
589 errno = socket_error();
590 }
591 return ret;
592}
593
594
595#undef listen
596int qemu_listen_wrap(int sockfd, int backlog)
597{
598 int ret;
599 ret = listen(sockfd, backlog);
600 if (ret < 0) {
601 errno = socket_error();
602 }
603 return ret;
604}
605
606
607#undef bind
608int qemu_bind_wrap(int sockfd, const struct sockaddr *addr,
609 socklen_t addrlen)
610{
611 int ret;
612 ret = bind(sockfd, addr, addrlen);
613 if (ret < 0) {
614 errno = socket_error();
615 }
616 return ret;
617}
618
619
620#undef socket
621int qemu_socket_wrap(int domain, int type, int protocol)
622{
623 int ret;
624 ret = socket(domain, type, protocol);
625 if (ret < 0) {
626 errno = socket_error();
627 }
628 return ret;
629}
630
631
632#undef accept
633int qemu_accept_wrap(int sockfd, struct sockaddr *addr,
634 socklen_t *addrlen)
635{
636 int ret;
637 ret = accept(sockfd, addr, addrlen);
638 if (ret < 0) {
639 errno = socket_error();
640 }
641 return ret;
642}
643
644
645#undef shutdown
646int qemu_shutdown_wrap(int sockfd, int how)
647{
648 int ret;
649 ret = shutdown(sockfd, how);
650 if (ret < 0) {
651 errno = socket_error();
652 }
653 return ret;
654}
655
656
657#undef ioctlsocket
658int qemu_ioctlsocket_wrap(int fd, int req, void *val)
659{
660 int ret;
661 ret = ioctlsocket(fd, req, val);
662 if (ret < 0) {
663 errno = socket_error();
664 }
665 return ret;
666}
667
668
669#undef closesocket
670int qemu_closesocket_wrap(int fd)
671{
672 int ret;
673 ret = closesocket(fd);
674 if (ret < 0) {
675 errno = socket_error();
676 }
677 return ret;
678}
679
680
681#undef getsockopt
682int qemu_getsockopt_wrap(int sockfd, int level, int optname,
683 void *optval, socklen_t *optlen)
684{
685 int ret;
686 ret = getsockopt(sockfd, level, optname, optval, optlen);
687 if (ret < 0) {
688 errno = socket_error();
689 }
690 return ret;
691}
692
693
694#undef setsockopt
695int qemu_setsockopt_wrap(int sockfd, int level, int optname,
696 const void *optval, socklen_t optlen)
697{
698 int ret;
699 ret = setsockopt(sockfd, level, optname, optval, optlen);
700 if (ret < 0) {
701 errno = socket_error();
702 }
703 return ret;
704}
705
706
707#undef getpeername
708int qemu_getpeername_wrap(int sockfd, struct sockaddr *addr,
709 socklen_t *addrlen)
710{
711 int ret;
712 ret = getpeername(sockfd, addr, addrlen);
713 if (ret < 0) {
714 errno = socket_error();
715 }
716 return ret;
717}
718
719
720#undef getsockname
721int qemu_getsockname_wrap(int sockfd, struct sockaddr *addr,
722 socklen_t *addrlen)
723{
724 int ret;
725 ret = getsockname(sockfd, addr, addrlen);
726 if (ret < 0) {
727 errno = socket_error();
728 }
729 return ret;
730}
731
732
733#undef send
734ssize_t qemu_send_wrap(int sockfd, const void *buf, size_t len, int flags)
735{
736 int ret;
737 ret = send(sockfd, buf, len, flags);
738 if (ret < 0) {
739 errno = socket_error();
740 }
741 return ret;
742}
743
744
745#undef sendto
746ssize_t qemu_sendto_wrap(int sockfd, const void *buf, size_t len, int flags,
747 const struct sockaddr *addr, socklen_t addrlen)
748{
749 int ret;
750 ret = sendto(sockfd, buf, len, flags, addr, addrlen);
751 if (ret < 0) {
752 errno = socket_error();
753 }
754 return ret;
755}
756
757
758#undef recv
759ssize_t qemu_recv_wrap(int sockfd, void *buf, size_t len, int flags)
760{
761 int ret;
762 ret = recv(sockfd, buf, len, flags);
763 if (ret < 0) {
764 errno = socket_error();
765 }
766 return ret;
767}
768
769
770#undef recvfrom
771ssize_t qemu_recvfrom_wrap(int sockfd, void *buf, size_t len, int flags,
772 struct sockaddr *addr, socklen_t *addrlen)
773{
774 int ret;
775 ret = recvfrom(sockfd, buf, len, flags, addr, addrlen);
776 if (ret < 0) {
777 errno = socket_error();
778 }
779 return ret;
780}
781