PDA

Archiv verlassen und diese Seite im Standarddesign anzeigen : Geschwindigkeit bei Addition von Bytes



Ruppi
30.10.2005, 09:09
Hallo,
kann mir jemand erklären, warum eine einfache Byte-Addition, also A=A+B oder C=A+B gleich 9 Takte benötigt?

Danke, Ruppi

30.10.2005, 09:35
Wenn du es effektiver willst, benutze Assembler.

ldi r16,15
ldi r17,12
add r16,r17

das sind genau 3 Takte ...

PicNick
30.10.2005, 09:56
Lieber Gast, du schummelst.
Ruppi will zwei VARIABLEN addieren und dann auch irgendwo wieder finden.
d.h auch im Assembler mußt du die beidern Werte erstmal aus dem SRAM holen, DANN addieren und das Ergebnis wieder zurückschreiben.

SprinterSB
30.10.2005, 10:08
Selbst mit Laden und Speichern komm ich nur auf 7 Takte:
2*2 Laden
1 Addition
2 Speichern

Wenn ein Summand im Flash liegt und man ein LPM braucht, dann sind es schon 10 Takte.
2 Z-vorladen
3 LPM
2 Laden
1 Addiation
2 Speichern

Warum 9 Takte gebraucht werden, wird dir erst ein Blick in den erzeugten Code erhellen. So ist's nur rumgerate.

PicNick
30.10.2005, 10:22
Beim BasCom kommt's auf die Variable an.
Die längste Variante ist die (zum beispiel bei "local" Variablen), daß er das XH u. XL mir der Variablen-Adresse lädt und dann das Register mit LD reg, X
Grad bei Variablen im Frame bleibt ihm (oder dem Assembler) auch nix anderes übrig.

SprinterSB
30.10.2005, 11:43
Hmmm..., das wär aber ungeschickt von BasCom. BasCom weiß ja den Offset einer Variablen zum Framepointer. Da wäre das Y-Register besser geeignet -- falls überhaupt ein Framepointer gebraucht wird. Dann ginge das Laden mit

LD Rn, Y
bzw
LDD Rn, Y+offset

zumindest falls 0 <= offset < 64.

Ruppi
31.10.2005, 07:11
Moin,
leider verstehe ich nichts von Assembler aber es wäre schon interessant für mich. Ist es denn mit Hilfe von Assembler möglich, zu einer Variablen eine andere hinzuzuaddieren? Also in der Form A=A+B
Und noch was: kennt jemand eine gute Online Einführung in Assembler? Ich bin leider von Hochsprachen geprägt und habe das ganze Programmierprinzip von Assembler noch nicht verstanden.

Vielen Dank für Eure Hilfe!
MfG Ruppi

PicNick
31.10.2005, 07:54
@SprinterSB: Das ginge nicht, der Framepointer liegt oberhalb der (lokalen) Variablen
Wenn's interessiert, ich hab' mich da ein wenig ausgetobt:
https://www.roboternetz.de/wiki/pmwiki.php?n=Main.Bascomstack

SprinterSB
31.10.2005, 08:26
Mein Wissen über AVR-Assembler hab ich aus den Kurzbeschreibungen (xxxx-summary.pdf) und es gibt ein 'atmel instruction set' bei Atmel, aber dort haben die Dokumente blöde Bezeichnungen, die kann ich mir nicht merken. Ausserdem hab ich beim Proggen immer im Auge, was der avr-gcc so anstellt und ob er das macht, das ich meine.

Von Hochspachen kommst du auch an Assembler ran. Zumindest bei Ada, C und C++. Bei letzteren heisst das auch 'Inline Assembler', bei Ada darf nicht gemischt werden. Da muss eine ganze Funktion in Assembler sein.

Ein einfaches Beispiel ist (avr-gcc, GNU C)

__asm volatile ("nop");

nop (no operation) ist von C aus nicht direkt formulierbar, da muß inline asm her. Gleiches für sei oder cli um global IRQs zu aktivieren/deaktivieren.

#define sei() __asm__ __volatile__ ("sei" ::)

Eine Duko zu inline asm in winavr findest du in <AVR-GCC>/doc/avr-lib/avr-libc-user-manual-xxx.pdf

Zwei Werte Addieren würd ich in inline so hinschreiben:

__asm volatile ("add %0, %2" : "=r" (a) : "0" (a), "r" (b));

Dabei sind a, b Werte vom Typ unsigned char, b kann auch ne Konstante sein. Um die richtigen Reloads kümmert sich gcc.

Asm Tutorials findest du nach kräftigem durchgurgeln, zB http://www.avr-asm-tutorial.net/ Ob das gut ist musst du selber entscheiden. Zudem kursieren hier im Forum immer wieder Links von den Assembler-Freaks.

::Edit::

Und noch was: Assembler ist nicht Assembler. Der Assembler von AVR-Studio ist anders als der GNU Assembler Code, den avr-gcc für den avr-as generiert. Die Mnemonics für die Befehle dürften weitgehend gleich sein, aber bei Direktiven, Makrodefinition/Auflösung, Labeldefinition hörts endgültig auf. Und Lokatierungen die man in asm vom Studio sieht, gehen in avr-as auch nicht. Zum Lokatieren ist schliesslich der Linker/Locator avr-ld da!