Are interrupts delayed or ignored with noInterrupts() ?

Short version:
Are interrupts delayed or ignored when I call noInterrupts() function?

Long version:
Consider the following sequence of events:

  1. noInterrupts() is called
  2. timer interrupt occures
  3. interrupts() is called
    Would the ISR be called after the interrupts are re-enabled or never at all?
    The difference is very important for my application, but I couldn't find the answer in the documentation.
    Any help is greatly appreciated.

A: The ISR would be called after the interrupts are re-enabled.

Read this discussion by Nick Gammon:
http://www.gammon.com.au/interrupts

I think only one interrupt is queued and subsequent interrupts are ignored so you may not be able to guarantee that the one you are interested in will trigger.

...R

LarryD:
Read this discussion by Nick Gammon:
Gammon Forum : Electronics : Microprocessors : Interrupts

Thanks Larry. I have found the answer in Nick's tutorial:

Interrupts events (that is, noticing the event) can occur at any time, and most are remembered by setting an "interrupt event" flag inside the processor. If interrupts are disabled, then that interrupt will be handled when they are enabled again, in priority order.

Robin2:
I think only one interrupt is queued and subsequent interrupts are ignored so you may not be able to guarantee that the one you are interested in will trigger.

Thanks Robin.
Yes, only one interrupt of each priority is queued.

Robin2:
I think only one interrupt is queued and subsequent interrupts are ignored so you may not be able to guarantee that the one you are interested in will trigger.

...R

This is true per interrupt type - each vectored interrupt has its own interrupt flag that is
set when the interrupt is triggered and cleared once its ISR is set running. So you can have
many pending interrupts so long as each is a different type. If more than one is pending
in this manner the highest priority one is the first to run when interripts are re-enabled.

This means you can only lose interrupts if two of the same type happen during interrupts being
blocked, but you will get at least one of each type.

Usually global interrupts are disabled for the duration of any ISR (unless you explicitly enable),
so that ISRs are strictly serialized by default.

Disabling of specific interrupts is different, the interrupt is truly ignored.

The global interupt flag is for writing critical sections of code where data is shared with an ISR.

MarkT:
... Disabling of specific interrupts is different, the interrupt is truly ignored ...

Mark, thanks for the addition. I didn't know there is a difference depending on how you disable the interrupt. But thinking about, it actually makes sense. Thanks!

MarkT:
Disabling of specific interrupts is different, the interrupt is truly ignored.

@MarkT: No. Interrupt events are stored whether or not you have them enabled. Try this code:

volatile bool triggered;

void myISR ()
{
  triggered = true;
}

void setup ()
{
  Serial.begin (115200);
  Serial.println ();
  Serial.println (F("Starting"));
  pinMode (2, INPUT_PULLUP);
  EIFR = bit (INTF0);  // clear flag for interrupt 0
  attachInterrupt (0, myISR, FALLING);
  detachInterrupt (0);
  pinMode (13, OUTPUT);
  digitalWrite (13, HIGH);
  Serial.println (triggered);
  delay (5000);
  digitalWrite (13, LOW);
  attachInterrupt (0, myISR, FALLING);
  Serial.println (triggered);
}  // end of setup

void loop ()
{
}  // end of loop

If you jumper pin 2 to ground in the 5 seconds that the on-board LED is high (on a Uno) then afterwards it reports "1". That is, the interrupt occurs.

This is despite the fact that interrupts were disabled for external interrupt 0 in the interim.

Disabling the interrupt merely prevents it from calling the ISR. However the event itself is flagged.

That is why, prior to attaching an interrupt, you (should) clear the flag. That is (in this case):

  EIFR = bit (INTF0);  // clear flag for interrupt 0

@Nick Thanks a lot for the correction.