[toc]

使用c语言在windows中读取程序的数据

1. C语言通过指针来获取地址的数据

  1. 完整代码:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
//Message.c
#include <stdio.h>

int main(int argc, char** argv)
{
int i = 666;
printf("var i vulue is %d\n", i);
printf("var i address is 0x%p\n", &i);
int *p = &i;
printf("var i vulue is %d\n", *p);
printf("var i address is 0x%p\n", p);
printf("point p address is 0x%p\n", &p);
getchar();
return 0;
}
  1. 为了方便测试,在项目中关闭随机地址

    2RandmBaseAddress

  2. 运行结果:

2_C+WindowsReault1

2. Windows程序中通过ReadProcessMemory读取地址的数据

  1. 保持Message程序运行

  2. 写一个C语言程序来读取Message程序中变量 i的值,完整代码如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
//main.c
#include <windows.h>
#include <stdio.h>


int main(int argc, char* argv[])
{
DWORD dwProcessId=19732;
HANDLE hProcess=OpenProcess(PROCESS_ALL_ACCESS, FALSE, dwProcessId);
DWORD lpBaseAddr = 0x0019FEDC;//0x0019FEDC is address
DWORD* buffer= malloc(4);//recive readed data
SIZE_T nSize= 4;//read 4 bytes data
SIZE_T* readLength = malloc(sizeof(SIZE_T));//output value is actully readed data size
ReadProcessMemory(hProcess, lpBaseAddr, buffer, nSize, readLength);
CloseHandle(hProcess);
printf("Read address 0x%p data is %d\n", lpBaseAddr,*buffer);
printf("Read data length is %d\n", *readLength);
return 0;
}

3.运行结果如下:

2_C+WindowsReault2

3. C语言读取字节集的数据

1.C语言读取1字节的数据

  1. 完整代码:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
//main.c
#include <windows.h>
#include <stdio.h>


int main(int argc, char* argv[])
{
DWORD dwProcessId = 19732;
HANDLE hProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, dwProcessId);
DWORD lpBaseAddr = 0x0019FEDC;//0x0019FEDC is address
unsigned char* buffer= malloc(1);//recive readed data
SIZE_T nSize = 1;//read 1 bytes data
SIZE_T* readLength = malloc(sizeof(SIZE_T));//output value is actully readed data size
ReadProcessMemory(hProcess, lpBaseAddr, buffer, nSize, readLength);
CloseHandle(hProcess);
printf("Read address 0x%p data is\t0x", lpBaseAddr);
printf("%02hhX",*buffer);
printf("\nRead data length is %d\n", *readLength);
return 0;
}
  1. 运行结果:

2_C+WindowsReault3

2.C语言读取多个字节的数据

  1. 完整代码:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
//main.c
#include <windows.h>
#include <stdio.h>


int main(int argc, char* argv[])
{
DWORD dwProcessId = 19732;
HANDLE hProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, dwProcessId);
DWORD lpBaseAddr = 0x0019FEDC;//0x0019FEDC is address
unsigned char* buffer= malloc(4);//recive readed data
SIZE_T nSize = 4;//read 4 bytes data
SIZE_T* readLength = malloc(sizeof(SIZE_T));//output value is actully readed data size
ReadProcessMemory(hProcess, lpBaseAddr, buffer, nSize, readLength);
CloseHandle(hProcess);
printf("Read address 0x%p data is\t0x", lpBaseAddr);
for (int i = 0; i < *readLength; i++)
{
printf("%02hhX",*buffer++);
}
printf("\nRead data length is %d\n", *readLength);
return 0;
}
  1. 运行结果:

    2_C+WindowsReault4

3.解决使用ReadProcessMemeory读取到字符集类型数据顺序是反的,解决办法为在x86程序中一次读取4个字节的数据

  1. 使用ReadProcessMemeory读取到0x0019FEDC的数据应该为666,16进制的值应该为29A,但在之前的程序中显示为9A2,会发现明显顺序不对,需要修改代码为一次性读取4个字节的数据,以下为完整代码:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
//main.c
#include <windows.h>
#include <stdio.h>


