mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik Festkommamultiplikation mit ARM


Autor: harald (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ich habe eine Frage.

Hintergrund:

Mit einem ARM7TDMI berechne ich einiges (mit Additionen und 
Multiplikationen) und nehme dazu Fließkommazahlen (32 bit) bzw 
Festkommazahlen (32bit).

Mein ARM hat keine FPU und deshalb ist Floatingpoint relativ langsam.
Falls ich die Berechnungen mit Festkommazahlen implementiere sind diese 
"nur" 2 mal so schnell.

Ich dachte ursprünglich, dass Festkommaimplementierungen sehr viel 
schneller sind. An den Additionen kann es nicht liegen, da diese 
"gleich" sind wie normale Integer.

Bei den Multiplikationen verwende ich als Zwischenergebnis eine 64 bit 
Zahl und schiebe anschließend zurück.

#define fmult(A,B) (long)(((long long)A * (long long)B) >> KOMMASTELLEN)

Zur eigentlichen Frage:
Wie kann ich die Multiplikation verbessern?

Autor: harald (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
nachdenk

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Festkommamultiplikation ist ganz praktisch, wenn man Hardware-Support 
für ganzzahlige Multiplikation hat. Bis rauf zu 32x32=64bit hat ARM das 
in Form eines Befehls, aber mit 64x64=64bit kann ARM nicht dienen und 
damit wird es komplizierter. Klüger wär's wohl, diesen 32x32=64bit 
Befehl auch zu nutzen, wenn man sowieso nicht mehr als den braucht.

Im GCC kann man das beispielsweise recht wirkungsvoll mit
inline long fmult(long x, long y)
{
  long long r;
  asm ("smull %0,%H0,%1,%2" : "=&r"(r) : "r"(x), "r"(y));
  return r >> KOMMASTELLEN;
}

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Bei 64x64bit hast du eine Laufzeitfunktion an der Backe, die nicht viel 
einfacher aussieht als die einer Fliesskommamultiplikation.

Autor: harald (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Vielen Dank A.K.! Es ist ja super, dass es dafür einen extra Befehl 
gibt.

Ich habe gesehen, es gibt auch den  "smlal" Befehl, könntest du mir kurz 
skizzieren, wie ich den mit dem "asm" benutzen kann?

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
static inline long long
smull(long x, long y)
{
  long long r;
  asm ("smull %0,%H0,%1,%2" : "=&r"(r) : "r"(x), "r"(y));
  return r;
}

static inline long long
smlal(long x, long y, long long sum)
{
  asm ("smlal %0,%H0,%1,%2" : "+r"(sum) : "r"(x), "r"(y));
  return sum;
}

Autor: harald (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Super, vielen Dank. Ich probiere es morgen aus und schaue ob es 
schneller wird.

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.