Hi, I'm new to microcontroller programming and am trying to get a Mega2560 running at 16Mhz to move a servo back and forth. I'm trying to controller the servo by letting the timer do all the work and for some reason I am having problems. I am curious as to whether or not this can be done without using interrupt handeling. My understanding is that when I set the Port to output, OC1A should be updated automatically. The idea is to clear OC1A when upcounting and set it again when downcounting. By changing the value of OCR1A, I should be able to change the pulse width. Unfortunately, it doesn't work in the simulator, which doesn't suprise me since the winavr simulator seems to have a number of bugs in it, but it doesn't work on my 2560 properly either. I'd appreciate any help. #include<avr/io.h> #ifndef F_CPU #warning "F_CPU war noch nicht definiert!" #define F_CPU 16000000UL #endif #include <util/delay.h> void main (void) { //Set testFactor to 1 for real life or to a higher value //to speed up the simulation int testFactor=1; //ICR1 and OCR1A are divided by this value //Initialize PORTB PORTB=0b00100000; //start with OC1A high DDRB= 0xFF; //set OC1A to output (among others) //Initialize Timer/Counter 1 //System Clock as source //Mode 8: Phase and Freq. Correct PWM top=ICR1 //OC1A output: Non-inverted //OC1B output: currently disabled //OC1C output: currently disabled ICR1=20000/testFactor; OCR1A=1000/testFactor; //set 1ms pulse 1000=1ms 2000=2ms TCCR1A=(1<<COM1A1);//COM1A1 Clear OCnA when match counting up,Set on down TCCR1B=(1<<WGM13)|(1<<CS11);// Phase and Freq correct ICR1=Top while (1) { OCR1A = 1000; //leave servo at min rotation _delay_ms(1000); OCR1A = 2000; //leave serve at max rotation _delay_ms(1000); }; }
:
Moved by Admin
>Unfortunately, it doesn't work in the simulator, >which doesn't suprise me since the winavr simulator seems to have a >number of bugs in it If you refer to simulavr, I would not call it "bugs". simulavr does not simulate any of the peripheral units at all. Beside that, I do not see any real problems in your code. If the 2560 is running at 16MHz, it should produce a suitable output. Did you check, if the clock frequency is actually 16MHz? External crystal in place? Fuses programmed accordingly? Oliver
Hi Oliver, thank you very much for having a look. I've been looking at the fuse bits and they have the following values BODLEVEL disabled OCDEN unchecked JTAGEN unchecked SPIEN checked WDTON unchecked EESAVE unchecked BOOTSZ Flash size = 4096 words start address=$1F000 BOOTRST checked CKDIV8 unchecked CKOUT unchecked SUT_CKSEL Ext. Crystal Osc. 8.0- MHz; Start -up time: 16K CK + 65ms I would assume (although assumptions are bad) that this is configured to run from the external crystal running at 16Mhz, but am uncertain due to the 8.0 MHz listed in the SUT_CKSEL. Also, since I am using Timer 1, do you know if I need to set EXCLK in the ASSR register to get it to use the 16MHz crystal instead of the internal clock? As far as the simulator, it is the built in software AVR Simulator that comes with AVR Studio. It shows WGM mode 0x02 running the software, which is obviously wrong-a "feature" as we used to call it. Playing around manually with WGM10, WGM11, WGM12, and WGM13, I am unable to access WGMs higher than 0x03. I've read in other threads about this problem with other targets under AVRStudio. Once again, thanks, and I will post later to let you know if changing the clock speed helps. Dave
I have solved the problem. The trafo connected to the servos had a defective voltage divider and overloaded the servos. The original program does work. Thanks for the help.
Please log in before posting. Registration is free and takes only a minute.
Existing account
Do you have a Google/GoogleMail account? No registration required!
Log in with Google account
Log in with Google account
No account? Register here.