Forum: Mikrocontroller und Digitale Elektronik STM32F4 64 Bit Operation Dauer


von Nate (Gast)


Lesenswert?

Hallo alle zusammen!

Ich bin gerade dran auf einem STM32F4 board 64 bit operationen 
auszuführen (bitte nicht mit assembler anfangen, ich weiß das man damit 
das Problem lösen kann).

Ich führe eine einfache Addition in einer Schleife aus, hierbei ist zu 
beachten dass erstmal der Fall beachtet wird, bei dem e aus kleinen 
Zahlen besteht! Also wird Poly[j] vorerst (bis auf sonderfälle die hier 
nicht betrachtet werden) nicht größer als 32 bit. Bitte nicht fragen 
wieso 64 bit benutzt wird => wird für den Sonderfall benötigt.

int64_t Poly = {0};
int32_t e = ....; //mit Zahlen gefüllt, pos und negativ

for (uint16_t i = 0; i < PARAM_W; i++)
{
  for (uint16_t j = 0; j < PARAM_N; j++)
  {
    Poly[j] += e[PARAM_N - c[i] + j];
  }


c ist ein Array der Länge PARAM_W.

Wenn ich die Anzahl der benötigten clock cycles für den Schritt
Poly[j] += e[PARAM_N - c[i] + j];
mir ausgeben lasse auf dem STM32F4 board, variiert diese um 5 clock 
cycles!

Hier noch die Compiler Optionen/flags
-Wall -g -std=c99 -O3 mfloat-abi=softfp
Optimazation flag ändern ändert nichts, variiert trotzdem um 5 cc.

Hat jemand eine erklärung wieso das so ist? Warum dauert genau die selbe 
addition länger? Kann es sein, dass es der Fall ist, wenn Poly[j] durch 
die addition eines Wertes sich im Vorzeichen ändert? Woran könnte es 
sonst liegen?

Danke schon einmal für die Hilfe!

Beste Grüße
Nate

von (prx) A. K. (prx)


Lesenswert?

Nate schrieb:
> variiert diese um 5 clock cycles

Wie gemessen?

: Bearbeitet durch User
von Nate (Gast)


Lesenswert?

Ich meine damit, dass ich zwei verschiedene clock cycles bekomme für die 
Operation (164 und 159). langsamer oder schneller ist vom standpunkt 
abhängig ;)

von (prx) A. K. (prx)


Lesenswert?

Ist die Messung taktgenau per SysTick ohne Teiler, oder spielt da I/O 
mit hinein?

von Nate (Gast)


Lesenswert?

Gemessen mit dem Data Watchpoint and Trace (DWT) Unit

von (prx) A. K. (prx)


Lesenswert?

Nate schrieb:
> Ich meine damit, dass ich zwei verschiedene clock cycles bekomme für die
> Operation (164 und 159).

Für die Schleife oder für die Operation?
Für die einzelne Operation wärs zu viel.

von Nate E. (nate24)


Lesenswert?

So sorry, bin der selbe hab mich nur angemeldet.

Nur für die Operation. Messe die clock cycles mit:

*DWT_CYCCNT = 0;
*DWT_CONTROL = *DWT_CONTROL | 1 ;

und lese nach der Operation DWT_CYCCNT aus

Beitrag #5134717 wurde vom Autor gelöscht.
von (prx) A. K. (prx)


Lesenswert?

Für ein paar Loads mit Additionen ist das zu viel.
Da spielt noch mehr mit.

Der Generierte Asm-Code der Schleife mitsamt der DWT Operationen wäre 
sinnvoll.

: Bearbeitet durch User
von Nate E. (nate24)


Lesenswert?

Ahh sorry mein Fehler, es bezieht sich nicht auf die Addition. Die Frage 
bezieht sich auf die Modulo Operation danach.

for(uint16_t i = 0; i< PARAM_N; i++)
{
w[i] = Poly[i] % PARAM_Q;
}

Tut mir Leid für den Fehler.
Die Modulo Operation dauert unterschiedlich lange, unabhängig ob es ein 
negativer oder ein positiver Wert ist.

: Bearbeitet durch User
von Sebastian K. (sek)


Lesenswert?

Die Modulo Operation verwendet DIV, falls der Compiler dies nicht 
wegoptimiert bekommt. Und der braucht für die Abarbeitung 
unterschiedlich lange, 2-12 Cycles.

von Nate E. (nate24)


Lesenswert?

Sebastian K. schrieb:
> Die Modulo Operation verwendet DIV, falls der Compiler dies nicht
> wegoptimiert bekommt. Und der braucht für die Abarbeitung
> unterschiedlich lange, 2-12 Cycles.

Danke! Das erklärt meine Frage :)

von rmu (Gast)


Lesenswert?

Nate schrieb:
> Ich meine damit, dass ich zwei verschiedene clock cycles bekomme für die
> Operation (164 und 159). langsamer oder schneller ist vom standpunkt
> abhängig ;)

164 oder 159 zyklen für eine Operation finde ich auch exzessiv, ASM wär 
interessant.

5 Zyklen Unterschied können aber schon möglich sein. Es wird zu einer 
64bit-Zahl eine 32bit-Zahl dazugezählt, die durchgeführten Operationen 
sind auch nur 32bit breit. Kommt es also zu einem "Überlauf" wenn man 
die untersten 32bit addiert, dann muss man den Überlauf in die oberen 
32bit dazurechnen, gibts keinen Überlauf kann das (addieren von 0) 
entfallen.

von (prx) A. K. (prx)


Lesenswert?

rmu schrieb:
> 164 oder 159 zyklen für eine Operation finde ich auch exzessiv,

Für eine 64-Bit MOD Operation vielleicht nicht.

von Jim M. (turboj)


Lesenswert?

rmu schrieb:
> Kommt es also zu einem "Überlauf" wenn man
> die untersten 32bit addiert, dann muss man den Überlauf in die oberen
> 32bit dazurechnen, gibts keinen Überlauf kann das (addieren von 0)
> entfallen.

Und so kommt man dann auf die 5 Takte, denn auch das Laden und Sichern 
der oberen 32 Bits entfallen dann.

Denn:

Lade Register: 2 Takte
Inkrementiere Register: 1 Takt
Speichere Register: 2 Takte
========
Summe: 5 Takte

Und die 3 Instruktionen müssten auch ein einen IT Block passen, und 
Cortex M4 kennt IT Folding.

Fazit: Der Compiler war wieder mal deutlich cleverer als der 
Programmierer...

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.