Solved solved thanks

Hexui Undetected CSGO Cheats Sinkicheat PUBG Cheat

kirk465

Newbie
Full Member
Jan 21, 2015
33
158
0
So yeah, after hours of browsing other forums/threads and stuff I cannot calculate this pointer dma
The offsets/base address stay the same, I've simplified my code as much as possible yet it doesn't want to work out

The only thing I want to do is reading the value out of the address as I don't need it for anything else, I would like to use a simple ReadProcessMemory, which apparently doesn't work out quite well with any level 2+ pointer

Screen CE

And this below is the most simple piece of code I came up with in order to find a solution

I wasn't able to find the Shield HP in my Static Player Base, else then that I found everything ( P Health/X/Y/Z/View Angles(X/Y/Z)/Reload/Ammo ) ...

Thanks for any kind of help in advance!

Regards
 
Last edited:

Broihon

edgy 12 y/o
Escobar Tier VIP
Fleep Tier Donator
Dec 22, 2013
1,746
40,528
316
C++:
DWORD dw_Offset[] = { 0xF8, 0xEC, 0x4, 0x8, 0x50 };
DWORD dw_Base = 0x40BC8C; // "BlaBla.exe" + BC8C What's the base address of your process?

DWORD Addy0;
ReadProcessMemory(hProc, reinterpret_cast<void*>(dw_Base), &Addy0, sizeof(DWORD), nullptr);
Addy0 += dw_Offset[0];

DWORD Addy1;
ReadProcessMemory(hProc, reinterpret_cast<void*>(Addy0), &Addy1, sizeof(DWORD), nullptr);
Addy1 += dw_Offset[1];

DWORD Addy2;
ReadProcessMemory(hProc, reinterpret_cast<void*>(Addy1), &Addy2, sizeof(DWORD), nullptr);
Addy2 += dw_Offset[2];

DWORD Addy3;
ReadProcessMemory(hProc, reinterpret_cast<void*>(Addy2), &Addy3, sizeof(DWORD), nullptr);
Addy3 += dw_Offset[3];

DWORD Addy4;
ReadProcessMemory(hProc, reinterpret_cast<void*>(Addy3), &Addy4, sizeof(DWORD), nullptr);
Addy4 += dw_Offset[4];

// Addy4 now contains your DMA
 

kirk465

Newbie
Full Member
Jan 21, 2015
33
158
0
Testing too

edit;

Thanks for your post Broihon, I've translated what you wrote into C and tried it out, unfortunately without lots of luck. I've also already did the following ;

- Followed Spocks tutorial ( my asm knowledge is basic but I did understand it ) ( link: https://guidedhacking.com/showthrea...cquiring-static-base-pointer-the-easy-way-8-2 ) -> this didn't work out quite well

Here is a pic of my current source;

edit; I'm able to easily read stats like Hitpoints/Energy/Speed/Position etc from my playerbase where everything is a level 1 pointer using fleeps FindDma function which apparently doesn't seem to work out on this one sadly

regards

Another edit;

When dissecting Data Structure with Cheat Engine it shows the value as "BYTE" and not as float ( float is the one I search for ) is this any useful?
 
Last edited:

kirk465

Newbie
Full Member
Jan 21, 2015
33
158
0
This can be closed, I've solved the problem on my own.

Thank you all anyways, it works now , yay!
 

kirk465

Newbie
Full Member
Jan 21, 2015
33
158
0
Damn I got another problem, anyone has an idea why this :

void ReadStringFromMem(HANDLE hProcHandle) {

int len = 64;
char pHMemory_NickBuffer[64];

ReadProcessMemory(hProcHandle, (LPCVOID)ADDY, pHMemory_NickBuffer, len, 0);

puts(pHMemory_NickBuffer);
}

does only return the first char of the nickname?

I've already used puts instead of printf to prevent usage errors. The address is static and correct, the first char of the array is printed but I'm missing all the rest...

Anyone an idea? I've already read on several sites about possible solutions which don't seem to work, though already adjusted my code to cover some of the changes (UC/mpqh source)

regards
 
Last edited:

till0sch

Respected Hacker
Dank Tier VIP
Dank Tier Donator
Oct 14, 2012
1,104
12,593
51
Damn I got another problem, anyone has an idea why this :

void ReadStringFromMem(HANDLE hProcHandle) {

int len = 64;
char pHMemory_NickBuffer[64];

ReadProcessMemory(hProcHandle, (LPCVOID)0x6732F0, pHMemory_NickBuffer, len, 0);

puts(pHMemory_NickBuffer);
}

does only return the first char of the nickname?

I've already used puts instead of printf to prevent usage errors. The address is static and correct, the first char of the array is printed but I'm missing all the rest...

Anyone an idea? I've already read on several sites about possible solutions which don't seem to work, though already adjusted my code to cover some of the changes (UC/mpqh source)

regards
Wide char?
 

Broihon

edgy 12 y/o
Escobar Tier VIP
Fleep Tier Donator
Dec 22, 2013
1,746
40,528
316
Damn I got another problem, anyone has an idea why this :

void ReadStringFromMem(HANDLE hProcHandle) {

int len = 64;
char pHMemory_NickBuffer[64];

ReadProcessMemory(hProcHandle, (LPCVOID)0x6732F0, pHMemory_NickBuffer, len, 0);

puts(pHMemory_NickBuffer);
}

does only return the first char of the nickname?

I've already used puts instead of printf to prevent usage errors. The address is static and correct, the first char of the array is printed but I'm missing all the rest...

Anyone an idea? I've already read on several sites about possible solutions which don't seem to work, though already adjusted my code to cover some of the changes (UC/mpqh source)

regards
C++:
size_t ReadStringFromMem(HANDLE hProcHandle, void* pAddress, char* lpOut, size_t sMax)
{
      if(lpOut)
      {    
            size_t Ret = 0; 
            if(ReadProcessMemory(hProcHandle, pAddress, lpOut, sMax, &Ret))
            {
                  return Ret;                  
            }
      }
      return 0;
}
 

kirk465

Newbie
Full Member
Jan 21, 2015
33
158
0
Вroihon;34787 said:
C++:
size_t ReadStringFromMem(HANDLE hProcHandle, void* pAddress, char* lpOut, size_t sMax)
{
      if(lpOut)
      {    
            size_t Ret = 0; 
            if(ReadProcessMemory(hProcHandle, pAddress, lpOut, sMax, &Ret))
            {
                  return Ret;                  
            }
      }
      return 0;
}
What would the call for this look like, in theory? It doesn't seem to work out and you are returning the number of bytes read but not the buffer, I'm wondering why

I've tried

RetVal = ReadStringFromMem(hProcHandle, &Address, &NickBuff, slen);

This way your function always returns 0

Though thanks already for the help
till0sch Wide char? What do you mean :eek:

regards

EDIT; Screw that, I found out that when looking via cheat engine on the string it shows a space between each character that the game assembles to a string later. Any idea how I can skip the spaces between each char?
 
Last edited:

Broihon

edgy 12 y/o
Escobar Tier VIP
Fleep Tier Donator
Dec 22, 2013
1,746
40,528
316
What would the call for this look like, in theory? It doesn't seem to work out and you are returning the number of bytes read but not the buffer, I'm wondering why

Though thanks already for the help
till0sch Wide char? What do you mean :eek:

regards
It's more efficient and stable this way.
C++:
//EXAMPLE CALL
char Playername[50];
size_t Ret = ReadStringFromMem(hProc, reinterpret_cast<void*>(0x123456), Playername, 50);
if(!Ret)
{
      //Error
}
//the name is now stored in Playername
Edit:
RetVal = ReadStringFromMem(hProcHandle, &Address, &NickBuff, slen);
Since "Address" is probably a DWORD this won't work because now you're passing the address of your variable. So a pointer to your address.
Just cast it as a (void*).
 
Last edited:

till0sch

Respected Hacker
Dank Tier VIP
Dank Tier Donator
Oct 14, 2012
1,104
12,593
51
EDIT; Screw that, I found out that when looking via cheat engine on the string it shows a space between each character that the game assembles to a string later. Any idea how I can skip the spaces between each char?
Yea um thats called.. let me think.. I got it: wide char
 

Broihon

edgy 12 y/o
Escobar Tier VIP
Fleep Tier Donator
Dec 22, 2013
1,746
40,528
316
C++:
#ifdef UNICODE
#define ReadStringFromMem ReadStringFromMemW
#else
#define ReadStringFromMem ReadStringFromMemA
#endif

size_t ReadStringFromMemW(HANDLE hProc, DWORD dwAddress, wchar_t* lpOut, size_t MaxLength)
{
	if (!lpOut)
	{
		return 0;
	}
	size_t Ret = 0;
	wchar_t Buffer = 0x1;
	while (Buffer != 0x0000 && Ret <= MaxLength)
	{
		if (!ReadProcessMemory(hProc, reinterpret_cast<void*>(dwAddress + Ret * 2), &Buffer, 1, nullptr))
		{
			return 0;
		}
		lpOut[Ret] = Buffer;
		Ret++;
	}
	return Ret;
}

size_t ReadStringFromMemA(HANDLE hProc, DWORD dwAddress, char* lpOut, size_t MaxLength)
{
	if (!lpOut)
	{
		return 0;
	}
	size_t Ret = 0;
	char Buffer = 0x1;
	while (Buffer != 0x00 && Ret <= MaxLength)
	{
		if (!ReadProcessMemory(hProc, reinterpret_cast<void*>(dwAddress + Ret), &Buffer, 1, nullptr))
		{
			return 0;
		}
		lpOut[Ret] = Buffer;
		Ret++;
	}
	return Ret;
}

Example call ASCII:
C++:
char Name[50];
size_t Length = ReadStringFromMemA(hProc, Address, Name, 50);
Example call UNICODE:
C++:
wchar_t Name[50];
size_t Length = ReadStringFromMemW(hProc, Address, Name, 50);
 

kirk465

Newbie
Full Member
Jan 21, 2015
33
158
0
Вroihon;34792 said:
C++:
#ifdef UNICODE
#define ReadStringFromMem ReadStringFromMemW
#else
#define ReadStringFromMem ReadStringFromMemA
#endif

size_t ReadStringFromMemW(HANDLE hProc, DWORD dwAddress, wchar_t* lpOut, size_t MaxLength)
{
	if (!lpOut)
	{
		return 0;
	}
	size_t Ret = 0;
	wchar_t Buffer = 0x1;
	while (Buffer != 0x0000 && Ret <= MaxLength)
	{
		if (!ReadProcessMemory(hProc, reinterpret_cast<void*>(dwAddress + Ret * 2), &Buffer, 1, nullptr))
		{
			return 0;
		}
		lpOut[Ret] = Buffer;
		Ret++;
	}
	return Ret;
}

size_t ReadStringFromMemA(HANDLE hProc, DWORD dwAddress, char* lpOut, size_t MaxLength)
{
	if (!lpOut)
	{
		return 0;
	}
	size_t Ret = 0;
	char Buffer = 0x1;
	while (Buffer != 0x00 && Ret <= MaxLength)
	{
		if (!ReadProcessMemory(hProc, reinterpret_cast<void*>(dwAddress + Ret), &Buffer, 1, nullptr))
		{
			return 0;
		}
		lpOut[Ret] = Buffer;
		Ret++;
	}
	return Ret;
}

Example call ASCII:
C++:
char Name[50];
size_t Length = ReadStringFromMemA(hProc, Address, Name, 50);
Example call UNICODE:
C++:
wchar_t Name[50];
size_t Length = ReadStringFromMemW(hProc, Address, Name, 50);
Thank you man, you saved my day it works wonderfully!

I've had to adjust your code and translate it to C, afterwards I had to adjust the output method. Printf needs to output it with "%ls" instead of "%s" as it is a wide char

:)
 

