cheat-engine/Cheat Engine/FileMapping.pas

112 lines
2.9 KiB
ObjectPascal
Raw Permalink Normal View History

2011-07-04 19:52:53 +00:00
unit FileMapping;
{$MODE Delphi}
{
Wrapper class for filemapping
version 0.1: Only supports opening of exisiting files and no appending
version 0.2: copy on write, you can now write to it without actually messing up the file
}
interface
uses {$ifdef darwin}
macport,
{$endif}
{$ifdef windows}
windows,
{$endif}
LCLIntf,classes,SysUtils;
2011-07-04 19:52:53 +00:00
type
EFileMapError=class(Exception);
TFileMapping=class
2011-07-04 19:52:53 +00:00
private
FileHandle: THandle;
FileMapping: THandle;
FFileContent: pointer;
2016-06-30 04:21:32 +02:00
FFileSize: Qword;
FFilename: string;
2011-07-04 19:52:53 +00:00
public
property fileContent: pointer read FFileContent;
2016-06-30 04:21:32 +02:00
property filesize: qword read FFileSize;
property filename: string read FFilename;
2011-07-04 19:52:53 +00:00
constructor create(filename: string);
destructor destroy; override;
end;
implementation
2016-06-30 04:21:32 +02:00
//function GetFileSize(hFile:HANDLE; lpFileSizeHigh:LPDWORD):DWORD; external 'kernel32' name 'GetFileSize';
2011-07-04 19:52:53 +00:00
resourcestring
rsDoesNotExist = '%s does not exist';
rsMappingFailed = 'Mapping failed';
rsFailedCreatingAProperView = 'Failed creating a proper view';
destructor TFileMapping.destroy;
begin
//clean up the mapping
if FFileContent<>nil then
UnmapViewOfFile(FFileContent);
if FileMapping<>0 then
CloseHandle(FileMapping);
if FileHandle<>0 then
CloseHandle(FileHandle);
inherited destroy;
end;
constructor TFileMapping.create(filename: string);
begin
inherited create;
try
//open file
FileHandle := CreateFile(PChar(filename), GENERIC_READ or GENERIC_WRITE, FILE_SHARE_READ, nil, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0);
2022-10-14 16:46:00 +02:00
if (FileHandle = 0) or (FileHandle=INVALID_HANDLE_VALUE) then
2011-07-04 19:52:53 +00:00
FileHandle := CreateFile(PChar(filename), GENERIC_READ, FILE_SHARE_READ, nil, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0);
2022-10-14 16:46:00 +02:00
if (FileHandle = 0) or (FileHandle=INVALID_HANDLE_VALUE) then
raise EFileMapError.create(Format(rsDoesNotExist, [filename]));
2011-07-04 19:52:53 +00:00
2016-06-30 04:21:32 +02:00
FFileSize:=0;
FFileSize:=GetFileSize(FileHandle,pointer(ptruint(@fileSize)+4));
2011-07-04 19:52:53 +00:00
2022-10-14 16:46:00 +02:00
if FFileSize=0 then
raise EFileMapError.create('Can not map an empty file');
2011-07-04 19:52:53 +00:00
//still here, so create filemapping
FileMapping := CreateFileMapping(FileHandle, nil, PAGE_WRITECOPY , 0, 0, nil);
2022-10-14 16:46:00 +02:00
if (FileMapping = 0) or (FileMapping=INVALID_HANDLE_VALUE) then
raise EFileMapError.create(rsMappingFailed);
2011-07-04 19:52:53 +00:00
2014-05-19 10:39:47 +00:00
//map it completely
2011-07-04 19:52:53 +00:00
FFileContent:= MapViewOfFile(FileMapping, FILE_MAP_COPY , 0, 0, 0);
if FFileContent=nil then raise EFileMapError.Create(rsFailedCreatingAProperView);
2011-07-04 19:52:53 +00:00
ffilename:=filename;
2011-07-04 19:52:53 +00:00
except
on e: exception do
begin
if (FileMapping<>0) and (filemapping<>INVALID_HANDLE_VALUE) then
CloseHandle(FileMapping);
if (FileHandle<>0) and (FileHandle<>INVALID_HANDLE_VALUE) then
CloseHandle(FileHandle);
raise EFileMapError.create(e.message);
2011-07-04 19:52:53 +00:00
end;
end;
end;
end.