attachInterrupt()

Last revision:2025/04/25

名称

attachInterrupt()

割り込みの利用

マイクロコントローラのプログラム中で自動的に何かを行おうとしたときに、割り込みは有用であり、タイミング問題のを容易に解決する。割り込みを使うよい例には、ロータリーエンコーダの読み込みや、ユーザ入力の監視などがある。

プログラムが、ロータリーエンコーダからの信号を欠落することなく常に補足することを保証したいと思ったら、発生した信号を捕捉するためにプログラムは常にエンコーダがつながっているセンサーを監視しなければならないので、(割り込みを使わない場合は)何をするにもとても巧妙なプログラムを書く必要がある。クリックを捕捉するための音センサや硬貨が落ちるのを捕捉する赤外線センサといった、他のセンサーもインタフェースに関する同様の問題をもっている。これらの全ての状況において、割り込みを利用することで、呼び鈴が鳴ったことの検出を失敗することな く、他の作業をマイクロコントローラに自由に実行させることができる。

書式

  • attachInterrupt(digitalPinToInterrupt(pin), ISR, mode) (推奨)
  • attachInterrupt(interrupt, ISR, mode) (非推奨)
  • attachInterrupt(pin, ISR, mode) (非推奨、Arduino SAMDボード、Uno WiFi Rev2、Due、101のみ)

C言語シグネチャ(avr)

  • void attachInterrupt(digitalPinToInterrupt(pin), void (*userFunc)(void), int mode); (推奨)
  • void attachInterrupt(uint8_t interruptNum, void (*userFunc)(void), int mode); (非推奨)

引数

interrupt割り込みの番号。データ型: int
pinピン番号。
ISR割り込みが発生したときに呼び出す関数へのポインタ。この関数は引数も返り値も持たない。割り込みサービスルーチンと呼ばれることもある。
modeいつ割り込みサービスルーチンを呼び出すかを指定する。以下に示す4個の定数が定義されている。
<b>LOW</b> ピンがLOWのときに割り込みサービスルーチンを呼び出す
<b>CHANGE</b> ピンの値が変わった時に割り込みサービスルーチンを呼び出す
<b>RISING</b> ピンがLOWからHIGHになった時に割り込みサービスルーチンを呼び出す
<b>FALLING</b> ピンがHIGHからLOWになった時に割り込みサービスルーチンを呼び出す

DueとZero、MKR1000ボードでは、以下も利用可能。

<b>HIGH</b> ピンがHIGHのときに割り込みサービスルーチンを呼び出す。

ISR(Interrupt Service Routine: 割り込みサービスルーチン)について

ISRは、他の多くの関数が持っていない特徴を持つ特別な関数である。ISRは、引数をとることができず、戻り値もない。

一般に、ISRはできる限り短くかつ速くなければならない。スケッチ内に複数のISRがあっても、同時には一つだけが実行される。他のISRは現在のISRの終了後、優先度に応じた順序で実行される。millis()の計測は割り込みに依存しているので、他のISRの実行中には増加しない。delay()の動作には割り込みが必要なので、ISRの中から呼ばれても動作しない。micros()は、最初は動作するが、1~2秒後には乱れてしまう。delayMicroseconds()は(割り込みに依存する)カウンタを利用しないので、通常通り動作する。

一般的に、ISRとメインプログラムとのデータのやり取りにはグローバル変数を利用する。ISRとメインプログラムで共有する変数が確実に更新されるためには、その変数をvolatileとして宣言する必要がある。

割り込みについては、Nick Gammon’s notesを参照のこと(英語ページです)。

戻り値

なし。

コード例

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
const byte ledPin = 13;
const byte interruptPin = 2;  // input pin that the interruption will be attached to
volatile byte state = LOW;  // variable that will be updated in the ISR

void setup() {
  pinMode(ledPin, OUTPUT);
  pinMode(interruptPin, INPUT_PULLUP);
  attachInterrupt(digitalPinToInterrupt(interruptPin), blink, CHANGE);
}

void loop() {
  digitalWrite(ledPin, state);
}

void blink() {
  state = !state;
}

割り込みが利用可能なデジタルピン

attachInterrupt()の1番目の引数は割り込み番号である。通常、デジタルピンを割り込み番号に変換するには、digitalPinToInterrupt(pin)を利用する必要がある。例えば、3番ピンを利用するときには、digitalPinToInterrupt(3)を、attachInterrupt()の1番目の引数に指定する。

ボード 割り込みに利用可能なデジタルピン 備考
Uno R3, Nano, Mini, other 328-based 2, 3
UNO R4 Minima, UNO R4 WiFi 2, 3
Uno WiFi Rev.2, Nano Every 全てのデジタルピン
>Mega, Mega2560, MegaADK 2, 3, 18, 19, 20, 21 20番ピンと21番ピンは、I2C通信に利用されているときは、割り込みには利用不可。無効化できない外部プルアップもある。
Micro, Leonardo 0, 1, 2, 3, 7
Zero 0-3、5-13、A0-A5 4番ピンは割り込みに使えない。
MKR Family boards 0, 1, 4, 5, 6, 7, 8, 9, A1, A2
Nano 33 IoT 2, 3, 9, 10, 11, 13, A1, A5, A7
Nano 33 BLE, Nano 33 BLE Sense (Rev 1 & 2) 全てのピン
Nano RP2040 Connect 0-13, A0-A5
Nano ESP32 全てのピン
GIGA R1 WiFi 全てのピン
Due 全てのデジタルピン
101 全てのデジタルピン 2、5、7、8、10、11、12、13はCHANGEだけ動作する。

割り込み番号

通常、割り込み番号を直接スケッチに記述するのではなく、digitalPinToInterrupt(pin)を利用すべきである。ピン番号と割り込み番号のマッピングはボードにより異なる。割り込み番号を直接書くのは簡単に見えるが、他のボードで利用するときの互換性に問題がある。

しかし、古いスケッチではしばしば割り込み番号を直接記述している。0(デジタルピン2番)と1(デジタルピン3番)がよく使われている。以下の表に各ボードでのピンと割り込み番号の関係を示す。

以下の表で示されている数値(int.X)は、attachInterrupt()に渡される割り込み番号を示していることに注意すること。歴史的な理由により、この数値はATMegaチップの割り込み番号と常に関連しているというわけではない。例えば、ATmega2560チップでは、int.0はINT4と関連している。

Board int.0 int.1 int.2 int.3 int.4 int.5
UNO, Ethernet 2 3
Mega 2560 2 3 21 20 19 18
32u4 based (e.g Leonardo, Micro) 3 2 0 1 7

Uno WiFiRev.2とDue、Zero、MKR Family、101では、割り込み番号=ピン番号である。

注意

指定した関数の中では、delay()は動作せず、また、millis()によって返却される値も増加しない。その関数の実行中に受信したシリアルデータはなくなる可能性がある。指定した関数の中で変更する変数は、volatile変数として宣言するべ きである。下記のISRを参照のこと。

参照

オリジナルのページ

https://docs.arduino.cc/language-reference/en/functions/external-interrupts/attachInterrupt/

実装の解析

attachInterrupt()

最終更新日

July 12, 2026

inserted by FC2 system