kirk465

Newbie
Full Member
Jan 21, 2015
33
158
0
Okay, I've got a working code, I can read memory and all the values I need/want but the problem is, whenever loading a new level I'll have to actualize my DMAs, I've set it on CTRL+Z to manually actualize them in an if statement but I would like to do this automatically whenever one of the old DMAs is invalid
And honestly I don't want to call 20x ReadProcessMemory per 10 seconds, that would be some kind of awful

So is there any way to see if readprocessmemory returns an error/invalid value? Maybe I'm just unable to see it right now, will sit on it though.

regards

Edit; Limiting the read value to a certain one is nearly impossible as there are hundred of different usable players with different hitpoints/shields/energy etc...

EDIT2; forget that, I solved it :) anyways
 
Last edited:

till0sch

Respected Hacker
Dank Tier VIP
Dank Tier Donator
Oct 14, 2012
1,104
12,593
51
Вroihon;34792 said:
C++:
#ifdef UNICODE
#define ReadStringFromMem ReadStringFromMemW
#else
#define ReadStringFromMem ReadStringFromMemA
#endif

size_t ReadStringFromMemW(HANDLE hProc, DWORD dwAddress, wchar_t* lpOut, size_t MaxLength)
{
	if (!lpOut)
	{
		return 0;
	}
	size_t Ret = 0;
	wchar_t Buffer = 0x1;
	while (Buffer != 0x0000 && Ret <= MaxLength)
	{
		if (!ReadProcessMemory(hProc, reinterpret_cast<void*>(dwAddress + Ret * 2), &Buffer, 1, nullptr))
		{
			return 0;
		}
		lpOut[Ret] = Buffer;
		Ret++;
	}
	return Ret;
}

size_t ReadStringFromMemA(HANDLE hProc, DWORD dwAddress, char* lpOut, size_t MaxLength)
{
	if (!lpOut)
	{
		return 0;
	}
	size_t Ret = 0;
	char Buffer = 0x1;
	while (Buffer != 0x00 && Ret <= MaxLength)
	{
		if (!ReadProcessMemory(hProc, reinterpret_cast<void*>(dwAddress + Ret), &Buffer, 1, nullptr))
		{
			return 0;
		}
		lpOut[Ret] = Buffer;
		Ret++;
	}
	return Ret;
}

