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

📄 mstartup.cpp

📁 C语言库函数的原型,有用的拿去
💻 CPP
📖 第 1 页 / 共 2 页
字号:
            DefaultDomain::InitializedNativeFromCCTOR = true;
            CurrentDomain::InitializedNative = Progress::Finished;
        }
    }

    // Initializes per-process managed globals
    [System::Diagnostics::DebuggerStepThroughAttribute]
    SECURITYCRITICAL_ATTRIBUTE
    inline void InitializePerProcess()
    {
        MANAGED_ASSERT(CurrentDomain::IsDefaultDomain, "Per-process globals must be initialized in the default domain");

        ErrorMessage = L"The C++ module failed to load during process initialization.\n";

        CurrentDomain::InitializedPerProcess = Progress::Started;

        _initatexit_m();

        _initterm_m((const _PVFVM *) __xc_mp_a, (const _PVFVM *)__xc_mp_z );

        CurrentDomain::InitializedPerProcess = Progress::Finished;

        DefaultDomain::InitializedPerProcess = true;
    }

#endif  /* defined (_M_CEE_MIXED) */

    // Initializes per-appdomain managed globals
    [System::Diagnostics::DebuggerStepThroughAttribute]
    SECURITYCRITICAL_ATTRIBUTE
    inline void InitializePerAppDomain()
    {
        ErrorMessage = L"The C++ module failed to load during appdomain initialization.\n";

        CurrentDomain::InitializedPerAppDomain = Progress::Started;

        _initatexit_app_domain();

        _initterm_m( __xc_ma_a, __xc_ma_z );

        CurrentDomain::InitializedPerAppDomain = Progress::Finished;
    }

    // Registers for appdomain unload event
    [System::Diagnostics::DebuggerStepThroughAttribute]
    SECURITYCRITICAL_ATTRIBUTE
    inline void InitializeUninitializer()
    {
        ErrorMessage = L"The C++ module failed to load during registration for the unload events.\n";
        EventHandler^ handler = gcnew EventHandler(&DomainUnload);
        RegisterModuleUninitializer(handler);
    }

    // Initializes vtables and globals required for C++ language
    [System::Diagnostics::DebuggerStepThroughAttribute]
    [System::Runtime::ConstrainedExecution::ReliabilityContract(
        System::Runtime::ConstrainedExecution::Consistency::WillNotCorruptState,
        System::Runtime::ConstrainedExecution::Cer::Success)]
    SECURITYCRITICAL_ATTRIBUTE
    inline void _Initialize()
    {
        CurrentDomain::IsDefaultDomain = AppDomain::CurrentDomain->IsDefaultAppDomain();
#if defined (_M_CEE_MIXED)
        if (CurrentDomain::IsDefaultDomain)
        {
            DefaultDomain::Entered = true;
        }
#endif  /* defined (_M_CEE_MIXED) */

#if defined (_M_CEE_MIXED)
        void *lock_free=0;
        void *fiberid=_getFiberPtrId();
        int nested=false;
        int done=false;
        int doInitializeDefaultAppDomain=false;
        System::Runtime::CompilerServices::RuntimeHelpers::PrepareConstrainedRegions();
        // this make sure that __native_startup_lock is released no matter what, in line with the
        // ReliabilityContract asserted above
        try
        {
            while (!done)
            {
                try { }
                finally
                {
#if defined (_WIN64)
                    lock_free = (void*)Interlocked::CompareExchange((System::Int64&)__native_startup_lock, (System::Int64)fiberid, (System::Int64)0);
#else  /* defined (_WIN64) */
                    lock_free = (void*)Interlocked::CompareExchange((System::IntPtr&)__native_startup_lock, (System::IntPtr)fiberid, (System::IntPtr)0);
#endif  /* defined (_WIN64) */
                    if (lock_free == 0)
                    {
                        done = true;
                    }
                    else if(lock_free == fiberid)
                    {
                        nested = true;
                        done = true;
                    }
                }
                if (!done)
                {
                    // Some other thread is running native startup/shutdown during a cctor/domain unload.
                    // Should only happen if this DLL was built using the Everett-compat loader lock fix in vcclrit.h.
                    // Wait for the other thread to complete init before we return
                    Sleep(1000);
                }
            }

            InitializeVtables();

            if (CurrentDomain::IsDefaultDomain)
            {
                    InitializeNative();
                    InitializePerProcess();
            }
            else if(DefaultDomain::NeedsInitialization())
            {
                // Do not InitializeDefaultAppDomain() when holding __native_startup_lock.
                // Essentially InitializeDefaulAppDomain() is a callback to the
                // default appdomain.  If we do the call back while holding the lock, it can
                // result in a deadlock.
                //
                // For example:
                // 1. thread1: .cctor() of a non-default appdomain calls _Initialize() and
                //    grabs the _native_startup_lock
                // 2. thread2: .cctor() of default appdomain starts to execute and tries to grab the
                //             __native_startup_lock, but fails.  Hence, busy waiting for lock.
                // 3. thread1: (still holding the lock) and do a callback to default appdomain.
                //             The CLR detects that .cctor of default appdomain has started, but
                //             not finish.  Hence block until .cctor of default app domain finishes.
                // 4. deadlock.
                doInitializeDefaultAppDomain = true;
            }
        }
        finally
        {
            if(!nested)
            {
#if defined (_WIN64)
                Interlocked::Exchange((System::Int64&)__native_startup_lock, (System::Int64)0);
#else  /* defined (_WIN64) */
                Interlocked::Exchange((System::IntPtr&)__native_startup_lock, (System::IntPtr)0);
#endif  /* defined (_WIN64) */
            }
        }

        /*
         * Note: Since this out of the lock, it is possible that we are
         * doing extra calls to InitializeDefaultAppDomain().
         * Since InitializeDefaultAppDomain()is just a dummy callback to force the
         * .cctor() of the default appdomain to run, it is save to call
         * InitalizeDefaultAppDomain() more than once
         * (although we will suffer a domain transition performance penalty.)
         */
        if (doInitializeDefaultAppDomain)
        {
            InitializeDefaultAppDomain();
        }
#else  /* defined (_M_CEE_MIXED) */
        InitializeVtables();

#endif  /* defined (_M_CEE_MIXED) */

        InitializePerAppDomain();

        CurrentDomain::Initialized = 1;

        InitializeUninitializer();
    }

    // Uninitializes per-appdomain managed globals
    SECURITYCRITICAL_ATTRIBUTE
    inline static void UninitializeAppDomain()
    {
        _app_exit_callback();
    }

