Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Programmieren allgemein (https://www.delphipraxis.net/40-programmieren-allgemein/)
-   -   Problem in Assembler: Grundrechenarten (https://www.delphipraxis.net/64827-problem-assembler-grundrechenarten.html)

der olli 8. Mär 2006 19:01


Problem in Assembler: Grundrechenarten
 
Hi!

Wir programmieren in der Schule momentan Assembler in Delphi. Zu nächster Stunde sollen wir ein Programm, welches die Grundrechenarten beherrscht (- Addieren, Subtrahieren, Multiplizieren und Dividieren -), schreiben, sollen uns das Wissen allerdings selber aneignen.
Addition und Subtraktion habe ich bereits geschafft zu programmieren, allerdings hänge ich nun bei der Syntax für die Multiplikation und die Division (- es soll geprüft werden, ob durch 0 dividiert wird -) - und da wir erst letzte Stunde mit dem Thema angefangen haben, weiß ich leider nicht so recht, wie ich es richtig machen soll. Es hängt wohl irgendwie damit zusammen, dass ich mit Integer arbeite ... Ich poste einfach mal den Quellcode:
Delphi-Quellcode:
var
  Form1: TForm1;
  x, y : Integer;

implementation

{$R *.DFM}

procedure TForm1.Button1Click(Sender: TObject);
begin
 x := StrToInt(InputBox('Eingabe','Erste Zahl',''));
 y := StrToInt(InputBox('Eingabe','Zweite Zahl',''));
end;

procedure TForm1.bt_beendenClick(Sender: TObject);
begin
 Form1.Close
end;

procedure TForm1.Button2Click(Sender: TObject);  // Addition
var h : Integer;
begin
 h := y;
 asm
  mov EAX, x
  add h, EAX
 end;
 ShowMessage('Ergebnis: ' + IntToStr(h))
end;

procedure TForm1.Button3Click(Sender: TObject);  // Subtraktion
var h, h2 : Integer;
begin
 h := y;
 h2 := x;
 asm
  mov EAX, h
  sub h2, EAX
 end;
 ShowMessage('Ergebnis: ' + IntToStr(h2))
end;

procedure TForm1.Button4Click(Sender: TObject);  // Multiplikation
var h, h2 : Integer;
begin
 h := y;
 h2 := x;
 asm
  mov EAX, h
  // fmul h2, EAX
 end;
 ShowMessage('Ergebnis: ' + IntToStr(h2))
end;

procedure TForm1.Button5Click(Sender: TObject);  // Division
var h, h2 : Integer;
begin
 h := y;
 h2 := x;
 asm
  mov EAX, h
  idiv h2, EAX
 end;
end;
Wie ihr seht, bin ich bei den beiden Prozeduren noch nicht allzu weit gekommen (- Fehlermeldung: Ungültige Kombination von Opcode und Operanden -) ... Ich hoffe, mir kann jemand bei der Lösung helfen!

Gruß,
Olli

Ben 9. Mär 2006 10:51

Re: Problem in Assembler: Grundrechenarten
 
Hallo,

ich bin ganz und gar kein Assembler-Profi, allerdings kann ich dir sagen, dass fmul nur Fließkommazahlen vom Real-Typ verarbeiten kann. Eine Multiplikation in Assembler würde etwa so gehen:

Delphi-Quellcode:
var
  g,h: Real;
begin

  g := x;
  h := y;

  asm
    fld g
    fmul h
    fstp h
  end;
end;
Kurze Erklärung: die Variable g wird in den FPU-Speicher geladen und mit h multipliziert, abschließend wird h gespeichert.

Was die Division angeht, so kann ich dir nicht helfen, Google spuckt aber das hier aus.

Mit freundlichen Grüßen,
Ben

BlackJack 9. Mär 2006 11:07

Re: Problem in Assembler: Grundrechenarten
 
ich denke mal es wird um die multiplikation und division von integern gehen. dabei hilft dir (oh wunder ;) ) imul und idiv. zu beachten bei den beiden ist, dass sie nur einen integer als "parameter" bekommen, den anderen int muss man vorher in EAX (oder war's EDX :gruebel:) packen, der wird dann implizit benutzt. das ergebniss steht dann in EDX:EAX (d.h. wenn das ergebniss nicht in nen Integer passt, werden die "überstehenden" bits in EDX gepackt).

das ganze bezieht sich jetzt auf vorzeichenbehaftete zahlen (wies Integer nunmal sind), wenn du mit vorzeichenlose zahlen rechnen willst, nimmst du einfach mul/div statt imul/idiv.

edit:
ich hab grad nochmal nachgeschaut, beim idiv ist es etwas anders. da ist nachher in EAX das ergebniss der division und in EDX der Rest. das ganze läuft also für einen Integer so ab:

Code:
imul Int: EDX:EAX := EAX * Int
idiv Int: EAX := EAX div Int / EDX := EAX mod Int
edit2: hier ein link zu nem Opcode-PDF: http://www.jegerlehner.ch/intel/IntelCodeTable.pdf

edit3: beim idiv ist es nochmal anders, da steht der 1. operand in EDX:EAX. also so:
Code:
idiv Int: EAX := EDX:EAX div Int / EDX := EDX:EAX mod Int

brechi 9. Mär 2006 11:17

Re: Problem in Assembler: Grundrechenarten
 
Delphi-Quellcode:
asm
  mov eax, 8
  mov ecx, 2

  {CDQ erweitert das EAX-Register vorzeichengerecht auf 64 Bit
  und speichert das Ergebnis im Registerpaar EDX:EAX.
  Eine vorzeichengerechte Erweiterung bedeutet,
  daß Bit 31 des EAX-Registers in alle Bits des EDX-Registers geschrieben wird.
  Mit Hilfe von CDQ kann die Division eines DWords durch ein
  anderes DWord vorbereitet werden.
  }
  cdq
  {IDIV dividiert das AX-REGISTER bzw. das Registerpaar DX:AX
  durch den Quelloperanden unter Berücksichtigung des Vorzeichens.}
  idiv ecx
  //eax ganzzahl
  //edx rest
  //
  //http://www.fh-wedel.de/~bek/asm/befehle1.html
end;


Alle Zeitangaben in WEZ +1. Es ist jetzt 12:38 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