AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Thema durchsuchen
Ansicht
Themen-Optionen

Zwei Hexwerte tauschen

Ein Thema von magoo2002de · begonnen am 15. Apr 2004 · letzter Beitrag vom 15. Apr 2004
Antwort Antwort
magoo2002de

Registriert seit: 26. Mär 2003
60 Beiträge
 
Delphi 2005 Personal
 
#1

Zwei Hexwerte tauschen

  Alt 15. Apr 2004, 13:13
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!
  Mit Zitat antworten Zitat
bttb930

Registriert seit: 6. Okt 2003
372 Beiträge
 
#2

Re: Zwei Hexwerte tauschen

  Alt 15. Apr 2004, 13:37
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;
  Mit Zitat antworten Zitat
magoo2002de

Registriert seit: 26. Mär 2003
60 Beiträge
 
Delphi 2005 Personal
 
#3

Re: Zwei Hexwerte tauschen

  Alt 15. Apr 2004, 13:43
Vielen Dank!
Ich werde es gleich einmal ausprobieren!
  Mit Zitat antworten Zitat
Benutzerbild von nTE
nTE

Registriert seit: 8. Sep 2003
60 Beiträge
 
#4

Re: Zwei Hexwerte tauschen

  Alt 15. Apr 2004, 14:16
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:
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;
Erklärung:

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. ^^
  Mit Zitat antworten Zitat
magoo2002de

Registriert seit: 26. Mär 2003
60 Beiträge
 
Delphi 2005 Personal
 
#5

Re: Zwei Hexwerte tauschen

  Alt 15. Apr 2004, 14:37
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:
- Man nehme einen Hexeditor und öffnet die BIN-Datei
- Nach Hex 12027702 suchen
- Darunter steht dann 12027726
- Diese Werte miteinander tauschen
- Datei abspeichern und fertig ist die Liste
Dies möchte ich nun von meinem Programm erledigen lassen. Sprich, ich wähle die Datei aus und mein Programm sucht automatisch nach den Werten und tauscht diese.
  Mit Zitat antworten Zitat
Benutzerbild von nTE
nTE

Registriert seit: 8. Sep 2003
60 Beiträge
 
#6

Re: Zwei Hexwerte tauschen

  Alt 15. Apr 2004, 15:19
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.
  Mit Zitat antworten Zitat
magoo2002de

Registriert seit: 26. Mär 2003
60 Beiträge
 
Delphi 2005 Personal
 
#7

Re: Zwei Hexwerte tauschen

  Alt 15. Apr 2004, 15:32
Vielen Dank nTE! Ich werde es gleich einmal probieren!
  Mit Zitat antworten Zitat
Benutzerbild von nTE
nTE

Registriert seit: 8. Sep 2003
60 Beiträge
 
#8

Re: Zwei Hexwerte tauschen

  Alt 15. Apr 2004, 16:14
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.
  Mit Zitat antworten Zitat
Benutzerbild von glkgereon
glkgereon

Registriert seit: 16. Mär 2004
2.287 Beiträge
 
#9

Re: Zwei Hexwerte tauschen

  Alt 15. Apr 2004, 19:30
was heisst tauschen???
heisst das das:
Delphi-Quellcode:
procedure tausch(a, b:*hexwert*):*hexwert*
var c:*hexwert*
begin
c:=a;
a:=b;
b:=c;
end;
oder was?
»Unlösbare Probleme sind in der Regel schwierig...«
  Mit Zitat antworten Zitat
Benutzerbild von glkgereon
glkgereon

Registriert seit: 16. Mär 2004
2.287 Beiträge
 
#10

Re: Zwei Hexwerte tauschen

  Alt 15. Apr 2004, 19:36
also, wohlgemerkt, erst einlesen, und dann wieder inne datei rein, wobei das auch so ginge:

Delphi-Quellcode:
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;
kann sein das man statt der memo auch ne richedit nehmen muss...

oder hab ichs falsch verstanden???
»Unlösbare Probleme sind in der Regel schwierig...«
  Mit Zitat antworten Zitat
Antwort Antwort


Forumregeln

Es ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks are an
Pingbacks are an
Refbacks are aus

Gehe zu:

Impressum · AGB · Datenschutz · Nach oben
Alle Zeitangaben in WEZ +1. Es ist jetzt 00:27 Uhr.
Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz