Hallo,
bei meinem LPC1768 Cortex-M3 in Kombination mit meiner GCC 4.4.1
Toolchain (Linux) habe ich heute ein komisches Verhalten entdeckt, wenn
Fließkommazahlen in Modulen auftauchen. Es geht dabei um folgende
Beispielfunktion:
1
voiddemo_fail(unsignedlongp1,unsignedlongp2){
2
log("STEP 1");
3
doublef=0.0,d=1.0;
4
5
log("STEP 2");
6
f=(double)p1/(16.0*(double)p2*d);
7
8
log("STEP 3");
9
if(f<=1.1||f>=1.9){
10
11
log("STEP 4");
12
for(f=1.1;f<=1.9;f+=0.1)
13
d++;
14
}
15
16
log("STEP 5");
17
}
Ist diese Funktion innerhalb meiner main.c, funktioniert deren Aufruf
"demo_fail(1,1)" komplett. Ist sie hingegen in ein Modul ausgelagert,
ist "STEP 2" die letzte Ausgabe, die ich sehe (also hängt die
double-Berechnung).
Übersetzt wird das Ganze fehlerfrei mit:
eine Funktion log zu benennen halte ich nicht für gut, denn in math.h
gibt es ja: double log(double x) natürlicher Logarithmus ln(x), x > 0
vielleicht liegt da der Fehler.!?
Da habe ich beim Vereinfachen des Codes nicht nachgedacht. Ich habe die
Funktion nur der Einfachheit halber hier log() genannt (auch wenn ich
nicht gegen die libmath linke). Das ist also nicht das Problem. :)
Das kannst du mir ruhig glauben, ich habe eine eigens übersetzte
Toolchain und absichtlich keine libc und libmath... wieso glaubst du,
dass es damit funktioniert? Das sieht mir irgendwie eher nach einem Bug
aus.
Ich meine vor laaanger zeit hatte ich mal ein ähnliches Problem. Kann
mich nur noch dunkel daran erinnern. Erst mit dem Einbinden ging es
dann.
Im Setup von Codesourcery werden die Libs mit installiert.
Das kommt mir bekannt vor, ich kann mich ebenso dunkel an einen Fall
erinnern, bei dem das Funktionieren von der Position der libgcc in der
Parameterliste abhing.
Leider scheint das hier nicht der Fall zu sein, ich habe es gerade mit
der Codesourcery Toolchain gemäß deinem Vorschlag versucht, das Ergebnis
ist aber leider dasselbe. Trotzdem danke für die Idee.
Ich habe meine Formel wegen der Geschwindigkeit umgebaut. Du könntest
vielleicht eine Float-Zahl wandeln in eine s32, dann berechnen, dann
wiederzurück in Float. Ich weiß ja nicht wie komplex Deine Formeln sind,
bzw. ob Du cos/sin Funktionen brauchst.
PS: Versuche es doch mal mit dem Datentyp float un nicht mit double.
Versteh mich bitte nicht falsch, aber mir geht's da eher ums Prinzip.
Falls es tatsächlich ein Bug ist, ist er in den aktuellen Versionen auch
noch vorhanden. Habe mittlerweile folgende Kombinationen durch:
gcc 4.4.1 / binutils 2.19.1
gcc 4.4.1 / binutils 2.19.51.20090709 (Sourcery)
gcc 4.5.0 / binutils 2.20
Mit "float" kommt er immerhin zu "STEP 3".
Halte ich zwar für unwahrscheinlich dass es daran liegt, aber trotzdem:
Prober mal statt -O3 lieber -O2 oder -O0 (zumindest testweise), evtl.
ist das schlicht ein Compilerbug oder sowas in der Richtung.
Außerdem könnten die Optionen die du beim bauen der Toolchain verwendet
hast eine Rolle spielen (also nicht nur die Optionen mit denen du den
Compiler aufrufst), z.B. --with-float=soft u.ä.
Und/oder probier auch mal eine andere toolchain-Version um festzustellen
ob es evtl. ein Compilerbug in dieser Version ist.
HTH, Uwe.
Unterschiedliche Optimierungsstufen habe ich schon hinter mir und
unterschiedliche Toolchains auch, siehe oben. Die Toolchains sind wie
folgt konfiguriert:
Eduard Steinberg schrieb:> ich habe eine eigens übersetzte> Toolchain und absichtlich keine libc und libmath...
Weshalb eigentlich selbst übersetzt?
Gibt es nichts fertiges für dich?
Evtl. hättest du dir den Ärger sparen können aber jetzt hast du
was gelernt ;-)
Ich hab's doch auch mit der Toolchain von CodeSourcery versucht, doch
auch da muss man nun mal gegen die thumb2-libgcc linken... ;-) Zum Thema
selbst übersetzen: ich habe da einfach die bessere Kontrolle über
diverse Einstellungen (z.B. SMALLMEM bei der newlib).
Vieleicht eine division durch 0? Ja ich weiss, sollte es ned sein,
berechne den Divident und Divisior vor und schau ob diese 0 sind...
Ansonsten wäre ein direkter vergleich der Disassemblies interessant (als
Modul vs. in Main, mit dem gleichen Compiler...)