⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 umsthreadproxy.h

📁 C语言库函数的原型,有用的拿去
💻 H
📖 第 1 页 / 共 2 页
字号:
// ==++==
//
// Copyright (c) Microsoft Corporation.  All rights reserved.
//
// ==--==
// =+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
//
// UMSThreadProxy.h
//
// Proxy for a UMS thread.
//
// =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-

#if defined(_DEBUG)
#define UMS_DEBUGBIT_CRITICALBLOCK 0x00000001
#define UMS_DEBUGBIT_BLOCKED 0x00000002
#define UMS_DEBUGBIT_COMPLETION 0x00000004
#define UMS_DEBUGBIT_TRANSFERLIST 0x00000008
#define UMS_DEBUGBIT_CRITICALNOTIFY 0x00000010
#define UMS_DEBUGBIT_SKIPPEDCOMPLETION 0x00000020
#define UMS_DEBUGBIT_HANDEDTOPOLLER 0x00000040
#define UMS_DEBUGBIT_PULLEDFROMTRANSFERLIST 0x00000080
#define UMS_DEBUGBIT_POLLERFOUNDCOMPLETION 0x00000100
#define UMS_DEBUGBIT_YIELDED 0x00000200
#define UMS_DEBUGBIT_FREELIST 0x00000400
#define UMS_DEBUGBIT_CRITICALAWAKENING 0x00000800
#define UMS_DEBUGBIT_DEACTIVATEDPROXY 0x00001000
#define UMS_DEBUGBIT_ACTIVATEDPROXY 0x00002000
#define UMS_DEBUGBIT_COMPLETIONTERMINATED 0x00004000
#define UMS_DEBUGBIT_EXECUTEFAILURESUSPENDED 0x80000000
#define UMS_DEBUGBIT_EXECUTEFAILURETERMINATED 0x40000000
#endif // _DEBUG

// A magic value for m_pTransmogrification that indicates it should be immediately unblocked when defer created.
#define TRANSMOGRIFICATION_UNBLOCKED ((PVOID)1)

namespace Concurrency
{
namespace details
{
    class UMSThreadProxy : public UMSBaseObject, public Concurrency::IUMSThreadProxy, public Concurrency::IUMSUnblockNotification
    {
    public:
        /// <summary>
        ///     Constructs a thread proxy.
        /// </summary>
        /// <param name="pFactory">
        ///     The thread proxy factory that created this thread proxy, and maintains the idle pool of thread proxies.
        /// </param>
        /// <param name="pStartupList">
        ///     The initial UMS completion list that this UMS thread should be put on upon creation.  A primary cannot schedule
        ///     the thread until it has appeared on the specified completion list.
        /// </param>
        /// <param name="stackSize">
        ///     The stack size of the created thread.
        /// </param>
        UMSThreadProxy(IThreadProxyFactory * pFactory, PUMS_COMPLETION_LIST pStartupList, unsigned int stackSize);

        /// <summary>
        ///     Destroys a thread proxy.
        /// </summary>
        virtual ~UMSThreadProxy();

        /// <summary>
        ///     Retrieves a process unique id for the thread proxy.
        /// </summary>
        unsigned int GetId() const;

        /// <summary>
        ///     Gets the stack size of the thread proxy. Multiply by 1 KB to get actual stack size in bytes.
        /// </summary>
        unsigned int GetStackSize()
        {
            return m_stackSize;
        }

        /// <summary>
        ///     Cancels the thread proxy causing the underlying thread to exit.
        /// </summary>
        void Cancel();

        /// <summary>
        ///     Returns the virtual processor root the thread proxy is running on.
        /// </summary>
        UMSFreeVirtualProcessorRoot *GetVirtualProcessorRoot()
        {
            return m_pRoot;
        }

        /// <summary>
        ///     Returns the previous virtual processor root the thread proxy is running on.  If it is running, the current one is returned.
        /// </summary>
        UMSFreeVirtualProcessorRoot *GetLastVirtualProcessorRoot()
        {
            return m_pLastRoot;
        }

        /// <summary>
        ///     Returns a Win32 handle to the thread that is backing this proxy.
        /// </summary>
        HANDLE GetThreadHandle()
        {
            return m_hPhysicalContext;
        }

        /// <summary>
        ///     Returns our understanding of a UMS context (a UMS thread proxy) from the UMS system's understanding (a UMS_CONTEXT)
        /// </summary>
        /// <param name="pUMSContext">
        ///     UMS context
        /// </param>
        /// <returns>
        ///     UMS thread proxy
        /// </returns>
        static UMSThreadProxy *FromUMSContext(PUMS_CONTEXT pUMSContext);

        /// <summary>
        ///     Returns our understanding of a UMS context (a UMS thread proxy) from the SLIST_ENTRY used to place it on an SLIST (e.g.: the transfer list).
        /// </summary>
        /// <param name="pListEntry">
        ///     Pointer to the SList entry in the thread proxy
        /// </param>
        /// <returns>
        ///     UMS thread proxy
        /// </returns>
        static UMSThreadProxy *FromListEntry(PSLIST_ENTRY pListEntry);

        /// <summary>
        ///     Returns the current UMS context.
        /// </summary>
        /// <returns>
        ///     Current UMS thread proxy
        /// </returns>
        static UMSThreadProxy *GetCurrent()
        {
            return UMSThreadProxy::FromUMSContext(UMS::GetCurrentUmsThread());
        }

        /// <summary>
        ///     Returns the PUMS_CONTEXT associated with this UMS thread.
        /// </summary>
        /// <returns>
        ///     UMS context for this thread
        /// </returns>
        PUMS_CONTEXT GetUMSContext() const
        {
            return m_pUMSContext;
        }

        /// <summary>
        ///     Returns whether the action that this thread took to get itself "unscheduled" was a message/yield pair.  This could be an explicit
        ///     SwitchTo, a Deactivate, a pooling, etc...
        /// </summary>
        /// <returns>
        ///     Returns true if the thread last yielded to the primary
        /// </returns>
        bool MessagedYield()
        {
            return (m_yieldAction != ActionNone);
        }

        /// <summary>
        ///     Enters a critical region within the resource manager.  This definition is constrained to the resource manager's definition
        ///     of a critical region.  While inside a critical region, asynchronous suspensions (page faults, etc...) are hidden from view
        ///     of the underlying scheduling code (within the RM and the scheduler).
        /// </summary>
        /// <returns>
        ///     Returns the current critical region count
        /// </returns>
        virtual int EnterCriticalRegion()
        {
            // Entering a critical region should be done on the same thread
            CORE_ASSERT(UMSThreadProxy::GetCurrent() == this);

            return(++m_criticalRegionCount);
        }

        /// <summary>
        ///     Exits a critical region within the resource manager.   This definition is constrained to the resource manager's definition
        ///     of a critical region.  While inside a critical region, asynchronous suspensions (page faults, etc...) are hidden from view
        ///     of the underlying scheduling code (within the RM and the scheduler).
        /// </summary>
        /// <returns>
        ///     Returns the current critical region count
        /// </returns>
        virtual int ExitCriticalRegion()
        {
            CORE_ASSERT(m_criticalRegionCount > 0);
            return(--m_criticalRegionCount);
        }

        /// <summary>
        ///     Identical to EnterHyperCriticalRegion -- this is a private version for utilization within the RM that does not follow the 
        ///     "on-the-owning" thread rule.
        /// </summary>
        /// <returns>
        ///     Returns the current hypercritical region count
        /// </returns>
        int ForceEnterHyperCriticalRegion()
        {
            m_criticalRegionCount++;
            return(++m_hyperCriticalRegionCount);
        }

        /// <summary>
        ///     Enters a hyper-critical region within the resource manager.  This definition is constrained to the resource manager's definition
        ///     of a hyper-critical region.  When inside a hyper-critical region, any suspension is hidden from view of the underlying scheduling
        ///     code.  This requires EXTRA care with regards to the locks which are taken inside the region.  No lock taken inside the region
        ///     can be shared with code outside such a region!
        /// </summary>
        /// <returns>
        ///     Returns the current hypercritical region count
        /// </returns>
        virtual int EnterHyperCriticalRegion()
        {
            // Entering a critical region should be done on the same thread
            CORE_ASSERT(UMSThreadProxy::GetCurrent() == this);

            return ForceEnterHyperCriticalRegion();
        }

        /// <summary>
        ///     Exit a hyper-critical region within the resource manager.  This definition is constrained to the resource manager's definition
        ///     of a hyper-critical region.  When inside a hyper-critical region, any suspension is hidden from view of the underlying scheduling
        ///     code.  This requires EXTRA care with regards to the locks which are taken inside the region.  No lock taken inside the region
        ///     can be shared with code outside such a region!
        /// </summary>
        /// <returns>
        ///     Returns the current hypercritical region count
        /// </returns>
        virtual int ExitHyperCriticalRegion()
        {
            CORE_ASSERT(m_hyperCriticalRegionCount > 0);
            CORE_ASSERT(m_criticalRegionCount > 0);
            int val = --m_hyperCriticalRegionCount;
            m_criticalRegionCount--;

            return val;
        }

        /// <summary>
        ///     Returns whether or not this UMS thread proxy is within a critical region (either inside the RM or inside the scheduler).
        ///     Note that the scheduler's definition of a critical region may be stronger than ours.
        /// </summary>
        /// <returns>
        ///     Whether or not this UMS thread proxy is within a critical region.
        /// </returns>
        virtual CriticalRegionType GetCriticalRegionType() const
        {
            if (m_hyperCriticalRegionCount > 0)
                return InsideHyperCriticalRegion;
            if (m_criticalRegionCount > 0)
                return InsideCriticalRegion;

            return OutsideCriticalRegion;
        }

        /// <summary>
        ///     Clears the critical region bits.  This should be done before reusing the context or placing it on the idle pool as certain operations
        ///     require a "until the end of time" critical region.
        /// </summary>
        void ClearCriticalRegion()
        {
            m_criticalRegionCount = m_hyperCriticalRegionCount = 0;
        }

        /// <summary>
        ///     Gets the priority of the thread proxy.
        /// </summary>
        /// <returns>
        ///     The priority of the thread proxy
        /// </returns>
        int GetPriority()
        {
            return m_threadPriority;
        }

        /// <summary>
        ///     Sets the priority of the underlying thread.
        /// </summary>
        /// <param name="priority">
        ///     The new priority value for the thread.
        /// </param>
        void SetPriority(int priority);

        /// <summary>
        ///     Notifies the thread proxy that it is blocked (due to UMS activation of the primary). 
        /// </summary>
        /// <param name="fCritically">
        ///     Indication that this thread is critically blocked (inside critical region)
        /// </param>
        void NotifyBlocked(bool fCritically)
        {
            CORE_ASSERT(m_pRoot != NULL);
#if defined(_DEBUG)
            CORE_ASSERT((m_UMSDebugBits & (UMS_DEBUGBIT_DEACTIVATEDPROXY | UMS_DEBUGBIT_ACTIVATEDPROXY)) != UMS_DEBUGBIT_DEACTIVATEDPROXY);
#endif // _DEBUG

            m_blockingType = fCritically ? BlockingCritical : BlockingNormal;
            if (!fCritically)
                InterlockedExchangePointer((volatile PVOID*)&m_pRoot, (PVOID)NULL);
        }

        /// <summary>
        ///     Returns whether or not this thread is currently suspended.
        /// </summary>
        /// <returns>
        ///     Returns true if the thread is suspended
        /// </returns>
        bool IsSuspended();

        /// <summary>
        ///     Returns whether or not this thread is currently terminated.
        /// </summary>
        /// <returns>

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -