diff -r 000000000000 -r c9bc50fca66e usbmgmt/usbmgr/host/fdf/production/server/inc/deviceproxy.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/usbmgmt/usbmgr/host/fdf/production/server/inc/deviceproxy.h Tue Feb 02 02:02:59 2010 +0200 @@ -0,0 +1,149 @@ +/* +* Copyright (c) 2007-2009 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "Eclipse Public License v1.0" +* which accompanies this distribution, and is available +* at the URL "http://www.eclipse.org/legal/epl-v10.html". +* +* Initial Contributors: +* Nokia Corporation - initial contribution. +* +* Contributors: +* +* Description: +* +*/ + +/** + @file + @internalComponent +*/ + +#ifndef DEVICEPROXY_H +#define DEVICEPROXY_H + +#include +#include "usbhoststack.h" + +#ifdef __OVER_DUMMYUSBDI__ +#include +#else +#include +#endif + +class TDeviceEvent; +class TOtgDescriptor; + +NONSHARABLE_CLASS(CDeviceProxy) : public CBase + { +public: + /** Link between elements of this type in a TSglQue. */ + TSglQueLink iLink; + +public: + static CDeviceProxy* NewL(RUsbHubDriver& aHubDriver, TUint aDeviceId); + ~CDeviceProxy(); + +public: // querying information from the device + TInt GetDeviceDescriptor(TUsbDeviceDescriptor& aDescriptor); + TInt GetConfigurationDescriptor(TUsbConfigurationDescriptor& aDescriptor) const; + const RArray& GetSupportedLanguages() const; + void GetManufacturerStringDescriptorL(TUint32 aLangId, TName& aString) const; + void GetProductStringDescriptorL(TUint32 aLangId, TName& aString) const; + void GetSerialNumberStringDescriptorL(TUint32 aLangId, TName& aString) const; + + void GetOtgDescriptorL(TOtgDescriptor& aDescriptor) const; + void SetOtgDescriptorL(const TUsbOTGDescriptor& aDescriptor); + +public: // management + TInt GetTokenForInterface(TUint aIndex, TUint32& aToken) const; + TUint DeviceId() const; + void SetDriverLoadingEventData(TDriverLoadStatus aStatus, TInt aError = KErrNone); + TInt Suspend(); + + // These methods TAKE OWNERSHIP of the relevant objects. + TDeviceEvent* GetAttachmentEventObject(); + TDeviceEvent* GetDriverLoadingEventObject(); + TDeviceEvent* GetDetachmentEventObject(); + inline void SetMultipleDriversFlag() + { + iMultipleDriversFound = ETrue; + } + + inline TBool MultipleDriversFlag() + { + return iMultipleDriversFound; + } + inline void SetHasIADFlag() + { + iHasIAD = ETrue; + } + inline TBool HasIADFlag() + { + return iHasIAD; + } + +private: + CDeviceProxy(TUint aDeviceId); + void ConstructL(RUsbHubDriver& aHubDriver); + +private: // utility + void Log(); + void ReadStringDescriptorsL(); + void PopulateStringDescriptorsL(TUint8 aStringDescriptorIndex, RArray& aStringArray); + void GetStringDescriptorFromUsbdL(TUint32 aLangId, TName& aString, TUint8 aStringDescriptorIndex) const; + void GetStringDescriptorFromCacheL(TUint32 aLangId, TName& aString, const RArray& aStringArray) const; + +private: // owned + RUsbDevice iHandle; + const TUint iId; + + TDeviceEvent* iAttachmentEvent; + TDeviceEvent* iDriverLoadingEvent; + TDeviceEvent* iDetachmentEvent; + + // The design of string descriptor access in this class deserves some + // explanation. + // In the simplest implementation of the FDF, we handle a device + // attachment without getting or storing any string descriptors from the + // device. If the FDF doesn't load any drivers for the device, it must + // suspend the device to save power. If USBMAN, subsequent to this, + // queries any string descriptors, the FDF will have to resume the device + // first (string descriptors are not requested or cached by USBD). + // Resuming a device is an asynchronous operation. We must therefore + // either make querying a string descriptor asynchronous as far as USBMAN + // is concerned (which would clearly make the relevant APIs much less + // friendly) or find another way round. [For completeness: this + // asynchronicity would rely on + // RHubDriver::QueueDeviceStateChangeNotification.] + // Solution 1: if the FDF doesn't load drivers for the device, wait until + // USBSVR has queried string descriptors from us before suspending the + // device. Con: USBMAN only queries string descriptors when its client (in + // licensee-land) does so. We can't make any assumptions about their doing + // it in a timely manner or indeed at all. + // Solution 2: use User::After to give the device time to resume + // synchronously. Con: this is a major no-no in a production thread which + // must remain responsive to user requests and lower-level events. + // Mentioned only for completeness. + // Solution 3 (implemented): request and cache all supported string + // descriptors at attachment time. String descriptors are typically small + // (a dozen characters, say), we only support 3 of them (manufacturer, + // product and serial number- not all of which may actually be supported + // by a particular device) and there is usually only 1 language, if that. + // Having cached the string descriptors, it is trivial to look them up + // later when the client wants. + // These arrays are tied together, i.e. iManufacturerStrings[2] is the + // manufacturer string in the language with ID iLangIds[2]. Note that this + // may be KNullDesC if the device doesn't support the manufacturer string + // descriptor, but there's still an entry in the array for it. + RArray iLangIds; + RArray iManufacturerStrings; + RArray iProductStrings; + RArray iSerialNumberStrings; + TBool iHasIAD; + TBool iMultipleDriversFound; + TOtgDescriptor* iOtgDescriptor; // Owned + }; + +#endif // DEVICEPROXY_H