VirtualBox

source: vbox/trunk/src/VBox/HostDrivers/Support/SUPDrvSem.c@ 30111

Last change on this file since 30111 was 28800, checked in by vboxsync, 15 years ago

Automated rebranding to Oracle copyright/license strings via filemuncher

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 11.0 KB
Line 
1/* $Revision: 28800 $ */
2/** @file
3 * VBoxDrv - The VirtualBox Support Driver - Common OS agnostic.
4 */
5
6/*
7 * Copyright (C) 2006-2009 Oracle Corporation
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
27/*******************************************************************************
28* Header Files *
29*******************************************************************************/
30#define LOG_GROUP LOG_GROUP_SUP_DRV
31#define SUPDRV_AGNOSTIC
32#include "SUPDrvInternal.h"
33
34/** @todo trim this down. */
35#include <iprt/param.h>
36#include <iprt/alloc.h>
37#include <iprt/cpuset.h>
38#include <iprt/handletable.h>
39#include <iprt/mp.h>
40#include <iprt/power.h>
41#include <iprt/process.h>
42#include <iprt/semaphore.h>
43#include <iprt/spinlock.h>
44#include <iprt/thread.h>
45#include <iprt/uuid.h>
46
47#include <VBox/param.h>
48#include <VBox/log.h>
49#include <VBox/err.h>
50
51
52/**
53 * Destructor for objects created by SUPSemEventCreate.
54 *
55 * @param pvObj The object handle.
56 * @param pvUser1 The IPRT event handle.
57 * @param pvUser2 NULL.
58 */
59static DECLCALLBACK(void) supR0SemEventDestructor(void *pvObj, void *pvUser1, void *pvUser2)
60{
61 Assert(pvUser2 == NULL);
62 NOREF(pvObj);
63 RTSemEventDestroy((RTSEMEVENT)pvUser1);
64}
65
66
67SUPDECL(int) SUPSemEventCreate(PSUPDRVSESSION pSession, PSUPSEMEVENT phEvent)
68{
69 int rc;
70 RTSEMEVENT hEventReal;
71
72 /*
73 * Input validation.
74 */
75 AssertReturn(SUP_IS_SESSION_VALID(pSession), VERR_INVALID_PARAMETER);
76 AssertPtrReturn(phEvent, VERR_INVALID_POINTER);
77
78 /*
79 * Create the event semaphore object.
80 */
81 rc = RTSemEventCreate(&hEventReal);
82 if (RT_SUCCESS(rc))
83 {
84 void *pvObj = SUPR0ObjRegister(pSession, SUPDRVOBJTYPE_SEM_EVENT, supR0SemEventDestructor, hEventReal, NULL);
85 if (pvObj)
86 {
87 uint32_t h32;
88 rc = RTHandleTableAllocWithCtx(pSession->hHandleTable, pvObj, SUPDRV_HANDLE_CTX_EVENT, &h32);
89 if (RT_SUCCESS(rc))
90 {
91 *phEvent = (SUPSEMEVENT)(uintptr_t)h32;
92 return VINF_SUCCESS;
93 }
94 SUPR0ObjRelease(pvObj, pSession);
95 }
96 else
97 RTSemEventDestroy(hEventReal);
98 }
99 return rc;
100}
101
102
103SUPDECL(int) SUPSemEventClose(PSUPDRVSESSION pSession, SUPSEMEVENT hEvent)
104{
105 uint32_t h32;
106 PSUPDRVOBJ pObj;
107
108 /*
109 * Input validation.
110 */
111 AssertReturn(SUP_IS_SESSION_VALID(pSession), VERR_INVALID_PARAMETER);
112 if (hEvent == NIL_SUPSEMEVENT)
113 return VINF_SUCCESS;
114 h32 = (uint32_t)(uintptr_t)hEvent;
115 if (h32 != (uintptr_t)hEvent)
116 return VERR_INVALID_HANDLE;
117
118 /*
119 * Do the job.
120 */
121 pObj = (PSUPDRVOBJ)RTHandleTableFreeWithCtx(pSession->hHandleTable, h32, SUPDRV_HANDLE_CTX_EVENT);
122 if (!pObj)
123 return VERR_INVALID_HANDLE;
124
125 Assert(pObj->cUsage >= 2);
126 SUPR0ObjRelease(pObj, pSession); /* The free call above. */
127 return SUPR0ObjRelease(pObj, pSession); /* The handle table reference. */
128}
129
130
131SUPDECL(int) SUPSemEventSignal(PSUPDRVSESSION pSession, SUPSEMEVENT hEvent)
132{
133 int rc;
134 uint32_t h32;
135 PSUPDRVOBJ pObj;
136
137 /*
138 * Input validation.
139 */
140 AssertReturn(SUP_IS_SESSION_VALID(pSession), VERR_INVALID_PARAMETER);
141 h32 = (uint32_t)(uintptr_t)hEvent;
142 if (h32 != (uintptr_t)hEvent)
143 return VERR_INVALID_HANDLE;
144 pObj = (PSUPDRVOBJ)RTHandleTableLookupWithCtx(pSession->hHandleTable, h32, SUPDRV_HANDLE_CTX_EVENT);
145 if (!pObj)
146 return VERR_INVALID_HANDLE;
147
148 /*
149 * Do the job.
150 */
151 rc = RTSemEventSignal((RTSEMEVENT)pObj->pvUser1);
152
153 SUPR0ObjRelease(pObj, pSession);
154 return rc;
155}
156
157
158SUPDECL(int) SUPSemEventWait(PSUPDRVSESSION pSession, SUPSEMEVENT hEvent, uint32_t cMillies)
159{
160 int rc;
161 uint32_t h32;
162 PSUPDRVOBJ pObj;
163
164 /*
165 * Input validation.
166 */
167 AssertReturn(SUP_IS_SESSION_VALID(pSession), VERR_INVALID_PARAMETER);
168 h32 = (uint32_t)(uintptr_t)hEvent;
169 if (h32 != (uintptr_t)hEvent)
170 return VERR_INVALID_HANDLE;
171 pObj = (PSUPDRVOBJ)RTHandleTableLookupWithCtx(pSession->hHandleTable, h32, SUPDRV_HANDLE_CTX_EVENT);
172 if (!pObj)
173 return VERR_INVALID_HANDLE;
174
175 /*
176 * Do the job.
177 */
178 rc = RTSemEventWait((RTSEMEVENT)pObj->pvUser1, cMillies);
179
180 SUPR0ObjRelease(pObj, pSession);
181 return rc;
182}
183
184
185SUPDECL(int) SUPSemEventWaitNoResume(PSUPDRVSESSION pSession, SUPSEMEVENT hEvent, uint32_t cMillies)
186{
187 int rc;
188 uint32_t h32;
189 PSUPDRVOBJ pObj;
190
191 /*
192 * Input validation.
193 */
194 AssertReturn(SUP_IS_SESSION_VALID(pSession), VERR_INVALID_PARAMETER);
195 h32 = (uint32_t)(uintptr_t)hEvent;
196 if (h32 != (uintptr_t)hEvent)
197 return VERR_INVALID_HANDLE;
198 pObj = (PSUPDRVOBJ)RTHandleTableLookupWithCtx(pSession->hHandleTable, h32, SUPDRV_HANDLE_CTX_EVENT);
199 if (!pObj)
200 return VERR_INVALID_HANDLE;
201
202 /*
203 * Do the job.
204 */
205 rc = RTSemEventWaitNoResume((RTSEMEVENT)pObj->pvUser1, cMillies);
206
207 SUPR0ObjRelease(pObj, pSession);
208 return rc;
209}
210
211
212/**
213 * Destructor for objects created by SUPSemEventMultiCreate.
214 *
215 * @param pvObj The object handle.
216 * @param pvUser1 The IPRT event handle.
217 * @param pvUser2 NULL.
218 */
219static DECLCALLBACK(void) supR0SemEventMultiDestructor(void *pvObj, void *pvUser1, void *pvUser2)
220{
221 Assert(pvUser2 == NULL);
222 NOREF(pvObj);
223 RTSemEventMultiDestroy((RTSEMEVENTMULTI)pvUser1);
224}
225
226
227SUPDECL(int) SUPSemEventMultiCreate(PSUPDRVSESSION pSession, PSUPSEMEVENTMULTI phEventMulti)
228{
229 int rc;
230 RTSEMEVENTMULTI hEventMultReal;
231
232 /*
233 * Input validation.
234 */
235 AssertReturn(SUP_IS_SESSION_VALID(pSession), VERR_INVALID_PARAMETER);
236 AssertPtrReturn(phEventMulti, VERR_INVALID_POINTER);
237
238 /*
239 * Create the event semaphore object.
240 */
241 rc = RTSemEventMultiCreate(&hEventMultReal);
242 if (RT_SUCCESS(rc))
243 {
244 void *pvObj = SUPR0ObjRegister(pSession, SUPDRVOBJTYPE_SEM_EVENT_MULTI, supR0SemEventMultiDestructor, hEventMultReal, NULL);
245 if (pvObj)
246 {
247 uint32_t h32;
248 rc = RTHandleTableAllocWithCtx(pSession->hHandleTable, pvObj, SUPDRV_HANDLE_CTX_EVENT_MULTI, &h32);
249 if (RT_SUCCESS(rc))
250 {
251 *phEventMulti = (SUPSEMEVENTMULTI)(uintptr_t)h32;
252 return VINF_SUCCESS;
253 }
254 SUPR0ObjRelease(pvObj, pSession);
255 }
256 else
257 RTSemEventMultiDestroy(hEventMultReal);
258 }
259 return rc;
260}
261
262
263SUPDECL(int) SUPSemEventMultiClose(PSUPDRVSESSION pSession, SUPSEMEVENTMULTI hEventMulti)
264{
265 uint32_t h32;
266 PSUPDRVOBJ pObj;
267
268 /*
269 * Input validation.
270 */
271 AssertReturn(SUP_IS_SESSION_VALID(pSession), VERR_INVALID_PARAMETER);
272 if (hEventMulti == NIL_SUPSEMEVENTMULTI)
273 return VINF_SUCCESS;
274 h32 = (uint32_t)(uintptr_t)hEventMulti;
275 if (h32 != (uintptr_t)hEventMulti)
276 return VERR_INVALID_HANDLE;
277
278 /*
279 * Do the job.
280 */
281 pObj = (PSUPDRVOBJ)RTHandleTableFreeWithCtx(pSession->hHandleTable, h32, SUPDRV_HANDLE_CTX_EVENT_MULTI);
282 if (!pObj)
283 return VERR_INVALID_HANDLE;
284
285 Assert(pObj->cUsage >= 2);
286 SUPR0ObjRelease(pObj, pSession); /* The free call above. */
287 return SUPR0ObjRelease(pObj, pSession); /* The handle table reference. */
288}
289
290
291SUPDECL(int) SUPSemEventMultiSignal(PSUPDRVSESSION pSession, SUPSEMEVENTMULTI hEventMulti)
292{
293 int rc;
294 uint32_t h32;
295 PSUPDRVOBJ pObj;
296
297 /*
298 * Input validation.
299 */
300 AssertReturn(SUP_IS_SESSION_VALID(pSession), VERR_INVALID_PARAMETER);
301 h32 = (uint32_t)(uintptr_t)hEventMulti;
302 if (h32 != (uintptr_t)hEventMulti)
303 return VERR_INVALID_HANDLE;
304 pObj = (PSUPDRVOBJ)RTHandleTableLookupWithCtx(pSession->hHandleTable, h32, SUPDRV_HANDLE_CTX_EVENT_MULTI);
305 if (!pObj)
306 return VERR_INVALID_HANDLE;
307
308 /*
309 * Do the job.
310 */
311 rc = RTSemEventMultiSignal((RTSEMEVENTMULTI)pObj->pvUser1);
312
313 SUPR0ObjRelease(pObj, pSession);
314 return rc;
315}
316
317
318SUPDECL(int) SUPSemEventMultiReset(PSUPDRVSESSION pSession, SUPSEMEVENTMULTI hEventMulti)
319{
320 int rc;
321 uint32_t h32;
322 PSUPDRVOBJ pObj;
323
324 /*
325 * Input validation.
326 */
327 AssertReturn(SUP_IS_SESSION_VALID(pSession), VERR_INVALID_PARAMETER);
328 h32 = (uint32_t)(uintptr_t)hEventMulti;
329 if (h32 != (uintptr_t)hEventMulti)
330 return VERR_INVALID_HANDLE;
331 pObj = (PSUPDRVOBJ)RTHandleTableLookupWithCtx(pSession->hHandleTable, h32, SUPDRV_HANDLE_CTX_EVENT_MULTI);
332 if (!pObj)
333 return VERR_INVALID_HANDLE;
334
335 /*
336 * Do the job.
337 */
338 rc = RTSemEventMultiReset((RTSEMEVENTMULTI)pObj->pvUser1);
339
340 SUPR0ObjRelease(pObj, pSession);
341 return rc;
342}
343
344
345SUPDECL(int) SUPSemEventMultiWait(PSUPDRVSESSION pSession, SUPSEMEVENTMULTI hEventMulti, uint32_t cMillies)
346{
347 int rc;
348 uint32_t h32;
349 PSUPDRVOBJ pObj;
350
351 /*
352 * Input validation.
353 */
354 AssertReturn(SUP_IS_SESSION_VALID(pSession), VERR_INVALID_PARAMETER);
355 h32 = (uint32_t)(uintptr_t)hEventMulti;
356 if (h32 != (uintptr_t)hEventMulti)
357 return VERR_INVALID_HANDLE;
358 pObj = (PSUPDRVOBJ)RTHandleTableLookupWithCtx(pSession->hHandleTable, h32, SUPDRV_HANDLE_CTX_EVENT_MULTI);
359 if (!pObj)
360 return VERR_INVALID_HANDLE;
361
362 /*
363 * Do the job.
364 */
365 rc = RTSemEventMultiWait((RTSEMEVENTMULTI)pObj->pvUser1, cMillies);
366
367 SUPR0ObjRelease(pObj, pSession);
368 return rc;
369}
370
371
372SUPDECL(int) SUPSemEventMultiWaitNoResume(PSUPDRVSESSION pSession, SUPSEMEVENTMULTI hEventMulti, uint32_t cMillies)
373{
374 int rc;
375 uint32_t h32;
376 PSUPDRVOBJ pObj;
377
378 /*
379 * Input validation.
380 */
381 AssertReturn(SUP_IS_SESSION_VALID(pSession), VERR_INVALID_PARAMETER);
382 h32 = (uint32_t)(uintptr_t)hEventMulti;
383 if (h32 != (uintptr_t)hEventMulti)
384 return VERR_INVALID_HANDLE;
385 pObj = (PSUPDRVOBJ)RTHandleTableLookupWithCtx(pSession->hHandleTable, h32, SUPDRV_HANDLE_CTX_EVENT_MULTI);
386 if (!pObj)
387 return VERR_INVALID_HANDLE;
388
389 /*
390 * Do the job.
391 */
392 rc = RTSemEventMultiWaitNoResume((RTSEMEVENTMULTI)pObj->pvUser1, cMillies);
393
394 SUPR0ObjRelease(pObj, pSession);
395 return rc;
396}
397
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