Arduino variable not updating - Page 1
Forum section: electronics / general

author: robzy
author_rank: Regular Contributor
timestamp: February 05, 2018, 02:09:26 pm
content: The short story here is that I'm trying to use an Arduino Uno's (ATMega328) Timer1 to send some pulses of a known length through pin 10.I'm ~90% sure that the timer code is correct, but it seems to be impacting other code in really weird and inexplicable ways. I've read a fair chunk of the ATMega328 datasheet, I've done some Googling, and I've tried two different Arduino Uno boards, but I've been unable to figure out why it's happening.The problem:The code below continually prints out the "4" on the serial port. It never increments. And its driving me mad. Even if my Timer1 code is wrong, I haven't been able to identify any way that it might be impacting code in loop().Known so far:If I remove the "TCCR1B |= _BV(CS11);" code from loop() then the serial output increments as expected. But how can this line impact any other code? My googles have left me empty.Am I missing something obvious?Code:void setup() {Serial.begin(230400);// Stop Timer1TCCR1B &= ~(_BV(CS12) | _BV(CS11) | _BV(CS10));// Want non-inverting fast-pwm mode where TOP=ICR1// Non-inverting (COM1x[1:0] to 0x3)TCCR1A |= _BV(COM1B1);TCCR1A &= ~(_BV(COM1A1) | _BV(COM1A0) | _BV(COM1B0));// Fast PWM where TOP=ICR1 (WGM1[3:0] = 0xE)TCCR1B |= _BV(WGM13) | _BV(WGM12);TCCR1A |= _BV(WGM11);TCCR1A &= ~_BV(WGM10);// Enable the interruptsTIMSK1 |= _BV(ICIE1) | _BV(OCIE1B);TIMSK1 &= ~_BV(OCIE1A);TCNT1 = 0x00; // starting valueICR1 = 0xFFFF; // ending valueOCR1B = 0x8FFF;}void loop() {int pulseMilliseconds = 3;while (true) {pulseMilliseconds = pulseMilliseconds + 1;TCCR1B |= _BV(CS11); // start timer with clk/8 prescalerSerial.println(pulseMilliseconds);delay(1000);}}SIGNAL(TIMER1_COMPB_vect) {}(Note, this is a minimal codeset that replicates the issue that I'm seeing with the full codeset)

author: agehall
author_rank: Frequent Contributor
timestamp: February 05, 2018, 03:39:03 pm
content: I'd start by removing the while(true) loop - that sort of thing can mess up arduino code.

author: paulca
author_rank: Super Contributor
timestamp: February 05, 2018, 04:28:04 pm
content: Is it resetting?Add aSerial.println("I'm alive!");to setup().

author: phil from seattle
author_rank: Super Contributor
timestamp: February 05, 2018, 04:30:48 pm
content: I looked at that code and didn't see anything obvious. Timer 1 doesn't conflict with delay().So, I put it on an Arduino Mega and got the same results as you. I was suspicious of the printing 4 repetitively. The only way that can happen is if the sketch is being restarted. So, I slapped a logic analyzer on it and toggled a pin (2 in this case) in setup() and sure enough it's restarting - I can see the toggle happening at about 30 hz. Your timer code is somehow causing the reset. I also toggled a pin in the interrupt handler and can see that 2 interrupts happen shortly before restart (about 25 uS). The two interrupts are 2.4 uS apart. I did a quick look at the datasheet but didn't see anything obvious. I don't have time to dig deeper so good luck. ha! Paul beat me to it

author: rstofer
author_rank: Super Contributor
timestamp: February 05, 2018, 04:49:22 pm
content: Try it without enabling the interrupts.I didn't study the code but I wonder if you are getting an interrupt for which you provide no handler.

author: paulca
author_rank: Super Contributor
timestamp: February 05, 2018, 04:49:43 pm
content: As to why it's reseting, no idea.However I would try this:SIGNAL(TIMER1_COMPB_vect) {return;}Just in case. Although I would very much doubt that GCC would be that silly.The only other thing that it could be is the line:TCCR1B |= _BV(CS11); // start timer with clk/8 prescalerIs crashing it the second time through.

author: westfw
author_rank: Super Contributor
timestamp: February 05, 2018, 09:35:11 pm
content: QuoteYou're enabling two interrupts, but only providing one ISR. Also, you're mixing obsolete "SIGNAL" with current vector names.Make the end of your program like this:Code:ISR(TIMER1_COMPB_vect) {}ISR(TIMER1_CAPT_vect ) {}

author: robzy
author_rank: Regular Contributor
timestamp: February 05, 2018, 10:29:22 pm
content: Quote from: westfw on February 05, 2018, 09:35:11 pmBingo! That's exactly what it was. I replaced the code and it worked perfectly. I misunderstood what the ICIE1 flag was for. Thank you so much.Thanks to everyone else for helping out too, it sounds like you were all heading in the right direction. Special props to phil for confirming I wasn't losing my mind, and that it really was happening.