AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Zurück Delphi-PRAXiS Tutorials Delphi Inline ASM für Win32 - Einsteiger Crashkurs
Tutorial durchsuchen
Ansicht
Themen-Optionen

Inline ASM für Win32 - Einsteiger Crashkurs

Ein Tutorial von Balu der Bär · begonnen am 7. Okt 2006 · letzter Beitrag vom 1. Mai 2007
Antwort Antwort
Benutzerbild von sirius
sirius

Registriert seit: 3. Jan 2007
Ort: Dresden
3.443 Beiträge
 
Delphi 7 Enterprise
 
#1

Re: Inline ASM für Win32 - Einsteiger Crashkurs

  Alt 5. Feb 2007, 12:45
Schönes Tut
(Ich bin nur zufällig durch deine Signatur hierher gekommen. Manchmal ist man aber auch neugierig...)

Was einen Anfänger verwirren könnte ist folgende Zeile:
Delphi-Quellcode:
function ShowText : PChar;
asm
  JMP @start
  @test: DB 'Hallo Du!', 0
  @start: LEA EAX, @test
  RET
end;
Du sprichst davon, dass hinter dem Label test eine Variable steht. Das könnte für Frustration sorgen, da die Speicherseiten in die der Code am Anfang geladen werden, "nur" mit 'Execute and Read' ausgestattet sind. Demnach kann man da nicht speichern und demnach ist es keine Variable sondern eine Konstante. Stört in deiner Funktion ja auch nicht weiter, denn du greifst ja nicht schreibend auf diese Speicherplätze zu.
Aber der eine oder andere könnte ja auf die Idee kommen, auf diese Art lokale Variablen anzulegen. Und das klappt nicht (==>Frustration).


Also müsste man (insofern du überhaupt willst) etwas über lokale Variablen erzählen (EBP+Stack)


Oder, man holt ganz weit aus (da ich im Erklären/Tut schreiben nicht so gut bin, nehme ich lieber gleich Code):
Delphi-Quellcode:
var MBI: TMemoryBasicInformation;
    tmp:integer;
    memory:pointer;
begin
  memory:=@Showtext;
  VirtualQuery(memory, MBI, SizeOf(MBI));
  Virtualprotect(memory,mbi.RegionSize,page_execute_readWRITE,@tmp);
...und verändert einfach die Zugriffsrechte auf die Speicherseiten.
Jetzt könnte man mit "mov byte ptr [eax],64" aus Dem "H" von Hallo ein "A" machen.


Oder man legt die Funktion in einen neu alloziierten Speicherbereich und tobt sich da aus (inkl. selbst modifiziertem code)

Delphi-Quellcode:
program Pasm;

{$APPTYPE CONSOLE}

uses windows;


//Die Assembler-Routine mit einer statischen/lokalen Variable hinter @1
//Hier wird der Parameter c entsprechend mit add (oder sub) zur statischen Variable @1 gerechnet und zurückgegeben
function testasm(c:integer):integer;
asm
     jmp @2 //Variable überspringen

 @1: dd 10 //unsere 32bit-Variable (static)

 @2: call @3 //Addresse von @1 in edx speichern
 @3: pop edx
     sub edx,9

     add eax,[edx] //@1 zu c addieren

     //Speichern des Ergebnisses in @1
     mov [edx],eax //normalerweise: EAccessViolation;
                    //aber wir dürfen ja in unserem eigenen Speicherbereich (siehe VirtualAlloc)schreiben
     
     {Hier wäre eigentlich soweit Schluss, aber man kann ja auch noch etwas rumspielen ;-)
      und mal einen Befehl verändern}

     // verändern von "add eax,[edx]" zu "sub eax,[edx]"
     // =>verändern von $0302 zu $2B02
     //und natürlich auch wieder zurück
     add edx,13 //Addresse auf den add-Befehl errechnen
     cmp byte ptr [edx],$03 //gucken, was drinn ist
     je @4
     mov byte ptr [edx],$03 //und ändern
     ret
 @4: mov byte ptr [edx],$2b //oder eben wieder zurückändern
end;

//wird als Referenz benötigt um "size" zu bestimmen
procedure dispatch;
asm
  nop
end;

var memory:pointer;
    size:cardinal;
    result:integer;
    i:integer;
begin

  //function testasm in eine neue Speicherseite kopieren -->memory
  size:=cardinal(@dispatch)-cardinal(@testasm); //Größe der Funktion testasm ermitteln
  memory:=Virtualalloc(nil,size,MEM_COMMIT,PAGE_EXECUTE_READWRITE); //Ich will auf meinem neuen Speicherbereich (memory)
                                                                    //ausführen,lesen und schreiben
  movememory(memory,@testasm,size); //copy

  //kleine Test-Schleife
  for i:=1 to 10 do begin
    asm
      mov eax,i
      call memory
      mov result,eax
    end;
    writeln(result);
  end;

  //folgende Zeile würde hier so nicht funktionieren
  //writeln(testasm(2));

  virtualfree(memory,size,MEM_DECOMMIT);
  readln;
end.

Es reicht fürs erste sicherlich aus dem Wort Variable in deinem Tut "Konstante" zu machen Für die Einführung in asm würde alles weitere nur verwirren.


Edit: Wie langweilig, wäre doch das Leben ohne Fehler; Ich habe mal eine sinnlose Variable aus dem zweiten CodeSchnippsel von mir entfernt.
Edit2: Fehler über Fehler (im code zum ändern von add und sub)
Dieser Beitrag ist für Jugendliche unter 18 Jahren nicht geeignet.
  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 06:13 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