VirtualBox

source: vbox/trunk/src/VBox/Additions/common/VBoxGuestLib/SysHlp.cpp@ 4056

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

More assertions

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 7.1 KB
Line 
1/** @file
2 *
3 * VBoxGuestLib - A support library for VirtualBox guest additions:
4 * Physical memory heap
5 */
6
7/*
8 * Copyright (C) 2006-2007 innotek GmbH
9 *
10 * This file is part of VirtualBox Open Source Edition (OSE), as
11 * available from http://www.virtualbox.org. This file is free software;
12 * you can redistribute it and/or modify it under the terms of the GNU
13 * General Public License as published by the Free Software Foundation,
14 * in version 2 as it comes in the "COPYING" file of the VirtualBox OSE
15 * distribution. VirtualBox OSE is distributed in the hope that it will
16 * be useful, but WITHOUT ANY WARRANTY of any kind.
17 *
18 * If you received this file as part of a commercial VirtualBox
19 * distribution, then only the terms of your commercial VirtualBox
20 * license agreement apply instead of the previous paragraph.
21 */
22#define LOG_GROUP LOG_GROUP_HGCM
23#include <VBox/log.h>
24
25#include <VBox/VBoxGuestLib.h>
26#include "SysHlp.h"
27
28#include <iprt/assert.h>
29#if !defined(RT_OS_WINDOWS) && !defined(RT_OS_LINUX)
30#include <iprt/memobj.h>
31#endif
32
33
34int vbglLockLinear (void **ppvCtx, void *pv, uint32_t u32Size, bool fWriteAccess)
35{
36 int rc = VINF_SUCCESS;
37
38#ifdef RT_OS_WINDOWS
39 PMDL pMdl = IoAllocateMdl (pv, u32Size, FALSE, FALSE, NULL);
40
41 if (pMdl == NULL)
42 {
43 rc = VERR_NOT_SUPPORTED;
44 AssertMsgFailed(("IoAllocateMdl %VGv %x failed!!\n", pv, u32Size));
45 }
46 else
47 {
48 __try {
49 /* Calls to MmProbeAndLockPages must be enclosed in a try/except block. */
50 MmProbeAndLockPages (pMdl,
51 KernelMode,
52 (fWriteAccess) ? IoModifyAccess : IoReadAccess);
53
54 *ppvCtx = pMdl;
55
56 } __except(EXCEPTION_EXECUTE_HANDLER) {
57
58 IoFreeMdl (pMdl);
59 rc = VERR_INVALID_PARAMETER;
60 AssertMsgFailed(("MmProbeAndLockPages %VGv %x failed!!\n", pv, u32Size));
61 }
62 }
63
64#elif defined(RT_OS_LINUX)
65 NOREF(ppvCtx);
66 NOREF(pv);
67 NOREF(u32Size);
68
69#else
70 /* Default to IPRT - this ASSUMES that it is USER addresses we're locking. */
71 RTR0MEMOBJ MemObj;
72 rc = RTR0MemObjLockUser(&MemObj, pv, u32Size, NIL_RTR0PROCESS);
73 if (RT_SUCCESS(rc))
74 *ppvCtx = MemObj;
75 else
76 *ppvCtx = NIL_RTR0MEMOBJ;
77
78#endif
79
80 return rc;
81}
82
83void vbglUnlockLinear (void *pvCtx, void *pv, uint32_t u32Size)
84{
85 NOREF(pv);
86 NOREF(u32Size);
87
88#ifdef RT_OS_WINDOWS
89 PMDL pMdl = (PMDL)pvCtx;
90
91 if (pMdl != NULL)
92 {
93 MmUnlockPages (pMdl);
94 IoFreeMdl (pMdl);
95 }
96
97#elif defined(RT_OS_LINUX)
98 NOREF(pvCtx);
99
100#else
101 /* default to IPRT */
102 RTR0MEMOBJ MemObj = (RTR0MEMOBJ)pvCtx;
103 int rc = RTR0MemObjFree(MemObj, false);
104 AssertRC(rc);
105
106#endif
107}
108
109#ifndef VBGL_VBOXGUEST
110
111#if defined (RT_OS_LINUX) && !defined (__KERNEL__)
112# include <unistd.h>
113# include <errno.h>
114# include <sys/fcntl.h>
115# include <sys/ioctl.h>
116#endif
117
118#ifdef RT_OS_LINUX
119__BEGIN_DECLS
120extern DECLVBGL(void *) vboxadd_cmc_open (void);
121extern DECLVBGL(void) vboxadd_cmc_close (void *);
122extern DECLVBGL(int) vboxadd_cmc_call (void *opaque, uint32_t func, void *data);
123__END_DECLS
124#endif /* RT_OS_LINUX */
125
126#ifdef RT_OS_OS2
127__BEGIN_DECLS
128/*
129 * On OS/2 we'll do the connecting in the assembly code of the
130 * client driver, exporting a g_VBoxGuestIDC symbol containing
131 * the connection information obtained from the 16-bit IDC.
132 */
133extern VBOXGUESTOS2IDCCONNECT g_VBoxGuestIDC;
134__END_DECLS
135#endif
136
137
138int vbglDriverOpen (VBGLDRIVER *pDriver)
139{
140#ifdef RT_OS_WINDOWS
141 UNICODE_STRING uszDeviceName;
142 RtlInitUnicodeString (&uszDeviceName, L"\\Device\\VBoxGuest");
143
144 PDEVICE_OBJECT pDeviceObject = NULL;
145 PFILE_OBJECT pFileObject = NULL;
146
147 NTSTATUS rc = IoGetDeviceObjectPointer (&uszDeviceName, FILE_ALL_ACCESS,
148 &pFileObject, &pDeviceObject);
149
150 if (NT_SUCCESS (rc))
151 {
152 Log(("vbglDriverOpen VBoxGuest successful pDeviceObject=%x\n", pDeviceObject));
153 pDriver->pDeviceObject = pDeviceObject;
154 pDriver->pFileObject = pFileObject;
155 return VINF_SUCCESS;
156 }
157 /** @todo return RTErrConvertFromNtStatus(rc)! */
158 Log(("vbglDriverOpen VBoxGuest failed with ntstatus=%x\n", rc));
159 return rc;
160
161#elif defined (RT_OS_LINUX)
162 void *opaque;
163
164 opaque = (void *) vboxadd_cmc_open ();
165 if (!opaque)
166 {
167 return VERR_NOT_IMPLEMENTED;
168 }
169 pDriver->opaque = opaque;
170 return VINF_SUCCESS;
171
172#elif defined (RT_OS_OS2)
173 /*
174 * Just check whether the connection was made or not.
175 */
176 if ( g_VBoxGuestIDC.u32Version == VMMDEV_VERSION
177 && VALID_PTR(g_VBoxGuestIDC.u32Session)
178 && VALID_PTR(g_VBoxGuestIDC.pfnServiceEP))
179 {
180 pDriver->u32Session = g_VBoxGuestIDC.u32Session;
181 return VINF_SUCCESS;
182 }
183 pDriver->u32Session = UINT32_MAX;
184 Log(("vbglDriverOpen: failed\n"));
185 return VERR_FILE_NOT_FOUND;
186
187#else
188# error "Port me"
189#endif
190}
191
192int vbglDriverIOCtl (VBGLDRIVER *pDriver, uint32_t u32Function, void *pvData, uint32_t cbData)
193{
194#ifdef RT_OS_WINDOWS
195 IO_STATUS_BLOCK ioStatusBlock;
196
197 KEVENT Event;
198 KeInitializeEvent (&Event, NotificationEvent, FALSE);
199
200 PIRP irp = IoBuildDeviceIoControlRequest (u32Function,
201 pDriver->pDeviceObject,
202 pvData,
203 cbData,
204 pvData,
205 cbData,
206 FALSE, /* external */
207 &Event,
208 &ioStatusBlock);
209 if (irp == NULL)
210 {
211 Log(("vbglDriverIOCtl: IoBuildDeviceIoControlRequest failed\n"));
212 return VERR_NO_MEMORY;
213 }
214
215 NTSTATUS rc = IoCallDriver (pDriver->pDeviceObject, irp);
216
217 if (rc == STATUS_PENDING)
218 {
219 Log(("vbglDriverIOCtl: STATUS_PENDING\n"));
220 rc = KeWaitForSingleObject(&Event,
221 Executive,
222 KernelMode,
223 FALSE,
224 NULL);
225
226 rc = ioStatusBlock.Status;
227 }
228
229 if (!NT_SUCCESS(rc))
230 Log(("vbglDriverIOCtl: IoCallDriver failed with ntstatus=%x\n", rc));
231
232 return NT_SUCCESS(rc)? VINF_SUCCESS: VERR_VBGL_IOCTL_FAILED;
233
234#elif defined (RT_OS_LINUX)
235 return vboxadd_cmc_call (pDriver->opaque, u32Function, pvData);
236
237#elif defined (RT_OS_OS2)
238 if ( pDriver->u32Session
239 && pDriver->u32Session == g_VBoxGuestIDC.u32Session)
240 return g_VBoxGuestIDC.pfnServiceEP(pDriver->u32Session, u32Function, pvData, cbData, NULL);
241
242 Log(("vbglDriverIOCtl: No connection\n"));
243 return VERR_WRONG_ORDER;
244
245#else
246# error "Port me"
247#endif
248}
249
250void vbglDriverClose (VBGLDRIVER *pDriver)
251{
252#ifdef RT_OS_WINDOWS
253 Log(("vbglDriverClose pDeviceObject=%x\n", pDriver->pDeviceObject));
254 ObDereferenceObject (pDriver->pFileObject);
255
256#elif defined (RT_OS_LINUX)
257 vboxadd_cmc_close (pDriver->opaque);
258
259#elif defined (RT_OS_OS2)
260 pDriver->u32Session = 0;
261
262#else
263# error "Port me"
264#endif
265}
266
267#endif /* !VBGL_VBOXGUEST */
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