 |
Cheat Engine The Official Site of Cheat Engine
|
View previous topic :: View next topic |
Author |
Message |
contao How do I cheat?
Reputation: 0
Joined: 24 Oct 2012 Posts: 4
|
Posted: Wed Oct 24, 2012 7:56 am Post subject: How does CE do it? |
|
|
Hallo
I'm new here and I have a questions about CE..
As you can see on the pictures CE put a value out. My problem is now I don't know how does CE buid the momory address where the red marked value is stored.
Code: | solitaire.exe+0xBAFA8 => ?????????????? (value) |
I think I need a "basic" address of solitaire.exe and add 0xBAFA8. So I will get a new address and after that I have to read out the new address. But how I get this address?
My plan is to create a script in Python. If someone could give me some advice (maybe in C or better in Python), I would be very grateful.
[img]xxx://imageshack.us/scaled/landing/18/ceon.png[/img]
[img]xxx://imageshack.us/a/img24/2638/ceoff.png[/img]
PS: sry4my bad english
Description: |
|
Filesize: |
18.95 KB |
Viewed: |
10760 Time(s) |

|
Description: |
|
Filesize: |
17.47 KB |
Viewed: |
10760 Time(s) |

|
|
|
Back to top |
|
 |
Gniarf Grandmaster Cheater Supreme
Reputation: 43
Joined: 12 Mar 2012 Posts: 1285
|
Posted: Wed Oct 24, 2012 12:32 pm Post subject: |
|
|
Well I'm python retarded so my script may be improved, but it will show you how to write at [[[solitaire.exe+BAFA8]+50]+14] (provided that area is writable in the first place.
http://pastebin.com/QyiwzgMA
(paste will expire around 2012/11/24)
|
|
Back to top |
|
 |
contao How do I cheat?
Reputation: 0
Joined: 24 Oct 2012 Posts: 4
|
Posted: Thu Oct 25, 2012 12:41 am Post subject: |
|
|
Hi
Thank you very much for the script. But it seems that the script can not open the process.
Code: | Something went wrong when getting GameBaseAddress
Error at pointer level 1
Error at pointer level 2
|
This is my code but without any function to get the base addresse.
PS: I am also Python retarded
pastebin. com/r3kqNLGk
|
|
Back to top |
|
 |
Gniarf Grandmaster Cheater Supreme
Reputation: 43
Joined: 12 Mar 2012 Posts: 1285
|
Posted: Thu Oct 25, 2012 5:19 am Post subject: |
|
|
I bet it's because the window name is incorrect. Your script uses "Solitär", mine "Solitaire".
To find window names, target the desired game in cheat engine, go to memory viewer->tools->dissect windows. Window names are between "-"s.
To quickly test several window names:
-open a python shell (double click on python.exe) and type in it:
from ctypes import * [enter]
user32 = windll.user32 [enter]
print user32.FindWindowA(0,"A window name")
-If python replies with something else than "0", the window name is valid. Otherwise press [up] and try another.
|
|
Back to top |
|
 |
contao How do I cheat?
Reputation: 0
Joined: 24 Oct 2012 Posts: 4
|
Posted: Thu Oct 25, 2012 5:47 am Post subject: |
|
|
Hi
I have a german Win 7 x64 version so the window name is "Solitär". I changed "Solitaire" to "Solitär" in your skript. But if I fill in an other window name like FreeCell or something else without unicode I get a window handle number.
With the extern module "win32ui" it works or rather I will get a handle number.
Code: | HWND = win32ui.FindWindow(None,u"Solitär").GetSafeHwnd() |
My ambition is to have a Python script with only standard includes modules. But I think we are on a good way...
PS:
CE Dissect Windows: Solit?r- (Solitaire) see attacht picture
Description: |
|
Filesize: |
26.4 KB |
Viewed: |
10654 Time(s) |

|
|
|
Back to top |
|
 |
Gniarf Grandmaster Cheater Supreme
Reputation: 43
Joined: 12 Mar 2012 Posts: 1285
|
Posted: Thu Oct 25, 2012 7:16 am Post subject: |
|
|
Ah yes, my script uses FindWindowA. The A means Ascii, so it won't work with unicode strings (like: u"Something"). The unicode version is FindWindowW (Wide characters), though since your code works, FindWindow alone is ok too.
|
|
Back to top |
|
 |
contao How do I cheat?
Reputation: 0
Joined: 24 Oct 2012 Posts: 4
|
Posted: Thu Oct 25, 2012 8:20 am Post subject: |
|
|
Thank you very much. I think something is going wrong with the GameBaseAddress because it's empty.
Prints:
Code: | Window handel: 1312738 as Hex: 0x1407e2
PID: c_ulong(4360L)
hProcess: 148
GameBaseAddress: c_ulong(0L)
Something went wrong when getting GameBaseAddress
Error at pointer level 1
Error at pointer level 2 |
Script:
Code: | #-*- coding: utf-8 -*-
from ctypes import *
#PSAPI.DLL
psapi = windll.psapi
#Kernel32.DLL
kernel = windll.kernel32
#user32.DLL
user32 = windll.user32
#WindowName = u"Solitär"
def GetProcessHandleByWindowName(WindowName):
PROCESS_ALL_ACCESS = 0x1F0FFF
PROCESS_QUERY_INFORMATION = 0x0400
PROCESS_VM_READ = 0x0010
PROCESS_VM_WRITE = 0x0020
ProcessID=c_ulong()
GameWindow=user32.FindWindowW(None,WindowName)
print "Window handel:", GameWindow, "as Hex:", hex(GameWindow)
user32.GetWindowThreadProcessId(GameWindow,byref(ProcessID))
print "PID:",ProcessID
#return kernel.OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ | PROCESS_VM_WRITE, False, ProcessID )
return kernel.OpenProcess(PROCESS_ALL_ACCESS, False, ProcessID )
def GetExecutableBaseAddress(hProcess):
hModule = c_ulong() #room for only one module
count = c_ulong()
if hProcess:
#EnumProcessModules returns a list of all modules in a process. The first one is ALWAYS the .exe
psapi.EnumProcessModules(hProcess, byref(hModule), sizeof(hModule), byref(count))
print "hProcess:", hProcess
return hModule
return c_ulong(0)
points = int(raw_input("Plz enter value:"))
if __name__ == '__main__':
hProcess = GetProcessHandleByWindowName(u"Solitär") #win32ui.FindWindow(None,u"Solitär").GetSafeHwnd()
GameBaseAddress=GetExecutableBaseAddress(hProcess)
print "GameBaseAddress:", GameBaseAddress
ReadBuffer=c_ulong()
if GameBaseAddress.value !=0:
kernel.ReadProcessMemory(hProcess,GameBaseAddress.value+0xBAFA8,byref(ReadBuffer),4,0)
else:
print "Something went wrong when getting GameBaseAddress"
if ReadBuffer.value !=0:
kernel.ReadProcessMemory(hProcess,ReadBuffer.value+0x50,byref(ReadBuffer),4,0)
else:
print "Error at pointer level 1"
if ReadBuffer.value !=0:
DesiredValue=c_ulong(points) #change the 4 to any other value you'd want to write into the game
kernel.WriteProcessMemory(hProcess,ReadBuffer.value+0x14,byref(DesiredValue),4,0)
else:
print "Error at pointer level 2\n"
kernel.CloseHandle(hProcess) |
|
|
Back to top |
|
 |
Gniarf Grandmaster Cheater Supreme
Reputation: 43
Joined: 12 Mar 2012 Posts: 1285
|
Posted: Thu Oct 25, 2012 11:03 am Post subject: |
|
|
EnumProcessModules called from an 32bit program will only list 32bit modules. The same function called from a 64bit program will list both 32bit and 64bit modules.
So if you're using a 32bit python interpreter and targeting a 64bit solitaire, the script will not find the .exe base address. You'll need a 64bit python for that.
|
|
Back to top |
|
 |
contao How do I cheat?
Reputation: 0
Joined: 24 Oct 2012 Posts: 4
|
Posted: Thu Oct 25, 2012 11:29 am Post subject: |
|
|
Hi
I am using a 64bit Python interpreter on my computer.
Code: | Python 2.7.3 (default, Apr 10 2012, 23:24:47) [MSC v.1500 64 bit (AMD64)] on win32
Type "help", "copyright", "credits" or "license" for more information.
>>> |
l'll try for some time yet, and I hope I find the solution.
Thx
Last edited by contao on Fri Oct 26, 2012 12:07 am; edited 3 times in total |
|
Back to top |
|
 |
