sl@0: // Copyright (c) 1998-2009 Nokia Corporation and/or its subsidiary(-ies). sl@0: // All rights reserved. sl@0: // This component and the accompanying materials are made available sl@0: // under the terms of the License "Eclipse Public License v1.0" sl@0: // which accompanies this distribution, and is available sl@0: // at the URL "http://www.eclipse.org/legal/epl-v10.html". sl@0: // sl@0: // Initial Contributors: sl@0: // Nokia Corporation - initial contribution. sl@0: // sl@0: // Contributors: sl@0: // sl@0: // Description: sl@0: // os\kernelhwsrv\kernel\eka\include\drivers\display.h sl@0: // Interface to LDD of the Display GCE driver sl@0: // Kernel side definitions for the GCE driver sl@0: // sl@0: sl@0: /** sl@0: @file sl@0: @internalTechnology sl@0: @prototype sl@0: */ sl@0: sl@0: sl@0: #ifndef __DISPLAY_H__ sl@0: #define __DISPLAY_H__ sl@0: sl@0: #include sl@0: #include sl@0: #include sl@0: #include sl@0: sl@0: sl@0: sl@0: const TInt KDisplayLBMax = 2; sl@0: const TInt KDisplayCBMax = 2; sl@0: const TInt KDisplayUBMax = 8; sl@0: sl@0: sl@0: const TInt KPendingReqArraySize = RDisplayChannel::EReqWaitForPost +1; sl@0: sl@0: const TInt KMaxQueuedRequests = 3; sl@0: sl@0: class DDisplayChannel; sl@0: sl@0: sl@0: enum TBufferType sl@0: { sl@0: EBufferTypeLegacy = 0, sl@0: EBufferTypeComposition, sl@0: EBufferTypeUser, sl@0: }; sl@0: sl@0: sl@0: enum TBufferState sl@0: { sl@0: EBufferFree = 0, sl@0: EBufferCompose, sl@0: EBufferPending, sl@0: EBufferActive sl@0: }; sl@0: sl@0: sl@0: typedef struct sl@0: { sl@0: TInt iType; sl@0: TInt iBufferId; sl@0: TBool iFree; sl@0: TInt iHandle; sl@0: TInt iSize; sl@0: TUint32 iAddress; sl@0: TUint32 iPhysicalAddress; sl@0: TInt iOffset ; sl@0: DChunk * iChunk ; sl@0: TBufferState iState; sl@0: TRequestStatus* iPendingRequest; sl@0: sl@0: } TBufferNode; sl@0: sl@0: sl@0: /** sl@0: An object encapsulating a request from the client(iOwningThread) to the GCE driver. sl@0: */ sl@0: typedef struct sl@0: { sl@0: sl@0: /** The TClientRequest object associated with the request - used to signal completion of the request and pass back a sl@0: completion code. */ sl@0: TClientRequest* iTClientReq; sl@0: sl@0: /** The thread which issued the request and which supplied the request status. */ sl@0: DThread* iOwningThread; sl@0: sl@0: } TRequestNode; sl@0: sl@0: sl@0: sl@0: class DDisplayPdd; sl@0: sl@0: sl@0: /** sl@0: Logical Channel factory class for 'Display Channel LDD' sl@0: */ sl@0: sl@0: class DDisplayLddFactory : public DLogicalDevice sl@0: { sl@0: public: sl@0: static DDisplayLddFactory* CreateInstance(); sl@0: ~DDisplayLddFactory(); sl@0: // Inherited from DLogicalDevice sl@0: virtual TInt Install(); sl@0: virtual void GetCaps(TDes8& aDes) const; sl@0: virtual TInt Create(DLogicalChannelBase*& aChannel); sl@0: TBool IsUnitOpen(TInt aUnit); sl@0: TInt SetUnitOpen(TInt aUnit,TBool aIsOpenSetting); sl@0: private: sl@0: DDisplayLddFactory(); sl@0: sl@0: sl@0: private: sl@0: /** Mask to keep track of which units have a channel open on them. */ sl@0: TUint iUnitsOpenMask; sl@0: /** A mutex to protect access to the unit info mask. */ sl@0: NFastMutex iUnitInfoMutex; sl@0: }; sl@0: sl@0: sl@0: /** sl@0: Logical Channel class for 'Display Channel LDD' sl@0: */ sl@0: class DDisplayLdd : public DLogicalChannel sl@0: { sl@0: sl@0: public: sl@0: // create one instance of this object sl@0: static DDisplayLdd* CreateInstance(); sl@0: virtual ~DDisplayLdd(); sl@0: virtual TInt DoCreate(TInt aUnit, const TDesC8* anInfo, const TVersion& aVer); sl@0: virtual void HandleMsg(TMessageBase* aMsg); sl@0: sl@0: private: sl@0: DDisplayLdd(); sl@0: sl@0: private: sl@0: // Implementation for the differnt kinds of messages sent through RBusLogicalChannel sl@0: TInt DoControl(TInt aFunction, TAny* a1, TAny* a2, DThread* aClient); sl@0: TInt DoRequest(TInt aReqNo, TAny* a1, TAny* a2, TInt index, DThread* aClient); sl@0: void DoCancel(TUint aMask); sl@0: sl@0: TInt SendRequest(TMessageBase* aMsg); sl@0: TInt SendControl(TMessageBase* aMsg); sl@0: TInt SendMsg(TMessageBase* aMsg); sl@0: sl@0: TBufferNode* FindUserBufferNode(TInt aBufferId); sl@0: TInt CheckAndOpenUserBuffer(TBufferNode* aNode, TInt aHandle, TInt aOffset, DThread* aClient); sl@0: TInt FreeUserBufferNode(TBufferNode* aNode); sl@0: sl@0: void CompleteRequest(DThread* aThread, TClientRequest*& aTClientReq, TInt aReason); sl@0: sl@0: DDisplayPdd * Pdd(); sl@0: sl@0: public: sl@0: virtual TInt RequestComplete(TInt aRequest, TInt ); sl@0: sl@0: sl@0: public: sl@0: sl@0: // display info sl@0: RDisplayChannel::TDisplayInfo iLegacyInfo; sl@0: RDisplayChannel::TDisplayInfo iDisplayInfo; sl@0: sl@0: // post counters sl@0: RDisplayChannel::TPostCount iCurrentPostCount; sl@0: RDisplayChannel::TPostCount iRequestedPostCount; sl@0: sl@0: sl@0: DThread* iClient; sl@0: TInt iUnit; sl@0: sl@0: // frame buffer nodes sl@0: TBufferNode iLegacyBuffer[KDisplayLBMax]; sl@0: TBufferNode iCompositionBuffer[KDisplayCBMax]; sl@0: TBufferNode iUserBuffer[KDisplayUBMax]; sl@0: sl@0: //pending queue for asynchronous requests sl@0: TRequestNode iPendingReq[KPendingReqArraySize][KMaxQueuedRequests]; sl@0: sl@0: //Queue of TClientRequest objects, one for each type of asynchronous request. sl@0: TClientRequest* iClientRequest[KPendingReqArraySize][KMaxQueuedRequests]; sl@0: sl@0: //The index in structures iPendingReq and iClientRequest that identifies the active TClientRequest object. sl@0: //For each type of asynchronous request, iPendingIndex is the index of the active TClientRequest object sl@0: //in iPendingReq sl@0: TInt iPendingIndex[KPendingReqArraySize]; sl@0: sl@0: // Protect access of iClientRequest sl@0: DMutex * iClientRequestMutex; sl@0: sl@0: sl@0: // current index sl@0: TInt iLegacyBuffIdx; sl@0: TInt iCompositionBuffIdx; sl@0: TInt iUserBuffIdx; sl@0: sl@0: sl@0: RDisplayChannel::TDisplayRotation iLegacyRotation; sl@0: RDisplayChannel::TDisplayRotation iCurrentRotation; sl@0: sl@0: sl@0: TBool iReady; sl@0: sl@0: /** Used in debug builds to track that all calls to DThread::Open() are balanced with a close before the driver closes. */ sl@0: TInt iThreadOpenCount; sl@0: sl@0: /** Used in debug builds to track the number of asynchronous requests that are queued is equal to the number of sl@0: requests that are completed, before the driver closes.*/ sl@0: TInt iAsyncReqCount; sl@0: sl@0: /** Chunk used in UDEB only for testing user buffers. */ sl@0: DChunk* iChunk; sl@0: }; sl@0: sl@0: sl@0: /** sl@0: Display PDD base class with GCE support. sl@0: */ sl@0: sl@0: class DDisplayPdd : public DBase sl@0: { sl@0: sl@0: public: sl@0: sl@0: /** sl@0: Called by the LDD to handle the device specific part of switching to Legacy mode. sl@0: sl@0: @return KErrNone if successful; or one of the other system wide error codes. sl@0: */ sl@0: virtual TInt SetLegacyMode()=0; sl@0: sl@0: /** sl@0: Called by the LDD to handle the device specific part of switching to GCE mode. sl@0: sl@0: @return KErrNone if successful; or one of the other system wide error codes. sl@0: */ sl@0: virtual TInt SetGceMode()=0; sl@0: sl@0: /** sl@0: Called by the LDD to handle the device specific part of setting the rotation. sl@0: sl@0: @return KErrNone if successful; or one of the other system wide error codes. sl@0: */ sl@0: virtual TInt SetRotation(RDisplayChannel::TDisplayRotation aRotation)=0; sl@0: sl@0: /** sl@0: Called by the LDD to handle the device specific part of posting a User Buffer. sl@0: sl@0: @return KErrNone if successful; or one of the other system wide error codes. sl@0: */ sl@0: virtual TInt PostUserBuffer(TBufferNode* aNode)=0; sl@0: sl@0: /** sl@0: Called by the LDD to handle the device specific part of posting a Composition Buffer sl@0: sl@0: @return KErrNone if successful; or one of the other system wide error codes. sl@0: */ sl@0: virtual TInt PostCompositionBuffer(TBufferNode* aNode)=0; sl@0: sl@0: /** sl@0: Called by the LDD to handle the device specific part of posting the Legacy Buffuer sl@0: sl@0: @return KErrNone if successful; or one of the other system wide error codes. sl@0: */ sl@0: virtual TInt PostLegacyBuffer()=0; sl@0: sl@0: /** sl@0: Called by the LDD to handle device specific cleanup operations when a channel is closed. sl@0: sl@0: @return KErrNone if successful; or one of the other system wide error codes. sl@0: */ sl@0: virtual TInt CloseMsg()=0; sl@0: sl@0: /** sl@0: Called by the LDD to handle device specific initialisation tasks when a channel is opened. sl@0: sl@0: @param aUnit The screen/hardware unit number. sl@0: @return KErrNone if successful; or one of the other system wide error codes. sl@0: */ sl@0: virtual TInt CreateChannelSetup(TInt aUnit)=0; sl@0: sl@0: /** sl@0: Called by the LDD in order to detect whether a post operation is pending. This type of sl@0: information is specific to the actual physical device. sl@0: sl@0: @return ETrue if a Post operation is pending otherwise EFalse. sl@0: */ sl@0: virtual TBool PostPending()=0; sl@0: sl@0: /** sl@0: Called by the LDD to retrieve the DFC Queue created in the PDD. sl@0: sl@0: @param aUnit The screen/hardware unit number. sl@0: @return A pointer to the TDfcQue object created in the PDD. sl@0: */ sl@0: virtual TDfcQue* DfcQ(TInt aUnit)=0; sl@0: sl@0: /** sl@0: Called by the PDD when an asynchronous request should be completed with a specific reason. sl@0: (Just calls the LDD's RequestComplete method) sl@0: sl@0: @param aRequest Any value from the RDisplayChannel::TRequest enumeration. sl@0: @param aReason Any valid error reason. sl@0: sl@0: @return KErrNone if successful; or one of the other system wide error codes. sl@0: */ sl@0: inline TInt RequestComplete(TInt aRequest, TInt aReason ); sl@0: sl@0: sl@0: public: sl@0: /** sl@0: A pointer to the logical device driver's channel that owns this device. sl@0: */ sl@0: DDisplayLdd *iLdd; sl@0: /** sl@0: Every post operation sets this flag to true in order to identify when sl@0: the previsouly posted buffer is no longer in use by the display hardware. sl@0: */ sl@0: TBool iPostFlag; sl@0: sl@0: }; sl@0: sl@0: sl@0: inline DDisplayPdd * DDisplayLdd::Pdd() sl@0: { return (DDisplayPdd*) iPdd; } sl@0: sl@0: sl@0: inline TInt DDisplayPdd::RequestComplete(TInt aRequest, TInt aReason) sl@0: { return iLdd->RequestComplete(aRequest,aReason); } sl@0: sl@0: sl@0: sl@0: sl@0: //#define _GCE_DISPLAY_DEBUG sl@0: sl@0: #ifdef _GCE_DISPLAY_DEBUG sl@0: sl@0: #define __DEBUG_PRINT(a) Kern::Printf(a) sl@0: #define __DEBUG_PRINT2(a,b) Kern::Printf(a,b) sl@0: #define __DEBUG_PRINT3(a,b,c) Kern::Printf(a,b,c) sl@0: #define __DEBUG_PRINT4(a,b,c,d) Kern::Printf(a,b,c,d) sl@0: #define __DEBUG_PRINT5(a,b,c,d,e) Kern::Printf(a,b,c,d,e) sl@0: sl@0: #else sl@0: #define __DEBUG_PRINT(a) sl@0: #define __DEBUG_PRINT2(a,b) sl@0: #define __DEBUG_PRINT3(a,b,c) sl@0: #define __DEBUG_PRINT4(a,b,c,d) sl@0: #define __DEBUG_PRINT5(a,b,c,d,e) sl@0: sl@0: #endif sl@0: sl@0: sl@0: #endif // __DISPLAY_H__