Hallo zusammen, ich bin recht neu im bereich ic programirung in c und hoffe das ich hir richtig bin ;) ich habe ein Test Programm geschrieben mit dem mann verschieden schalter auslesen kann mein probel bestet zumindest darin das der ic eine bestimmet zeit lang etwas machen soll dazu das code beispiel : for (a = 0;a < 1000;a ++) { PORTB = 0b000000; PORTB = 0b001000;_delay_ms(1); if ( ! (PINB & (1<<PINB0)) ){ a;break;} if ( ! (PINB & (1<<PINB1)) ){ a;break;} } meine idee ist, dass die schleife solang bzw max 1000 msec. lang leuft, bis einer der schalter betätigt wird. Alles leuft sowiel aber die zeit ist nicht max. 1000 msec sondern deutlich merh so ca 5 sec oder mehr. meine idee war zuerst das ich mit #define F_cpu den programm akt ändere, aber ich kann die zahl dahinter veränder wie ich will, es andert sich nichs?! es würde mich sehr freun wenn ihr mir helfen könnts ;) mit freundlichen grüßen Sebastian
Häng' bitte deinen Sourcecode an, das Projekt bringt uns wenig :) Mal davon abgesehen, dass ich nicht wirklich versteh' was du vor hast... sebastian schrieb: > #define F_cpu den programm akt ändere, aber ich kann die zahl dahinter > veränder wie ich will, es andert sich nichs?! Ist der Wert vielleicht schon an anderer Stelle im AVR-Studio gesetzt? Bei den Projekteinstellungen oder so? PS: Kommentier' doch bitte deinen Code damit man erahnen kann was du vor hast.
ich habe vor einen kleinen Roboter zu bauen der erkennt wenn er gegen eine Wand fährt und dann dementsprechend reagiert. Da ich mir noch nicht sicher bin ob das überhaupt klappt (mit meinem bisherigen Kenntnissen ;) ) teste ich die groben Funktionen anhand einer led Schaltung ich programmiere in c mit dem AVR studio mit einem atmega8, der quell Code meines Versuches ist: /* * schalter_2.c * * Created: 08.04.2012 10:30:31 * Author: Sebastian */ #define F_CPU 1200000 #include <avr/io.h> #include <util/delay.h> int main(void) {DDRB = 0b001100; int a; while(1) { anfang: while(2) { if ( ! (PINB & (1<<PINB1)) )goto led1; if ( ! (PINB & (1<<PINB0)) )goto led2; } led1: for (a = 0;a < 1000;a ++) { PORTB = 0b000000; PORTB = 0b001000;_delay_ms(1); if ( ! (PINB & (1<<PINB0)) ){ a = a+1000;} if ( ! (PINB & (1<<PINB1)) ){ a = a+1000;} } PORTB = 0b0000000; goto anfang; led2: for (a = 0;a<1000; a ++) { PORTB = 0b000000; PORTB = 0b000100;_delay_ms(1); if ( ! (PINB & (1<<PINB0)) ){a = a + 1000;} if ( ! (PINB & (1<<PINB1)) ){a = a + 1000;} } PORTB = 0b000000; } } Ich kann stadt #define F_CPU 1200000 auch #define F_CPU 500000 schreiben oder die zeile sogar gans weglassen ohne das eine Veränderung im Programm auftritt
Hast du vielleicht vergessen die notwendige Optimierung beim Kompilieren einzuschalten? "Note: In order for these functions to work as intended, compiler optimizations must be enabled, and the delay time must be an expression that is a known constant at compile-time. If these requirements are not met, the resulting delay will be much longer (and basically unpredictable), and applications that otherwise do not use floating-point calculations will experience severe code bloat by the floating-point library routines linked into the application." http://www.nongnu.org/avr-libc/user-manual/group__util__delay.html
Schau mal in delay.h rein, ob da F_CPU nicht auch definiert wurde... Oder einfach eben mal so probieren: /* * schalter_2.c * * Created: 08.04.2012 10:30:31 * Author: Sebastian */ #define F_CPU 1200000 #include <avr/io.h> #include <util/delay.h> // hierhin verschieben #define F_CPU 1200000 int main(void)
FALSCH!!! Schreibfehler!!! /* * schalter_2.c * * Created: 08.04.2012 10:30:31 * Author: Sebastian */ #include <avr/io.h> #include <util/delay.h> #define F_CPU 1200000 // hierhin verschieben int main(void) So ist's fein!
also ich habe die standart einstellungen des compilers genommen und gelassen, da ich da noch nicht rumspielen will mit wäre auch nicht bewust wo ich solche einstllungen jetzt vornemen könnte auser bei den Fuses
Du kannst dein Programm C-typischer schreiben, wenn du auf goto verzichtest z.B. so
1 | /*
|
2 | * schalter_3.c
|
3 | */
|
4 | |
5 | #define F_CPU 1200000
|
6 | #include <avr/io.h> |
7 | #include <util/delay.h> |
8 | |
9 | #define LED1 PORTB3
|
10 | #define LED2 PORTB2
|
11 | #define TASTER1 PINB1
|
12 | #define TASTER2 PINB0
|
13 | |
14 | void led(int lednummer) |
15 | {
|
16 | PORTB &= ~((1<<LED1) | (1<<LED2)); // Beide LEDs aus |
17 | PORTB |= (1<<lednummer); // LED1 ein |
18 | for (int a = 0; a < 1000; a++) |
19 | {
|
20 | _delay_ms(1); |
21 | // Abbruch der for-Schleife bei Tastendruck
|
22 | if ( !(PINB & (1<<TASTER2)) || !(PINB & (1<<TASTER1))) |
23 | break; |
24 | }
|
25 | PORTB &= ~((1<<LED1) | (1<<LED2)); // Beide LEDs aus |
26 | }
|
27 | |
28 | int main(void) |
29 | {
|
30 | DDRB = (1<<PINB3)|(1<<PINB2); // LED1 und LED2 |
31 | |
32 | // TASTER1 und TASTER2 sind LOW aktiv
|
33 | // Interne Pull-Ups sind nicht aktiviert
|
34 | // d.h. externer Pull-Up Widerstand erforderlich
|
35 | |
36 | while(1) |
37 | {
|
38 | if ( !(PINB & (1<<TASTER2)) ) |
39 | led(LED1); |
40 | if ( !(PINB & (1<<TASTER1)) ) |
41 | led(LED2); |
42 | }
|
43 | }
|
Das Programm (Original oder verbessert) wird aber mehr schlecht als recht laufen, weil du 1/ nicht auf das Loslassen der Taste wartest und 2/ keine Entprellung vorhanden ist. Der AVR ist so rasend schnell, dass der die Wartezeit bereits abbricht, wenn du noch meinst, gerade eine Aktion auszulösen. Umgekehrt genauso - Du brichst die Wartezeit in der for-Schleife ab und der AVR ist im nächsten Moment bereits in der while-Schleife dran, eine neue Leuchtaktion zu starten, während dein Finger noch nicht mal auf dem Taster gezuckt hat! Das #define F_CPU 1200000 vor #include <util/delay.h> ist schon die richtige Reihenfolge, weil F_CPU in delay.h bereits benutzt wird.
> wo ich solche einstllungen jetzt vornemen könnte
Im AVRStudio 5:
- ALT-F7 drücken. Die Project-Properties werden angezeigt.
- Reiter "Toolchain" wählen.
- Menüpunkt "AVR / GNU C Compiler" anwählen.
- Untermenü "Optimization" anwählen.
- Rechts den gewünschten "Optimization Level" (Optimierungsgrad)
einstellen.
ich danke euch allen jetzt leut es richtig ! ich binn mir bewust das das was ich da geschrieben hab nicht sonderlich sauber ist weil ich erst seit 3 monaten mich mit c auseinander stetzt. aber was noch nicht ist kann noch werden :D ich werde mir zumindest deine code anschauen und schauen wie ich des übernemne kann und in zukunft draus lernen kann. aber für das kleine projekt was ich mir ausgedacht habe reicht das vollkommen das das progtamm bei einer taster berürung dirket in die while schleife geh danke nochmal Sebastian
Gibts compiler Warnungen? Sowas wie "F_CPU not defined in util/delay " ? Wenn nicht, nimm das #define F_CPU mal raus und schau ob es dann Warnungen gibt.
du weißt aber schon dass dein #define F_CPU zu den Fuse Einstellungen passen muss damit die Delay-Zeiten stimmen?
nein ich kriege bei keinem der meldungen wen ich was in der optimirung ändere wenn ich es rausneme kommt die warnung aber kein Fehler
ich schrieb: > #include <util/delay.h> > #define F_CPU 1200000 // hierhin verschieben Die Reihenfolge ist böser Unsinn. Wie soll delay.h mit der korrekten CPU Frequenz rechnen, wenn das entsprechende Define erst nach der Einbindung der Header-Datei erfolgt? In delay.h sind Vorkehrungen getroffen, das eine bereits definierte F_CPU nicht überschrieben wird. Außerdem schmeißt der Preprozessor eine Warnung, falls er dort auf den Default-Wert zurückgegreifen sollte.
1 | #ifndef F_CPU |
2 | /* prevent compiler error by supplying a default */ |
3 | # warning "F_CPU not defined for <util/delay.h>" |
4 | # define F_CPU 1000000UL |
5 | #endif |
Krapao schrieb: > #define F_CPU 1200000 Vermutlich paßt die Zahl nicht in den Datentyp. Probier's mal mit einem unsigned long Datentyp, d.h. #define F_CPU 1200000UL
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.