Example call ASCII:
C++:
char Name[50];
size_t Length = ReadStringFromMemA(hProc, Address, Name, 50);
Example call UNICODE:
C++:
wchar_t Name[50];
size_t Length = ReadStringFromMemW(hProc, Address, Name, 50);
No need to check each byte, 25 calls for 1 byte each is slower than 1 call and read 50 bytes..

The validation will happen anyways when it comes to outputting, due to the 0-termination (in this case 00 00)


If you do it like you did, at least use virtualprotect to secure you can safely write to your variable..
 

Broihon

edgy 12 y/o
Escobar Tier VIP
Fleep Tier Donator
Dec 22, 2013
1,746
40,528
316
No need to check each byte, 25 calls for 1 byte each is slower than 1 call and read 50 bytes..
Yes, one RPM call is enough indeed.

The validation will happen anyways when it comes to outputting, due to the 0-termination (in this case 00 00)
Not if the string to read is longer than MaxLength.

If you do it like you did, at least use virtualprotect to secure you can safely write to your variable..
No need for VirtualProtect at all. Not sure what you meant by that part. The function assumes that lpOut is a valid write pointer.
Edit: It's a bad idea to call VirtualProtect on the pointer passed to the function. When someone passes a wrong argument it could be a pointer to a code region which maybe has to be a read/execute only region.
If you now call VirtualProtect on that region and write your string there you'll cause a crash.


Anyway:
C++:
#ifdef UNICODE
#define ReadStringFromMem ReadStringFromMemW
#else
#define ReadStringFromMem ReadStringFromMemA
#endif

size_t ReadStringFromMemW(HANDLE hProc, DWORD dwAddress, wchar_t* lpOut, size_t MaxLength)
{
	MEMORY_BASIC_INFORMATION MBI;
	if (!VirtualQuery(reinterpret_cast<void*>(dwAddress), &MBI, sizeof(MEMORY_BASIC_INFORMATION)))
	{
		return 0;
	}
	if (!(MBI.Protect & PAGE_EXECUTE_READWRITE | MBI.Protect & PAGE_EXECUTE_WRITECOPY | MBI.Protect & PAGE_WRITECOPY | MBI.Protect & PAGE_WRITECOMBINE | MBI.Protect & PAGE_READWRITE))
	{
		return 0;
	}

	wchar_t* Buffer = new wchar_t[MaxLength];
	if (!ReadProcessMemory(hProc, reinterpret_cast<void*>(dwAddress), Buffer, MaxLength * 2, nullptr))
	{
		return 0;
	}

	size_t Ret = 0;
	while (*Buffer && Ret != MaxLength)
	{
		*lpOut = *Buffer;
		Buffer++;
		lpOut++;
		Ret++;
	}
	*lpOut = 0;

	return Ret;
}

size_t ReadStringFromMemA(HANDLE hProc, DWORD dwAddress, char* lpOut, size_t MaxLength)
{
	MEMORY_BASIC_INFORMATION MBI;
	if (!VirtualQuery(reinterpret_cast<void*>(dwAddress), &MBI, sizeof(MEMORY_BASIC_INFORMATION)))
	{
		return 0;
	}
	if (!(MBI.Protect & PAGE_EXECUTE_READWRITE | MBI.Protect & PAGE_EXECUTE_WRITECOPY | MBI.Protect & PAGE_WRITECOPY | MBI.Protect & PAGE_WRITECOMBINE | MBI.Protect & PAGE_READWRITE))
	{
		return 0;
	}

	char* Buffer = new char[MaxLength];
	if (!ReadProcessMemory(hProc, reinterpret_cast<void*>(dwAddress), Buffer, MaxLength, nullptr))
	{
		return 0;
	}

	size_t Ret = 0;
	while (*Buffer && Ret != MaxLength)
	{
		*lpOut = *Buffer;
		Buffer++;
		lpOut++;
		Ret++;
	}
	*lpOut = 0;

	return Ret;
}

Even with retard check.
 
Last edited:

kirk465

Newbie
Full Member
Jan 21, 2015
33
158
0
I'd say that it is personal preference and honestly, I don't want to convert over 1,000 lines of C into Cpp just to gain one or two advantages
 
Attention! Before you post:

Read the How to Ask Questions Guide
99% of questions are answered in the Beginner's Guide, do it before asking a question.

No Hack Requests. Post in the correct section.  Search the forum first. Read the rules.

How to make a good post:

  • Fill out the form correctly
  • Tell us the game name & coding language
  • Post everything we need to know to help you
  • Ask specific questions, be descriptive
  • Post errors, line numbers & screenshots
  • Post code snippets using code tags
  • If it's a large project, zip it up and attach it

If you do not comply, your post may be deleted.  We want to help, please make a good post and we will do our best to help you.

Community Mods