Hallo Hobby-Elektroniker, Ich habe z.Z. mit meinem AVR-Board das Phänomen, das mein Programm nur korrekt läuft wenn der mkII-Programmer ange- schlossen ist. mC: Atmega 168A, Board: my-MCU mkII (V2.20) , AtmelStudio 7 Hier mein Code, er dient zum Testen von PWM-Funktionen und läuft anstandlos durch (bei angestecktem Programmer) /* * 2018_MotorTreiberAnsteuerung.c * Code Funktioniert Stand_04 (beendet:30.3.2018) */ /*---------------------------------------------------------------------- -----------------*/ /* * Created: 11.03.2018 23:00:26 * * Entwicklungsumgebung: Atmel Studio 7 (7.0.1417) Compiler u. Linker * sind enthalten, lauft auf Windows 8.1 (64bit) * Author : Dirk U_ */ #define F_CPU 8000000 /* 8 MHz (Externer Quarz Resonator) */ /* Fuses: High: 0xD9 ; Low: 0xCD ; Extendet: 0xF9 */ #include <avr/io.h> #include <avr/wdt.h> /* Watch Dog Timer Funktionalitaeten */ #include <util/delay.h> #include <stdbool.h> /* bool'schen Datentyp verwendbar machen */ #define VOR 0x1 /* 0x0 == vorwaerts, 0x0 == rueckwaerts */ #define PWM_1_DDR DDRB #define PWM_2_DDR DDRB #define PWM_1_PORT PORTB #define PWM_2_PORT PORTB #define PWM_1_PIN PB3 /* PWM_REG_1_1 8-Bit Timer Reg. A (ATm168A) */ #define PWM_2_PIN PB4 /* OCR2B 8-Bit Timer Reg. B (ATm168A) */ #define PWM_REG_1 OCR2A /* PB3 bei ATm168A */ bool TEST_mode = true; bool OP_mode_1 = false; /*---------------------------------------------------------------------- -----------------*/ typedef struct { uint8_t vor_oder_zurueck ; uint8_t prozent_max_Umin ; } DCmotor_t; DCmotor_t motor_1 ; /*----------------- L O C A L -- P R O T O T Y P E S ------------------------------------*/ uint8_t Test_mode_execute( void ) ; // Ausfuehrungs-Fktn in Hauptschleife uint8_t Op_mode_1_execute( void ) ; // Ausfuehrungs-Fktn in Hauptschleife void Pause_in_Sek( unsigned short int x_sek_pause); // getestet (in Stand_03), funktioniert. void IO_init_MotorDriverPins(uint8_t pwm1_or_pwm2_or_beide); // Para: 1, 2, oder 3 // getestet (in Stand_03), funktioniert. void PWM_Timer2_ATm168_init(uint16_t pwm_vorteiler); //Vorteiler legt f v. PWM fest void inline PWM_1_Off( void ); void inline PWM_1_Start( void ); void inline PWM_1_SET_DutyCycle(uint16_t pwm_1_dutyCycle); void inline WDT_Off( void ) ; // Watchdog Ausschalten // Watchdog zu Ausloesewert konfigurieren und anschalten extern void wdt_enable(const uint8_t value) ; /* Start: main ########################################################### Start: main */ int main(void) /* Stand_04 */ { wdt_enable(WDTO_60MS); /* Watchdog enabel, WDT-Zeit: 60 milli-sek.*/ IO_init_MotorDriverPins( 1 ); /* 1 == PWM_1 auf Pin PB3 */ PWM_Timer2_ATm168_init ( 256 ); /* Prescaler = 256*/ /* WDT aus ; 3 Sek. Pause ; WDT Ein*/ WDT_Off() ; Pause_in_Sek( 3 ); wdt_enable(WDTO_60MS); PWM_Timer2_ATm168_init ( 1024 ); /* Prescaler = 1024*/ /* WDT aus ; 3 Sek. Pause */ WDT_Off(); Pause_in_Sek( 3 ); PWM_1_Start(); Pause_in_Sek( 1 ); /* Test der Start/Off Funktionen */ PWM_1_Off(); Pause_in_Sek( 1 ); PWM_1_Start(); Pause_in_Sek( 1 ); PWM_1_Start(); wdt_enable(WDTO_60MS); /* Start: Hauptschleife ------------------------------------------- Start: Hauptschleife */ while (1) /* Stand_04 */ { wdt_reset(); if ( TEST_mode == true ){ /* Test Modus */ Test_mode_execute(); } if ( OP_mode_1 == true ){ /* Operations Modus 1 */ Op_mode_1_execute(); } } /* Ende: Hauptschleife- - - - - - - - - - - - - - - - - - - - - - - - Ende: Hauptschleife*/ return 0; } /*Ende: main # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # Ende: main */ uint8_t Test_mode_execute( void ){ PWM_1_SET_DutyCycle( 25 ) ; /* 25 Proz. Duty-Cycle */ /* WDT aus ; 3 Sek. Pause ; WDT Ein*/ WDT_Off(); Pause_in_Sek( 3 ); wdt_enable(WDTO_60MS); PWM_1_SET_DutyCycle( 75 ) ; /* 75 Proz. Duty-Cycle */ /* WDT aus ; 3 Sek. Pause ; WDT Ein*/ WDT_Off(); Pause_in_Sek( 3 ); wdt_enable(WDTO_60MS); return 0; /* Spaetere Fehler Rueckgabe geplant */ } uint8_t Op_mode_1_execute( void ){ ; return 0; /* Spaetere Fehler Rueckgabe geplant*/ } void Pause_in_Sek( unsigned short int x_sek_pause){ if( x_sek_pause < sizeof( unsigned short int ) && ( x_sek_pause >= 0) ){ #define YES 1 } else { #define NO 0 } #ifdef YES for( unsigned short int i =0; i < x_sek_pause; i ++ ){ _delay_ms(200); _delay_ms(200); _delay_ms(200) ; _delay_ms(200); _delay_ms(200) ; } #undef YES #else #error "Wert ist <0 oder zu gross !!" #undef NO #endif } /* Ende Funktion: Pause_in_Sek */ void IO_init_MotorDriverPins( uint8_t pwm1_or_pwm2_or_beide ){ if (pwm1_or_pwm2_or_beide == 1 ){ PWM_1_DDR |= (1 << PWM_1_PIN); } else if (pwm1_or_pwm2_or_beide == 2 ){ PWM_2_DDR |= (1 << PWM_2_PIN); } else if (pwm1_or_pwm2_or_beide == 3 ){ PWM_1_DDR |= (1 << PWM_1_PIN); PWM_2_DDR |= (1 << PWM_2_PIN); } else { ; /* zukuenftig evtl. Fehlerwert setzen */ } } /* Ende Funktion: IO_init_MotorDriverPins */ void PWM_Timer2_ATm168_init ( uint16_t pwm_vorteiler ){ TCCR2B = ((1<<CS21) | (1<<CS20)); /*Clock select*/ TCCR2A = ((1<<COM2A1) | (1<<WGM21) | (1<<WGM20)); /*Waveform generation mode*/ #define ATM_168A 10 /* Einige Comp. meckern wenn einer define kein Wert zugew.*/ #ifdef ATM_168A /* Atmega 168A, ..ist zu klären fuer welche uC noch gilt */ #define VORTEILER_REG TCCR2B #define BIT_1 CS20 #define BIT_2 CS21 #define BIT_3 CS22 #undef ATM_168A #endif /* The PWM frequency for the output can be calculated by the following equation: * Frequ.PWM = (clk_I/O) : (256 * N) * N represents the prescale divider (1, 8, 64, 256, or 1024). */ /*---------------------------------------------------------------------- -----------------*/ if ( pwm_vorteiler == 1024 ){ VORTEILER_REG &= ~(1<< BIT_2 ); /* immer: erst loeschen (&=~), dann setzen (|=).*/ VORTEILER_REG |= (1<< BIT_1 ); VORTEILER_REG |= (1<< BIT_3 ); } if ( pwm_vorteiler == 256 ){ VORTEILER_REG &= ~(1<< BIT_1 ); VORTEILER_REG &= ~(1<< BIT_2 ); VORTEILER_REG |= (1<< BIT_3 ); } if ( pwm_vorteiler == 64 ){ VORTEILER_REG &= ~(1<< BIT_3 ); VORTEILER_REG |= (1<< BIT_1 ); VORTEILER_REG |= (1<< BIT_2 ); } if ( pwm_vorteiler == 8 ){ VORTEILER_REG &= ~(1<< BIT_1 ); VORTEILER_REG &= ~(BIT_3 ); VORTEILER_REG |= (1<< BIT_2 ); } if ( pwm_vorteiler == 1 ){ VORTEILER_REG &= ~(1<< BIT_2 ); VORTEILER_REG &= ~(1<< BIT_3 ); VORTEILER_REG |= (1<< BIT_1 ); } #undef VORTEILER_REG #undef BIT_1 /* PB3 <- OCR2A (ATm168A)*/ #undef BIT_2 #undef BIT_3 PWM_REG_1 = 127 ; /* Default Duty Cycle von OC2A = 50 Prozent*/ } /* ____ Ende Funktion: PWM_Timer2_ATm168_init __________*/ void inline PWM_1_Off (void) { /* Normale Port Operation, OCR2A disconnected.*/ TCCR2A &= ~COM0B0; TCCR2A &= ~COM0B1; /* Ok tested auf ATm168A */ } void inline PWM_1_Start (void) { TCCR2A = ( TCCR2A | COM0B0 ); /* Ok tested auf ATm168A */ TCCR2A = ( TCCR2A | COM0B1 ); } void inline PWM_1_SET_DutyCycle (uint16_t pwm_1_dutyCycle ){ /* pwm_1_dutyCycle == Duty Cycle in Prozent */ /* PWM_REG_1 8-Bit Timer Reg. B (ATm168A) */ /* Wert zuweisen u. Groessenbegrenzung auf 2^8 == 256. */ switch ( pwm_1_dutyCycle ) { case 0: PWM_REG_1 = 0; break; case 1: PWM_REG_1 = 3; break; case 2: PWM_REG_1 = 4; break; /**/ case 3: PWM_REG_1 = 7; break; case 4: PWM_REG_1 =10; break; case 5: PWM_REG_1 =13; break; /**/ case 6: PWM_REG_1 =15; break; case 7: PWM_REG_1 =18; break; case 8: PWM_REG_1 =20; break; /**/ case 9: PWM_REG_1 =23; break; case 10: PWM_REG_1 =26; break; case 11: PWM_REG_1 =28; break; /**/ case 12: PWM_REG_1 =31; break; case 13: PWM_REG_1 =33; break; case 14: PWM_REG_1 =36; break; /**/ case 15: PWM_REG_1 =38; break; case 16: PWM_REG_1 =41; break; case 17: PWM_REG_1 =43; break; /**/ case 18: PWM_REG_1 =46; break; case 19: PWM_REG_1 =48; break; case 20: PWM_REG_1 =51; break; /**/ case 21: PWM_REG_1 =54; break; case 22: PWM_REG_1 =56; break; case 23: PWM_REG_1 =59; break; /**/ case 24: PWM_REG_1 =61; break; case 25: PWM_REG_1 =64; break; case 26: PWM_REG_1 =66; break; /**/ case 27: PWM_REG_1 =69; break; case 28: PWM_REG_1 =71; break; case 29: PWM_REG_1 =74; break; /**/ case 30: PWM_REG_1 =77; break; case 31: PWM_REG_1 =79; break; case 32: PWM_REG_1 =82; break; /**/ case 33: PWM_REG_1 =84; break; case 34: PWM_REG_1 =87; break; case 35: PWM_REG_1 =89; break; /**/ case 36: PWM_REG_1 =92; break; case 37: PWM_REG_1 =94; break; case 38: PWM_REG_1 =97; break; /**/ case 39: PWM_REG_1 =99; break; case 40: PWM_REG_1 =102; break; case 41: PWM_REG_1 =105; break; /**/ case 42: PWM_REG_1 =107; break; case 43: PWM_REG_1 =110; break; case 44: PWM_REG_1 =112; break; /**/ case 45: PWM_REG_1 =115; break; case 46: PWM_REG_1 =118; break; case 47: PWM_REG_1 =120; break; /**/ case 48: PWM_REG_1 =122; break; case 49: PWM_REG_1 =125; break; case 50: PWM_REG_1 =128; break; /**/ case 51: PWM_REG_1 =130; break; case 52: PWM_REG_1 =133; break; case 53: PWM_REG_1 =135; break; /**/ case 54: PWM_REG_1 =138; break; case 55: PWM_REG_1 =141; break; case 56: PWM_REG_1 =143; break; /**/ case 57: PWM_REG_1 =145; break; case 58: PWM_REG_1 =149; break; case 59: PWM_REG_1 =150; break; /**/ case 60: PWM_REG_1 =153; break; case 61: PWM_REG_1 =156; break; case 62: PWM_REG_1 =158; break; /**/ case 63: PWM_REG_1 =161; break; case 64: PWM_REG_1 =164; break; case 65: PWM_REG_1 =166; break; /**/ case 66: PWM_REG_1 =168; break; case 67: PWM_REG_1 =171; break; case 68: PWM_REG_1 =173; break; /**/ case 69: PWM_REG_1 =176; break; case 70: PWM_REG_1 =179; break; case 71: PWM_REG_1 =181; break; /**/ case 72: PWM_REG_1 =184; break; case 73: PWM_REG_1 =186; break; case 74: PWM_REG_1 =189; break; /**/ case 75: PWM_REG_1 =191; break; case 76: PWM_REG_1 =194; break; case 77: PWM_REG_1 =196; break; /**/ case 78: PWM_REG_1 =199; break; case 79: PWM_REG_1 =201; break; case 80: PWM_REG_1 =204; break; /**/ case 81: PWM_REG_1 =206; break; case 82: PWM_REG_1 =209; break; case 83: PWM_REG_1 =212; break; /**/ case 84: PWM_REG_1 =214; break; case 85: PWM_REG_1 =217; break; case 86: PWM_REG_1 =219; break; /**/ case 87: PWM_REG_1 =222; break; case 88: PWM_REG_1 =224; break; case 89: PWM_REG_1 =227; break; /**/ case 90: PWM_REG_1 =230; break; case 91: PWM_REG_1 =232; break; case 92: PWM_REG_1 =235; break; /**/ case 93: PWM_REG_1 =237; break; case 94: PWM_REG_1 =240; break; case 95: PWM_REG_1 =242; break; /**/ case 96: PWM_REG_1 =245; break; case 97: PWM_REG_1 =247; break; case 98: PWM_REG_1 =250; break; /**/ case 99: PWM_REG_1 =253; break; case 100: PWM_REG_1 = 0xFF; break; default: PWM_REG_1 = 25; break; /* 1/10 PWM im Default Fall, To Do Fehlerbit setzen */ } } /* Ende Funktion: PWM_1_SET_DutyCycle */ /*---------------------------------------------------------------------- -----------------*/ /* W A T C H D O G T I M E R * zur Absicherung gegen "Haengenbleiben" des uC durch evtl. Fehler */ void inline WDT_Off( void ) { /* Diese Funktion disabelt den WDT */ WDTCSR = ( (1<<WDCE) | (1<<WDE) ); WDTCSR = 0x00; } /* EOF / Stand_04 */
Dirk U. schrieb: > Ich habe z.Z. mit meinem AVR-Board das Phänomen, das mein > Programm nur korrekt läuft wenn der mkII-Programmer ange- > schlossen ist. Mach mal einen Pullup-Widerstand an den Reset Pin des AVR.
@ Andi: Er läuft mit einer im Low-Bereich verwaschenen PWM, die ändert sich auch nicht, keine Programmabarbeitung erkennbar.
@ Axel: Habe es doch jetzt gleich mal probiert, 2k also recht niederohmig als PullUp an Reset , leider der gleiche Fehler..
Dirk U. schrieb: > Ja das werde ich heute Abend probieren Zunächst solltest du mal lernen die Hinweise die bei jedem Posten gezeigt werden zu lesen, zu verstehen und danach zu handeln. Zum besseren Verständnis habe ich dir im Anhang die Regeln nochmal mitgegeben. Solltest du sie nicht verstehen und/oder nicht danach handeln können dann solltest du auch das Programmieren sein lassen. Es hat schon Sinn hier nicht das grosse Chaos ausbrechen zu lassen.
Der Pull-Up kam mir auch als erstes in den Sinn, allerdings sollte sein AVR Board den ja sinnvollerweise mitbringen. Du verwendest für die PWM Steuerung ja den Port-B. Das ist bei dem uC auch der ISP Port. Kann es sein, dass Du bei Deiner Schaltung auf das Taktsignal des AVR-ISP angewiesen bist? Das hier ist Dein Board, oder? http://www.myavr.info/download/produkte/myavr_board_mk2/techb_schaltplan-myavr-board-mk2-usb.png
@ Regeln Erklärbär: Ich werde den Hinweis bei meinem nächsten post beachten, Vielen Dank für den Hinweis.
@Andi: Jawoll, das ist mein board ... Ist eine Idee dass sich ISP Pin x mit PWM-Pin überschneidet. Aber: Es wird doch erst der mC programmiert, dann läuft die PWM, Ich meine da hat doch der Programmer gar nix mehr zu wollen, oder!? Aber sicher ein Versuch ist es wert, einen anderen Pin zu nutzen.
Dirk U. schrieb: > Ich werde den Hinweis bei meinem nächsten post beachten, > Vielen Dank für den Hinweis. Immerhin bist du hier schon so lang angemeldet dass dir die Regeln schon mal in Auge gestochen sein müssten.
Hallo, zeig mal ein Bild Deiner Schaltung und der Platine. Ich glaube nicht, dass es ein Softwareproblem ist, da die Software ja nach Deinen Aussagen mit angeschlossenem ISP funktioniert. Gruß Frank
Ist das das gesamte Programm? Zwei Dinge fallen mir spontan ein: 1. Timing (debuggst du das Programm, wenn der MK2 eingesteckt ist, oder lässt du es ganz normal laufen?) 2. printf: Falls du ein printf (oder ähnlich) in deinem Code verwendest, kann es auch sein, dass es ohne Debugger nicht funktioniert.
Der AVR isp mkII hat kein DebugWire. Ich tippe auf fehlenden Massebezug oder fehlenden Reset-Pull-Up-Widerstand.
Walter T. schrieb: > Ich tippe auf fehlenden Massebezug > oder fehlenden Reset-Pull-Up-Widerstand. Ich tippe auf dilettantischen Aufbau, das Board ist nicht bekannt. Dirk U. schrieb: > Ich habe z.Z. mit meinem AVR-Board Dirk U. schrieb: > mC: Atmega 168A, Board: my-MCU mkII (V2.20) Ein g* Suche ergibt kein erkennbares Board. Dilettantismus erkennt man auch daran dass man seine Verhältnisse nicht klar darstellen kann, selbst auf Nachfrage. Und wenn mit "Board: my-MCU mkII (V2.20)" der AVR ISP MKII gemeint sein soll, .... na dann bestätigen sich nur meine Vorurteile ...
Das board ist bekannt, Schaltplan oben verlinkt, PullUp vorhanden.
Ok, also, anbei ein Foto des Aufbaus Getauscht wurde von mir der 7805 gegen einen neuen, der alte war scheinbar defekt. Es liegen 5V am mC an. Die zwei Wiederstände die über den mC gehen( sieh Bild) sind der (zusätzliche) Pull-Up von Reset. Nachgemessen von mir, Reset auf + Pegel. links im Bild dann eine angesteckte Laborplatine mit Anschlusss für ein LCD - wird z.Z. nicht genutzt. Das Board ist das MK2 der Marke "myMCU" (früher "myAVR") http://shop.mymcu.de/Systemboards%20und%20Programmer/myAVR%20Board%20MK2,%20bestückt.htm?sp=article.sp.php&artID=40
Habe jetzt zum Test ein anderes Programm draufgespielt. Es funktioniert mit und ohne angestecktem Programmer.
Hier noch ein Bild des Aufbaus (von einen anderen Programm), es läuft ein Programm zur Drehimpulsgerber Auswertung und Visualisierung mittels 4 x 20 LCD. Wie bereits gesagt, keine Probs mit oder ohne angestecktem Programmer.
Nun gut - als nächste Schritte werde ich den Controller mal tauschen, nur zum Test , ausserdem einen nicht zu den ISP-Pins gehörenden Pin als Ausgang benutzen ...
Hast Du die Möglichkeit eine zusätzliche LED anzusteuern um zu prüfen ob Dein Controller nicht ständig ein Reset durchführt? Ansonsten, würde ich damit beginnen, die ganzen WDT Aufrufe auszukommentieren und das Programm immer weiter zureduzieren bist Du den Fehler gefunden hast. Gruß Frank
:
Bearbeitet durch User
Tipp: Der MKII macht am Anfang immer 2 Resets mit einer halben Sekunde Pause nacheinander. Vielleicht kommt bei Deinem Programm eine Initialisierung zu zeitig, so dass sie mit MKII beim zweiten Mal funktioniert, ohne MKII aber nicht greift. Hatte ich auch schonmal bei einem Display, mit MKII alles gut, ohne MKII war das Display noch nicht bereit für die Init-Sequenz.
Karl schrieb: > Der MKII macht am Anfang immer 2 Resets Nein, macht er nicht immer, sondern nur dann, wenn die Spannung an der Schaltung, in die er gesteckt ist, eingeschaltet wird. Dann gibt er der Schaltung einen Moment, um die Spannung zu stabilisieren und macht dann einen Reset, um seine Treiber auf den Pegel einzustellen.
Meiner macht das auch, wenn er gerade am USB angesteckt wird. Und beim Neuschreiben macht er auch zwei Resets: Schreiben und Verify. Kann aber sein, dass das bei verschiedenen Firmware-Versionen unterschiedlich ist.
Ja, erst einmal Danke an Frank, Karl und Thomas und alle anderen konstruktiven Hobbyfreunde. Werde die Tipps einmal in den nächsten Tagen ausprobieren. Ja der Wachhund ... allerdings kommt der nicht im Programmgetrieb mit ISP angesteckt... vllt. wird der durch den angesteckten Programmer "unterdrückt"? --- Auf alle Fälle sinnvoll den mal rauszunehmen ...
So hier der aktuelle Code, ohne Watchdog ohne Funktionen, mit Toggeln einer LED, mit 2. PWM-Ausgabe auf einen Pin der nicht zu den ISP-Pins gehört. Leider die selben Probleme.
Inzwischen habe ich noch weitere Tests gemacht: 1. Satt dem myMCU MK2 - Board ein Arduino Uno R3 -> Fehler in Hardware ausschliessen 2. Anderer Mikrocontroller, statt ATm168A ein ATm328P 3. Eine leere Warteschleife vor allem anderen Code eingefügt (ca. 1 Sekunde) Auch das Alles ohne Erfolg. Weitere Ansätze meinerseits - evtl. falsch gesetzte Fuses allerdings lief der mC ja mit den in meinem Code angegebenen Fuses einwandfrei ... - Firmware Update des AVRISP mkII MfG, Dirk
Hallo, einige haben ja meinen Code vom gestrigen (2.4.) post herunter geladen. Jetzt interessiert mich natürlich brennend ob das Programm bei euch die gleichen Probleme hervorruft wie bei mir... Ich freue mich auf Rückmeldung! MfG, Dirk
Wie stellst du fest, dass die PWM nicht funktioniert? Vermutlich mit einem Messgerät. Welches? Und wie ist es mit deiner Schaltung verbunden. Ganz besonders interessiert mich die Masse Verbindung. Dein Hinweis darauf, dass das Signal "verwaschen" sei, mach mich hellhörig. Lass mich raten: Du hältst die Spitze eines Tastkopfes von deinem Oszilloskop an den Ausgang des Mikrocontrollers und hast Dir über die Masse Verbindung keine Gedanken gemacht - sprich: nicht vorhanden.
Ich messe mit einem Oszi, Nee nee, Masseverbindung ist da ...
Hast Du denn die Möglichkeit den Code mal bei Dir zu probieren ?
> Masseverbindung ist da
Sicher? Überprüfe es. Vielleicht hast dein Kabel einen Bruch.
Dirk U. schrieb: > So hier der aktuelle Code, ohne Watchdog > ohne Funktionen, mit Toggeln einer LED, mit 2. PWM-Ausgabe > auf einen Pin der nicht zu den ISP-Pins gehört. > Leider die selben Probleme. Das hier: #define F_CPU 8000000 gehört nicht in ein c- oder h-File sondern in das Makefile. Bevor Du mit dem Programm startest, füge mal ein _delay_ms(10) ein:
1 | int main(void) { |
2 | _delay_ms(100); // warten bis alle Spannungen stabil sind |
3 | PWM_1_DDR = (PWM_1_DDR | (1 << PWM_1_PIN )); /* PWM 1 */ |
R-Masse mC-Board zu Oszi-Buchse: 1,5 Ohm das mit dem #define F_CPU habe ich schon in einigen Büchern so gesehen und es hat bisher auch zum Erfolg geführt. Es geht ja nur darum der delay-Routine den Takt bekannt zu geben. Ich werde es trotzdem ausprobieren ...
Dirk U. schrieb: > Es geht ja nur darum der delay-Routine den Takt bekannt zu geben. Genau. Und der Compiler steuert die Übersetzung der Files. Kannst Du garantieren, dass main.c zuerst übersetzt wird oder nicht vielleicht doch irgendwo noch ein anderes F_CPU deklariert ist?
Seltsam, das Programm funktioniert jetzt, aber ich weiss nicht eindeutig was die Ursache war. Habe alle _delay_ms durch Warteschleifen ersetzt. Schön ist sowas freilich nicht, weil der mC für die Zeit der Schleife völlig blockiert ist( ausser f. Interrupts). Aber ich glaube bei _delay_ms/us ist das auch der Fall. Am #define F_CPU lag es nicht, dass steht für mich fest. Folgendes habe ich noch getestet mit diesem Ergebnis: 1. Programmer USB-seitig am Rechner abziehen bei mC unter Spannung, und laufendem Programm (war sonst nie Problem): -> Programm läuft nicht. 2. Prog. läuft mit angestecktem Programmer; Spannungsvers. aus; 5s warten, Programmer USB-seitig abziehen, Spannungsvers. einschalten -> Programm läuft nicht. 3. Prog. läuft mit angestecktem Programmer; Spannungsvers. aus; 5s warten, Programmer mC -seitig abziehen, Spannungsvers. einschalten -> Programm LÄUFT.
> Aber ich glaube bei _delay_ms/us ist das auch der Fall.
Korrekt. Für gesparte zeit bekommst du kein Geld zurück. Also wenn es in
dieser Anwendung nicht stört, dann lass einfach so.
Für fortgeschrittene Anwendungen ohne Delay-Schleifen schreibt man
endliche Automaten in Kombination mit einem System-Timer.
Eventuell steigt die Spannungsversorgung beim Einschalten nicht schnell
genug an oder sackt dabei sogar nochmal ab. In beiden Fällen hilft es,
den Brown-Out Detektor zu benutzen oder einen großen Kondensator am
Reset Pin zu verwenden. Der muss dann aber weg, wenn man via ISP
programmieren will.
Jup, da gebe ich Dir auch Recht, die _delays waren nur da, um die Verschiedenen Funktionen für die PWM-Ansteuerung zu testen und die Änderungen von PWM-f und PW besser sichtbar zu machen.
Tja, jetzt läuft es zwar, aber Du weist immer noch nicht was der Fehler war.
Dirk U. schrieb: > R-Masse mC-Board zu Oszi-Buchse: 1,5 Ohm Miss mal ohne µC Die Verbindungen vom Spannungseingang der Platine zu den *VCC und *GND Pins im µC-Sockel, wenn du solche Probleme hast. Könnte auch ein defekter Abblockkondesator and der Versorgung sein (die 100nF Dinger). Wenn der keine Verbindung oder Kapazität hat und der Controller was tut, was kurzzeitig viel Strom zieht, dann kann der abstürzen. Bei einfachen Platinen lösen sich die Kupferbahnen gerne mal, wenn man auf die Bauteile drückt.
Ja pete77, das stimmt und ist unbefriedigend. Safari, ich werde auch deine Vermutung prüfen. Vpp U-Regler --- U-Pin AVR: 0,25 Ohm Masse U-Regler --- GND AVR: 0,22 Ohm Allerdings gibt es ja mit einem anderen Programm da nicht solche Probleme -> mein post vom 31.3. Drehimpulsgeber auswerten. In dem genannten Prog gibt es auch #define F_CPU am Programmanfang, sowie _delay_ms in der Hauptschleife. Ich werde mich melden wenn ich neue Erkenntnisse habe. Gruss, Dirk
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.