Ja, das stimmt. bei meinem system ist der durch GetSystemAllocationGranularity ermittelte buffer sogar genau 64 kb groß.
das TMemoryMappedFile erstelle ich durch eine leicht von deiner version abgewandelte prozedur (ich habe mir z.b. die property fSize eingebaut):
Delphi-Quellcode:
constructor TMemoryMappedFile.Create(
const FileName:
String);
var
P: Pointer;
begin
fFileHandle := FileOpen(FileName, fmOpenRead
or fmShareDenyWrite);
if fFileHandle = INVALID_HANDLE_VALUE
then
raise Exception.Create(Format('
Datei %s konnte nicht geöffnet werden!', [Filename]));
//if fFileHandle > 0 then
if fFileHandle <> INVALID_HANDLE_VALUE
then
begin
fSize := GetFileSize(fFileHandle,
nil);
if fSize > 0
then
begin
fFileMap := CreateFileMapping(fFileHandle,
nil, PAGE_READONLY, 0, 0,
nil);
{
if fFileMap <> 0 then
begin
P := MapViewOfFile(
fFileMap,
FILE_MAP_READ,
0, // beginn der map
0, //
0); // zu lesende bytes, fSize liest kompl. Datei ein
if P <> nil then
inherited SetPointer(P, fSize);
end;
}
end;
end;
inherited Create;
end;
wie du siehst, frage ich im create nicht MapViewOfFile ab, da ich dies erst beim vergleich mache.
hier die vergleichs prozedur:
Delphi-Quellcode:
function Tmf.CompareMemoryMappedFiles(
const File1, File2:
String): Boolean;
var
MMF1, MMF2: TMemoryMappedFile;
P1, P2: Pointer;
CurPos: Int64;
AllocGran: Cardinal;
begin
Result := False;
AllocGran := GetSystemAllocationGranularity;
//Todo: hier raus nehmen, nicht bei jedem aufruf erneut abfragen
MMF1 := TMemoryMappedFile.Create(File1);
MMF1.Position := 0;
try
MMF2 := TMemoryMappedFile.Create(File2);
MMF2.Position := 0;
try
begin
CurPos := 0;
while CurPos < MMF1.Size
do
begin
P1 := MapViewOfFile(MMF1.fFileMap, FILE_MAP_READ, CurPos, CurPos + AllocGran, AllocGran);
P2 := MapViewOfFile(MMF2.fFileMap, FILE_MAP_READ, CurPos, CurPos + AllocGran, AllocGran);
if not CompareMem(P1, P2, AllocGran)
then //hier kriege ich die AV
Exit;
Inc(CurPos, AllocGran);
end;
Result := True;
end;
finally
MMF2.Free;
end;
finally
MMF1.Free;
end;
end;
allerdings bekomme ich bei CompareMem eine
AV. ich glaube ich übergebe entweder die Length von Comparemem nicht korrekt oder es hapert bereits bei der P1, P2 pointer zuweisung.
mein problem ist auch, dass ich durch MapViewOfFile nicht die Length kenne. daher übergebe ich AllocGran.