/** @file * VirtualBox USB Proxy Service (base) class. */ /* * Copyright (C) 2006 InnoTek Systemberatung GmbH * * This file is part of VirtualBox Open Source Edition (OSE), as * available from http://www.virtualbox.org. This file is free software; * you can redistribute it and/or modify it under the terms of the GNU * General Public License as published by the Free Software Foundation, * in version 2 as it comes in the "COPYING" file of the VirtualBox OSE * distribution. VirtualBox OSE is distributed in the hope that it will * be useful, but WITHOUT ANY WARRANTY of any kind. * * If you received this file as part of a commercial VirtualBox * distribution, then only the terms of your commercial VirtualBox * license agreement apply instead of the previous paragraph. */ #ifndef ____H_USBPROXYSERVICE #define ____H_USBPROXYSERVICE #include "HostImpl.h" #include "HostUSBDeviceImpl.h" /** * Base class for the USB Proxy service. */ class USBProxyService { public: USBProxyService (Host *aHost); virtual ~USBProxyService(); /** * A filter was inserted / loaded. * * @param aFilter Pointer to the inserted filter. * @return ID of the inserted filter */ virtual void *insertFilter (IUSBDeviceFilter *aFilter); /** * A filter was removed. * * @param aID ID of the filter to remove */ virtual void removeFilter (void *aID); /** * A VM is trying to capture a device, do necessary preperations. * * @returns VBox status code. * @param pDevice The device in question. */ virtual int captureDevice (HostUSBDevice *pDevice); /** * The device is to be held so that the host OS will not start using it. * * @returns VBox status code. * @param pDevice The device in question. */ virtual int holdDevice (HostUSBDevice *pDevice); /** * A VM is releasing a device back to the host. * * @returns VBox status code. * @param pDevice The device in question. */ virtual int releaseDevice (HostUSBDevice *pDevice); /** * A VM is releaseing a device back to be held or assigned to another VM. * A port reset should be performed. * * @returns VBox status code. * @param pDevice The device in question. */ virtual int resetDevice (HostUSBDevice *pDevice); /** * Query if the service is active and working. * * @returns true if the service is up running. * @returns false if the service isn't running. */ bool isActive (void); /** * Get last error. * Can be used to check why the proxy !isActive() upon construction. * * @returns VBox status code. */ int getLastError (void); /** * Calculate the hash of the serial string. * * 64bit FNV1a, chosen because it is designed to hash in to a power of two * space, and is much quicker and simpler than, say, a half MD4. * * @returns the hash. * @param aSerial The serial string. */ static uint64_t calcSerialHash (const char *aSerial); protected: /** * Starts the service. * * @returns VBox status. */ int start (void); /** * Stops the service. * * @returns VBox status. */ int stop (void); /** * Wait for a change in the USB devices attached to the host. * * @returns VBox status (ignored). * @param aMillies Number of milliseconds to wait. */ virtual int wait (unsigned aMillies); /** * Interrupt any wait() call in progress. * * @returns VBox status. */ virtual int interruptWait (void); /** * Get a list of USB device currently attached to the host. * * @returns Pointer to a list of USB devices. * The list nodes are freed individually by calling freeDevice(). */ virtual PUSBDEVICE getDevices (void); public: /** * Free one USB device returned by getDevice(). * * @param pDevice Pointer to the device. */ static void freeDevice (PUSBDEVICE pDevice); private: /** * Process any relevant changes in the attached USB devices. */ void processChanges (void); /** * The service thread created by start(). * * @param Thread The thread handle. * @param pvUser Pointer to the USBProxyService instance. */ static DECLCALLBACK (int) serviceThread (RTTHREAD Thread, void *pvUser); protected: /** Pointer to the Host object. */ Host *mHost; /** Thread handle of the service thread. */ RTTHREAD mThread; /** Flag which stop() sets to cause serviceThread to return. */ bool volatile mTerminate; /** List of smart HostUSBDevice pointers. */ typedef std::list > HostUSBDeviceList; /** List of the known USB devices. */ HostUSBDeviceList mDevices; /** VBox status code of the last failure. * (Only used by start(), stop() and the child constructors.) */ int mLastError; }; #ifdef VBOX_WITH_USB # ifdef __LINUX__ # include /** * The Linux hosted USB Proxy Service. */ class USBProxyServiceLinux : public USBProxyService { public: USBProxyServiceLinux (Host *aHost, const char *aUsbfsRoot = "/proc/bus/usb"); ~USBProxyServiceLinux(); virtual int captureDevice (HostUSBDevice *aDevice); virtual int holdDevice (HostUSBDevice *aDevice); virtual int releaseDevice (HostUSBDevice *aDevice); virtual int resetDevice (HostUSBDevice *aDevice); protected: virtual int wait (unsigned aMillies); virtual int interruptWait (void); virtual PUSBDEVICE getDevices (void); private: /** File handle to the '/proc/bus/usb/devices' file. */ RTFILE mFile; /** Stream for mFile. */ FILE *mStream; /** Pipe used to interrupt wait(), the read end. */ RTFILE mWakeupPipeR; /** Pipe used to interrupt wait(), the write end. */ RTFILE mWakeupPipeW; /** The root of usbfs. */ Utf8Str mUsbfsRoot; }; # endif /* __LINUX__ */ # ifdef __WIN__ /** * The Win32 hosted USB Proxy Service. */ class USBProxyServiceWin32 : public USBProxyService { public: USBProxyServiceWin32 (Host *aHost); ~USBProxyServiceWin32(); virtual void *insertFilter (IUSBDeviceFilter *aFilter); virtual void removeFilter (void *aID); virtual int captureDevice (HostUSBDevice *aDevice); virtual int holdDevice (HostUSBDevice *aDevice); virtual int releaseDevice (HostUSBDevice *aDevice); virtual int resetDevice (HostUSBDevice *aDevice); protected: virtual int wait (unsigned aMillies); virtual int interruptWait (void); virtual PUSBDEVICE getDevices (void); private: HANDLE hEventInterrupt; }; # endif /* __WIN__ */ #endif /* VBOX_WITH_USB */ #endif /* !____H_USBPROXYSERVICE */