Exemple #1
0
// RegRegValueHome::GetEnregisteredValue
// Gets an enregistered value and returns it to the caller (see EnregisteredValueHome::GetEnregisteredValue
// for full header comment)
void RegRegValueHome::GetEnregisteredValue(MemoryRange valueOutBuffer)
{
    UINT_PTR* highWordAddr = m_pFrame->GetAddressOfRegister(m_reg1Info.m_kRegNumber);
    PREFIX_ASSUME(highWordAddr != NULL);

    UINT_PTR* lowWordAddr = m_pFrame->GetAddressOfRegister(m_reg2Info.m_kRegNumber);
    PREFIX_ASSUME(lowWordAddr != NULL);

    _ASSERTE(sizeof(*highWordAddr) + sizeof(*lowWordAddr) == valueOutBuffer.Size());

    memcpy(valueOutBuffer.StartAddress(), lowWordAddr, sizeof(*lowWordAddr));
    memcpy((BYTE *)valueOutBuffer.StartAddress() + sizeof(*lowWordAddr), highWordAddr, sizeof(*highWordAddr));

} // RegRegValueHome::GetEnregisteredValue
Exemple #2
0
// RegValueHome::GetEnregisteredValue
// Gets an enregistered value and returns it to the caller (see EnregisteredValueHome::GetEnregisteredValue
// for full header comment)
void RegValueHome::GetEnregisteredValue(MemoryRange valueOutBuffer)
{
    UINT_PTR* reg = m_pFrame->GetAddressOfRegister(m_reg1Info.m_kRegNumber);
    PREFIX_ASSUME(reg != NULL);
    _ASSERTE(sizeof(*reg) == valueOutBuffer.Size());

    memcpy(valueOutBuffer.StartAddress(), reg, sizeof(*reg));
} // RegValueHome::GetEnregisteredValue
Exemple #3
0
// RegRegValueHome::SetEnregisteredValue
// set a remote enregistered location to a new value (see EnregisteredValueHome::SetEnregisteredValue
// for full header comment)
void RegRegValueHome::SetEnregisteredValue(MemoryRange newValue, DT_CONTEXT * pContext, bool fIsSigned)
{
    _ASSERTE(newValue.Size() == 8);
    _ASSERTE(REG_SIZE == sizeof(void*));

    // Split the new value into high and low parts.
    SIZE_T highPart;
    SIZE_T lowPart;

    memcpy(&lowPart, newValue.StartAddress(), REG_SIZE);
    memcpy(&highPart, (BYTE *)newValue.StartAddress() + REG_SIZE, REG_SIZE);

    // Update the proper registers.
    SetContextRegister(pContext, m_reg1Info.m_kRegNumber, highPart); // throws
    SetContextRegister(pContext, m_reg2Info.m_kRegNumber, lowPart); // throws

    // update the frame's register display
    void * valueAddress = (void *)(m_pFrame->GetAddressOfRegister(m_reg1Info.m_kRegNumber));
    memcpy(valueAddress, newValue.StartAddress(), newValue.Size());
} // RegRegValueHome::SetEnregisteredValue
Exemple #4
0
// RegValueHome::SetEnregisteredValue
// set a remote enregistered location to a new value (see code:EnregisteredValueHome::SetEnregisteredValue
// for full header comment)
void RegValueHome::SetEnregisteredValue(MemoryRange newValue, DT_CONTEXT * pContext, bool fIsSigned)
{
    SIZE_T extendedVal = 0;

    // If the value is in a reg, then it's going to be a register's width (regardless of
    // the actual width of the data).
    // For signed types, like i2, i1, make sure we sign extend.

    if (fIsSigned)
    {
        // Sign extend. SSIZE_T is a register size signed value.
        // Casting
        switch(newValue.Size())
        {
            case 1:  _ASSERTE(sizeof( BYTE) == 1); 
                     extendedVal = (SSIZE_T) *(char*)newValue.StartAddress();           break;
            case 2:  _ASSERTE(sizeof( WORD) == 2); 
                     extendedVal = (SSIZE_T) *(short*)newValue.StartAddress();          break;
            case 4:  _ASSERTE(sizeof(DWORD) == 4); 
                     extendedVal = (SSIZE_T) *(int*)newValue.StartAddress();            break;
#if defined(DBG_TARGET_WIN64)
            case 8:  _ASSERTE(sizeof(ULONGLONG) == 8); 
                     extendedVal = (SSIZE_T) *(ULONGLONG*)newValue.StartAddress();      break;
#endif // DBG_TARGET_WIN64
            default: _ASSERTE(!"bad size");
        }
    }
    else
    {
        // Zero extend.
        switch(newValue.Size())
        {
            case 1:  _ASSERTE(sizeof( BYTE) == 1); 
                     extendedVal = *( BYTE*)newValue.StartAddress();     break;
            case 2:  _ASSERTE(sizeof( WORD) == 2);
                     extendedVal = *( WORD*)newValue.StartAddress();     break;
            case 4:  _ASSERTE(sizeof(DWORD) == 4);
                     extendedVal = *(DWORD*)newValue.StartAddress();     break;
#if defined(DBG_TARGET_WIN64)
            case 8:  _ASSERTE(sizeof(ULONGLONG) == 8); 
                     extendedVal = *(ULONGLONG*)newValue.StartAddress(); break;
#endif // DBG_TARGET_WIN64
            default: _ASSERTE(!"bad size");
        }
    }

    SetContextRegister(pContext, m_reg1Info.m_kRegNumber, extendedVal); // throws
} // RegValueHome::SetEnregisteredValue
Exemple #5
0
HRESULT DacReplacePatchesInHostMemory(MemoryRange range, PVOID pBuffer)
{
    SUPPORTS_DAC;

    // If the patch table is invalid, then there is no patch to replace.
    if (!DebuggerController::GetPatchTableValid())
    {
        return S_OK;
    }

    HASHFIND info;

    DebuggerPatchTable *      pTable = DebuggerController::GetPatchTable();
    DebuggerControllerPatch * pPatch = pTable->GetFirstPatch(&info);

    // <PERF>
    // The unwinder needs to read the stack very often to restore pushed registers, retrieve the 
    // return addres, etc.  However, stack addresses should never be patched.
    // One way to optimize this code is to pass the stack base and the stack limit of the thread to this 
    // function and use those two values to filter out stack addresses.
    //
    // Another thing we can do is instead of enumerating the patches, we could enumerate the address.
    // This is more efficient when we have a large number of patches and a small memory range.  Perhaps
    // we could do a hybrid approach, i.e. use the size of the range and the number of patches to dynamically
    // determine which enumeration is more efficient.
    // </PERF>
    while (pPatch != NULL)
    {
        CORDB_ADDRESS patchAddress = (CORDB_ADDRESS)dac_cast<TADDR>(pPatch->address);

        if (patchAddress != NULL)
        {
            PRD_TYPE opcode = pPatch->opcode;

            CORDB_ADDRESS address = (CORDB_ADDRESS)(dac_cast<TADDR>(range.StartAddress()));
            SIZE_T        cbSize  = range.Size();

            // Check if the address of the patch is in the specified memory range.
            if (IsPatchInRequestedRange(address, cbSize, patchAddress))
            {
                // Replace the patch in the buffer with the original opcode.
                CORDbgSetInstructionEx(reinterpret_cast<PBYTE>(pBuffer), address, patchAddress, opcode, cbSize);
            }
        }

        pPatch = pTable->GetNextPatch(&info);
    }

    return S_OK;
}
Exemple #6
0
    pRegAddr->addr = m_memAddr;
} // RegMemValueHome::CopyToIPCEType

// RegMemValueHome::SetEnregisteredValue
// set a remote enregistered location to a new value (see EnregisteredValueHome::SetEnregisteredValue
// for full header comment)
void RegMemValueHome::SetEnregisteredValue(MemoryRange newValue, DT_CONTEXT * pContext, bool fIsSigned)
{
    _ASSERTE(newValue.Size() == REG_SIZE >> 1); // make sure we have bytes for two registers
    _ASSERTE(REG_SIZE == sizeof(void*));

    // Split the new value into high and low parts.
    SIZE_T highPart;
    SIZE_T lowPart;

    memcpy(&lowPart, newValue.StartAddress(), REG_SIZE);
    memcpy(&highPart, (BYTE *)newValue.StartAddress() + REG_SIZE, REG_SIZE);

    // Update the proper registers.
    SetContextRegister(pContext, m_reg1Info.m_kRegNumber, highPart); // throws

    _ASSERTE(REG_SIZE == sizeof(lowPart));
    HRESULT hr = m_pFrame->GetProcess()->SafeReadStruct(m_memAddr, &lowPart);
    IfFailThrow(hr);
    
} // RegMemValueHome::SetEnregisteredValue

// RegMemValueHome::GetEnregisteredValue
// Gets an enregistered value and returns it to the caller (see EnregisteredValueHome::GetEnregisteredValue
// for full header comment)
void RegMemValueHome::GetEnregisteredValue(MemoryRange valueOutBuffer)