AVRはRISCアーキテクチャなので、割り込みのかなり基本的なハードウェア処理を備えています。ほとんどのプロセッサは割り込み中にスタックを混乱させますが、異なる方法を使用するいくつかの、特にARMとPowerPCがあります。
いずれにせよ、これはAVRが割り込みに対して行うことです。
割り込みが発生すると、プロセッサハードウェアは次の手順を実行します。これらの手順は単なるGOTOではありません。
- 現在の指示を終了します。
- グローバル割り込みフラグを無効にします。
- スタック上の次の命令のアドレスをプッシュします。
- (発生した割り込みに応じて)正しい割り込みベクトルのアドレスをプログラムカウンターにコピーします。
この時点で、ハードウェアは実行するすべてを実行しました。ソフトウェアは、物事を壊さないように正しく書かれている必要があります。通常、次のステップはこれらの線に沿っています。
ステータスレジスタをスタックにプッシュします。(これは変更する前に最初に行う必要があります)。
変更される(または変更される可能性がある)CPUレジスタをスタックにプッシュします。この方法で保存する必要があるレジスタは、プログラミングモデルによって定義されます。プログラミングモデルはコンパイラによって定義されます。
これで、作業中の割り込みコードを実行できます。関数を呼び出す問題に対応するために、関数が常に実行することを実行し、スタックに戻り値をプッシュし、完了時に戻ります。これは、これまでスタックに保存したこれらの以前の値には影響しません。
- ISR作業コードを実行します。
これで完了です。割り込みから復帰したいと思います。まず、ソフトウェアのクリーンアップを行う必要があります。
- 手順6でプッシュしたCPUレジスタをポップします。
- 保存したステータス値をステータスレジスタにポップします。この後、ステータスレジスタを変更する可能性のある命令を実行しないように注意する必要があります。
RTI命令を実行します。ハードウェアは、この命令に対して次の手順を実行します。
a。グローバル割り込みフラグを有効にします。(次の割り込みが受け付けられる前に、少なくとも1つの命令を実行する必要があることに注意してください。これにより、重い割り込みがバックグラウンドの作業を完全にブロックするのを防ぎます。)
b。保存された返信アドレスをPCにポップします。
これで通常のコードに戻りました。
特にステータスレジスタと変更される可能性のあるレジスタの保存に関しては、注意が必要な点がいくつかあることに注意してください。幸いにも、Cコンパイラを使用している場合、これらはすべて内部で処理されます。
また、スタックの深さに注意する必要があります。割り込みが有効になっているときはいつでも、ISRはローカルコードを見ると明らかなよりも多くのスタックを使用できます。もちろん、これは、メモリを限界まで押し出さない限り、実際にはあまり起こりません。
ここではあなたが参照したい場合は、このプロセスを記述したリンクです。