Exemplo n.º 1
0
//---------------------------------------------------------------------------------------
//
// Ensure the AppDomain friendly name has been set.
//
// Return value:
//    S_OK on success, or a failure code if we couldn't read the name for some reason.
//    There shouldn't be any reason in practice for this to fail other than a corrupt
//    process image.
//
// Assumptions:
//    The AppDomain object has already been initialized to know about
//    it's corresponding VM appdomain.
//    InvalidateName is called whenever the name may have changed to prompt us to re-fetch.
//
//---------------------------------------------------------------------------------------
HRESULT CordbAppDomain::RefreshName()
{
    if (m_strAppDomainName.IsSet())
    {
        // If we already have a valid name, we're done.
        return S_OK;
    }

    // Use DAC to get the name.
    
    _ASSERTE(!m_vmAppDomain.IsNull());
    IDacDbiInterface * pDac = NULL;
    HRESULT hr = S_OK;
    EX_TRY
    {
        pDac = m_pProcess->GetDAC();

    #ifdef _DEBUG
        // For debug, double-check the cached value against getting the AD via an AppDomainId.
        VMPTR_AppDomain pAppDomain = pDac->GetAppDomainFromId(m_AppDomainId);
        _ASSERTE(m_vmAppDomain == pAppDomain);
    #endif

        // Get the actual string contents.
        pDac->GetAppDomainFullName(m_vmAppDomain, &m_strAppDomainName);

        // Now that m_strAppDomainName is set, don't fail without clearing it.        
    }
    EX_CATCH_HRESULT(hr);

    _ASSERTE(SUCCEEDED(hr) == m_strAppDomainName.IsSet());
   
    return hr;
}
Exemplo n.º 2
0
/* static */
HRESULT CordbClass::GetStaticFieldValue2(CordbModule * pModule,
                                         FieldData * pFieldData,
                                         BOOL fEnCHangingField,
                                         const Instantiation * pInst,
                                         ICorDebugFrame * pFrame,
                                         ICorDebugValue ** ppValue)
{
    FAIL_IF_NEUTERED(pModule);
    INTERNAL_SYNC_API_ENTRY(pModule->GetProcess());
    _ASSERTE((pModule->GetProcess()->GetShim() == NULL) || pModule->GetProcess()->GetSynchronized());
    HRESULT hr = S_OK;

    if (!pFieldData->m_fFldIsStatic)
    {
        return CORDBG_E_FIELD_NOT_STATIC;
    }

    CORDB_ADDRESS pRmtStaticValue = NULL;
    CordbProcess * pProcess = pModule->GetProcess();

    if (pFieldData->m_fFldIsCollectibleStatic)
    {
        EX_TRY
        {
            pRmtStaticValue = pProcess->GetDAC()->GetCollectibleTypeStaticAddress(pFieldData->m_vmFieldDesc, 
                                                                                  pModule->GetAppDomain()->GetADToken());
        }
        EX_CATCH_HRESULT(hr);
        if(FAILED(hr)) 
        {
            return hr;
        }
    }
Exemplo n.º 3
0
HRESULT CordbAppDomain::EnumerateSteppers(ICorDebugStepperEnum **ppSteppers)
{
    PUBLIC_API_ENTRY(this);
    FAIL_IF_NEUTERED(this);
    ATT_REQUIRE_STOPPED_MAY_FAIL(GetProcess());
    VALIDATE_POINTER_TO_OBJECT(ppSteppers,ICorDebugStepperEnum **);

    HRESULT hr = S_OK;
    EX_TRY
    {
        //
        // !!! m_steppers may be modified while user is enumerating,
        // if steppers complete (if process is running)
        //

        RSInitHolder<CordbHashTableEnum> pEnum;
        CordbHashTableEnum::BuildOrThrow(
            GetProcess(), 
            GetProcess()->GetContinueNeuterList(),  // ownership
            &(m_pProcess->m_steppers),
            IID_ICorDebugStepperEnum,
            pEnum.GetAddr());

        pEnum.TransferOwnershipExternal(ppSteppers);
    }
    EX_CATCH_HRESULT(hr);
    return hr;
}
Exemplo n.º 4
0
// Implement public interface
HRESULT CordbAppDomain::GetModuleFromMetaDataInterface(
                                                  IUnknown *pIMetaData,
                                                  ICorDebugModule **ppModule)
{
    PUBLIC_API_ENTRY(this);
    FAIL_IF_NEUTERED(this);
    VALIDATE_POINTER_TO_OBJECT(pIMetaData, IUnknown *);
    VALIDATE_POINTER_TO_OBJECT(ppModule, ICorDebugModule **);

    

    HRESULT hr = S_OK;

    ATT_REQUIRE_STOPPED_MAY_FAIL(GetProcess());

    *ppModule = NULL;

    EX_TRY
    {
        CordbModule * pModule = GetModuleFromMetaDataInterface(pIMetaData);
        _ASSERTE(pModule != NULL); // thrown on error
        
        *ppModule = static_cast<ICorDebugModule*> (pModule);
        pModule->ExternalAddRef();        
    }
    EX_CATCH_HRESULT(hr);


    return hr;
}
Exemplo n.º 5
0
    template <class Type> List<Type>::~List()
    {
        HRESULT hr = S_OK;

        EX_TRY
        {
            RemoveAll();
        }
        EX_CATCH_HRESULT(hr);
    }
Exemplo n.º 6
0
STDAPI InternalDllGetClassObject(
    REFCLSID rclsid,
    REFIID riid,
    LPVOID FAR *ppv)
{
    // @todo: this is called before the runtime is really started, so the contract's don't work.
    STATIC_CONTRACT_NOTHROW;
    STATIC_CONTRACT_SO_TOLERANT;

    HRESULT hr = CLASS_E_CLASSNOTAVAILABLE;
    BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(return COR_E_STACKOVERFLOW);


    if (rclsid == CLSID_CorMetaDataDispenser || rclsid == CLSID_CorMetaDataDispenserRuntime ||
        rclsid == CLSID_CorRuntimeHost || rclsid == CLSID_CLRRuntimeHost ||
        rclsid == CLSID_TypeNameFactory
#ifdef FEATURE_HOSTED_BINDER
        || rclsid == __uuidof(CLRPrivRuntime)
#endif
       )
    {
        hr = MetaDataDllGetClassObject(rclsid, riid, ppv);
    }
#ifdef FEATURE_PROFAPI_ATTACH_DETACH
    else if (rclsid == CLSID_CLRProfiling)
    {
        hr = ICLRProfilingGetClassObject(rclsid, riid, ppv);
    }
#endif // FEATURE_PROFAPI_ATTACH_DETACH
#ifdef FEATURE_COMINTEROP
    else if (rclsid == CLSID_ComCallUnmarshal || rclsid == CLSID_ComCallUnmarshalV4)
    {
        // We still respond to the 1.0/1.1/2.0 CLSID so we don't break anyone who is instantiating
        // this (we could be called for CLSID_ComCallUnmarshal if the process is rollForward=true)
        hr = g_COMCallUnmarshal.QueryInterface(riid, ppv);
    }
    else if (rclsid == CLSID_CorSymBinder_SxS)
    {
        EX_TRY
        {

            // PDB format - use diasymreader.dll with COM activation
            InlineSString<_MAX_PATH> ssBuf;
            if (SUCCEEDED(GetHModuleDirectory(GetModuleInst(), ssBuf)))
            {
                hr = FakeCoCallDllGetClassObject(rclsid,
                    ssBuf,
                    riid,
                    ppv,
                    NULL
                    );
            }
        }
        EX_CATCH_HRESULT(hr);
    }
Exemplo n.º 7
0
// Block and wait for the next debug event from the debuggee process.
BOOL DbgTransportPipeline::WaitForDebugEvent(DEBUG_EVENT * pEvent, DWORD dwTimeout, CordbProcess * pProcess)
{
    if (!IsTransportRunning())
    {
        return FALSE;
    }

    // We need to wait for a debug event from the transport and the process termination event.
    // On Windows, process termination is communicated via a debug event as well, but that's not true for
    // the Mac debugging transport.
    DWORD cWaitSet = 2;
    HANDLE rghWaitSet[2];
    rghWaitSet[0] = m_pTransport->GetDebugEventReadyEvent();
    rghWaitSet[1] = m_hProcess;

    DWORD dwRet = ::WaitForMultipleObjectsEx(cWaitSet, rghWaitSet, FALSE, dwTimeout, FALSE);

    if (dwRet == WAIT_OBJECT_0)
    {
        // The Mac debugging transport actually transmits IPC events and not debug events.
        // We need to convert the IPC event to a debug event and pass it back to the caller.
        m_pTransport->GetNextEvent(m_pIPCEvent, CorDBIPC_BUFFER_SIZE);

        pEvent->dwProcessId = m_pIPCEvent->processId;
        _ASSERTE(m_dwProcessId == m_pIPCEvent->processId);

        // We are supposed to return a thread ID in the DEBUG_EVENT back to our caller.  
        // However, we don't actually store the thread ID in the DebuggerIPCEvent anymore.  Instead, 
        // we just get a VMPTR_Thread, and so we need to find the thread ID associated with the VMPTR_Thread.
        pEvent->dwThreadId = 0;
        HRESULT hr = S_OK;
        EX_TRY
        {
            if (!m_pIPCEvent->vmThread.IsNull())
            {
                pEvent->dwThreadId = pProcess->GetDAC()->TryGetVolatileOSThreadID(m_pIPCEvent->vmThread);
            }
        }
        EX_CATCH_HRESULT(hr);
        if (FAILED(hr))
        {
            return FALSE;
        }

        // The Windows implementation stores the target address of the IPC event in the debug event.
        // We can do that for Mac debugging, but that would require the caller to do another cross-machine
        // ReadProcessMemory().  Since we have all the data in-proc already, we just store a local address.
        // 
        // @dbgtodo  Mac - We are using -1 as a dummy base address right now.  
        // Currently Mac remote debugging doesn't really support multi-instance.
        InitEventForDebuggerNotification(pEvent, PTR_TO_CORDB_ADDRESS(reinterpret_cast<LPVOID>(-1)), m_pIPCEvent);

        return TRUE;
    }
Exemplo n.º 8
0
DWORD 
GetFileVersionInfoSizeW_NoThrow(
        LPCWSTR lptstrFilename, /* Filename of version stamped file */
        LPDWORD lpdwHandle
        )
{
    WRAPPER_NO_CONTRACT;
    HRESULT hr=S_OK;
    DWORD dwRet=0;
    EX_TRY
    {
        dwRet=GetFileVersionInfoSize( (LPWSTR)lptstrFilename,  lpdwHandle );  
    }
    EX_CATCH_HRESULT(hr);
    if (hr!=S_OK)
        SetLastError(hr);
    return dwRet;
    
}
Exemplo n.º 9
0
BOOL
VerQueryValueW_NoThrow(
        const LPVOID pBlock,
        LPCWSTR lpSubBlock,
        LPVOID * lplpBuffer,
        PUINT puLen
        )     
{
    WRAPPER_NO_CONTRACT;
    HRESULT hr=S_OK;
    BOOL bRet=FALSE;
    EX_TRY
    {
        bRet=VerQueryValueW( pBlock, (LPWSTR)lpSubBlock,lplpBuffer,puLen );
    }
    EX_CATCH_HRESULT(hr);
    if (hr!=S_OK)
        SetLastError(hr);
    return bRet;
    
}
Exemplo n.º 10
0
BOOL
GetFileVersionInfoW_NoThrow(
        LPCWSTR lptstrFilename, /* Filename of version stamped file */
        DWORD dwHandle,         /* Information from GetFileVersionSize */
        DWORD dwLen,            /* Length of buffer for info */
        LPVOID lpData
        )         
{
    WRAPPER_NO_CONTRACT;
    HRESULT hr=S_OK;
    BOOL bRet=FALSE;
    EX_TRY
    {
        bRet=GetFileVersionInfo( (LPWSTR)lptstrFilename, dwHandle,dwLen,lpData );  
    }
    EX_CATCH_HRESULT(hr);
    if (hr!=S_OK)
        SetLastError(hr);
    return bRet;
    
}
Exemplo n.º 11
0
HRESULT CordbAppDomain::EnumerateBreakpoints(ICorDebugBreakpointEnum **ppBreakpoints)
{
    PUBLIC_API_ENTRY(this);
    FAIL_IF_NEUTERED(this);
    ATT_REQUIRE_STOPPED_MAY_FAIL(GetProcess());
    VALIDATE_POINTER_TO_OBJECT(ppBreakpoints, ICorDebugBreakpointEnum **);

    HRESULT hr = S_OK;
    EX_TRY
    {
        RSInitHolder<CordbHashTableEnum> pEnum;
        CordbHashTableEnum::BuildOrThrow(
            this, 
            GetProcess()->GetContinueNeuterList(), // ownership
            &m_breakpoints,
            IID_ICorDebugBreakpointEnum,
            pEnum.GetAddr());

        pEnum.TransferOwnershipExternal(ppBreakpoints);
    }
    EX_CATCH_HRESULT(hr);
    return hr;
}
Exemplo n.º 12
0
LPSTR FillSymbolSearchPath(CQuickBytes &qb)
{
    STATIC_CONTRACT_NOTHROW;
    STATIC_CONTRACT_GC_NOTRIGGER;
    STATIC_CONTRACT_CANNOT_TAKE_LOCK;
    SCAN_IGNORE_FAULT; // Faults from Wsz funcs are handled.
    LPSTR retval;
    HRESULT hr = S_OK;

    EX_TRY
    {
        retval = FillSymbolSearchPathThrows(qb);
    }
    EX_CATCH_HRESULT(hr);

    if (hr != S_OK)
    {
        SetLastError(hr);
        retval = NULL;
    }

    return retval;
}
Exemplo n.º 13
0
//-----------------------------------------------------------------------------
// Get a ICorDebugValue for a static field on this class.
//
// Parameters:
//   fieldDef - metadata token for field on this class. Can not be from an 
//      inherited class.
//   pFrame - frame used to resolve Thread-static, AppDomain-static, etc.
//   ppValue - OUT: gets value of the field.
//
// Returns:
//    S_OK on success.
//    CORDBG_E_STATIC_VAR_NOT_AVAILABLE 
//-----------------------------------------------------------------------------
HRESULT CordbClass::GetStaticFieldValue(mdFieldDef fieldDef,
                                        ICorDebugFrame *pFrame,
                                        ICorDebugValue **ppValue)
{
    PUBLIC_REENTRANT_API_ENTRY(this);
    FAIL_IF_NEUTERED(this);
    VALIDATE_POINTER_TO_OBJECT(ppValue, ICorDebugValue **);
    ATT_REQUIRE_STOPPED_MAY_FAIL(GetProcess());

    HRESULT          hr = S_OK;
    *ppValue = NULL;
    BOOL             fEnCHangingField = FALSE;


    IMetaDataImport * pImport = NULL;
    EX_TRY
    {
        pImport = GetModule()->GetMetaDataImporter(); // throws

        // Validate the token.
        if (!pImport->IsValidToken(fieldDef) || (TypeFromToken(fieldDef) != mdtFieldDef))
        {
            ThrowHR(E_INVALIDARG);
        }

        // Make sure we have enough info about the class.
        Init();

        // Uninstantiated generics (eg, Foo<T>) don't have static data. Must use instantiated (eg Foo<int>)
        // But all CordbClass instances are uninstantiated. So this should fail for all generic types.
        // Normally, debuggers should be using ICorDebugType instead.
        // Though in the forward compat case, they'll hit this.
        if (HasTypeParams())
        {
            ThrowHR(CORDBG_E_STATIC_VAR_NOT_AVAILABLE);
        }


        // Lookup the field given its metadata token.
        FieldData *pFieldData;

        hr = GetFieldInfo(fieldDef, &pFieldData);

        // This field was added by EnC, need to use EnC specific code path
        if (hr == CORDBG_E_ENC_HANGING_FIELD)
        {
            // Static fields added with EnC hang off the EnCFieldDesc
            hr = GetEnCHangingField(fieldDef,
                &pFieldData,
                NULL);

            if (SUCCEEDED(hr))
            {
                fEnCHangingField = TRUE;
            }
            // Note: the FieldOffset in pFieldData has been cooked to produce
            // the correct address of the field in the syncBlock.
            // @todo: extend Debugger_IPCEFieldData so we don't have to cook the offset here
        }

        IfFailThrow(hr);

        {
            Instantiation emptyInst;

            hr = CordbClass::GetStaticFieldValue2(GetModule(),
                pFieldData,
                fEnCHangingField,
                &emptyInst,
                pFrame,
                ppValue);
            // Let hr fall through
        }
    }
    EX_CATCH_HRESULT(hr);

    // Translate Failure HRs.
    if (pImport != NULL)
    {
        hr = CordbClass::PostProcessUnavailableHRESULT(hr, pImport, fieldDef);
    }

    return hr;

}