Hallo Zusammen, mein mega8 läuft mit einem 4MHz Quarz. Nach einigen Vorüberlegungen müsste folgender Code ein Delay von 15ms erzeugen for(i=0; i<=12000; i++) {}; genaugenommen sind es 15000,5 us Mein Compiler generiert mir nun jedoch folgenden ASM Code 74: 8f ed ldi r24, 0xDF ; 223 76: 9e e2 ldi r25, 0x2E ; 46 78: 04 97 sbiw r24, 0x04 ; 4 ^-- WARUM ? 7a: 97 ff sbrs r25, 7 7c: fd cf rjmp .-6 ; 0x78 7e: 08 95 ret Was ich nun nicht verstehe ist warum an der markierten Stelle eine 4 und keine 1 steht. (BTW. füge ich noch ein NOP im C-Code ein wird der Wert mit 1 richtig generiert) Was mache ich bzw. der compiler hier falsch? Danke schon mal, der Jochen
static void delay(uint16_t us) { /*Verzögerung in Microsekunden*/ while ( us ) us--; } main(){ ... while(15000)} /*bin mir nicht sicher ob es 14999 sein müssen*/ du brauchst dann noch #include <inttypes.h> #include <avr/inttypes.h> funktioniert bei mir nicht, hat dafür jemand ne erklärung?
Hallo Alex, die Funktion kenne ich. Das Problem ist aber immer noch was der C-Compiler daraus macht. Siehe hierzu folgendes: void delay(void) { /*Verzögerung in Microsekunden*/ int us; us = 800; 80: 80 e2 ldi r24, 0x20 ; 32 82: 93 e0 ldi r25, 0x03 ; 3 while ( us ) us--; 84: 49 97 sbiw r24, 0x19 ; 25 --> Hier kommt der Teil den ich nicht verstehe !!!!! 86: f1 f7 brne .-4 ; 0x84 } 88: 08 95 ret sbiw ist laut Datenblat: Subtract imidiate from word. So wie ich das sehe wird hier pro Schleifendurchlauf 19h also 25d abgezogen. D.h. die Schleife dauert nur 1/25 der Zeit die ich eigentlich erwarte. Nun ist die Frage warum ist das so bzw. wo ist mein Verständnissproblem. Der Jochen
Mit compiler kenne ich mich nicht aus, ich versuche daher alles in c zu programmieren. Wie übersetzt du den C-Code in Assembler??? Würde mich interessieren. Habe deine Frage falsch verstanden, ich dachte dein Prog macht nicht was du willst.
Hallo Alex, wenn Du den C-Code mit gcc übersetzt gibt es unter anderem ein .lst File. In diesem File kannst Du den ASM-Code den der C-Compiler erzeugt sehen. Ich will halt einfach sicher gehen das die delays die ich programmiere auch eingehalten werden. Deshalb hab ich mir den ASM Code mal angesehen. Der Jochen
Solche extrem langen Delays von 15ms würde ich immer mit einem Timer machen, entweder mit einem Interrupt oder Polling. Das ist genauer und vor allem vom Compiler unabhängig. Peter
Der Compiler darf mit leeren Schleifen machen, was er will (komplett wegnehmen, verändern, ...). Es Ändert sich ja nix (OK, die Laufzeit, aber das ist dem Compiler Wurscht). Hängt man ein NOP rein, ist alles OK. /Berndt
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
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.