SteveAndrew Master Cheater
Reputation: 30
Joined: 02 Sep 2012 Posts: 323
|
Posted: Thu Oct 25, 2012 3:32 pm Post subject: |
|
|
Hello contao, okay so I think you want to get the base address of the exe and add a certain offset to it, before reading the value at this newly calculated address then add another offset to that, then read again, etc until you end up with the final address which you can use to read/write to the score...
This depends on whether or not you are operating from inside the executable itself or externally as its own separate executable. I don't know python so I'm not sure if the following methods are all applicable in python, but here they are in C.
And solitaire on win 64 is a 64bit application so you'll need to take that into account... (You'll need to compile a 64bit dll if you intend on injecting into a 64bit process, or and even if not using a dll, to remember that pointers are 64bits in 64bit programming...)
If your from within the exe (as say an injected DLL) you'll use GetModuleHandle with a NULL parameter to get the base address of the executable you are within... So here's some code:
Code: |
HMODULE ExeBaseAddress = GetModuleHandleA(0); //Get base address of executable we are within
sprintf(dbg, "Executable Base: %p", ExeBaseAddress);
OutputDebugStringA(dbg);
unsigned int *ScorePointer = 0;
unsigned long long ScoreAddress = *(unsigned long long*)((char*)ExeBaseAddress + 0xBAFA8);
if(ScoreAddress)
{
ScoreAddress = *(unsigned long long*)(ScoreAddress + 0x50);
if(ScoreAddress)
{
ScorePointer = (unsigned int*)(ScoreAddress += 0x14);
OutputDebugStringA("Got Dynamic Score Address!");
}
}
//an int is a 32bits in 64bit programming...
//Get Score value using the 64bit pointer to 32-bit int value we have calculated above...
unsigned int Score = *ScorePointer;
//Set Score value
*ScorePointer = 54321;
|
As you can see its not to tricky... You just have to get the value (dereference) at each step before adding the next offset... This can get a bit annoying to have to keep writing it like that though, especially when not with solitaire when using a game with a lot more pointers you'll want to modify...
So to make it easier for me, I use a 'Pointer' class I've created, and a 'PointerHelper' class...
The same kind of thing would be written like this with my Pointer class:
Code: |
Pointer *ScorePointer = new Pointer();
ScorePointer->BasePtr = GetModuleHandleA(0);
ScorePointer->AddOffset(0xBAFA8);
ScorePointer->AddOffset(0x50);
ScorePointer->AddOffset(0x14);
unsigned int Score = ScorePointer->ReadValue32();
ScorePointer->WriteValue32(0x539);
|
NOTE: win x64 Solitaire, although pointers are 64bit, it still stores the score as a 32-bit value, so the pointer to the 32-bit value is still 64-bits even though the actual value stored is only 32-bits...
As you can see its a bit more natural way to write it... Then I even took it a step further and noticed that even this can get annoying if your working with a lot of pointers!
Code: |
PointerHelper *PtrHelper = new PointerHelper(); //Allocate new Pointer Helper class object
unsigned int Score = 0;
HANDLE ExeBaseAddress = GetModuleHandleA(0); //Get base address of executable we are within
//example: Add "Score" pointer to helper object [[[Solitaire.exe+BAFA8]+50]+14]
PtrHelper->AddPointer("Score", ExeBaseAddress, 0xBAFA8, 0x50, 0x14, -1);
PtrHelper->WriteValue32("Score", 123456789); //example: Write 32-bit value to "Score" pointer
Score = PtrHelper->ReadValue32("Score"); //example: Read 32-bit value of "Score" pointer
Pointer *ScorePointer = PtrHelper->GetPointerByName("Score"); //example: Get pointer object from name
void *DynamicAddress = PtrHelper->GetPointerByName("Score")->CurrentDynamicAddress;
|
I made the 'AddPointer' method use a variable argument list, so that way you can add a pointer with a single line Just have to write an extra offset after the last one in this case '0x14' and just make it negative 1 / 0xFFFFFFFFFFFFFFFF
Example with a totally made up pointer:
Code: |
PtrHelper->AddPointer("Made up pointer", 0x123456, 0x32, 0x10, 0x4, -1);
|
It was either that or having to specify the number of offsets and I chose that!
So you simply add a pointer and give it a unique name which is case sensitive... Then you can read and write upto a 64-bit value to or from that pointer with ease!
Note that right now the class is only meant for 64-bit (as it treats all pointers as 64bit) But I'm revising it to work with 32-bit as well/ make a 32-bit version, as well as making it work externally, like how you seem to be doing it! I just thought I would show how easy it is when your working from the inside rather than externally (using read/write process memory, etc)
64bit pointer helper class: (It uses linked lists so no arrays YAY! [I thought it would make more sense in this case to use lists, and plus I like them better than arrays! )
Updated Code: Latest version Note: Works on 64-bit and 32-bit
Changes:
*Fixed the 'PointerHelper' class so now it works...
*Added ReadFloat/WriteFloat and ReadDouble/WriteDouble so it works with floating point pointers too...
*Changed name of 'Pointer' class to 'GamePointer' so if 'Pointer' is already defined it wont matter
*Made all read/write methods return -1 or -1.0f (for floating points) so if the value read is 0, and if you testing whether it actually read it wont seem like it failed. Write methods were changed just for consistency..
*Other small changes
PointerHelper.h:
Code: |
#include <Windows.h>
#include <stdio.h>
#include <cstdarg>
class PointerOffset
{
public:
unsigned long long Offset;
PointerOffset *NextOffset;
PointerOffset();
~PointerOffset();
};
class GamePointer
{
public:
char *Name;
void *BasePtr;
void *CurrentDynamicAddress;
PointerOffset *OffsetsList;
GamePointer *NextPointer;
GamePointer();
~GamePointer();
void AddOffset(unsigned long long Offset);
unsigned long long ReadValue64(); //read a 64-bit value using all offsets
unsigned long long WriteValue64(unsigned long long ValueToWrite); //write a 64-bit value using all offsets
unsigned int ReadValue32(); //read a 32-bit value using all offsets
unsigned int WriteValue32(unsigned int ValueToWrite);//write a 32-bit value using all offsets
float ReadFloat();
float WriteFloat(float ValueToWrite);
double ReadDouble();
double WriteDouble(double ValueToWrite);
unsigned short ReadValue16(); //read a 16-bit value...
unsigned short WriteValue16(unsigned short ValueToWrite); //write 16-bit etc...
unsigned char ReadByteValue();
unsigned char WriteByteValue(unsigned char ValueToWrite);
private:
unsigned long long GetDynamicAddress();
};
class PointerHelper
{
public:
GamePointer *PointerList;
PointerHelper();
~PointerHelper();
void AddPointer(char *Name, void *PointerBaseAddress, ...);
GamePointer *GetPointerByName(char *Name);
unsigned long long ReadValue64(char *Name);
unsigned long long WriteValue64(char *Name, unsigned long long ValueToWrite);
unsigned int ReadValue32(char *Name);
unsigned int WriteValue32(char *Name, unsigned int ValueToWrite);
float ReadFloat(char *Name);
float WriteFloat(char *Name, float ValueToWrite);
double ReadDouble(char *Name);
double WriteDouble(char *Name, double ValueToWrite);
unsigned short ReadValue16(char *Name);
unsigned short WriteValue16(char *Name, unsigned short ValueToWrite);
unsigned char ReadByteValue(char *Name);
unsigned char WriteByteValue(char *Name, unsigned char ValueToWrite);
};
|
PointerHelper.cpp:
Code: |
#include "PointerHelper.h"
PointerOffset::PointerOffset()
{
Offset = 0;
NextOffset = 0;
}
PointerOffset::~PointerOffset()
{
if(NextOffset) //So deleting the list head will automatically delete the whole list
delete NextOffset;
}
GamePointer::GamePointer()
{
Name = 0;
BasePtr = 0;
CurrentDynamicAddress = 0;
OffsetsList = 0;
NextPointer = 0;
}
GamePointer::~GamePointer()
{
if(Name)
delete[] Name;
if(OffsetsList)
delete OffsetsList;
if(NextPointer)
delete NextPointer;
}
PointerHelper::PointerHelper()
{
PointerList = 0;
};
PointerHelper::~PointerHelper()
{
if(PointerList)
{
delete PointerList;
}
}
void GamePointer::AddOffset(unsigned long long Offset)
{
if(!OffsetsList) //Its the first offset being added
{
OffsetsList = new PointerOffset;
OffsetsList->Offset = Offset;
}
else
{
//Create and initialize the new offset
PointerOffset *NewOffset = new PointerOffset;
NewOffset->Offset = Offset;
//Get to the last offset in the list
PointerOffset *OffsetsListLast = OffsetsList;
while(OffsetsListLast->NextOffset)
{
OffsetsListLast = OffsetsListLast->NextOffset;
}
//Add the new offset to the tail of the list, extending it...
OffsetsListLast->NextOffset = NewOffset;
}
}
unsigned long long GamePointer::ReadValue64()
{
unsigned long long PtrValue = GetDynamicAddress();
if(PtrValue)
return *(unsigned long long*)PtrValue;
return -1;
}
unsigned long long GamePointer::WriteValue64(unsigned long long ValueToWrite)
{
unsigned long long PtrValue = GetDynamicAddress();
if(PtrValue)
{
*(unsigned long long*)PtrValue = ValueToWrite;
return 1;
}
return -1;
}
unsigned int GamePointer::ReadValue32()
{
unsigned long long PtrValue = GetDynamicAddress();
if(PtrValue)
return *(unsigned int*)PtrValue;
return 0;
}
unsigned int GamePointer::WriteValue32(unsigned int ValueToWrite)
{
unsigned long long PtrValue = GetDynamicAddress();
if(PtrValue)
{
*(unsigned int*)PtrValue = ValueToWrite;
return 1;
}
return -1.0f;
}
float GamePointer::ReadFloat()
{
unsigned long long PtrValue = GetDynamicAddress();
if(PtrValue)
{
return *(float*)PtrValue;
}
return -1.0f;
}
float GamePointer::WriteFloat(float ValueToWrite)
{
unsigned long long PtrValue = GetDynamicAddress();
if(PtrValue)
{
*(float*)PtrValue = ValueToWrite;
return 1.0f;
}
return -1.0f;
}
double GamePointer::ReadDouble()
{
unsigned long long PtrValue = GetDynamicAddress();
if(PtrValue)
{
return *(double*)PtrValue;
}
return -1.0f;
}
double GamePointer::WriteDouble(double ValueToWrite)
{
unsigned long long PtrValue = GetDynamicAddress();
if(PtrValue)
{
*(double*)PtrValue = ValueToWrite;
return 1.0f;
}
return -1.0f;
}
unsigned short GamePointer::ReadValue16()
{
unsigned long long PtrValue = GetDynamicAddress();
if(PtrValue)
return *(unsigned short*)PtrValue;
return -1;
}
unsigned short GamePointer::WriteValue16(unsigned short ValueToWrite)
{
unsigned long long PtrValue = GetDynamicAddress();
if(PtrValue)
{
*(unsigned int*)PtrValue = ValueToWrite;
return 1;
}
return -1;
}
unsigned char GamePointer::ReadByteValue()
{
unsigned long long PtrValue = GetDynamicAddress();
if(PtrValue)
return *(unsigned char*)PtrValue;
return -1;
}
unsigned char GamePointer::WriteByteValue(unsigned char ValueToWrite)
{
unsigned long long PtrValue = GetDynamicAddress();
if(PtrValue)
{
*(unsigned char*)PtrValue = ValueToWrite;
return 1;
}
return -1;
}
unsigned long long GamePointer::GetDynamicAddress()
{
unsigned long long PtrValue = (unsigned long long)BasePtr;
if(OffsetsList)
{
//use all offsets in sequential order to end up with the final pointer
PointerOffset *CurrentOffset = OffsetsList;
while(CurrentOffset->NextOffset)
{
if(!PtrValue) //Don't try to access the pointer if its null
return 0;
PtrValue = *(unsigned long long*)(PtrValue + CurrentOffset->Offset);
CurrentOffset = CurrentOffset->NextOffset;
}
PtrValue += CurrentOffset->Offset;
CurrentDynamicAddress = (void*)PtrValue;
return PtrValue;
}
return 0;
}
void PointerHelper::AddPointer(char *Name, void *PointerBaseAddress, ...)
{
GamePointer *NewPointer = new GamePointer();
if(!PointerList)
{
NewPointer->BasePtr = PointerBaseAddress;
NewPointer->Name = new char[strlen(Name)+1]; //strlen +1 as it doesn't account for the null byte ;)
strncpy(NewPointer->Name, Name, strlen(Name)+1);
PointerList = NewPointer; //Add as list head
}
else
{
//Add to list tail...
GamePointer *PointerListLast = PointerList;
while(PointerListLast->NextPointer)
{
if(strcmp(PointerListLast->Name, Name) == 0) //dont add duplicates
{
delete NewPointer;
return;
}
PointerListLast = PointerListLast->NextPointer;
}
if(strcmp(PointerListLast->Name, Name) == 0)
{
delete NewPointer;
return;
}
NewPointer->BasePtr = PointerBaseAddress;
NewPointer->Name = new char[strlen(Name)+1];
strncpy(NewPointer->Name, Name, strlen(Name)+1);
PointerListLast->NextPointer = NewPointer;
}
va_list Params;
va_start(Params, PointerBaseAddress);
//for(int i = 0; i < NumberOfOffsets; i++)
for(;;)
{
unsigned int TheOffset = va_arg(Params, unsigned int);
if(TheOffset == 0xffffffff)
break;
else
NewPointer->AddOffset(TheOffset);
}
va_end(Params);
}
GamePointer *PointerHelper::GetPointerByName(char *Name)
{
if(Name && PointerList)
{
GamePointer *FoundPointer = PointerList;
if(PointerList->Name && strcmp(PointerList->Name, Name) == 0)
{
return FoundPointer;
}
while(FoundPointer->NextPointer)
{
FoundPointer = FoundPointer->NextPointer;
if(FoundPointer->Name && strcmp(FoundPointer->Name, Name) == 0)
{
return FoundPointer;
}
}
}
return 0;
}
unsigned long long PointerHelper::ReadValue64(char *Name)
{
GamePointer *Ptr = GetPointerByName(Name);
if(Ptr)
return Ptr->ReadValue64();
return -1;
}
unsigned long long PointerHelper::WriteValue64(char *Name, unsigned long long ValueToWrite)
{
GamePointer *Ptr = GetPointerByName(Name);
if(Ptr)
return Ptr->WriteValue64(ValueToWrite);
return -1;
}
unsigned int PointerHelper::ReadValue32(char *Name)
{
GamePointer *Ptr = GetPointerByName(Name);
if(Ptr)
return Ptr->ReadValue32();
return -1;
}
unsigned int PointerHelper::WriteValue32(char *Name, unsigned int ValueToWrite)
{
GamePointer *Ptr = GetPointerByName(Name);
if(Ptr)
return Ptr->WriteValue32(ValueToWrite);
return -1;
}
float PointerHelper::ReadFloat(char *Name)
{
GamePointer *Ptr = GetPointerByName(Name);
if(Ptr)
return Ptr->ReadFloat();
return -1.0f;
}
float PointerHelper::WriteFloat(char *Name, float ValueToWrite)
{
GamePointer *Ptr = GetPointerByName(Name);
if(Ptr)
return Ptr->WriteFloat(ValueToWrite);
return -1.0f;
}
double PointerHelper::ReadDouble(char *Name)
{
GamePointer *Ptr = GetPointerByName(Name);
if(Ptr)
return Ptr->ReadDouble();
return -1.0f;
}
double PointerHelper::WriteDouble(char *Name, double ValueToWrite)
{
GamePointer *Ptr = GetPointerByName(Name);
if(Ptr)
return Ptr->WriteDouble(ValueToWrite);
return -1.0f;
}
unsigned short PointerHelper::ReadValue16(char *Name)
{
GamePointer *Ptr = GetPointerByName(Name);
if(Ptr)
return Ptr->ReadValue16();
return -1;
}
unsigned short PointerHelper::WriteValue16(char *Name, unsigned short ValueToWrite)
{
GamePointer *Ptr = GetPointerByName(Name);
if(Ptr)
return Ptr->WriteValue16(ValueToWrite);
return -1;
}
unsigned char PointerHelper::ReadByteValue(char *Name)
{
GamePointer *Ptr = GetPointerByName(Name);
if(Ptr)
return Ptr->ReadByteValue();
return -1;
}
unsigned char PointerHelper::WriteByteValue(char *Name, unsigned char ValueToWrite)
{
GamePointer *Ptr = GetPointerByName(Name);
if(Ptr)
return Ptr->WriteByteValue(ValueToWrite);
return -1;
}
|
I know you asked for python but I don't know python so C/C++ is all I can help with!
Oh and here's the 64bit DLL project compiled in Microsoft Visual C++ 2010 for x64, which demonstrates reading and changing the score in 64bit solitaire using the class and not using it... you have to inject it into 64bit solitaire... Note: does NOT contain the latest code (which is posted above)
http://www.sendspace.com/file/4b3xs1
_________________
|
|
Back to top |
|
 |
|
|
You cannot post new topics in this forum You cannot reply to topics in this forum You cannot edit your posts in this forum You cannot delete your posts in this forum You cannot vote in polls in this forum You cannot attach files in this forum You can download files in this forum
|
|