#if defined (_M_CEE_MIXED)
    //static void __cdecl _UninitializeDefaultDomain()
    SECURITYCRITICAL_ATTRIBUTE
    static HRESULT __stdcall _UninitializeDefaultDomain(void* cookie)
    {
        cookie;
        MANAGED_ASSERT(AppDomain::CurrentDomain->IsDefaultAppDomain(), "This function must be called in the default domain");

        // Uninitialize per-process
        _exit_callback();

        DefaultDomain::InitializedPerProcess = false;

        if(DefaultDomain::InitializedNativeFromCCTOR)
        {
            // Uninitialize native
            _cexit();
            __native_startup_state = __uninitialized;

            DefaultDomain::InitializedNativeFromCCTOR = false;
        }

        DefaultDomain::InitializedNative = false;

        return S_OK;
    }

    SECURITYCRITICAL_ATTRIBUTE
    static void UninitializeDefaultDomain()
    {
        if (DefaultDomain::NeedsUninitialization())
        {
            if (AppDomain::CurrentDomain->IsDefaultAppDomain())
            {
                _UninitializeDefaultDomain(nullptr);
            }
            else
            {
                DoCallBackInDefaultDomain(&_UninitializeDefaultDomain, nullptr);
            }
        }
    }
#endif  /* defined (_M_CEE_MIXED) */

    // Called when the domain unloads
    // Compare with code in Cleanup
    [System::Runtime::ConstrainedExecution::PrePrepareMethod]
    [System::Runtime::ConstrainedExecution::ReliabilityContract(
        System::Runtime::ConstrainedExecution::Consistency::WillNotCorruptState,
        System::Runtime::ConstrainedExecution::Cer::Success)]
    SECURITYCRITICAL_ATTRIBUTE
    static void DomainUnload(Object^ source, EventArgs^ arguments)
    {
        if (CurrentDomain::Initialized && !Interlocked::Exchange(CurrentDomain::Uninitialized, (int)1))
        {
#if defined (_M_CEE_MIXED)
            bool lastDomain = (Interlocked::Decrement(AllDomains::Count) == 0);
#endif  /* defined (_M_CEE_MIXED) */

            UninitializeAppDomain();

#if defined (_M_CEE_MIXED)
            if (lastDomain)
            {
                UninitializeDefaultDomain();
            }
#endif  /* defined (_M_CEE_MIXED) */
        }
    }

    // Cleans up initialization in the event of an error
    // Compare with code in DomainUnload
    [System::Diagnostics::DebuggerStepThroughAttribute]
    [System::Runtime::ConstrainedExecution::ReliabilityContract(
        System::Runtime::ConstrainedExecution::Consistency::WillNotCorruptState,
        System::Runtime::ConstrainedExecution::Cer::Success)]
    SECURITYCRITICAL_ATTRIBUTE
    void Cleanup(System::Exception^ innerException)
    {
        try
        {
#if defined (_M_CEE_MIXED)
            // If we end up here, DomainUnload will not be called
            bool lastDomain = (Interlocked::Decrement(AllDomains::Count) == 0);
#endif  /* defined (_M_CEE_MIXED) */

            /*
             * Even though the current AppDomain might not be fully initialized,
             * we still want to call whatever that got registered in the on exit
             * list.
             */
            UninitializeAppDomain();

#if defined (_M_CEE_MIXED)
            if (lastDomain)
            {
                UninitializeDefaultDomain();
            }
#endif  /* defined (_M_CEE_MIXED) */
        }
        catch (System::Exception^ exception)
        {
            ThrowNestedModuleLoadException(innerException, exception);
        }
        catch (System::Object^ exception)
        {
            exception;
            ThrowNestedModuleLoadException(innerException, nullptr);
        }
    }

public:
    SECURITYCRITICAL_ATTRIBUTE
    LanguageSupport(){}
    SECURITYCRITICAL_ATTRIBUTE
    ~LanguageSupport(){}

    [System::Diagnostics::DebuggerStepThroughAttribute]
    [System::Runtime::ConstrainedExecution::ReliabilityContract(
        System::Runtime::ConstrainedExecution::Consistency::WillNotCorruptState,
        System::Runtime::ConstrainedExecution::Cer::Success)]
    SECURITYCRITICAL_ATTRIBUTE
    void Initialize()
    {
#if defined (_M_CEE_MIXED)
        bool allDomainsCountIncremented = false;

        // this make sure that AllDomains::Count reflects the actual count no matter what,
        // in line with the ReliabilityContract asserted above
        System::Runtime::CompilerServices::RuntimeHelpers::PrepareConstrainedRegions();
#endif  /* defined (_M_CEE_MIXED) */
        try
        {
            ErrorMessage = L"The C++ module failed to load.\n";
#if defined (_M_CEE_MIXED)
            System::Runtime::CompilerServices::RuntimeHelpers::PrepareConstrainedRegions();
            try { } finally
            {
                Interlocked::Increment(AllDomains::Count);
                allDomainsCountIncremented = true;
            }
#endif  /* defined (_M_CEE_MIXED) */
            _Initialize();
        }
        catch (System::Exception^ exception)
        {
#if defined (_M_CEE_MIXED)
            if (allDomainsCountIncremented)
#endif  /* defined (_M_CEE_MIXED) */
            {
                Cleanup(exception);
            }
            ThrowModuleLoadException(ErrorMessage, exception);
        }
        catch (System::Object^ exception)
        {
            exception;
#if defined (_M_CEE_MIXED)
            if (allDomainsCountIncremented)
#endif  /* defined (_M_CEE_MIXED) */
            {
                Cleanup(nullptr);
            }
            ThrowModuleLoadException(ErrorMessage, nullptr);
        }
    }

};

// we do lots of nasty things for /clr & /clr:pure - consuming code should
// automatically be marked for compatibility with the security model enforced in CLR v4+
[ assembly: System::Security::SecurityRules( System::Security::SecurityRuleSet::Level1 ) ];

} // namespace __identifier("<CrtImplementationDetails>")

/***
* .cctor - This is global constructor for user module.
*
* Purpose:
*       This function is called during appdomain creation. Here is we
*       initialize all the vtables, and native/process/appdomain variables.
*
* Exit:
*
* Entry:
*
*******************************************************************************/
[System::Diagnostics::DebuggerStepThroughAttribute]
SECURITYCRITICAL_ATTRIBUTE
void __clrcall __identifier(".cctor")()
{
    using namespace __identifier("<CrtImplementationDetails>");

    LanguageSupport languageSupport;
    languageSupport.Initialize();
}

⌨️ 快捷键说明

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