Хранение шестнадцатеричных адресов, недоразумение DWORD_PTR - PullRequest
0 голосов
/ 26 января 2019

Я пишу программу для записи значения в многоуровневый указатель, найденный с определенными смещениями.Функция, которую я покажу, должна вернуть правильный адрес.Предположим, у меня есть все типы данных переменных вне функции соответствия.

DWORD FindDmaAddy(int PointerLevel, HANDLE HProcHandle, DWORD Offsets[], DWORD BaseAddress) 
{
    DWORD Pointer = BaseAddress;
    DWORD pTemp = NULL;
    DWORD PointerAddR;
    for (int i = 0; i < PointerLevel; i++) {
        if (i == 0) {
            ReadProcessMemory(HProcHandle, (LPCVOID)Pointer, &pTemp, sizeof(pTemp), NULL); 
            std::cout << pTemp<<std::endl;
        }
        std::cout << "pTemp = " << pTemp << std::endl;
        PointerAddR = pTemp + Offsets[i];
        std::cout << "PointerAddR = " <<PointerAddR << std::endl;
        std::cout << "i = " << i<<std::endl;

        ReadProcessMemory(HProcHandle, (LPCVOID)PointerAddR, &pTemp, sizeof(pTemp), NULL); 
    }
    return PointerAddR;

Этот код работал нормально, когда была вызвана функция, и правильный адрес изменил значение (в другом месте есть функция записи), только он заранее выдал два одинаковых предупреждения.

Warning C4312   'type cast': conversion from 'DWORD' to 'LPCVOID' of greater size   

Я полагал, что это было бы исправлено, если бы я изменил соответствующие переменные на DWORD_PTR, поэтому я изменил его на это.

DWORD_PTR FindDmaAddy(int PointerLevel, HANDLE HProcHandle, DWORD_PTR Offsets[], DWORD_PTR BaseAddress) 
{
    DWORD_PTR Pointer = BaseAddress;
    DWORD_PTR pTemp = NULL;
    DWORD_PTR PointerAddR;
    for (int i = 0; i < PointerLevel; i++) {
        if (i == 0) {
            ReadProcessMemory(HProcHandle, (LPCVOID)Pointer, &pTemp, sizeof(pTemp), NULL); 
        }
        std::cout << "pTemp = " << pTemp << std::endl;
        PointerAddR = pTemp + Offsets[i];
        std::cout << "PointerAddR = " <<PointerAddR << std::endl;
        std::cout << "i = " << i<<std::endl;

        ReadProcessMemory(HProcHandle, (LPCVOID)PointerAddR, &pTemp, sizeof(pTemp), NULL); 
    }
return PointerAddR;

Но когда я использую этот код, он не работает.Я проверил вывод оригинала и измененного, и он идет от этого:

pTemp = 44803720
PointerAddR = 44804620
i = 0
pTemp = 44767240
PointerAddR = 44767260
i = 1
pTemp = 44804056
PointerAddR = 44804056
i = 2

К этому:

44803720
pTemp = 44803720
PointerAddR = 44804620
i = 0
pTemp = 34605865808631816
PointerAddR = 34605865808631836
i = 1
pTemp = 34605865808631816
PointerAddR = 34605865808631816
i = 2

Что дает?ReadProcessMemory отлично работает при первом запуске, а при втором запуске сохраняет адрес в этой странной форме.Но он читает те же самые типы данных и вызывается точно так же.

1 Ответ

0 голосов
/ 28 января 2019

В 32/64-битных программах, sizeof(DWORD) = 4; В 32-битных sizeof(DWORD_PTR) = 4, но в 64-битных, значение равно 8;первое значение, считываемое из pTemp в памяти (8 байт), равно 88A6AB0200000000, поэтому в соответствии с правилами порядка байтов значение равно 0x0000000002ABA688 (44803720), а второе значение в 8 байтов равно 0818AB02DAF17A, значение =34605865808631816, если вы читаете только предыдущие 4 байта, это будет 44767240, что является тем же результатом, что и ваш 32-битный результат.64-битный процесс не изменит память указателя на 32-битный в другом процессе.Таким образом, вы должны прочитать память процесса как бит целевого процесса здесь.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...