VirtualBox

source: vbox/trunk/src/VBox/HostDrivers/Support/win/SUPLib-win.cpp@ 10682

Last change on this file since 10682 was 10256, checked in by vboxsync, 17 years ago

SUPDRVIOC.h -> (../)SUPDrvIOC.h

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 24.3 KB
Line 
1/** $Id: SUPLib-win.cpp 10256 2008-07-04 20:28:51Z vboxsync $ */
2/** @file
3 * VirtualBox Support Library - Windows NT specific parts.
4 */
5
6/*
7 * Copyright (C) 2006-2007 Sun Microsystems, Inc.
8 *
9 * This file is part of VirtualBox Open Source Edition (OSE), as
10 * available from http://www.virtualbox.org. This file is free software;
11 * you can redistribute it and/or modify it under the terms of the GNU
12 * General Public License (GPL) as published by the Free Software
13 * Foundation, in version 2 as it comes in the "COPYING" file of the
14 * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
15 * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
16 *
17 * The contents of this file may alternatively be used under the terms
18 * of the Common Development and Distribution License Version 1.0
19 * (CDDL) only, as it comes in the "COPYING.CDDL" file of the
20 * VirtualBox OSE distribution, in which case the provisions of the
21 * CDDL are applicable instead of those of the GPL.
22 *
23 * You may elect to license modified versions of this file under the
24 * terms and conditions of either the GPL or the CDDL or both.
25 *
26 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa
27 * Clara, CA 95054 USA or visit http://www.sun.com if you need
28 * additional information or have any questions.
29 */
30
31
32/*******************************************************************************
33* Header Files *
34*******************************************************************************/
35#define LOG_GROUP LOG_GROUP_SUP
36#include <Windows.h>
37
38#include <VBox/sup.h>
39#include <VBox/types.h>
40#include <VBox/err.h>
41#include <VBox/param.h>
42#include <VBox/log.h>
43#include <iprt/assert.h>
44#include <iprt/path.h>
45#include <iprt/string.h>
46#include "../SUPLibInternal.h"
47#include "../SUPDrvIOC.h"
48
49
50/*******************************************************************************
51* Defined Constants And Macros *
52*******************************************************************************/
53/** The support service name. */
54#define SERVICE_NAME "VBoxDrv"
55/** Win32 Device name. */
56#define DEVICE_NAME "\\\\.\\VBoxDrv"
57/** NT Device name. */
58#define DEVICE_NAME_NT L"\\Device\\VBoxDrv"
59/** Win32 Symlink name. */
60#define DEVICE_NAME_DOS L"\\DosDevices\\VBoxDrv"
61
62
63
64/*******************************************************************************
65* Global Variables *
66*******************************************************************************/
67/** Handle to the open device. */
68static HANDLE g_hDevice = INVALID_HANDLE_VALUE;
69/** Flags whether or not we started the service. */
70static bool g_fStartedService = false;
71/** Pointer to the area of memory we reserve for SUPPageAlloc(). */
72static void *g_pvReserved = NULL;
73/** The number of bytes we reserved for SUPPageAlloc(). */
74static size_t g_cbReserved = 0;
75
76
77/*******************************************************************************
78* Internal Functions *
79*******************************************************************************/
80static int suplibOsCreateService(void);
81static int suplibOsUpdateService(void);
82static int suplibOsDeleteService(void);
83static int suplibOsStartService(void);
84static int suplibOsStopService(void);
85static int suplibConvertWin32Err(int);
86
87
88/**
89 * Initialize the OS specific part of the library.
90 * On Win32 this involves:
91 * - registering the device driver
92 * - start device driver.
93 * - open driver.
94 *
95 * @returns 0 on success.
96 * @returns current -1 on failure but this must be changed to proper error codes.
97 * @param cbReserve The number of bytes to reserver for contiguous virtual allocations.
98 */
99int suplibOsInit(size_t cbReserve)
100{
101 /*
102 * Check if already initialized.
103 */
104 if (g_hDevice != INVALID_HANDLE_VALUE)
105 return 0;
106
107 /*
108 * Try open the device.
109 */
110 g_hDevice = CreateFile(DEVICE_NAME,
111 GENERIC_READ | GENERIC_WRITE, FILE_SHARE_READ | FILE_SHARE_WRITE,
112 NULL,
113 OPEN_EXISTING,
114 FILE_ATTRIBUTE_NORMAL | FILE_FLAG_OVERLAPPED,
115 NULL);
116 if (g_hDevice == INVALID_HANDLE_VALUE)
117 {
118 /*
119 * Try start the service and retry opening it.
120 */
121 suplibOsStartService();
122 g_hDevice = CreateFile(DEVICE_NAME,
123 GENERIC_READ | GENERIC_WRITE, FILE_SHARE_READ | FILE_SHARE_WRITE,
124 NULL,
125 OPEN_EXISTING,
126 FILE_ATTRIBUTE_NORMAL | FILE_FLAG_OVERLAPPED,
127 NULL);
128 if (g_hDevice == INVALID_HANDLE_VALUE)
129 {
130 int rc = GetLastError();
131 switch (rc)
132 {
133 /** @todo someone must test what is actually returned. */
134 case ERROR_DEV_NOT_EXIST:
135 case ERROR_DEVICE_NOT_CONNECTED:
136 case ERROR_BAD_DEVICE:
137 case ERROR_DEVICE_REMOVED:
138 case ERROR_DEVICE_NOT_AVAILABLE:
139 return VERR_VM_DRIVER_LOAD_ERROR;
140 case ERROR_PATH_NOT_FOUND:
141 case ERROR_FILE_NOT_FOUND:
142 return VERR_VM_DRIVER_NOT_INSTALLED;
143 case ERROR_ACCESS_DENIED:
144 case ERROR_SHARING_VIOLATION:
145 return VERR_VM_DRIVER_NOT_ACCESSIBLE;
146 default:
147 return VERR_VM_DRIVER_OPEN_ERROR;
148 }
149
150 return -1 /** @todo define proper error codes for suplibOsInit failure. */;
151 }
152 }
153
154 /*
155 * Check driver version.
156 */
157 /** @todo implement driver version checking. */
158
159#if 0 /* obsolete code and restricts our virtual address space for the new allocation method */
160 /*
161 * Reserve memory.
162 */
163 if (cbReserve != 0)
164 {
165/** 1 1/2 GB - (a bit more than) current VBox max. */
166#define SUPLIB_MAX_RESERVE (_1G + _1M*512)
167 /*
168 * Find the right size to reserve.
169 */
170 if ( cbReserve == ~(size_t)0
171 || cbReserve > SUPLIB_MAX_RESERVE)
172 cbReserve = SUPLIB_MAX_RESERVE;
173 char szVar[64] = {0};
174 if (GetEnvironmentVariable("VBOX_RESERVE_MEM_LIMIT", szVar, sizeof(szVar) - 1))
175 {
176 uint64_t cb;
177 char *pszNext;
178 int rc = RTStrToUInt64Ex(szVar, &pszNext, 0, &cb);
179 if (VBOX_SUCCESS(rc))
180 {
181 switch (*pszNext)
182 {
183 case 'K':
184 case 'k':
185 cb *= _1K;
186 pszNext++;
187 break;
188 case 'M':
189 case 'm':
190 cb *= _1M;
191 pszNext++;
192 break;
193 case 'G':
194 case 'g':
195 cb *= _1G;
196 pszNext++;
197 break;
198 case '\0':
199 break;
200 }
201 if (*pszNext == 'b' || *pszNext == 'B')
202 pszNext++;
203 if (!pszNext)
204 cbReserve = RT_MIN(SUPLIB_MAX_RESERVE, cb);
205 }
206 }
207
208 /*
209 * Try reserve virtual address space, lowering the requirements in by _1M chunks.
210 * Make sure it's possible to get at least 3 chunks of 16MBs extra after the reservation.
211 */
212 for (cbReserve = RT_ALIGN_Z(cbReserve, _1M); cbReserve >= _1M * 64; cbReserve -= _1M)
213 {
214 void *pv = VirtualAlloc(NULL, cbReserve, MEM_RESERVE, PAGE_NOACCESS);
215 if (pv)
216 {
217 void *pv1 = VirtualAlloc(NULL, _1M * 16, MEM_RESERVE, PAGE_NOACCESS);
218 void *pv2 = VirtualAlloc(NULL, _1M * 16, MEM_RESERVE, PAGE_NOACCESS);
219 void *pv3 = VirtualAlloc(NULL, _1M * 16, MEM_RESERVE, PAGE_NOACCESS);
220 if (pv1)
221 VirtualFree(pv1, 0, MEM_RELEASE);
222 if (pv2)
223 VirtualFree(pv2, 0, MEM_RELEASE);
224 if (pv3)
225 VirtualFree(pv3, 0, MEM_RELEASE);
226 const int cFailures = !pv1 + !pv2 + !pv3;
227 if (!cFailures)
228 {
229 g_pvReserved = pv;
230 g_cbReserved = cbReserve;
231#if 0 /* too early, no logging. */
232 Log(("suplibOsInit: Reserved %zu bytes at %p\n", cbReserve, g_pvReserved));
233#endif
234 break;
235 }
236
237 cbReserve -= cFailures > 2 ? _1M * 16 : _1M;
238 }
239 else
240 cbReserve -= _1M;
241 }
242 /* ignore errors */
243 }
244#endif /* end of obsolete memory reservation hack */
245
246 /*
247 * We're done.
248 */
249 return VINF_SUCCESS;
250}
251
252
253/**
254 * Installs anything required by the support library.
255 *
256 * @returns 0 on success.
257 * @returns error code on failure.
258 */
259int suplibOsInstall(void)
260{
261 return suplibOsCreateService();
262}
263
264
265/**
266 * Installs anything required by the support library.
267 *
268 * @returns 0 on success.
269 * @returns error code on failure.
270 */
271int suplibOsUninstall(void)
272{
273 int rc = suplibOsStopService();
274 if (!rc)
275 rc = suplibOsDeleteService();
276 return rc;
277}
278
279
280/**
281 * Creates the service.
282 *
283 * @returns 0 on success.
284 * @returns -1 on failure.
285 */
286int suplibOsCreateService(void)
287{
288 /*
289 * Assume it didn't exist, so we'll create the service.
290 */
291 SC_HANDLE hSMgrCreate = OpenSCManager(NULL, NULL, SERVICE_CHANGE_CONFIG);
292 DWORD LastError = GetLastError(); NOREF(LastError);
293 AssertMsg(hSMgrCreate, ("OpenSCManager(,,create) failed rc=%d\n", LastError));
294 if (hSMgrCreate)
295 {
296 char szDriver[RTPATH_MAX];
297 int rc = RTPathProgram(szDriver, sizeof(szDriver) - sizeof("\\VBoxDrv.sys"));
298 if (VBOX_SUCCESS(rc))
299 {
300 strcat(szDriver, "\\VBoxDrv.sys");
301 SC_HANDLE hService = CreateService(hSMgrCreate,
302 SERVICE_NAME,
303 "VBox Support Driver",
304 SERVICE_QUERY_STATUS,
305 SERVICE_KERNEL_DRIVER,
306 SERVICE_DEMAND_START,
307 SERVICE_ERROR_NORMAL,
308 szDriver,
309 NULL, NULL, NULL, NULL, NULL);
310 DWORD LastError = GetLastError(); NOREF(LastError);
311 AssertMsg(hService, ("CreateService failed! LastError=%Rwa szDriver=%s\n", LastError, szDriver));
312 CloseServiceHandle(hService);
313 CloseServiceHandle(hSMgrCreate);
314 return hService ? 0 : -1;
315 }
316 CloseServiceHandle(hSMgrCreate);
317 return rc;
318 }
319 return -1;
320}
321
322/**
323 * Stops a possibly running service.
324 *
325 * @returns 0 on success.
326 * @returns -1 on failure.
327 */
328int suplibOsStopService(void)
329{
330 /*
331 * Assume it didn't exist, so we'll create the service.
332 */
333 int rc = -1;
334 SC_HANDLE hSMgr = OpenSCManager(NULL, NULL, SERVICE_STOP | SERVICE_QUERY_STATUS);
335 DWORD LastError = GetLastError(); NOREF(LastError);
336 AssertMsg(hSMgr, ("OpenSCManager(,,delete) failed rc=%d\n", LastError));
337 if (hSMgr)
338 {
339 SC_HANDLE hService = OpenService(hSMgr, SERVICE_NAME, SERVICE_STOP | SERVICE_QUERY_STATUS);
340 if (hService)
341 {
342 /*
343 * Stop the service.
344 */
345 SERVICE_STATUS Status;
346 QueryServiceStatus(hService, &Status);
347 if (Status.dwCurrentState == SERVICE_STOPPED)
348 rc = 0;
349 else if (ControlService(hService, SERVICE_CONTROL_STOP, &Status))
350 {
351 int iWait = 100;
352 while (Status.dwCurrentState == SERVICE_STOP_PENDING && iWait-- > 0)
353 {
354 Sleep(100);
355 QueryServiceStatus(hService, &Status);
356 }
357 if (Status.dwCurrentState == SERVICE_STOPPED)
358 rc = 0;
359 else
360 AssertMsgFailed(("Failed to stop service. status=%d\n", Status.dwCurrentState));
361 }
362 else
363 {
364 DWORD LastError = GetLastError(); NOREF(LastError);
365 AssertMsgFailed(("ControlService failed with LastError=%Rwa. status=%d\n", LastError, Status.dwCurrentState));
366 }
367 CloseServiceHandle(hService);
368 }
369 else if (GetLastError() == ERROR_SERVICE_DOES_NOT_EXIST)
370 rc = 0;
371 else
372 {
373 DWORD LastError = GetLastError(); NOREF(LastError);
374 AssertMsgFailed(("OpenService failed LastError=%Rwa\n", LastError));
375 }
376 CloseServiceHandle(hSMgr);
377 }
378 return rc;
379}
380
381
382/**
383 * Deletes the service.
384 *
385 * @returns 0 on success.
386 * @returns -1 on failure.
387 */
388int suplibOsDeleteService(void)
389{
390 /*
391 * Assume it didn't exist, so we'll create the service.
392 */
393 int rc = -1;
394 SC_HANDLE hSMgr = OpenSCManager(NULL, NULL, SERVICE_CHANGE_CONFIG);
395 DWORD LastError = GetLastError(); NOREF(LastError);
396 AssertMsg(hSMgr, ("OpenSCManager(,,delete) failed rc=%d\n", LastError));
397 if (hSMgr)
398 {
399 SC_HANDLE hService = OpenService(hSMgr, SERVICE_NAME, DELETE);
400 if (hService)
401 {
402 /*
403 * Delete the service.
404 */
405 if (DeleteService(hService))
406 rc = 0;
407 else
408 {
409 DWORD LastError = GetLastError(); NOREF(LastError);
410 AssertMsgFailed(("DeleteService failed LastError=%Rwa\n", LastError));
411 }
412 CloseServiceHandle(hService);
413 }
414 else if (GetLastError() == ERROR_SERVICE_DOES_NOT_EXIST)
415 rc = 0;
416 else
417 {
418 DWORD LastError = GetLastError(); NOREF(LastError);
419 AssertMsgFailed(("OpenService failed LastError=%Rwa\n", LastError));
420 }
421 CloseServiceHandle(hSMgr);
422 }
423 return rc;
424}
425
426#if 0
427/**
428 * Creates the service.
429 *
430 * @returns 0 on success.
431 * @returns -1 on failure.
432 */
433int suplibOsUpdateService(void)
434{
435 /*
436 * Assume it didn't exist, so we'll create the service.
437 */
438 SC_HANDLE hSMgr = OpenSCManager(NULL, NULL, SERVICE_CHANGE_CONFIG);
439 DWORD LastError = GetLastError(); NOREF(LastError);
440 AssertMsg(hSMgr, ("OpenSCManager(,,delete) failed LastError=%Rwa\n", LastError));
441 if (hSMgr)
442 {
443 SC_HANDLE hService = OpenService(hSMgr, SERVICE_NAME, SERVICE_CHANGE_CONFIG);
444 if (hService)
445 {
446 char szDriver[RTPATH_MAX];
447 int rc = RTPathProgram(szDriver, sizeof(szDriver) - sizeof("\\VBoxDrv.sys"));
448 if (VBOX_SUCCESS(rc))
449 {
450 strcat(szDriver, "\\VBoxDrv.sys");
451
452 SC_LOCK hLock = LockServiceDatabase(hSMgr);
453 if (ChangeServiceConfig(hService,
454 SERVICE_KERNEL_DRIVER,
455 SERVICE_DEMAND_START,
456 SERVICE_ERROR_NORMAL,
457 szDriver,
458 NULL, NULL, NULL, NULL, NULL, NULL))
459 {
460
461 UnlockServiceDatabase(hLock);
462 CloseServiceHandle(hService);
463 CloseServiceHandle(hSMgr);
464 return 0;
465 }
466 else
467 {
468 DWORD LastError = GetLastError(); NOREF(LastError);
469 AssertMsgFailed(("ChangeServiceConfig failed LastError=%Rwa\n", LastError));
470 }
471 }
472 UnlockServiceDatabase(hLock);
473 CloseServiceHandle(hService);
474 }
475 else
476 {
477 DWORD LastError = GetLastError(); NOREF(LastError);
478 AssertMsgFailed(("OpenService failed LastError=%Rwa\n", LastError));
479 }
480 CloseServiceHandle(hSMgr);
481 }
482 return -1;
483}
484#endif
485
486/**
487 * Attempts to start the service, creating it if necessary.
488 *
489 * @returns 0 on success.
490 * @returns -1 on failure.
491 * @param fRetry Indicates retry call.
492 */
493int suplibOsStartService(void)
494{
495 /*
496 * Check if the driver service is there.
497 */
498 SC_HANDLE hSMgr = OpenSCManager(NULL, NULL, SERVICE_QUERY_STATUS | SERVICE_START);
499 if (hSMgr == NULL)
500 {
501 AssertMsgFailed(("couldn't open service manager in SERVICE_QUERY_CONFIG | SERVICE_QUERY_STATUS mode!\n"));
502 return -1;
503 }
504
505 /*
506 * Try open our service to check it's status.
507 */
508 SC_HANDLE hService = OpenService(hSMgr, SERVICE_NAME, SERVICE_QUERY_STATUS | SERVICE_START);
509 if (!hService)
510 {
511 /*
512 * Create the service.
513 */
514 int rc = suplibOsCreateService();
515 if (rc)
516 return rc;
517
518 /*
519 * Try open the service.
520 */
521 hService = OpenService(hSMgr, SERVICE_NAME, SERVICE_QUERY_STATUS | SERVICE_START);
522 }
523
524 /*
525 * Check if open and on demand create succeeded.
526 */
527 int rc = -1;
528 if (hService)
529 {
530
531 /*
532 * Query service status to see if we need to start it or not.
533 */
534 SERVICE_STATUS Status;
535 BOOL fRc = QueryServiceStatus(hService, &Status);
536 Assert(fRc);
537 if ( Status.dwCurrentState != SERVICE_RUNNING
538 && Status.dwCurrentState != SERVICE_START_PENDING)
539 {
540 /*
541 * Start it.
542 */
543 fRc = StartService(hService, 0, NULL);
544 DWORD LastError = GetLastError(); NOREF(LastError);
545 AssertMsg(fRc, ("StartService failed with LastError=%Rwa\n", LastError));
546 }
547
548 /*
549 * Wait for the service to finish starting.
550 * We'll wait for 10 seconds then we'll give up.
551 */
552 QueryServiceStatus(hService, &Status);
553 if (Status.dwCurrentState == SERVICE_START_PENDING)
554 {
555 int iWait;
556 for (iWait = 100; iWait > 0 && Status.dwCurrentState == SERVICE_START_PENDING; iWait--)
557 {
558 Sleep(100);
559 QueryServiceStatus(hService, &Status);
560 }
561 DWORD LastError = GetLastError(); NOREF(LastError);
562 AssertMsg(Status.dwCurrentState != SERVICE_RUNNING,
563 ("Failed to start. LastError=%Rwa iWait=%d status=%d\n",
564 LastError, iWait, Status.dwCurrentState));
565 }
566
567 if (Status.dwCurrentState == SERVICE_RUNNING)
568 rc = 0;
569
570 /*
571 * Close open handles.
572 */
573 CloseServiceHandle(hService);
574 }
575 else
576 {
577 DWORD LastError = GetLastError(); NOREF(LastError);
578 AssertMsgFailed(("OpenService failed! LastError=%Rwa\n", LastError));
579 }
580 if (!CloseServiceHandle(hSMgr))
581 AssertFailed();
582
583 return rc;
584}
585
586
587int suplibOsTerm(void)
588{
589 /*
590 * Check if we're initited at all.
591 */
592 if (g_hDevice != INVALID_HANDLE_VALUE)
593 {
594 if (!CloseHandle(g_hDevice))
595 AssertFailed();
596 g_hDevice = INVALID_HANDLE_VALUE;
597 }
598
599 /*
600 * If we started the service we might consider stopping it too.
601 *
602 * Since this won't work unless the the process starting it is the
603 * last user we might wanna skip this...
604 */
605 if (g_fStartedService)
606 {
607 suplibOsStopService();
608 g_fStartedService = false;
609 }
610
611 return 0;
612}
613
614
615/**
616 * Send a I/O Control request to the device.
617 *
618 * @returns 0 on success.
619 * @returns VBOX error code on failure.
620 * @param uFunction IO Control function.
621 * @param pvIn The request buffer.
622 * @param cbReq The size of the request buffer.
623 */
624int suplibOsIOCtl(uintptr_t uFunction, void *pvReq, size_t cbReq)
625{
626 AssertMsg(g_hDevice != INVALID_HANDLE_VALUE, ("SUPLIB not initiated successfully!\n"));
627
628 /*
629 * Issue the device I/O control.
630 */
631 PSUPREQHDR pHdr = (PSUPREQHDR)pvReq;
632 Assert(cbReq == RT_MAX(pHdr->cbIn, pHdr->cbOut));
633 DWORD cbReturned = (ULONG)pHdr->cbOut;
634 if (DeviceIoControl(g_hDevice, uFunction, pvReq, pHdr->cbIn, pvReq, cbReturned, &cbReturned, NULL))
635 return 0;
636
637 return suplibConvertWin32Err(GetLastError());
638}
639
640
641int suplibOsIOCtlFast(uintptr_t uFunction)
642{
643 /*
644 * Issue device I/O control.
645 */
646 int rc = VERR_INTERNAL_ERROR;
647 DWORD cbReturned = (ULONG)sizeof(rc);
648 if (DeviceIoControl(g_hDevice, uFunction, NULL, 0, &rc, (DWORD)sizeof(rc), &cbReturned, NULL))
649 return rc;
650 return suplibConvertWin32Err(GetLastError());
651}
652
653
654/**
655 * Allocate a number of zero-filled pages in user space.
656 *
657 * @returns VBox status code.
658 * @param cPages Number of pages to allocate.
659 * @param ppvPages Where to return the base pointer.
660 */
661int suplibOsPageAlloc(size_t cPages, void **ppvPages)
662{
663 if (g_pvReserved)
664 {
665 if (VirtualFree(g_pvReserved, 0, MEM_RELEASE))
666 Log(("suplibOsPageAlloc: Freed %zu bytes of reserved memory at %p.\n", g_cbReserved, g_pvReserved));
667 else
668 {
669 DWORD LastError = GetLastError(); NOREF(LastError);
670 AssertMsgFailed(("LastError=%Rwa g_pvReserved=%p\n", LastError, g_pvReserved));
671 }
672 g_pvReserved = NULL;
673 }
674
675 *ppvPages = VirtualAlloc(NULL, (size_t)cPages << PAGE_SHIFT, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
676 if (*ppvPages)
677 return VINF_SUCCESS;
678 return suplibConvertWin32Err(GetLastError());
679}
680
681
682/**
683 * Frees pages allocated by suplibOsPageAlloc().
684 *
685 * @returns VBox status code.
686 * @param pvPages Pointer to pages.
687 */
688int suplibOsPageFree(void *pvPages, size_t /* cPages */)
689{
690 if (VirtualFree(pvPages, 0, MEM_RELEASE))
691 return VINF_SUCCESS;
692 return suplibConvertWin32Err(GetLastError());
693}
694
695
696/**
697 * Converts a supdrv error code to an nt status code.
698 *
699 * @returns corresponding SUPDRV_ERR_*.
700 * @param rc Win32 error code.
701 */
702static int suplibConvertWin32Err(int rc)
703{
704 /* Conversion program (link with ntdll.lib from ddk):
705 #define _WIN32_WINNT 0x0501
706 #include <windows.h>
707 #include <ntstatus.h>
708 #include <winternl.h>
709 #include <stdio.h>
710
711 int main()
712 {
713 #define CONVERT(a) printf(#a " %#x -> %d\n", a, RtlNtStatusToDosError((a)))
714 CONVERT(STATUS_SUCCESS);
715 CONVERT(STATUS_NOT_SUPPORTED);
716 CONVERT(STATUS_INVALID_PARAMETER);
717 CONVERT(STATUS_UNKNOWN_REVISION);
718 CONVERT(STATUS_INVALID_HANDLE);
719 CONVERT(STATUS_INVALID_ADDRESS);
720 CONVERT(STATUS_NOT_LOCKED);
721 CONVERT(STATUS_IMAGE_ALREADY_LOADED);
722 CONVERT(STATUS_ACCESS_DENIED);
723 CONVERT(STATUS_REVISION_MISMATCH);
724
725 return 0;
726 }
727 */
728
729 switch (rc)
730 {
731 //case 0: return STATUS_SUCCESS;
732 case 0: return VINF_SUCCESS;
733 //case SUPDRV_ERR_GENERAL_FAILURE: return STATUS_NOT_SUPPORTED;
734 case ERROR_NOT_SUPPORTED: return VERR_GENERAL_FAILURE;
735 //case SUPDRV_ERR_INVALID_PARAM: return STATUS_INVALID_PARAMETER;
736 case ERROR_INVALID_PARAMETER: return VERR_INVALID_PARAMETER;
737 //case SUPDRV_ERR_INVALID_MAGIC: return STATUS_ACCESS_DENIED;
738 case ERROR_UNKNOWN_REVISION: return VERR_INVALID_MAGIC;
739 //case SUPDRV_ERR_INVALID_HANDLE: return STATUS_INVALID_HANDLE;
740 case ERROR_INVALID_HANDLE: return VERR_INVALID_HANDLE;
741 //case SUPDRV_ERR_INVALID_POINTER: return STATUS_INVALID_ADDRESS;
742 case ERROR_UNEXP_NET_ERR: return VERR_INVALID_POINTER;
743 //case SUPDRV_ERR_LOCK_FAILED: return STATUS_NOT_LOCKED;
744 case ERROR_NOT_LOCKED: return VERR_LOCK_FAILED;
745 //case SUPDRV_ERR_ALREADY_LOADED: return STATUS_IMAGE_ALREADY_LOADED;
746 case ERROR_SERVICE_ALREADY_RUNNING: return VERR_ALREADY_LOADED;
747 //case SUPDRV_ERR_PERMISSION_DENIED: return STATUS_ACCESS_DENIED;
748 case ERROR_ACCESS_DENIED: return VERR_PERMISSION_DENIED;
749 //case SUPDRV_ERR_VERSION_MISMATCH: return STATUS_REVISION_MISMATCH;
750 case ERROR_REVISION_MISMATCH: return VERR_VERSION_MISMATCH;
751 }
752
753 /* fall back on the default conversion. */
754 return RTErrConvertFromWin32(rc);
755}
756
757
758
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette