VirtualBox

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

Last change on this file since 4800 was 4800, checked in by vboxsync, 18 years ago

Redid the supdrv interface. works on windows and linux while the other OSes still needs some adjusting/testing. internal networking is temporarily broken as the SUPCallVMMR0Ex interface is being reworked (this is what all this is really about).

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

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