-
Notifications
You must be signed in to change notification settings - Fork 225
This issue was moved to a discussion.
You can continue the conversation there. Go to discussion →
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Unable to trigger either TIMER0_COMPA or TIMER1_COMPA interrupts on an attiny85 #287
Comments
Quite embarrassingly, I had the wrong avr-spec configured in config.toml. I had duplicated my project from another arduino nano project, and seemingly changed everything but the build target. |
Glad you got it figured out! Btw, your code looks a bit odd: First of all, in this line:
The critical section is superfluous. "Atomics" do not need a critical section by their nature of only accessing the value atomically. Then, looking at this:
You are using both "atomics" and a mutex at the same time. This does not really make sense and just produces unnecessary overhead. When there's already a mutex involved, just use mutexes for the rest as well: static COUNTER: Mutex<Cell<u8>> = Mutex::new(Cell::new(0));
static TOGGLE: Mutex<Cell<bool>> = Mutex::new(Cell::new(false));
fn count() {
avr_device::interrupt::free(|cs| {
let counter = COUNTER.borrow(cs);
let toggle = TOGGLE.borrow(cs);
let value = counter.get();
if value > 30 {
counter.set(0);
toggle.set(!toggle.get());
} else {
counter.set(value + 1);
}
});
} There is one more reason why you should do this: "Atomics" do not actually exist on AVR. The |
Thank you for pointing this out @Rahix! I had assumed that mutating anything from interrupt handler needed to be inside an explicit critical section. This makes perfect sense, and probably should've been quite obvious. |
Actually, now that you mention it, interrupt handlers are even more special... On AVR, interrupts will always be disabled while the interrupt handler is running. So technically the critical section there wouldn't actually be needed because the CPU already enforces it. We've been thinking about passing a |
That makes sense. Further, at least for the Attiny85, I think that interrupts will only fire in order of priority, so if at any point multiple interrupts are triggered, the CPU guarantees that PCINT0 will run before TIMER1_COMPA, for example. Would explicitly having a critical section in an interrupt handler just be good practice to indicate that this handler is changing volatile data until #52 is added to avr-devices? |
I would add the critical section only when it is needed. After all, you can't safely get to the contents of a mutex without the |
Perfect. Thank you for all your feedback ❤️ |
This issue was moved to a discussion.
You can continue the conversation there. Go to discussion →
I have an attiny85 with a RGB LED's red leg connected to PB3, and I'm trying to toggle it using a timer interrupt. I cannot work out why I can't get
TIMER0_COMPA
orTIMER1_COMPA
to fire, I can only get them working in Arduino. I think I've ported the code to rust exactly how I have it in arduino.The working Arduino code:
The code I've ported to rust:
I've used the binary values for setting the registers so I can match them against the datasheet easily, and have tested those exact values in the arduino code too.
I'm pretty sure I'm missing something crucial, but I just cannot see what. Any pointers would be hugely appreciated!
P.S. The actual frequency the LED is toggled is irrelevant, as long as the light toggles
P.P.S This is an amazing library, thank you!
Update: Edited to show that I actually couldn't get TIMER1_COMPA working, I had set the
TOIE1
bit instead of theOCIE1A
bit. With the TOIE1 bit set, it pulses on PB4 based off what was written to theOCR1C
register (I think).The text was updated successfully, but these errors were encountered: