2

EDIT: Fixed my problem.. I was using the wrong address the whole time...

How do I read a string or character array of unknown size from a process using the function ReadProcessMemory in C++?

What I've tried:

    std::string temp;
    ReadProcessMemory(*hProcess, (LPCVOID)(address+offset), &temp, sizeof(temp), &bytesRead);               
    mywString = string2wstring(temp);

The function string2wstring(): Source of function

std::wstring string2wstring(const std::string& str)
{
    int size_needed = MultiByteToWideChar(CP_UTF8, 0, &str[0], (int)str.size(), NULL, 0);
    std::wstring wstrTo(size_needed, 0);
    MultiByteToWideChar(CP_UTF8, 0, &str[0], (int)str.size(), &wstrTo[0], size_needed);
    return wstrTo;
}

I was able to successfully read the string but I keep getting an read access violation when I run this:

#include <iostream>
#include <windows.h>
#include <string>


void main()
{
    HANDLE hProcess;
    DWORD pID = 000;
    SIZE_T bytesRead;
    uintptr_t address = 0x000;

    //HWND gameWindow = FindWindow(NULL, L"TEXTCHECK");
    //GetWindowThreadProcessId(gameWindow, &pID);

    hProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, pID);


    std::string temp;
    if (ReadProcessMemory(hProcess, (LPCVOID)(address), &temp, sizeof(temp), &bytesRead))
    {
    }

    std::cout << temp;

    system("pause");

}

Testing against:

#include <iostream>
#include <string>
#include <Windows.h>
#include <stdlib.h>

using namespace std;

int main() {

    int varInt = 123456;
    string varString = "DefaultString";
    const char arrChar[128] = "Long char array AABBCCDDEEFFGGHHIIJJKKLL"; 
    int* ptr2int = &varInt;
    int** ptr2ptr = &ptr2int;
    int*** ptr2ptr2 = &ptr2ptr;



    while (1) {
        cout << "Process ID: " << GetCurrentProcessId() << "\n";
        cout << "\n";
        cout << "varInt     (0x" << &varInt << ") = " << varInt << "\n";
        cout << "varString  (0x" << &varString << ") = " << varString << "\n";
        cout << "arrChar    (0x" << &arrChar << ") = " << arrChar << "\n";
        cout <<"\n";
        cout << "ptr2int    (0x" << &ptr2int << ") = 0x" << ptr2int << "\n";
        cout << "ptr2ptr    (0x" << &ptr2ptr << ") = 0x" << ptr2ptr << "\n";
        cout << "ptr2ptr2   (0x" << &ptr2ptr2 << ") = 0x" << ptr2ptr2 << "\n";

        cout << "\n";
        cout << "Press ENTER to print again.";
        cout << "\n";
        cout << flush;
        cin.get();
        cout << "----------------------------------------\n\n\n";
        //system("CLS");

    }
    return 0;
}

managed win32 exception occurred while GETSTRINGFROMMEM.EXE [16984]

JwGaming
  • 79
  • 6

1 Answers1

1

You have to know the exact size to read. If you don't know the size, your only hope is if either:

  • the string data is prefixed with its size that you can read

  • the string data is null terminated, in which case you must read 1 char at a time until you find the null terminator.

Remy Lebeau
  • 555,201
  • 31
  • 458
  • 770
  • How would I do that? I am not finding anything about it. What I am trying isn't working and I am just getting exceptions. – JwGaming Jun 02 '18 at 18:10
  • @JwGaming if you don't know the exact format of what you are trying to read, you can't read it effectively. You can't just read arbitrary data from arbitrary processes. What are you really trying to accomplish exactly? – Remy Lebeau Jun 02 '18 at 18:22