VirtualBox

source: vbox/trunk/src/VBox/Main/include/USBProxyService.h@ 7466

Last change on this file since 7466 was 5999, checked in by vboxsync, 17 years ago

The Giant CDDL Dual-License Header Change.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 11.8 KB
Line 
1/* $Id: USBProxyService.h 5999 2007-12-07 15:05:06Z vboxsync $ */
2/** @file
3 * VirtualBox USB Proxy Service (base) class.
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 (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
18
19#ifndef ____H_USBPROXYSERVICE
20#define ____H_USBPROXYSERVICE
21
22#include "HostImpl.h"
23#include "HostUSBDeviceImpl.h"
24
25/**
26 * Base class for the USB Proxy service.
27 */
28class USBProxyService
29{
30public:
31 USBProxyService (Host *aHost);
32 virtual ~USBProxyService();
33
34 /**
35 * A filter was inserted / loaded.
36 *
37 * @param aFilter Pointer to the inserted filter.
38 * @return ID of the inserted filter
39 */
40#ifdef VBOX_WITH_USBFILTER
41 virtual void *insertFilter (PCUSBFILTER aFilter);
42#else
43 virtual void *insertFilter (IUSBDeviceFilter *aFilter);
44#endif
45
46 /**
47 * A filter was removed.
48 *
49 * @param aId ID of the filter to remove
50 */
51 virtual void removeFilter (void *aId);
52
53 /**
54 * A VM is trying to capture a device, do necessary preperations.
55 *
56 * @returns VBox status code.
57 * @param aDevice The device in question.
58 */
59 virtual int captureDevice (HostUSBDevice *aDevice);
60
61 /**
62 * The device is going to be detached from a VM.
63 *
64 * @param aDevice The device in question.
65 */
66 virtual void detachingDevice (HostUSBDevice *aDevice);
67
68 /**
69 * A VM is releasing a device back to the host.
70 *
71 * @returns VBox status code.
72 * @param aDevice The device in question.
73 */
74 virtual int releaseDevice (HostUSBDevice *aDevice);
75
76 /**
77 * Updates the device state.
78 * This is responsible for calling HostUSBDevice::updateState() and check for async completion.
79 *
80 * @returns true if there is a state change.
81 * @param aDevice The device in question.
82 * @param aUSBDevice The USB device structure for the last enumeration.
83 */
84 virtual bool updateDeviceState (HostUSBDevice *aDevice, PUSBDEVICE aUSBDevice);
85
86 /**
87 * Add device notification hook for the OS specific code.
88 *
89 * @param aDevice The device in question.
90 * @param aUSBDevice The USB device structure.
91 */
92 virtual void deviceAdded (HostUSBDevice *aDevice, PUSBDEVICE aUSBDevice);
93
94 /**
95 * Remove device notification hook for the OS specific code.
96 *
97 * @param aDevice The device in question.
98 */
99 virtual void deviceRemoved (HostUSBDevice *aDevice);
100
101 /**
102 * Query if the service is active and working.
103 *
104 * @returns true if the service is up running.
105 * @returns false if the service isn't running.
106 */
107 bool isActive (void);
108
109 /**
110 * Get last error.
111 * Can be used to check why the proxy !isActive() upon construction.
112 *
113 * @returns VBox status code.
114 */
115 int getLastError (void);
116
117 /**
118 * Calculate the hash of the serial string.
119 *
120 * 64bit FNV1a, chosen because it is designed to hash in to a power of two
121 * space, and is much quicker and simpler than, say, a half MD4.
122 *
123 * @returns the hash.
124 * @param aSerial The serial string.
125 */
126 static uint64_t calcSerialHash (const char *aSerial);
127
128#ifdef VBOX_WITH_USBFILTER
129 /**
130 * Initializes a filter with the data from the specified device.
131 *
132 * @param aFilter The filter to fill.
133 * @param aDevice The device to fill it with.
134 */
135 static void initFilterFromDevice (PUSBFILTER aFilter, HostUSBDevice *aDevice);
136#endif
137
138protected:
139
140 /**
141 * Starts the service.
142 *
143 * @returns VBox status.
144 */
145 int start (void);
146
147 /**
148 * Stops the service.
149 *
150 * @returns VBox status.
151 */
152 int stop (void);
153
154 /**
155 * Wait for a change in the USB devices attached to the host.
156 *
157 * @returns VBox status (ignored).
158 * @param aMillies Number of milliseconds to wait.
159 */
160 virtual int wait (unsigned aMillies);
161
162 /**
163 * Interrupt any wait() call in progress.
164 *
165 * @returns VBox status.
166 */
167 virtual int interruptWait (void);
168
169 /**
170 * Get a list of USB device currently attached to the host.
171 *
172 * @returns Pointer to a list of USB devices.
173 * The list nodes are freed individually by calling freeDevice().
174 */
175 virtual PUSBDEVICE getDevices (void);
176
177 /**
178 * First call made on the service thread, use it to do
179 * thread initialization.
180 */
181 virtual void serviceThreadInit (void);
182
183 /**
184 * First call made on the service thread, use it to do
185 * thread termination.
186 */
187 virtual void serviceThreadTerm (void);
188
189 /**
190 * Implement fake capture, ++.
191 *
192 * @returns true if there is a state change.
193 * @param pDevice The device in question.
194 * @param pUSBDevice The USB device structure for the last enumeration.
195 */
196 bool updateDeviceStateFake (HostUSBDevice *aDevice, PUSBDEVICE aUSBDevice);
197
198
199public:
200 /**
201 * Free all the members of a USB interface returned by getDevice().
202 *
203 * @param pIf Pointer to the interface.
204 * @param cIfs Number of consecutive interfaces pIf points to
205 */
206 static void freeInterfaceMembers (PUSBINTERFACE pIf, unsigned cIfs);
207
208 /**
209 * Free all the members of a USB device returned by getDevice().
210 *
211 * @param pDevice Pointer to the device.
212 */
213 static void freeDeviceMembers (PUSBDEVICE pDevice);
214
215 /**
216 * Free one USB device returned by getDevice().
217 *
218 * @param pDevice Pointer to the device.
219 */
220 static void freeDevice (PUSBDEVICE pDevice);
221
222private:
223 /**
224 * Process any relevant changes in the attached USB devices.
225 */
226 void processChanges (void);
227
228 /**
229 * The service thread created by start().
230 *
231 * @param Thread The thread handle.
232 * @param pvUser Pointer to the USBProxyService instance.
233 */
234 static DECLCALLBACK (int) serviceThread (RTTHREAD Thread, void *pvUser);
235
236protected:
237 /** Pointer to the Host object. */
238 Host *mHost;
239 /** Thread handle of the service thread. */
240 RTTHREAD mThread;
241 /** Flag which stop() sets to cause serviceThread to return. */
242 bool volatile mTerminate;
243 /** List of smart HostUSBDevice pointers. */
244 typedef std::list <ComObjPtr <HostUSBDevice> > HostUSBDeviceList;
245 /** List of the known USB devices. */
246 HostUSBDeviceList mDevices;
247 /** VBox status code of the last failure.
248 * (Only used by start(), stop() and the child constructors.) */
249 int mLastError;
250};
251
252
253#ifdef VBOX_WITH_USB
254
255# ifdef RT_OS_DARWIN
256# include <VBox/param.h>
257# undef PAGE_SHIFT
258# undef PAGE_SIZE
259# define OSType Carbon_OSType
260# include <Carbon/Carbon.h>
261# undef OSType
262
263/**
264 * The Darwin hosted USB Proxy Service.
265 */
266class USBProxyServiceDarwin : public USBProxyService
267{
268public:
269 USBProxyServiceDarwin (Host *aHost);
270 ~USBProxyServiceDarwin();
271
272#ifdef VBOX_WITH_USBFILTER
273 virtual void *insertFilter (PCUSBFILTER aFilter);
274 virtual void removeFilter (void *aId);
275#endif
276
277 virtual int captureDevice (HostUSBDevice *aDevice);
278 virtual void detachingDevice (HostUSBDevice *aDevice);
279 virtual int releaseDevice (HostUSBDevice *aDevice);
280 virtual bool updateDeviceState (HostUSBDevice *aDevice, PUSBDEVICE aUSBDevice);
281
282protected:
283 virtual int wait (unsigned aMillies);
284 virtual int interruptWait (void);
285 virtual PUSBDEVICE getDevices (void);
286 virtual void serviceThreadInit (void);
287 virtual void serviceThreadTerm (void);
288
289private:
290 /** Reference to the runloop of the service thread.
291 * This is NULL if the service thread isn't running. */
292 CFRunLoopRef mServiceRunLoopRef;
293 /** The opaque value returned by DarwinSubscribeUSBNotifications. */
294 void *mNotifyOpaque;
295 /** A hack to work around the problem with the usb device enumeration
296 * not including newly attached devices. */
297 bool mWaitABitNextTime;
298#ifndef VBOX_WITH_USBFILTER
299 /** Whether we've got a fake async event and should return without entering the runloop. */
300 bool volatile mFakeAsync;
301#endif
302 /** Whether we've successfully initialized the USBLib and should call USBLibTerm in the destructor. */
303 bool mUSBLibInitialized;
304};
305# endif /* RT_OS_DARWIN */
306
307
308# ifdef RT_OS_LINUX
309# include <stdio.h>
310
311/**
312 * The Linux hosted USB Proxy Service.
313 */
314class USBProxyServiceLinux : public USBProxyService
315{
316public:
317 USBProxyServiceLinux (Host *aHost, const char *aUsbfsRoot = "/proc/bus/usb");
318 ~USBProxyServiceLinux();
319
320 virtual int captureDevice (HostUSBDevice *aDevice);
321 virtual int releaseDevice (HostUSBDevice *aDevice);
322 virtual bool updateDeviceState (HostUSBDevice *aDevice, PUSBDEVICE aUSBDevice);
323 virtual void deviceAdded (HostUSBDevice *aDevice, PUSBDEVICE aUSBDevice);
324
325protected:
326 virtual int wait (unsigned aMillies);
327 virtual int interruptWait (void);
328 virtual PUSBDEVICE getDevices (void);
329 int addDeviceToChain (PUSBDEVICE pDev, PUSBDEVICE *ppFirst, PUSBDEVICE **pppNext, int rc);
330
331private:
332 /** File handle to the '/proc/bus/usb/devices' file. */
333 RTFILE mFile;
334 /** Stream for mFile. */
335 FILE *mStream;
336 /** Pipe used to interrupt wait(), the read end. */
337 RTFILE mWakeupPipeR;
338 /** Pipe used to interrupt wait(), the write end. */
339 RTFILE mWakeupPipeW;
340 /** The root of usbfs. */
341 Utf8Str mUsbfsRoot;
342 /** Number of 500ms polls left to do. See usbDeterminState for details. */
343 unsigned mUdevPolls;
344};
345# endif /* RT_OS_LINUX */
346
347
348# ifdef RT_OS_OS2
349# include <usbcalls.h>
350
351/**
352 * The Linux hosted USB Proxy Service.
353 */
354class USBProxyServiceOs2 : public USBProxyService
355{
356public:
357 USBProxyServiceOs2 (Host *aHost);
358 ~USBProxyServiceOs2();
359
360 virtual int captureDevice (HostUSBDevice *aDevice);
361 virtual int releaseDevice (HostUSBDevice *aDevice);
362 virtual bool updateDeviceState (HostUSBDevice *aDevice, PUSBDEVICE aUSBDevice);
363
364protected:
365 virtual int wait (unsigned aMillies);
366 virtual int interruptWait (void);
367 virtual PUSBDEVICE getDevices (void);
368 int addDeviceToChain (PUSBDEVICE pDev, PUSBDEVICE *ppFirst, PUSBDEVICE **pppNext, int rc);
369
370private:
371 /** The notification event semaphore */
372 HEV mhev;
373 /** The notification id. */
374 USBNOTIFY mNotifyId;
375 /** The usbcalls.dll handle. */
376 HMODULE mhmod;
377 /** UsbRegisterChangeNotification */
378 APIRET (APIENTRY *mpfnUsbRegisterChangeNotification)(PUSBNOTIFY, HEV, HEV);
379 /** UsbDeregisterNotification */
380 APIRET (APIENTRY *mpfnUsbDeregisterNotification)(USBNOTIFY);
381 /** UsbQueryNumberDevices */
382 APIRET (APIENTRY *mpfnUsbQueryNumberDevices)(PULONG);
383 /** UsbQueryDeviceReport */
384 APIRET (APIENTRY *mpfnUsbQueryDeviceReport)(ULONG, PULONG, PVOID);
385};
386# endif /* RT_OS_LINUX */
387
388
389# ifdef RT_OS_WINDOWS
390/**
391 * The Win32 hosted USB Proxy Service.
392 */
393class USBProxyServiceWin32 : public USBProxyService
394{
395public:
396 USBProxyServiceWin32 (Host *aHost);
397 ~USBProxyServiceWin32();
398
399 virtual void *insertFilter (IUSBDeviceFilter *aFilter);
400 virtual void removeFilter (void *aID);
401
402 virtual int captureDevice (HostUSBDevice *aDevice);
403 virtual int releaseDevice (HostUSBDevice *aDevice);
404 virtual bool updateDeviceState (HostUSBDevice *aDevice, PUSBDEVICE aUSBDevice);
405
406protected:
407 virtual int wait (unsigned aMillies);
408 virtual int interruptWait (void);
409 virtual PUSBDEVICE getDevices (void);
410
411private:
412
413 HANDLE hEventInterrupt;
414};
415# endif /* RT_OS_WINDOWS */
416
417#endif /* VBOX_WITH_USB */
418
419
420#endif /* !____H_USBPROXYSERVICE */
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