How does the Arduino NANO deal with simultaneous external interrupts?

(deleted)

If you really want to know, the data sheet should have it. Why does it matter though? Both interrupts will be serviced one way or another. Is it important to you to know which goes first in this hypothetical situation?

(deleted)

at least with older processors, each interrupt had a priority.

Within the microprocessor interrupts have an order of priority which determines the order in which they are serviced when there is a conflict.

If a second interrupt happens for the same I/O pin while the first interrupt is being dealt with it will be queued and dealt with when the first interrupt is complete. If there happened to be a third interrupt for the same I/O pin it would be ignored.

An interrupt for a different I/O pin will also be handled when the first ISR completes.

A higher priority interrupt that is triggered while a lower priority interrupt is being serviced will also have to wait until the current ISR completes.

It should be obvious from this that code in a ISR should complete very quickly - 100 microsecs would be a long time.

Have a look at Nick Gammon's interrupt Tutorial

Separate from all of that it would be very unusual to need an interrupt to handle a button-press by a human because humans are very slow.

...R

The order of precedence for AVRs is the order the interrupt vector appears in the vector table. The lower the vector number, the higher the precedence.
I'm pretty sure that's in the datasheet.

Edit: Yup, page 23 of the 328's datasheet (DS40001906C)

A flexible interrupt module has its control registers in the I/O space with an additional global interrupt
enable bit in the Status register. All interrupts have a separate interrupt vector in the interrupt vector table.
The interrupts have priority in accordance with their interrupt vector position. The lower the interrupt
vector address, the higher the priority.

Nano uses the ATMega328.

See section 7.7 Reset and Interrupt Handling

The lowest addresses in the program memory space are by default defined as the Reset and Interrupt Vectors. The complete list of vectors is shown in ”Interrupts” on page 66. The list also determines the priority levels of the different interrupts. The lower the address the higher is the priority level. RESET has the highest priority, and next is INT0 – the External Interrupt Request 0.

So page 66 onwards has your answer. See section 12.4 Interrupt Vectors in ATmega328 and ATmega328P.

However the definition of "priority" and "first" may not be what you think it is. What probably actually happens is...

  1. When an event occurs the relevant interrupt flag is set by the hardware. At this point no attention is paid to order or priority. So if A happens before B, or B happens before A, the end result is the same. Interrupt flags for A and B are both set and there is no record of which happened first.
  2. When the current instruction is complete, and assuming global interrupts are enabled, the CPU...
    i) Examines all the interrupt flags in order of priority
    ii) The highest priority flag that is set gets serviced

So if you're trying to establish if pin-2 or pin-3 was the first to go high, and you want to do that at sub-instruction level granularity (for some unknown reason) then you aren't going to be able to.

Also using interrupts for push buttons is not at all recommended. I guess, as you have this requirement to tell which was pushed first to an insane level of accuracy, you have no choice.

Perhaps best to describe your use case as perhaps there is a better option. Some external hardware for example.

Is this for a quiz show button? I can present a simple software solution to ensure fairness (in the rare case of simultaneous button pressing) if that is what you are after.