59190ecd61435d19ba3515b876272aee7bd12298vboxsync/* $Id$ */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** @file
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * VirtualBox Ring-0 USB Filter Manager.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/*
c7814cf6e1240a519cbec0441e033d0e2470ed00vboxsync * Copyright (C) 2007-2012 Oracle Corporation
59190ecd61435d19ba3515b876272aee7bd12298vboxsync *
c55c68b6a3324172e9dc207926215845880b0f90vboxsync * This file is part of VirtualBox Open Source Edition (OSE), as
c55c68b6a3324172e9dc207926215845880b0f90vboxsync * available from http://www.virtualbox.org. This file is free software;
c55c68b6a3324172e9dc207926215845880b0f90vboxsync * you can redistribute it and/or modify it under the terms of the GNU
c55c68b6a3324172e9dc207926215845880b0f90vboxsync * General Public License (GPL) as published by the Free Software
c55c68b6a3324172e9dc207926215845880b0f90vboxsync * Foundation, in version 2 as it comes in the "COPYING" file of the
c55c68b6a3324172e9dc207926215845880b0f90vboxsync * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
c55c68b6a3324172e9dc207926215845880b0f90vboxsync * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/*******************************************************************************
59190ecd61435d19ba3515b876272aee7bd12298vboxsync* Header Files *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync*******************************************************************************/
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#include <VBox/usbfilter.h>
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#include "VBoxUSBFilterMgr.h"
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#include <iprt/mem.h>
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#ifdef VBOXUSBFILTERMGR_USB_SPINLOCK
59190ecd61435d19ba3515b876272aee7bd12298vboxsync# include <iprt/spinlock.h>
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#else
59190ecd61435d19ba3515b876272aee7bd12298vboxsync# include <iprt/semaphore.h>
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#endif
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#include <iprt/string.h>
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/*******************************************************************************
59190ecd61435d19ba3515b876272aee7bd12298vboxsync* Defined Constants And Macros *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync*******************************************************************************/
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** @def VBOXUSBFILTERMGR_LOCK
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Locks the filter list. Careful with scoping since this may
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * create a temporary variable. Don't call twice in the same function.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** @def VBOXUSBFILTERMGR_UNLOCK
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Unlocks the filter list.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#ifdef VBOXUSBFILTERMGR_USB_SPINLOCK
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync# define VBOXUSBFILTERMGR_LOCK() \
f0ed7ab5e7f8d2f73b5aa08e46eb3a04cbb31cb2vboxsync RTSpinlockAcquire(g_Spinlock)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync# define VBOXUSBFILTERMGR_UNLOCK() \
f0ed7ab5e7f8d2f73b5aa08e46eb3a04cbb31cb2vboxsync RTSpinlockRelease(g_Spinlock)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#else
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync# define VBOXUSBFILTERMGR_LOCK() \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync do { int rc2 = RTSemFastMutexRequest(g_Mtx); AssertRC(rc2); } while (0)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync# define VBOXUSBFILTERMGR_UNLOCK() \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync do { int rc2 = RTSemFastMutexRelease(g_Mtx); AssertRC(rc2); } while (0)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#endif
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/*******************************************************************************
59190ecd61435d19ba3515b876272aee7bd12298vboxsync* Structures and Typedefs *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync*******************************************************************************/
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** Pointer to an VBoxUSB filter. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsynctypedef struct VBOXUSBFILTER *PVBOXUSBFILTER;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** Pointer to PVBOXUSBFILTER. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsynctypedef PVBOXUSBFILTER *PPVBOXUSBFILTER;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/**
ad27e1d5e48ca41245120c331cc88b50464813cevboxsync * VBoxUSB internal filter representation.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsynctypedef struct VBOXUSBFILTER
59190ecd61435d19ba3515b876272aee7bd12298vboxsync{
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The core filter. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync USBFILTER Core;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The filter owner. */
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync VBOXUSBFILTER_CONTEXT Owner;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The filter Id. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync uintptr_t uId;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** Pointer to the next filter in the list. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pNext;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync} VBOXUSBFILTER;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/**
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * VBoxUSB filter list.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsynctypedef struct VBOXUSBFILTERLIST
59190ecd61435d19ba3515b876272aee7bd12298vboxsync{
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The head pointer. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pHead;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The tail pointer. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pTail;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync} VBOXUSBFILTERLIST;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** Pointer to a VBOXUSBFILTERLIST. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsynctypedef VBOXUSBFILTERLIST *PVBOXUSBFILTERLIST;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/*******************************************************************************
59190ecd61435d19ba3515b876272aee7bd12298vboxsync* Global Variables *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync*******************************************************************************/
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#ifdef VBOXUSBFILTERMGR_USB_SPINLOCK
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** Spinlock protecting the filter lists. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsyncstatic RTSPINLOCK g_Spinlock = NIL_RTSPINLOCK;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#else
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** Mutex protecting the filter lists. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsyncstatic RTSEMFASTMUTEX g_Mtx = NIL_RTSEMFASTMUTEX;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#endif
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** The per-type filter lists.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @remark The first entry is empty (USBFILTERTYPE_INVALID). */
59190ecd61435d19ba3515b876272aee7bd12298vboxsyncstatic VBOXUSBFILTERLIST g_aLists[USBFILTERTYPE_END];
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/**
ad27e1d5e48ca41245120c331cc88b50464813cevboxsync * Initializes the VBoxUSB filter manager.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @returns IPRT status code.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsyncint VBoxUSBFilterInit(void)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync{
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#ifdef VBOXUSBFILTERMGR_USB_SPINLOCK
f0ed7ab5e7f8d2f73b5aa08e46eb3a04cbb31cb2vboxsync int rc = RTSpinlockCreate(&g_Spinlock, RTSPINLOCK_FLAGS_INTERRUPT_SAFE, "VBoxUSBFilter");
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#else
59190ecd61435d19ba3515b876272aee7bd12298vboxsync int rc = RTSemFastMutexCreate(&g_Mtx);
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#endif
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if (RT_SUCCESS(rc))
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /* not really required, but anyway... */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync for (unsigned i = USBFILTERTYPE_FIRST; i < RT_ELEMENTS(g_aLists); i++)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync g_aLists[i].pHead = g_aLists[i].pTail = NULL;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync return rc;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync}
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/**
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Internal worker that frees a filter.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param pFilter The filter to free.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsyncstatic void vboxUSBFilterFree(PVBOXUSBFILTER pFilter)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync{
59190ecd61435d19ba3515b876272aee7bd12298vboxsync USBFilterDelete(&pFilter->Core);
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync pFilter->Owner = VBOXUSBFILTER_CONTEXT_NIL;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pFilter->pNext = NULL;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync RTMemFree(pFilter);
59190ecd61435d19ba3515b876272aee7bd12298vboxsync}
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/**
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Terminates the VBoxUSB filter manager.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsyncvoid VBoxUSBFilterTerm(void)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync{
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#ifdef VBOXUSBFILTERMGR_USB_SPINLOCK
59190ecd61435d19ba3515b876272aee7bd12298vboxsync RTSpinlockDestroy(g_Spinlock);
59190ecd61435d19ba3515b876272aee7bd12298vboxsync g_Spinlock = NIL_RTSPINLOCK;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#else
59190ecd61435d19ba3515b876272aee7bd12298vboxsync RTSemFastMutexDestroy(g_Mtx);
59190ecd61435d19ba3515b876272aee7bd12298vboxsync g_Mtx = NIL_RTSEMFASTMUTEX;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#endif
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync for (unsigned i = USBFILTERTYPE_FIRST; i < RT_ELEMENTS(g_aLists); i++)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pCur = g_aLists[i].pHead;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync g_aLists[i].pHead = g_aLists[i].pTail = NULL;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync while (pCur)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pNext = pCur->pNext;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync vboxUSBFilterFree(pCur);
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pCur = pNext;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync}
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/**
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Adds a new filter.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * The filter will be validate, duplicated and added.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @returns IPRT status code.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param pFilter The filter.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param Owner The filter owner. Must be non-zero.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param puId Where to store the filter ID.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
df294ff29aab74013667896ef2d4f5bd1f782143vboxsyncint VBoxUSBFilterAdd(PCUSBFILTER pFilter, VBOXUSBFILTER_CONTEXT Owner, uintptr_t *puId)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync{
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /*
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Validate input.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync int rc = USBFilterValidate(pFilter);
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if (RT_FAILURE(rc))
59190ecd61435d19ba3515b876272aee7bd12298vboxsync return rc;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync if (!Owner || Owner == VBOXUSBFILTER_CONTEXT_NIL)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync return VERR_INVALID_PARAMETER;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if (!VALID_PTR(puId))
59190ecd61435d19ba3515b876272aee7bd12298vboxsync return VERR_INVALID_POINTER;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /*
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Allocate a new filter.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pNew = (PVBOXUSBFILTER)RTMemAlloc(sizeof(*pNew));
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if (!pNew)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync return VERR_NO_MEMORY;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync memcpy(&pNew->Core, pFilter, sizeof(pNew->Core));
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pNew->Owner = Owner;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pNew->uId = (uintptr_t)pNew;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pNew->pNext = NULL;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync *puId = pNew->uId;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /*
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Insert it.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTERLIST pList = &g_aLists[pFilter->enmType];
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync VBOXUSBFILTERMGR_LOCK();
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if (pList->pTail)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pList->pTail->pNext = pNew;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync else
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pList->pHead = pNew;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pList->pTail = pNew;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync VBOXUSBFILTERMGR_UNLOCK();
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync return VINF_SUCCESS;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync}
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/**
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Removes an existing filter.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * The filter will be validate, duplicated and added.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @returns IPRT status code.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @retval VINF_SUCCESS if successfully removed.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @retval VERR_FILE_NOT_FOUND if the specified filter/owner cannot be found.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param Owner The filter owner.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param uId The ID of the filter that's to be removed.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Returned by VBoxUSBFilterAdd().
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
df294ff29aab74013667896ef2d4f5bd1f782143vboxsyncint VBoxUSBFilterRemove(VBOXUSBFILTER_CONTEXT Owner, uintptr_t uId)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync{
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /*
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Validate input.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if (!uId)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync return VERR_INVALID_PARAMETER;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync if (!Owner || Owner == VBOXUSBFILTER_CONTEXT_NIL)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync return VERR_INVALID_PARAMETER;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /*
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Locate and unlink it.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pCur = NULL;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync VBOXUSBFILTERMGR_LOCK();
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync for (unsigned i = USBFILTERTYPE_FIRST; !pCur && i < RT_ELEMENTS(g_aLists); i++)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pPrev = NULL;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pCur = g_aLists[i].pHead;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync while (pCur)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if ( pCur->uId == uId
59190ecd61435d19ba3515b876272aee7bd12298vboxsync && pCur->Owner == Owner)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pNext = pCur->pNext;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if (pPrev)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pPrev->pNext = pNext;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync else
59190ecd61435d19ba3515b876272aee7bd12298vboxsync g_aLists[i].pHead = pNext;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if (!pNext)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync g_aLists[i].pTail = pPrev;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync break;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pPrev = pCur;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pCur = pCur->pNext;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync VBOXUSBFILTERMGR_UNLOCK();
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /*
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Free it (if found).
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if (pCur)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
59190ecd61435d19ba3515b876272aee7bd12298vboxsync vboxUSBFilterFree(pCur);
59190ecd61435d19ba3515b876272aee7bd12298vboxsync return VINF_SUCCESS;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync return VERR_FILE_NOT_FOUND;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync}
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
df294ff29aab74013667896ef2d4f5bd1f782143vboxsyncVBOXUSBFILTER_CONTEXT VBoxUSBFilterGetOwner(uintptr_t uId)
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync{
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync Assert(uId);
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync /*
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync * Validate input.
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync */
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync if (!uId)
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync return VBOXUSBFILTER_CONTEXT_NIL;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync /*
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync * Result.
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync */
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync VBOXUSBFILTER_CONTEXT Owner = VBOXUSBFILTER_CONTEXT_NIL;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync VBOXUSBFILTERMGR_LOCK();
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync for (unsigned i = USBFILTERTYPE_FIRST; i < RT_ELEMENTS(g_aLists); i++)
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync {
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync for (PVBOXUSBFILTER pCur = g_aLists[i].pHead; pCur; pCur = pCur->pNext)
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync {
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync if (pCur->uId == uId)
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync {
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync Owner = pCur->Owner;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync Assert(Owner != VBOXUSBFILTER_CONTEXT_NIL);
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync break;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync }
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync }
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync }
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync Assert(Owner != VBOXUSBFILTER_CONTEXT_NIL);
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync VBOXUSBFILTERMGR_UNLOCK();
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync return Owner;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync}
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/**
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Removes all filters belonging to the specified owner.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * This is typically called when an owner disconnects or
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * terminates unexpectedly.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param Owner The owner
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
df294ff29aab74013667896ef2d4f5bd1f782143vboxsyncvoid VBoxUSBFilterRemoveOwner(VBOXUSBFILTER_CONTEXT Owner)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync{
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /*
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Collect the filters that should be freed.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pToFree = NULL;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync VBOXUSBFILTERMGR_LOCK();
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync for (unsigned i = USBFILTERTYPE_FIRST; i < RT_ELEMENTS(g_aLists); i++)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pPrev = NULL;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pCur = g_aLists[i].pHead;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync while (pCur)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if (pCur->Owner == Owner)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pNext = pCur->pNext;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if (pPrev)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pPrev->pNext = pNext;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync else
59190ecd61435d19ba3515b876272aee7bd12298vboxsync g_aLists[i].pHead = pNext;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if (!pNext)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync g_aLists[i].pTail = pPrev;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pCur->pNext = pToFree;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pToFree = pCur;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pCur = pNext;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync else
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pPrev = pCur;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pCur = pCur->pNext;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync VBOXUSBFILTERMGR_UNLOCK();
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /*
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Free any filters we've found.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync while (pToFree)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pNext = pToFree->pNext;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync vboxUSBFilterFree(pToFree);
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pToFree = pNext;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync}
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/**
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Match the specified device against the filters.
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync * Unlike the VBoxUSBFilterMatch, returns Owner also if exclude filter is matched
59190ecd61435d19ba3515b876272aee7bd12298vboxsync *
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync * @returns Owner on if matched, VBOXUSBFILTER_CONTEXT_NIL it not matched.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param pDevice The device data as a filter structure.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * See USBFilterMatch for how to construct this.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param puId Where to store the filter id (optional).
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync * @param pfFilter Where to store whether the device must be filtered or not
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
df294ff29aab74013667896ef2d4f5bd1f782143vboxsyncVBOXUSBFILTER_CONTEXT VBoxUSBFilterMatchEx(PCUSBFILTER pDevice, uintptr_t *puId, bool fRemoveFltIfOneShot, bool *pfFilter, bool *pfIsOneShot)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync{
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /*
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Validate input.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync int rc = USBFilterValidate(pDevice);
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync AssertRCReturn(rc, VBOXUSBFILTER_CONTEXT_NIL);
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync *pfFilter = false;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync if (puId)
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync *puId = 0;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /*
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Search the lists for a match.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * (The lists are ordered by priority.)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync VBOXUSBFILTERMGR_LOCK();
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync for (unsigned i = USBFILTERTYPE_FIRST; i < RT_ELEMENTS(g_aLists); i++)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pPrev = NULL;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync PVBOXUSBFILTER pCur = g_aLists[i].pHead;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync while (pCur)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if (USBFilterMatch(&pCur->Core, pDevice))
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /*
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Take list specific actions and return.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * The code does NOT implement the case where there are two or more
ad27e1d5e48ca41245120c331cc88b50464813cevboxsync * filter clients, and one of them is releasing a device that's
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * requested by some of the others. It's just too much work for a
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * situation that noone will encounter.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if (puId)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync *puId = pCur->uId;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync VBOXUSBFILTER_CONTEXT Owner = pCur->Owner;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync *pfFilter = !!(i != USBFILTERTYPE_IGNORE
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync && i != USBFILTERTYPE_ONESHOT_IGNORE);
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if ( i == USBFILTERTYPE_ONESHOT_IGNORE
59190ecd61435d19ba3515b876272aee7bd12298vboxsync || i == USBFILTERTYPE_ONESHOT_CAPTURE)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync {
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync if (fRemoveFltIfOneShot)
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync {
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync /* unlink */
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync PVBOXUSBFILTER pNext = pCur->pNext;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync if (pPrev)
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync pPrev->pNext = pNext;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync else
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync g_aLists[i].pHead = pNext;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync if (!pNext)
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync g_aLists[i].pTail = pPrev;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync VBOXUSBFILTERMGR_UNLOCK();
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync if ( i == USBFILTERTYPE_ONESHOT_IGNORE
59190ecd61435d19ba3515b876272aee7bd12298vboxsync || i == USBFILTERTYPE_ONESHOT_CAPTURE)
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync {
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync if (fRemoveFltIfOneShot)
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync {
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync vboxUSBFilterFree(pCur);
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync }
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync if (pfIsOneShot)
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync *pfIsOneShot = true;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync }
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync else
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync {
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync if (pfIsOneShot)
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync *pfIsOneShot = false;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync return Owner;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pPrev = pCur;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync pCur = pCur->pNext;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync }
59190ecd61435d19ba3515b876272aee7bd12298vboxsync
59190ecd61435d19ba3515b876272aee7bd12298vboxsync VBOXUSBFILTERMGR_UNLOCK();
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync return VBOXUSBFILTER_CONTEXT_NIL;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync}
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync/**
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync * Match the specified device against the filters.
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync *
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync * @returns Owner on if matched, VBOXUSBFILTER_CONTEXT_NIL it not matched.
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync * @param pDevice The device data as a filter structure.
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync * See USBFilterMatch for how to construct this.
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync * @param puId Where to store the filter id (optional).
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync */
df294ff29aab74013667896ef2d4f5bd1f782143vboxsyncVBOXUSBFILTER_CONTEXT VBoxUSBFilterMatch(PCUSBFILTER pDevice, uintptr_t *puId)
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync{
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync bool fFilter = false;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync VBOXUSBFILTER_CONTEXT Owner = VBoxUSBFilterMatchEx(pDevice, puId,
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync true, /* remove filter is it's a one-shot*/
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync &fFilter, NULL /* bool * fIsOneShot */);
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync if (fFilter)
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync {
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync Assert(Owner != VBOXUSBFILTER_CONTEXT_NIL);
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync return Owner;
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync }
df294ff29aab74013667896ef2d4f5bd1f782143vboxsync return VBOXUSBFILTER_CONTEXT_NIL;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync}
59190ecd61435d19ba3515b876272aee7bd12298vboxsync