williamr@4: // Copyright (c) 2000-2009 Nokia Corporation and/or its subsidiary(-ies). williamr@4: // All rights reserved. williamr@4: // This component and the accompanying materials are made available williamr@4: // under the terms of the License "Eclipse Public License v1.0" williamr@4: // which accompanies this distribution, and is available williamr@4: // at the URL "http://www.eclipse.org/legal/epl-v10.html". williamr@4: // williamr@4: // Initial Contributors: williamr@4: // Nokia Corporation - initial contribution. williamr@4: // williamr@4: // Contributors: williamr@4: // williamr@4: // Description: williamr@4: // e32/include/drivers/usbc.h williamr@4: // Kernel side definitions for the USB Device driver stack (PIL + LDD). williamr@4: // williamr@4: // williamr@4: williamr@4: /** williamr@4: @file usbc.h williamr@4: @internalTechnology williamr@4: */ williamr@4: williamr@4: #ifndef __USBC_H__ williamr@4: #define __USBC_H__ williamr@4: williamr@4: #include williamr@4: #include williamr@4: #include williamr@4: #include williamr@4: williamr@4: #include williamr@4: williamr@4: #include williamr@4: williamr@4: williamr@4: williamr@4: /** LDD Major version, This should agree with the information in RDevUsbcClient::TVer. williamr@4: */ williamr@4: const TInt KUsbcMajorVersion = 0; williamr@4: williamr@4: /** LDD Minor version, This should agree with the information in RDevUsbcClient::TVer. williamr@4: */ williamr@4: const TInt KUsbcMinorVersion = 1; williamr@4: williamr@4: /** LDD Build version, This should agree with the information in RDevUsbcClient::TVer. williamr@4: */ williamr@4: const TInt KUsbcBuildVersion = KE32BuildVersionNumber; williamr@4: williamr@4: /** Must correspond to the max enum of TRequest + 1; williamr@4: currently this is ERequestOtgFeaturesNotify = 10. williamr@4: */ williamr@4: const TInt KUsbcMaxRequests = 11; williamr@4: williamr@4: // williamr@4: //########################### Logical Device Driver (LDD) ############################# williamr@4: // williamr@4: williamr@4: /** USB LDD factory class. williamr@4: */ williamr@4: class DUsbcLogDevice : public DLogicalDevice williamr@4: { williamr@4: public: williamr@4: DUsbcLogDevice(); williamr@4: virtual TInt Install(); williamr@4: virtual void GetCaps(TDes8& aDes) const; williamr@4: virtual TInt Create(DLogicalChannelBase*& aChannel); williamr@4: }; williamr@4: williamr@4: williamr@4: /** OUT buffering is a collection of flat buffers. Each is either fillable or drainable. williamr@4: When one buffer becomes full (notified by the PIL) it is marked as not-fillable and the next williamr@4: fillable buffer is used. When the buffer has finished draining it is marked as fillable. williamr@4: */ williamr@4: class TDmaBuf williamr@4: { williamr@4: public: williamr@4: TDmaBuf(); williamr@4: TDmaBuf(TUsbcEndpointInfo* aEndpointInfo, TInt aBandwidthPriority); williamr@4: ~TDmaBuf(); williamr@4: TInt Construct(TUsbcEndpointInfo* aEndpointInfo); williamr@4: TInt BufferTotalSize() const; williamr@4: TInt BufferSize() const; williamr@4: TInt SetBufferAddr(TInt aBufInd, TUint8* aBufAddr); williamr@4: TInt BufferNumber() const; williamr@4: void SetMaxPacketSize(TInt aSize); williamr@4: void Flush(); williamr@4: // Rx (OUT) variants williamr@4: void RxSetActive(); williamr@4: void RxSetInActive(); williamr@4: TBool RxIsActive(); williamr@4: TBool IsReaderEmpty(); williamr@4: void ReadXferComplete(TInt aNoBytesRx, TInt aNoPacketsRx, TInt aErrorCode); williamr@4: TInt RxCopyDataToClient(DThread* aThread, TClientBuffer *aTcb, TInt aLength, TUint32& aDestOffset, williamr@4: TBool aRUS, TBool& aCompleteNow); williamr@4: TInt RxCopyPacketToClient(DThread* aThread,TClientBuffer *aTcb, TInt aLength); williamr@4: TInt RxGetNextXfer(TUint8*& aBufferAddr, TUsbcPacketArray*& aIndexArray, TUsbcPacketArray*& aSizeArray, williamr@4: TInt& aLength, TPhysAddr& aBufferPhys); williamr@4: TBool RxIsEnoughSpace(TInt aSize); williamr@4: inline TInt RxBytesAvailable() const; williamr@4: inline void IncrementBufferIndex(TInt& aIndex); williamr@4: inline TInt NoRxPackets() const; williamr@4: TInt SetDrainable(TInt aBufferNum); williamr@4: // Tx (IN) variants williamr@4: void TxSetActive(); williamr@4: void TxSetInActive(); williamr@4: TBool TxIsActive(); williamr@4: TInt TxStoreData(DThread* aThread,TClientBuffer *aTcb, TInt aTxLength, TUint32 aBufferOffset); williamr@4: TInt TxGetNextXfer(TUint8*& aBufferAddr, TInt& aTxLength, TPhysAddr& aBufferPhys); williamr@4: TBool ShortPacketExists(); williamr@4: williamr@4: #if defined(USBC_LDD_BUFFER_TRACE) williamr@4: TInt NoRxPacketsAlt() const; williamr@4: TInt NoRxBytesAlt() const; williamr@4: #endif williamr@4: williamr@4: private: williamr@4: TBool AdvancePacket(); williamr@4: inline TInt GetCurrentError(); williamr@4: TBool NextDrainableBuffer(); williamr@4: TBool NextFillableBuffer(); williamr@4: void FreeDrainedBuffers(); williamr@4: TInt PeekNextPacketSize(); williamr@4: TInt PeekNextDrainableBuffer(); williamr@4: void ModifyTotalRxBytesAvail(TInt aVal); williamr@4: void ModifyTotalRxPacketsAvail(TInt aVal); williamr@4: void AddToDrainQueue(TInt aBufferIndex); williamr@4: inline TInt CopyToUser(DThread* aThread, const TUint8* aSourceAddr, TInt aLength, williamr@4: TClientBuffer *aTcb, TUint32& aDestOffset); williamr@4: private: williamr@4: TInt iExtractOffset; // offset into current packet for data read williamr@4: TInt iMaxPacketSize; williamr@4: TInt iNumberofBuffers; williamr@4: TInt iBufSz; williamr@4: TBool iRxActive; williamr@4: TBool iTxActive; williamr@4: TInt iTotalRxBytesAvail; williamr@4: TInt iTotalRxPacketsAvail; williamr@4: // williamr@4: TUint8* iBufBasePtr; williamr@4: TUint8* iCurrentDrainingBuffer; williamr@4: TInt iCurrentDrainingBufferIndex; williamr@4: TInt iCurrentFillingBufferIndex; williamr@4: TUint iCurrentPacket; williamr@4: TUsbcPacketArray* iCurrentPacketIndexArray; williamr@4: TUsbcPacketArray* iCurrentPacketSizeArray; williamr@4: TUint8* iBuffers[KUsbcDmaBufNumMax]; williamr@4: TBool iDrainable[KUsbcDmaBufNumMax]; williamr@4: TUsbcPacketArray iPacketInfoStorage[KUsbcDmaBufNumMax * KUsbcDmaBufNumArrays * KUsbcDmaBufMaxPkts]; williamr@4: TUsbcPacketArray* iPacketIndex[KUsbcDmaBufNumMax]; williamr@4: TUsbcPacketArray* iPacketSize[KUsbcDmaBufNumMax]; williamr@4: TUint iNumberofBytesRx[KUsbcDmaBufNumMax]; williamr@4: TUint iNumberofPacketsRx[KUsbcDmaBufNumMax]; williamr@4: TInt iError[KUsbcDmaBufNumMax]; williamr@4: TPhysAddr iBufferPhys[KUsbcDmaBufNumMax]; williamr@4: TBool iCanBeFreed[KUsbcDmaBufNumMax]; williamr@4: TInt iDrainQueue[KUsbcDmaBufNumMax + 1]; williamr@4: TInt iDrainQueueIndex; williamr@4: TUint iEndpointType; williamr@4: williamr@4: #if defined(USBC_LDD_BUFFER_TRACE) williamr@4: TInt iFillingOrder; williamr@4: TInt iFillingOrderArray[KUsbcDmaBufNumMax]; williamr@4: TInt iDrainingOrder; williamr@4: TUint iNumberofBytesRxRemain[KUsbcDmaBufNumMax]; williamr@4: TUint iNumberofPacketsRxRemain[KUsbcDmaBufNumMax]; williamr@4: #endif williamr@4: }; williamr@4: williamr@4: williamr@4: class DLddUsbcChannel; williamr@4: williamr@4: /** Endpoint tracking for the LDD buffering etc. williamr@4: */ williamr@4: class TUsbcEndpoint williamr@4: { williamr@4: public: williamr@4: TUsbcEndpoint(); williamr@4: TUsbcEndpoint(DLddUsbcChannel* aLDD, DUsbClientController* aController, williamr@4: const TUsbcEndpointInfo* aEndpointInfo, TInt aEndpointNum, williamr@4: TInt aBandwidthPriority); williamr@4: ~TUsbcEndpoint(); williamr@4: TInt Construct(); williamr@4: TInt TryToStartRead(TBool aReEntrant); williamr@4: TInt TryToStartWrite(TEndpointTransferInfo* pTfr); williamr@4: TInt CopyToClient(DThread* aThread, TClientBuffer *aTcb); williamr@4: TInt CopyToClient(DThread* aClient, TBool& aCompleteNow, TClientBuffer *aTcb); williamr@4: TInt ContinueWrite(); williamr@4: void SetMaxPacketSize(TInt aSize); williamr@4: void CancelTransfer(DThread* aThread, TClientBuffer *aTcb); williamr@4: void AbortTransfer(); williamr@4: inline TUsbcEndpointInfo* EndpointInfo(); williamr@4: inline TInt RxBytesAvailable() const; williamr@4: williamr@4: inline TInt BufferSize() const; williamr@4: inline TInt SetBufferAddr( TInt aBufInd, TUint8* aAddr); williamr@4: inline TInt BufferNumber() const; williamr@4: williamr@4: inline void SetTransferInfo(TEndpointTransferInfo* aTransferInfo); williamr@4: inline void ResetTransferInfo(); williamr@4: inline void SetClientReadPending(TBool aVal); williamr@4: inline void SetClientWritePending(TBool aVal); williamr@4: inline TBool ClientWritePending(); williamr@4: inline TBool ClientReadPending(); williamr@4: inline void SetRealEpNumber(TInt aRealEpNumber); williamr@4: inline TInt RealEpNumber() const; williamr@4: williamr@4: public: williamr@4: TDmaBuf* iDmaBuffers; williamr@4: williamr@4: private: williamr@4: static void RequestCallback(TAny* aTUsbcEndpoint); williamr@4: void TxComplete(); williamr@4: TInt RxComplete(TBool aReEntrant); williamr@4: void RxCompleteNow(); williamr@4: TInt EndpointComplete(); williamr@4: williamr@4: private: williamr@4: DUsbClientController* iController; williamr@4: TUsbcEndpointInfo iEndpointInfo; williamr@4: TEndpointTransferInfo iTransferInfo; williamr@4: TBool iClientReadPending; williamr@4: TBool iClientWritePending; williamr@4: TInt iEndpointNumber; williamr@4: TInt iRealEpNumber; williamr@4: DLddUsbcChannel* iLdd; williamr@4: TInt iError; williamr@4: TUsbcRequestCallback* iRequestCallbackInfo; williamr@4: TUint32 iBytesTransferred; williamr@4: TInt iBandwidthPriority; williamr@4: }; williamr@4: williamr@4: williamr@4: /** Linked list of 'alternate setting' info for use by the LDD. williamr@4: */ williamr@4: class TUsbcAlternateSettingList williamr@4: { williamr@4: public: williamr@4: TUsbcAlternateSettingList(); williamr@4: ~TUsbcAlternateSettingList(); williamr@4: williamr@4: public: williamr@4: TUsbcAlternateSettingList* iNext; williamr@4: TInt iNumberOfEndpoints; williamr@4: TUint iSetting; williamr@4: TInt iEpNumDeOrderedByBufSize[KMaxEndpointsPerClient + 1]; williamr@4: TUsbcEndpoint* iEndpoint[KMaxEndpointsPerClient + 1]; williamr@4: }; williamr@4: williamr@4: williamr@4: struct TClientAsynchNotify williamr@4: { williamr@4: TClientBufferRequest *iBufferRequest; williamr@4: TClientBuffer *iClientBuffer; williamr@4: void Reset(); williamr@4: }; williamr@4: /** The channel class - the actual USB LDD. williamr@4: */ williamr@4: class DLddUsbcChannel : public DLogicalChannel williamr@4: { williamr@4: public: williamr@4: DLddUsbcChannel(); williamr@4: ~DLddUsbcChannel(); williamr@4: virtual TInt SendMsg(TMessageBase * aMsg); williamr@4: TInt PreSendRequest(TMessageBase * aMsg,TInt aReqNo, TRequestStatus* aStatus, TAny* a1, TAny* a2); williamr@4: TInt SendControl(TMessageBase* aMsg); williamr@4: virtual void HandleMsg(TMessageBase* aMsg); williamr@4: virtual TInt DoCreate(TInt aUnit, const TDesC8* aInfo, const TVersion& aVer); williamr@4: virtual TInt RequestUserHandle(DThread* aThread, TOwnerType aType); williamr@4: TInt DoRxComplete(TUsbcEndpoint* aTUsbcEndpoint, TInt aEndpoint, TBool aReentrant); williamr@4: void DoRxCompleteNow(TUsbcEndpoint* aTUsbcEndpoint, TInt aEndpoint); williamr@4: void DoTxComplete(TUsbcEndpoint* aTUsbcEndpoint, TInt aEndpoint, TInt aError); williamr@4: inline DThread* Client() const {return iClient;} williamr@4: inline TBool ChannelClosing() const {return iChannelClosing;} williamr@4: inline TUint AlternateSetting() const {return iAlternateSetting;} williamr@4: TClientBuffer *GetClientBuffer(TInt aEndpoint); williamr@4: williamr@4: private: williamr@4: TInt DoCancel(TInt aReqNo); williamr@4: void DoRequest(TInt aReqNo, TRequestStatus* aStatus, TAny* a1, TAny* a2); williamr@4: TInt DoControl(TInt aFunction, TAny* a1, TAny* a2); williamr@4: TInt DoTransferAsyncReq(TInt aEndpointNum, TAny* a1, TAny* a2, TBool& aNeedsCompletion); williamr@4: TInt DoOtherAsyncReq(TInt aReqNo, TAny* a1, TAny* a2, TBool& aNeedsCompletion); williamr@4: TBool AlternateDeviceStateTestComplete(); williamr@4: TInt SetInterface(TInt aInterfaceNum, TUsbcIfcInfo* aUserInterfaceInfoBuf); williamr@4: void StartEpReads(); williamr@4: void DestroyAllInterfaces(); williamr@4: void DestroyInterface(TUint aInterface); williamr@4: void DestroyEp0(); williamr@4: inline TBool ValidEndpoint(TInt aEndpoint); williamr@4: TInt DoEmergencyComplete(); williamr@4: void ReadDes8(const TAny* aPtr, TDes8& aDes); williamr@4: TInt SetupEp0(); williamr@4: DPlatChunkHw* ReAllocate(TInt aBuffersize, DPlatChunkHw* aHwChunk, TUint32 aCacheAttribs); williamr@4: DPlatChunkHw* Allocate(TInt aBuffersize, TUint32 aCacheAttribs); williamr@4: void ClosePhysicalChunk(DPlatChunkHw* &aHwChunk); williamr@4: void CancelNotifyEndpointStatus(); williamr@4: void CancelNotifyOtgFeatures(); williamr@4: static void StatusChangeCallback(TAny* aDLddUsbcChannel); williamr@4: static void EndpointStatusChangeCallback(TAny* aDLddUsbcChannel); williamr@4: static void OtgFeatureChangeCallback(TAny* aDLddUsbcChannel); williamr@4: static void EmergencyCompleteDfc(TAny* aDLddUsbcChannel); williamr@4: void DeConfigure(TInt aErrorCode); williamr@4: TInt SelectAlternateSetting(TUint aAlternateSetting); williamr@4: TInt EpFromAlternateSetting(TUint aAlternateSetting, TInt aEndpoint); williamr@4: TInt ProcessAlternateSetting(TUint aAlternateSetting); williamr@4: TInt ProcessDeviceState(TUsbcDeviceState aDeviceState); williamr@4: void ResetInterface(TInt aErrorCode); williamr@4: void AbortInterface(); williamr@4: // Set buffer address of the interface williamr@4: void ReSetInterfaceMemory(TUsbcAlternateSettingList* aAlternateSettingListRec, williamr@4: RArray &aHwChunks ); williamr@4: void UpdateEndpointSizes(); williamr@4: // Check and alloc memory for the interface williamr@4: TInt SetupInterfaceMemory(RArray &aHwChunks, williamr@4: TUint32 aCacheAttribs ); williamr@4: void PanicClientThread(TInt aReason); williamr@4: TInt PinMemory(TDesC8 *aDes, TVirtualPinObject *iPinObj); //Descriptor pinning helper. williamr@4: void CompleteBufferRequest(DThread* aThread, TInt aReqNo, TInt aReason); williamr@4: private: williamr@4: DUsbClientController* iController; williamr@4: DThread* iClient; williamr@4: TBool iValidInterface; williamr@4: TUsbcAlternateSettingList* iAlternateSettingList; williamr@4: TUsbcEndpoint* iEndpoint[KMaxEndpointsPerClient + 1]; // include ep0 williamr@4: TRequestStatus* iRequestStatus[KUsbcMaxRequests]; williamr@4: TClientAsynchNotify* iClientAsynchNotify[KUsbcMaxRequests]; williamr@4: TUsbcClientCallback iCompleteAllCallbackInfo; williamr@4: TAny* iStatusChangePtr; williamr@4: TUsbcStatusCallback iStatusCallbackInfo; williamr@4: TAny* iEndpointStatusChangePtr; williamr@4: TUsbcEndpointStatusCallback iEndpointStatusCallbackInfo; williamr@4: TAny* iOtgFeatureChangePtr; williamr@4: TUsbcOtgFeatureCallback iOtgFeatureCallbackInfo; williamr@4: TInt iNumberOfEndpoints; williamr@4: RArray iHwChunksEp0; williamr@4: RArray iHwChunks; williamr@4: williamr@4: TUsbcDeviceState iDeviceState; williamr@4: TUsbcDeviceState iOldDeviceState; williamr@4: TBool iOwnsDeviceControl; williamr@4: TUint iAlternateSetting; williamr@4: TBool iDeviceStatusNeeded; williamr@4: TUsbcDeviceStatusQueue* iStatusFifo; williamr@4: TBool iChannelClosing; williamr@4: TVirtualPinObject *iPinObj1; williamr@4: TVirtualPinObject *iPinObj2; williamr@4: TVirtualPinObject *iPinObj3; williamr@4: TClientDataRequest *iStatusChangeReq; williamr@4: TClientDataRequest *iEndpointStatusChangeReq; williamr@4: TClientDataRequest *iOtgFeatureChangeReq; williamr@4: TEndpointTransferInfo iTfrInfo; williamr@4: }; williamr@4: williamr@4: williamr@4: #include williamr@4: williamr@4: #endif // __USBC_H__