initial import
[picodrive.git] / platform / uiq3 / engine / polledas.cpp
diff --git a/platform/uiq3/engine/polledas.cpp b/platform/uiq3/engine/polledas.cpp
new file mode 100644 (file)
index 0000000..898f76e
--- /dev/null
@@ -0,0 +1,269 @@
+/*******************************************************************\r
+ *\r
+ *     File:           PolledAS.cpp\r
+ *\r
+ *     Author:         Peter van Sebille (peter@yipton.net)\r
+ *\r
+ *     (c) Copyright 2002, Peter van Sebille\r
+ *     All Rights Reserved\r
+ *\r
+ *******************************************************************/\r
+\r
+/*\r
+ * Oh Lord, forgive me for I have sinned.\r
+ * In their infinite wisdom, Symbian Engineers have decided that\r
+ * the Active Scheduler's queue of Active Objects is private\r
+ * and no getters are provided... sigh.\r
+ * This mere mortal will have to excercise the power of C pre-processor \r
+ * once more to circumvent the will of the gods.\r
+ */\r
+\r
+\r
+#include <e32std.h>\r
+\r
+// from e32base.h\r
+class CBase\r
+       {\r
+public:\r
+       /**\r
+       Default constructor\r
+       */\r
+       inline CBase()  {}\r
+       IMPORT_C virtual ~CBase();\r
+       inline TAny* operator new(TUint aSize, TAny* aBase) __NO_THROW { Mem::FillZ(aBase, aSize); return aBase; }\r
+       inline TAny* operator new(TUint aSize) __NO_THROW { return User::AllocZ(aSize); }\r
+       inline TAny* operator new(TUint aSize, TLeave) { return User::AllocZL(aSize); }\r
+       inline TAny* operator new(TUint aSize, TUint aExtraSize) { return User::AllocZ(aSize + aExtraSize); }\r
+       inline TAny* operator new(TUint aSize, TLeave, TUint aExtraSize) { return User::AllocZL(aSize + aExtraSize); }\r
+       IMPORT_C static void Delete(CBase* aPtr);\r
+protected:\r
+       IMPORT_C virtual TInt Extension_(TUint aExtensionId, TAny*& a0, TAny* a1);\r
+private:\r
+       CBase(const CBase&);\r
+       CBase& operator=(const CBase&);\r
+private:\r
+       };\r
+\r
+\r
+class TRequestStatusFaked\r
+       {\r
+public:\r
+       inline TRequestStatusFaked() : iFlags(0) {};\r
+       inline TRequestStatusFaked(TInt aVal) : iStatus(aVal), iFlags(aVal==KRequestPending ? TRequestStatusFaked::ERequestPending : 0) {}\r
+/*     inline TInt operator=(TInt aVal);\r
+       inline TBool operator==(TInt aVal) const;\r
+*/\r
+       inline TBool operator!=(TInt aVal) const {return(iStatus!=aVal);}\r
+/*\r
+       inline TBool operator>=(TInt aVal) const;\r
+       inline TBool operator<=(TInt aVal) const;\r
+       inline TBool operator>(TInt aVal) const;\r
+       inline TBool operator<(TInt aVal) const;\r
+       inline TInt Int() const;\r
+private:\r
+*/\r
+       enum\r
+               {\r
+               EActive                         = 1,  //bit0\r
+               ERequestPending         = 2,  //bit1\r
+               };\r
+       TInt iStatus;\r
+       TUint iFlags;\r
+       friend class CActive;\r
+       friend class CActiveScheduler;\r
+       friend class CServer2;\r
+       };\r
+\r
+\r
+class CActive : public CBase\r
+       {\r
+public:\r
+enum TPriority\r
+       {\r
+       EPriorityIdle=-100,\r
+       EPriorityLow=-20,\r
+       EPriorityStandard=0,\r
+       EPriorityUserInput=10,\r
+       EPriorityHigh=20,\r
+       };\r
+public:\r
+       IMPORT_C ~CActive();\r
+       IMPORT_C void Cancel();\r
+       IMPORT_C void Deque();\r
+       IMPORT_C void SetPriority(TInt aPriority);\r
+       inline TBool IsActive() const {return(iStatus.iFlags&TRequestStatus::EActive);}\r
+       inline TBool IsAdded() const {return(iLink.iNext!=NULL);}\r
+       inline TInt Priority() const {return iLink.iPriority;}\r
+protected:\r
+       IMPORT_C CActive(TInt aPriority);\r
+       IMPORT_C void SetActive();\r
+       virtual void DoCancel() =0;\r
+       virtual void RunL() =0;\r
+       IMPORT_C virtual TInt RunError(TInt aError);\r
+protected:\r
+       IMPORT_C virtual TInt Extension_(TUint aExtensionId, TAny*& a0, TAny* a1);\r
+public:\r
+       TRequestStatusFaked iStatus; // hope this will work\r
+private:\r
+//     TBool iActive;\r
+       TPriQueLink iLink;\r
+       TAny* iSpare;\r
+       friend class CActiveScheduler;\r
+       friend class CServer;\r
+       friend class CServer2;\r
+       friend class CPrivatePolledActiveScheduler; // added\r
+       };\r
+\r
+\r
+\r
+class CActiveScheduler : public CBase\r
+       {\r
+       friend class CActiveSchedulerWait;\r
+public:\r
+       struct TLoop;\r
+       typedef TLoop* TLoopOwner;\r
+public:\r
+       IMPORT_C CActiveScheduler();\r
+       IMPORT_C ~CActiveScheduler();\r
+       IMPORT_C static void Install(CActiveScheduler* aScheduler);\r
+       IMPORT_C static CActiveScheduler* Current();\r
+       IMPORT_C static void Add(CActive* aActive);\r
+       IMPORT_C static void Start();\r
+       IMPORT_C static void Stop();\r
+       IMPORT_C static TBool RunIfReady(TInt& aError, TInt aMinimumPriority);\r
+       IMPORT_C static CActiveScheduler* Replace(CActiveScheduler* aNewActiveScheduler);\r
+       IMPORT_C virtual void WaitForAnyRequest();\r
+       IMPORT_C virtual void Error(TInt aError) const;\r
+       IMPORT_C void Halt(TInt aExitCode) const;\r
+       IMPORT_C TInt StackDepth() const;\r
+private:\r
+       static void Start(TLoopOwner* aOwner);\r
+       IMPORT_C virtual void OnStarting();\r
+       IMPORT_C virtual void OnStopping();\r
+       IMPORT_C virtual void Reserved_1();\r
+       IMPORT_C virtual void Reserved_2();\r
+       void Run(TLoopOwner* const volatile& aLoop);\r
+       void DoRunL(TLoopOwner* const volatile& aLoop, CActive* volatile & aCurrentObj);\r
+       friend class CPrivatePolledActiveScheduler; // added\r
+protected:\r
+       IMPORT_C virtual TInt Extension_(TUint aExtensionId, TAny*& a0, TAny* a1);\r
+protected:\r
+       inline TInt Level() const {return StackDepth();}        // deprecated\r
+private:\r
+       TLoop* iStack;\r
+       TPriQue<CActive> iActiveQ;\r
+       TAny* iSpare;\r
+       };\r
+\r
+\r
+\r
+class TCleanupItem;\r
+class CleanupStack\r
+       {\r
+public:\r
+       IMPORT_C static void PushL(TAny* aPtr);\r
+       IMPORT_C static void PushL(CBase* aPtr);\r
+       IMPORT_C static void PushL(TCleanupItem anItem);\r
+       IMPORT_C static void Pop();\r
+       IMPORT_C static void Pop(TInt aCount);\r
+       IMPORT_C static void PopAndDestroy();\r
+       IMPORT_C static void PopAndDestroy(TInt aCount);\r
+       IMPORT_C static void Check(TAny* aExpectedItem);\r
+       inline static void Pop(TAny* aExpectedItem);\r
+       inline static void Pop(TInt aCount, TAny* aLastExpectedItem);\r
+       inline static void PopAndDestroy(TAny* aExpectedItem);\r
+       inline static void PopAndDestroy(TInt aCount, TAny* aLastExpectedItem);\r
+       };\r
+\r
+\r
+/*\r
+ * This will declare CPrivatePolledActiveScheduler as a friend\r
+ * of all classes that define a friend. CPrivatePolledActiveScheduler needs to\r
+ * be a friend of CActive\r
+ */\r
+//#define friend friend class CPrivatePolledActiveScheduler; friend\r
+\r
+\r
+/*\r
+ * This will change the:\r
+ *              void DoStart();\r
+ * method in CActiveScheduler to:\r
+ *              void DoStart(); friend class CPrivatePolledActiveScheduler;\r
+ * We need this to access the private datamembers in CActiveScheduler.\r
+ */\r
+//#define DoStart() DoStart(); friend class CPrivatePolledActiveScheduler;\r
+//#include <e32base.h>\r
+#include "PolledAS.h"\r
+\r
+\r
+class CPrivatePolledActiveScheduler : public CActiveScheduler\r
+{\r
+public:\r
+       void Schedule();\r
+};\r
+\r
+\r
+void CPrivatePolledActiveScheduler::Schedule()\r
+{\r
+       TDblQueIter<CActive> q(iActiveQ);\r
+       q.SetToFirst();\r
+       FOREVER\r
+       {\r
+               CActive *pR=q++;\r
+               if (pR)\r
+               {\r
+                       //TRequestStatus::EActive                               = 1,  //bit0\r
+                       //TRequestStatus::ERequestPending               = 2,  //bit1\r
+                       if (pR->IsActive() && pR->iStatus!=KRequestPending)\r
+                       {\r
+//                             pR->iActive=EFalse; // won't this cause trouble?\r
+                               pR->iStatus.iFlags&=~TRequestStatusFaked::EActive;\r
+                               //debugPrintFile(_L("as: %08x"), pR);\r
+                               TRAPD(r,pR->RunL());\r
+                               //pR->iStatus=TRequestStatus::ERequestPending;\r
+                               break;\r
+                       }\r
+               }\r
+               else\r
+                       break;\r
+       }\r
+}\r
+\r
+\r
+static CPolledActiveScheduler* sPolledActiveScheduler = NULL;\r
+\r
+CPolledActiveScheduler::~CPolledActiveScheduler()\r
+{\r
+       sPolledActiveScheduler = NULL;\r
+       delete iPrivatePolledActiveScheduler;\r
+}\r
+\r
+CPolledActiveScheduler* CPolledActiveScheduler::NewL()\r
+{\r
+       // if (sPolledActiveScheduler == NULL)\r
+       {\r
+               sPolledActiveScheduler = new(ELeave)CPolledActiveScheduler;\r
+               CleanupStack::PushL(sPolledActiveScheduler);\r
+               sPolledActiveScheduler->ConstructL();\r
+               CleanupStack::Pop();\r
+       }\r
+       return sPolledActiveScheduler;\r
+}\r
+\r
+void CPolledActiveScheduler::ConstructL()\r
+{\r
+       iPrivatePolledActiveScheduler = new(ELeave) CPrivatePolledActiveScheduler;\r
+       iPrivatePolledActiveScheduler->Install(iPrivatePolledActiveScheduler);\r
+}\r
+\r
+\r
+void CPolledActiveScheduler::Schedule()\r
+{\r
+       iPrivatePolledActiveScheduler->Schedule();\r
+}\r
+\r
+CPolledActiveScheduler* CPolledActiveScheduler::Instance()\r
+{\r
+//     return (CPolledActiveScheduler*) CActiveScheduler::Current();\r
+       return sPolledActiveScheduler;\r
+}\r