Skip to content

samd21: don't change priority of interrupts, this is really evil#4081

Merged
haukepetersen merged 1 commit intoRIOT-OS:masterfrom
daniel-k:pr/samd21_rtt_fix_irq_priority
Nov 10, 2015
Merged

samd21: don't change priority of interrupts, this is really evil#4081
haukepetersen merged 1 commit intoRIOT-OS:masterfrom
daniel-k:pr/samd21_rtt_fix_irq_priority

Conversation

@daniel-k
Copy link
Copy Markdown
Member

Changing interrupt priorities on cortex_m platforms has really bad consequences. RIOT assumes that there is no interrupt nesting (i.e. all IRQs have the same priority) which holds true until you change any IRQ priority.

Having low(er) priority interrupts is fine (they don't preempt e.g. the scheduler), but they can be preempted indeed (e.g. by a timer). When sending messages from within an interrupt callback with msg_send(), then msg_send_int() is used internally.

Inside msg_send_int() there's a call to sched_set_status() which assumes not to be preempted. That's where all the fun begins.

I was getting hardfaults inside sched_run() for some time now, but never really identified the cause. When a call to sched_set_status() gets preempted here the runqueue will be NULL for that process priority while runqueue_bitcache still indicates a non-empty runqueue.
Back in sched_run() this leads to next_thread pointing nowhere (yes, on samd21 you can dereference NULL pointer!). Boom.

Long story short: don't ever change interrupt priorities unless you really know what you're doing. It's okay to have such a limitation to not call msg_send() inside an interrupt that has a lower priority, but I wasn't aware of this yet.

$ cd cpu/
$ ack-grep NVIC_SetPriority

Yields a lot hits that may also lead to bugs like this one.

@daniel-k daniel-k added Type: bug The issue reports a bug / The PR fixes a bug (including spelling errors) Platform: ARM Platform: This PR/issue effects ARM-based platforms Area: core Area: RIOT kernel. Handle PRs marked with this with care! labels Oct 12, 2015
@jnohlgard
Copy link
Copy Markdown
Member

See also the discussion in #3450

@kaspar030
Copy link
Copy Markdown
Contributor

Long story short: don't ever change interrupt priorities unless you really know what you're doing.

Completely right, +1 for the change.

Other RTOS put functions in different classes, like "interrupt safe", so it is visible where functions can be called. Until we got that classifying, nested interrupts are a source of painful bugs.

@OlegHahm OlegHahm added this to the Release NEXT MAJOR milestone Oct 13, 2015
@daniel-k
Copy link
Copy Markdown
Member Author

@kaspar030 is this an ACK?

@daniel-k daniel-k added the CI: ready for build If set, CI server will compile all applications for all available boards for the labeled PR label Oct 30, 2015
@haukepetersen
Copy link
Copy Markdown
Contributor

ACK and go

haukepetersen added a commit that referenced this pull request Nov 10, 2015
samd21: don't change priority of interrupts, this is really evil
@haukepetersen haukepetersen merged commit 86da628 into RIOT-OS:master Nov 10, 2015
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Area: core Area: RIOT kernel. Handle PRs marked with this with care! CI: ready for build If set, CI server will compile all applications for all available boards for the labeled PR Platform: ARM Platform: This PR/issue effects ARM-based platforms Type: bug The issue reports a bug / The PR fixes a bug (including spelling errors)

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants