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