mirror of
https://github.com/cheat-engine/cheat-engine
synced 2026-08-15 02:26:08 -04:00
205 lines
4.5 KiB
ObjectPascal
Executable file
205 lines
4.5 KiB
ObjectPascal
Executable file
unit sharedMemory;
|
|
|
|
{$mode delphi}
|
|
|
|
interface
|
|
|
|
uses
|
|
{$ifdef windows}
|
|
windows,
|
|
{$endif}
|
|
Classes, SysUtils, symbolhandler, autoassembler, frmautoinjectunit,
|
|
cefuncproc, NewKernelHandler, Clipbrd, commonTypeDefs;
|
|
|
|
const FILE_MAP_EXECUTE = $20;
|
|
|
|
function allocateSharedMemory(name: string; size: integer=4096): pointer;
|
|
function allocateSharedMemoryIntoTargetProcess(name: string; size: integer=4096): pointer;
|
|
function createSharedMemory(name: string; size: integer): THandle;
|
|
|
|
implementation
|
|
|
|
uses ProcessHandlerUnit;
|
|
|
|
|
|
function createSharedMemory(name: string; size: integer): THandle;
|
|
begin
|
|
{$ifdef windows}
|
|
result:=CreateFileMapping(INVALID_HANDLE_VALUE,nil,PAGE_EXECUTE_READWRITE,0,size,pchar(name));
|
|
{$else}
|
|
result:=-1;
|
|
{$endif}
|
|
end;
|
|
|
|
function allocateSharedMemory(name: string; size: integer=4096): pointer;
|
|
var
|
|
access: dword;
|
|
h: thandle;
|
|
begin
|
|
{$ifdef windows}
|
|
access:=FILE_MAP_EXECUTE or FILE_MAP_READ or FILE_MAP_WRITE;
|
|
|
|
|
|
//if name does not exist allocate it first
|
|
h:=OpenFileMapping(access, false, pchar(name));
|
|
|
|
if h=0 then
|
|
h:=createSharedMemory(name, size);
|
|
|
|
result:=MapViewOfFile(h,access,0,0,0);
|
|
{$else}
|
|
result:=nil;
|
|
{$endif}
|
|
end;
|
|
|
|
function allocateSharedMemoryIntoTargetProcess(name: string; size: integer=4096): pointer;
|
|
var s: tstringlist;
|
|
disableinfo: TDisableInfo;
|
|
i: integer;
|
|
starttime: qword;
|
|
x: ptruint;
|
|
address: ptruint;
|
|
|
|
access: dword;
|
|
|
|
h: THandle;
|
|
begin
|
|
{$ifdef windows}
|
|
access:=FILE_MAP_EXECUTE or FILE_MAP_READ or FILE_MAP_WRITE;
|
|
|
|
|
|
//if name does not exist allocate it first
|
|
h:=OpenFileMapping(access, false, pchar(name));
|
|
|
|
if h=0 then
|
|
h:=createSharedMemory(name, size);
|
|
|
|
|
|
result:=nil;
|
|
s:=tstringlist.create;
|
|
|
|
|
|
s.add('alloc(allocator,1024)');
|
|
s.add('alloc(sname,128)');
|
|
s.add('alloc(address, 4)');
|
|
s.add('label(error)');
|
|
s.add('sname:');
|
|
s.add('db '''+name+''',0');
|
|
s.add('');
|
|
s.add('address:');
|
|
if processhandler.is64Bit then
|
|
s.add('dq 0')
|
|
else
|
|
s.add('dd 0');
|
|
|
|
s.add('');
|
|
s.add('allocator:');
|
|
|
|
if processhandler.is64bit then
|
|
begin
|
|
s.add('sub rsp,#64');
|
|
|
|
s.add('mov rcx,'+inttohex(access,16));
|
|
s.add('mov rdx,0');
|
|
s.add('mov r8,sname');
|
|
s.add('call OpenFileMappingA');
|
|
s.add('cmp rax,0');
|
|
end
|
|
else
|
|
begin
|
|
s.add('push sname');
|
|
s.add('push 0'); //inherit handle
|
|
s.add('push '+inttohex(access,8));
|
|
s.add('call OpenFileMappingA');
|
|
s.add('cmp eax,0');
|
|
end;
|
|
s.add('je short error');
|
|
s.add('');
|
|
if processhandler.is64bit then
|
|
begin
|
|
s.add('mov rcx,eax');
|
|
s.add('mov rdx,'+inttohex(access,16));
|
|
s.add('mov r8,0');
|
|
s.add('mov r9,0');
|
|
s.add('xor rax,rax');
|
|
|
|
s.add('mov [rsp],rcx'); //just to be sure...
|
|
s.add('mov [rsp+8],rdx');
|
|
s.add('mov [rsp+10],r8');
|
|
s.add('mov [rsp+18],r9');
|
|
s.add('mov [rsp+20],rax');
|
|
s.add('call MapViewOfFile');
|
|
s.add('mov [address],rax');
|
|
|
|
s.add('add rsp,#64');
|
|
end
|
|
else
|
|
begin
|
|
s.add('push 0');
|
|
s.add('push 0');
|
|
s.add('push 0');
|
|
s.add('push '+inttohex(access,8));
|
|
s.add('push eax');
|
|
s.add('call MapViewOfFile');
|
|
s.add('mov [address],eax');
|
|
|
|
end;
|
|
|
|
s.add('ret');
|
|
s.add('');
|
|
s.add('error:');
|
|
s.add('call GetLastError');
|
|
s.add('mov [address],eax');
|
|
if processhandler.is64bit then
|
|
s.add('add rsp,#64');
|
|
s.add('ret');
|
|
|
|
s.add('createThread(allocator)');
|
|
|
|
// Clipboard.AsText:=s.text;
|
|
|
|
disableinfo:=TDisableInfo.create;
|
|
try
|
|
|
|
if autoassemble(s,false, true, false, false, disableinfo) then
|
|
begin
|
|
starttime:=GetTickCount64;
|
|
for i:=0 to length(disableinfo.allocs)-1 do
|
|
begin
|
|
|
|
if disableinfo.allocs[i].varname='address' then
|
|
begin
|
|
while gettickcount64-starttime<10*1000 do
|
|
begin
|
|
//poll if address is still 0
|
|
|
|
if ReadProcessMemory(processhandle, pointer(disableinfo.allocs[i].address), @address, processhandler.pointersize, x) then
|
|
begin
|
|
if address<>0 then
|
|
begin
|
|
if address>=$10000 then
|
|
result:=pointer(address);
|
|
|
|
break;
|
|
end;
|
|
|
|
|
|
end else exit; //unreadable...
|
|
end;
|
|
break;
|
|
end;
|
|
end;
|
|
|
|
VirtualFreeEx(processhandle, pointer(disableinfo.allocs[0].address), 0, MEM_DECOMMIT);
|
|
end;
|
|
except
|
|
end;
|
|
|
|
disableinfo.free;
|
|
{$else}
|
|
result:=nil;
|
|
{$endif}
|
|
end;
|
|
|
|
end.
|
|
|