int main(int argc, char* argv[])
{
DWORD dwProcessId = 19732;
HANDLE hProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, dwProcessId);
DWORD lpBaseAddr = 0x0019FEDC;//0x0019FEDC is address
SIZE_T nSize = 4;//read 4 bytes data
BYTE** buffer = (BYTE**)malloc(sizeof(BYTE*));//recive readed data
*buffer = (BYTE*)malloc(sizeof(BYTE*));
SIZE_T* readLength = (SIZE_T*)malloc(sizeof(SIZE_T));//output value is actully readed data size
ReadProcessMemory(hProcess, lpBaseAddr, buffer, nSize, readLength);
CloseHandle(hProcess);
printf("Read address 0x%p data is\t0x", lpBaseAddr);
printf("%08X", *buffer);
printf("\nRead data length is %d\n", *readLength);
return 0;
}

运行结果:

2_C+WindowsReault5

  1. 读取多个字符集的完整代码

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    //main.c
    #include <windows.h>
    #include <stdio.h>
    #include <malloc.h>

    int main(int argc, char* argv[])
    {
    DWORD dwProcessId = 85064;
    HANDLE hProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, dwProcessId);
    DWORD lpBaseAddr = 0x0019FEDC;//0x0019FEDC is address
    ULONG addrNumber = 10;
    SIZE_T nSize = sizeof(BYTE*) * addrNumber;//read size 32/64 bit
    BYTE** buffer = (BYTE**)malloc(addrNumber);//recive readed data
    for (ULONG i = 0; i < addrNumber; i++)
    {
    *(buffer+i) = (BYTE*)malloc(sizeof(BYTE*));
    }
    SIZE_T* readLength = (SIZE_T*)malloc(sizeof(SIZE_T));//output value is actully readed data size
    ReadProcessMemory(hProcess, lpBaseAddr, buffer, nSize, readLength);
    CloseHandle(hProcess);
    if (0 == *readLength)return 0;
    int readSize = *readLength / sizeof(BYTE*);
    if (*readLength % sizeof(BYTE*) != 0)readSize++;
    for (ULONG i = 0; i < readSize; i++)
    {
    printf("%d\t", i + 1);
    printf("Read address 0x%p data is\t", lpBaseAddr + i * sizeof(BYTE*));
    printf("0x%p\n", *(buffer+i));
    }
    printf("Read data length is %d\n", *readLength);
    return 0;
    }

运行结果:

2_C+WindowsReault6

使用size_t类型的变量兼容x86与x86_64程序

  1. Message.c(被读取的数据)

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    //Message.c
    #include <stdio.h>
    #include <windows.h>
    int main(int argc, char** argv)
    {
    size_t var = 0x8070605040302010;
    printf("var vulue is 0x%llX\n", var);
    printf("var address is 0x%p\n", &var);
    size_t* p = &var;
    printf("var vulue is 0x%llX\n", *p);
    printf("var address is 0x%p\n", p);
    printf("point p address is 0x%p\n", &p);
    printf("ProcessID is %d\n", GetCurrentProcessId());
    printf("Module Message.exe address is 0x%p\n",GetModuleHandleA("Message.exe"));
    getchar();
    return 0;
    }
  2. main.c

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    #include <windows.h>
    #include <stdio.h>


    int main(int argc, char* argv[])
    {
    DWORD dwProcessId = 59568;
    HANDLE hProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, dwProcessId);
    size_t lpBaseAddr = 0x000000000014FCF8;//0x0019FEDC/0x000000000014FCF8 is address
    size_t* buffer = malloc(sizeof(size_t));//recive readed data
    SIZE_T nSize = sizeof(size_t);//read 4/8 bytes data
    SIZE_T* readLength = malloc(sizeof(SIZE_T));//output value is actully readed data size
    ReadProcessMemory(hProcess, lpBaseAddr, buffer, nSize, readLength);
    CloseHandle(hProcess);
    printf("Read address 0x%p data is 0x%llx\n", lpBaseAddr, *buffer);
    printf("Read data length is %d\n", *readLength);
    return 0;
    }