![]() |
Zwei Hexwerte tauschen
Hallo!
Ich habe zwar schon gesucht aber irgendwie nicht das richtige gefunden. Und zwar möchte in einer Datei zwei Hexwerte miteinander tauschen. Ist dies mit Delphi möglich? Und wenn ja, kann bitte jemand einen Code-Beispiel posten, wie man das machen kann? Vielen Dank schon einmal für eure Hilfe! |
Re: Zwei Hexwerte tauschen
geht glaube ich so:
Delphi-Quellcode:
procedure SwapHexValues(const aFileName, aOutFileName: string; const HexPos1, HexPos2: LongInt);
var InStream, OutStream: TFileStream; Hex: Byte; begin if HexPos2 < HexPos1 then SwapHexValues(aFileName, aOutFileName, HexPos2, HexPos1) else begin if not FileExists(aFileName) then exit; InStream := TFileStream.Create(aFileName, fmOpenRead); OutStream := TFileStream.Create(aOutFileName, fmCreate); InStream.Position := 0; OutStream.CopyFrom(InStream, HexPos1 - SizeOf(Hex)); InStream.Position := HexPos2; OutStream.CopyFrom(InStream, SizeOf(Hex)); InStream.Position := HexPos1 + SizeOf(Hex); OutStream.CopyFrom(InStream, HexPos2 - HexPos1 - SizeOf(Hex)); InStream.Position := HexPos1; OutStream.CopyFrom(InStream, SizeOf(Hex)); InStream.Position := HexPos2 + SizeOf(Hex); OutStream.CopyFrom(InStream, InStream.Size - HexPos2 - SizeOf(Hex)); OutStream.Free; InStream.Free; end; end; |
Re: Zwei Hexwerte tauschen
Vielen Dank!
Ich werde es gleich einmal ausprobieren! |
Re: Zwei Hexwerte tauschen
Da ich glaube, dass du Patchen meinst, bringe ich mal ein wenig alten Code von mir.
Allerdings habe ich das mit API-Calls gelöst:
Delphi-Quellcode:
Erklärung:
const
sPatchFile = 'ToPatch.bla'; NumBytesToWrite = 1; WhereToWrite : Array[1..NumBytesToWrite] of Longint = ($4B9A0, $4B9A1); var i : Integer; NumWritten : DWORD; hFile : THandle; BytesToWrite : Array[1..NumBytesToWrite] of Byte = ($00,$00); begin hFile := CreateFile(sPatchFile, GENERIC_WRITE, 0, nil, 3, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL); if hFile = DWORD(-1) then // Fehler, Datei nicht gefunden else begin for i := 1 to NumBytesToWrite do begin if SetFilePointer(hFile, WhereToWrite[i], nil, FILE_BEGIN) <> WhereToWrite[i] then begin NumWritten := 0; break; end; WriteFile(hFile, BytesToWrite[i], 1, NumWritten, nil); if NumWritten = 0 then // etwas ging schief beim Schreiben, NumWritten müsste immer 1 sein break; end; if NumWritten = 1 then // Patchen war erfolgreich else // Patchen ist fehlgeschlagen end; end; CloseHandle(hFile); end; hFile := CreateFile(sPatchFile, GENERIC_WRITE, 0, nil, 3, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL); CreateFile liefert ein FileHandle zurück, welches hFile zugewiesen wird (zur weiteren Arbeit mit der Datei bei SetFilePointer und WriteFile). Der 1. Parameter ist der Name der Datei, der 2. die Zugriffsmethode (GENERIC_WRITE, weil ja nur geschrieben werden soll), der 3. Parameter gibt den Freigabemodus an (d.h. ob andere Programme zur gleichen Zeit auf die Datei zugreifen dürfen) und ist auf nicht freigeben (also exklusiven Zugriff) gestellt. Der 4. Parameter steht für einen Zeiger auf eine Struktur vom Typ SECURITY_ATTRIBUTES, welcher verwendet werden kann um einem Kindprozess das Filehandle zu übergeben, aber da das nicht benötigt wird ist der Wert "nil". Der 5. Parameter sagt was gemacht werden soll, wenn die Datei schon existiert/noch nicht existiert, ich verwende OPEN_EXISTING, weil ja nur dann gepatcht werden soll, wenn die Datei existiert. Der 6. Parameter ist FILE_ATTRIBUTE_NORMAL, weil das für diese Zwecke ausreichen sollte. *g* SetFilePointer(hFile, WhereToWrite[i], nil, FILE_BEGIN); hFile steht für das Filehandle, an 2. Stelle die Position in der Datei an die der Datei-Zeiger gesetzt werden soll (damit WriteFile nicht einfach nur an den Anfang der Datei schreibt). Der 3. Parameter ist ein Zeiger auf das mögliche High-DWORD um Dateien mit Grössen über 4 GB zu unterstützen. Das ist hier nicht der Fall, daher ist der Parameter "nil", aber wenn man es benutzen wollte, dann müsste man eben einen Pointer auf eine DWORD (Cardinal)-Variable übergeben, da in diese dann auch das High-DWORD der neuen Position in der Datei geschrieben wird. Der 4. Parameter ist auf FILE_BEGIN, weil ja vom Anfang der Datei aus "losgegangen" werden soll. Zurückgegeben wird die neue Position in der Datei, welche mit WhereToWrite[i] verglichen wird um festzustellen ob alles geklappt hat. (Wenn ich sage "Setze an Position x vom Anfang der Datei aus gesehen", dann sollte die neue Position ja auch Position x sein. ;) WriteFile(hFile, BytesToWrite[i], 1, NumWritten, nil); hFile ist mal wieder das Filehandle, BytesToWrite[i] ist das Array mit den Byte-Werten die geschrieben werden sollen, der 3. Parameter steht für die Anzahl der Bytes die geschrieben werden sollen (also 1). Der 4. Parameter ist die Variable die Aufnehmen soll wieviele Bytes geschrieben wurden. (Sollte in diesem Falle immer 1 sein, außer es ging was schief.) Der 5. Parameter ist nur dann in Verwendung, wenn FILE_FLAG_OVERLAPPED genommen wird wo ich bei CreateFile FILE_ATTRIBUTE_NORMAL habe. Dass das jetzt die beste Lösung, wage ich zu bezweifeln, aber funktionieren tut es. :P Vielleicht habe ich dich aber auch nur falsch verstanden in dem was du bezwecken willst. Für diesen Fall würde ich dir an's Herz legen, dein Problem näher zu beschreiben, vielleicht auch mit Beispielen, da du sicher weißt was du willst, andere aber nicht immer. ^^ |
Re: Zwei Hexwerte tauschen
Also ich lade mir immer eine Programmliste für meinen Satelittenreceiver aus dem Internet. Die Liste muss aber immer mit einem Hexeditor noch geändert werden. Dazu habe ich folgende "Anleitung" erhalten:
Zitat:
|
Re: Zwei Hexwerte tauschen
Dann schau dir dazu noch ReadFile (API, ist WriteFile sehr ähnlich) und ändere bei CreateFile auf GENERIC_READ + GENERIC_WRITE.
Dazu musst du dir nur noch überlegen wieviele Bytes du mit einem Mal aus der Datei lesen willst, um dann nach dem Vorkommen der Hexwerte zu suchen, um den Filepointer an die richtige Stelle zu setzen. |
Re: Zwei Hexwerte tauschen
Vielen Dank nTE! Ich werde es gleich einmal probieren!
|
Re: Zwei Hexwerte tauschen
Bittschön. =)
Aber mir ist gerade eingefallen warum ich die API-Calls verwendet habe. Weil ich keine Delphi-Units einbinden wollte um die Größe der Exe klein zu halten. :P All das geht auch mit den Abkapslungen dieser Calls in Delphi: BlockRead/BlockWrite für ReadFile/WriteFile Seek für SetFilePointer (FilePos um den "Rückgabewert" zu überprüfen) AssignFile + Reset für CreateFile CloseFile für CloseHandle Dafür solltest du dann auch Beispiele und Erklärungen in der Delphi-Hilfe finden. |
Re: Zwei Hexwerte tauschen
was heisst tauschen???
heisst das das:
Delphi-Quellcode:
oder was?
procedure tausch(a, b:*hexwert*):*hexwert*
var c:*hexwert* begin c:=a; a:=b; b:=c; end; |
Re: Zwei Hexwerte tauschen
also, wohlgemerkt, erst einlesen, und dann wieder inne datei rein, wobei das auch so ginge:
Delphi-Quellcode:
kann sein das man statt der memo auch ne richedit nehmen muss...
procedure tausch(position1, position2, laenge:integer);
var i:integer; hilfswert:char; begin memo1.lines.loadfromfile('wasweiss.ich'); for 1:=position1 to position1+laenge do begin position2:=position2+1; //muss ja beides erhöht werden :-D //eigentliches tauschen hilfswert:=Memo1.lines.text[position1]; memo1.lines.text[position1]:=memo1.lines.text[position2]; memo1.lines.text[position2]:=hilfswert; //eigentliches tauschen zuende end; memo1.lines.savetofile('wasweiss.ich'); end; oder hab ichs falsch verstanden??? |
Alle Zeitangaben in WEZ +1. Es ist jetzt 15:27 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz