Bug in framework-arduinoespressif32 digitalPinToInterrupt

In many variants for ESP32S2 and ESP32S3, pins_arduino.h defines:

#define digitalPinToInterrupt(p)    (((p)<48)?(p):-1)

But pin 48 is also valid as interrupt source.
Without a fix, this crashes:

attachInterrupt(digitalPinToInterrupt(48), Callback, FALLING);

In the Arduino Uno, for example, attachInterrupt() is valid for two external interrupts, INT0 and INT1 on pins D2 and D3. Any other pin being passed will cause a return of -1 (aka 255 in unsigned speak) from digitalPinToInterrupt() to signal an error.

You cannot call, for example, digitalPinToInterrupt() and pass it a pin number which allows Pin Change Interrupts – these are also classed as external by the Atmel/Microchip docs, but are not the same as INT0 and INT1.

Also, using the calling attachInterrupt(digitalPinToInterrupt(48), Callback, FALLING) might lead to unexpected results if the wrong pin number is passed. Just because of how the code is written for the Arduino and the fact that it’s not checking the return value from digitalPinToInterrupt() for errors before passing the result into attachInterrupt().

So, my questions:

  • Are you expecting to be able to trap and action Pin Change Interrupts in your code while using attachInterrupt() in the manner you have described for pin 48, or are you hoping for an External Interrupt to be trapped and actioned?

  • If the latter, then is pin 48 listed in the data sheet as being configurable for External Interrupts, or just Pin Change Interrupts?

  • If the latter, then you cannot attachInterrupt() for pin 48, and you will have to find some valid pin change interrupt library to use it for those types of interrupts.

Having said that, t shouldn’t crash when digitalPinToInterrupt() is passed an invalid pin number, it should return an error code that is checked in attachInterrupt(). On the Uno, invalid pins – anything other than 2 or 3 – will return the error code 255 (the code returns -1 actually, but the return type is unsigned, so 255). AttachInterrupt() checks for values greater than the highest allowed interrupt pin, which is 3 in the Uno’s case, so the 255 error code is rejected and nothing happens. The interrupt is not attached and doesn’t trigger. If compiles quite happily, just doesn’t work!



This is the current bleeding edge code.

if you found a bug in those definitions, please directly report them to Arduino-ESP32 for them to fix, this is the wrong forum for it.

Thanks for writing all that, but AFAIK there’s no distinction between external and GPIO interrupts on ESP32. My interrupt works if I just avoid calling digitalPinToInterrupt().

1 Like

Thanks. I will verify again, then submit a bug to Arduino-ESP32.