Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How does one even use this? #44

Closed
MelerEcckmanLawler opened this issue Jul 5, 2019 · 4 comments
Closed

How does one even use this? #44

MelerEcckmanLawler opened this issue Jul 5, 2019 · 4 comments

Comments

@MelerEcckmanLawler
Copy link

MelerEcckmanLawler commented Jul 5, 2019

Trying to get the hang of this before moving on to doing what I originally set out to, but can't even get a simple test to work. I've got a notepad window open with the text "Hello World!" and I'm trying to find it with this code:

const memoryjs = require('memoryjs');
const processes = memoryjs.getProcesses();

var p;

for (let i = 0; i < processes.length; i++) {
  if (processes[i].szExeFile == 'notepad.exe') {
    p = memoryjs.openProcess(processes[i].th32ProcessID);
    }
  }
}

addr = memoryjs.findPattern(p.handle, 'notepad.exe', /^H/, memoryjs.STRING, 0, 0);
txt = memoryjs.readMemory(p.handle, addr, memoryjs.STRING);
console.log(txt); // outputs 'MZ', but should output 'Hello World!'

MZ is apparently the magic byte identifying a DOS executable, so I have a feeling it's getting this string from the actual notepad.exe file in memory. Not what I want.

@Rob--
Copy link
Owner

Rob-- commented Jul 5, 2019

Just do const p = memoryjs.openProcess('notepad.exe');

And also I'm not really sure what you're trying to do with the /^H/ in findPattern. The signature argument for findPattern is a string in the form of XX ? ? XX ? where XX are known bytes and ? are unknown bytes.

In this case you would need to find where notepad stores the text displayed in memory and read memory from that address.

@MelerEcckmanLawler
Copy link
Author

MelerEcckmanLawler commented Jul 5, 2019

The /^H/ was supposed to be a regular expression to find strings beginning with H, but I see now the pattern function doesn't expect a regular expression.

I am trying to find the memory address where notepad stores displayed text by searching the entire memory of notepad for the string that matches my pattern. Here is my new code:

const memoryjs = require('memoryjs');

const p = memoryjs.openProcess('notepad.exe');
const sig = '48??????????21'; //'Hello World!' -> '48656C6C6F20576F726C6421' -> '48??????????21'
const addr = memoryjs.findPattern(p.handle, 'notepad.exe', sig, memoryjs.READ, 0, 0);
const txt = memoryjs.readMemory(p.handle, addr, 'string');

console.log(txt); // should show 'Hello World!' but actually shows nothing or gives the error: 'TypeError: unable to read string (no null-terminator found after 1 million chars)'

My open notepad window contains the text Hello World! and I thought my code could find it. But apparently not?

I'm trying to do what CheatEngine does, searching for memory addresses within a process which contain a certain string. Isn't memoryjs capable of that? If not, then I am disappointed.

UPDATE: Changing the signature type to memoryjs.NORMAL gives me the string MZ� which is the original problem I had in the first place. Clearly the signature is being totally ignored, because MZ� are magic-bytes which definitely don't match the pattern 48??????????21.

UPDATE: Seems the signature must have a space before and after each question mark, because after adding spaces it's now returning something that does match the signature. It's not what I'm looking for though, it's some nonsesnse (H�H���!) but I will continue experimenting.

UPDATE: Neither the signatures 48 ? ? ? ? ? ? ? ? ? ? 2121 nor 48 ? ? ? ? ? ? ? ? ? ? 21 21 nor even the exact, full string 48656C6C6F20576F726C642121 are able to find the displayed text Hello World!!. They just give the following error:

TypeError: unable to read string (no null-terminator found after 1 million chars)

Why is CheatEngine able to find the string but not memoryjs?

@Rob--
Copy link
Owner

Rob-- commented Jul 6, 2019

I see what is happening. I'm not gonna lie, I don't know much about text and unicode. But from what I see, it seems that notepad.exe stores text with Utf16 encoding (I guess this means each character takes up 2 bytes instead of 1 byte which memoryjs is expecting).

Take a look at the following image:
Cheat Engine

As you can tell, the text Hello world! in hex is 48 65 6c 6c 6f 20 77 6f 72 6c 64 21. Now, I'm guessing Notepad stores text as Utf16 because in memory Cheat Engine is telling us the text appears as 48 00 65 00 6c 00 6c 00 6f 00 20 00 77 00 6f 00 72 00 6c 00 64 00 21 which implies each character is taking up 2 bytes.

Therefore, if you alter your signature to have 00 after each byte, you will be able to find the correct address. However, my implementation of reading a string in memory causes the readMemory function to fail when it encounters a 00 byte (null character/string terminator) because the text is expected to be Utf8. To counter this, this section of code would need to be altered to support Utf16 strings. This also means a parameter would need to be passed when reading strings from memory to flag whether the string is Utf8 or Utf16 (or even higher).

@MelerEcckmanLawler
Copy link
Author

That makes sense, thank you very much!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants