PICで複数の外部割り込みを使用する


9

いくつかのプロジェクトでPIC16F877データシート)を使用しました。単一の外部ピン変更割り込みの場合、PORTB0割り込みを使用できます。しかし、今度は1つの回路で8つの独立した外部ピン変更割り込みをサポートする必要があります。

データシートには、に15の割り込みがあるとありますがPIC16F877、タイマーのオーバーフロー割り込みなどを含めてカウントされていると思います。この場合は役に立ちません。

これはデータシートがINTCONレジスターについて述べていることです。

ここに画像の説明を入力してください

bit0を使用して4つの独立した割り込みを持つことはできますRBIFか?それはの変化を表していPB7:PB4ます。どのピンが変更されたかをどのように識別できますか、それは割り込みルーチンでポート値を読み取ることによってですか?

上記に対して肯定的な回答を得ても、8つの割り込みが必要ですか?もちろん、私はまだINTEPORTB0変更のために使用できます。その後4 + 1 = 5、しかし、どのような他の約3?(ただし、8つの割り込みイベントはすべて同じタイプ4 + 1 + 3 = 8なので、醜いように見えますね。)

8ピンを監視すること以外に、マイクロコントローラから期待される他の重いタスクはありません。(他のタスクについては、一連の個別のカウンター変数を維持し、頻繁に約4バイトをPCにシリアルに送信する必要があります)

どんな提案でも大歓迎です。それがマイクロコントローラーをより適したものに変更することについてであってもです(しかし、ええと。sから離れるように言わないでくださいPIC)。


2
割り込みを使用せずに、メインプログラムのピンを監視できる場合があります。しかし、それは完璧ではありません。代わりに、Arduinoに行くことができます。PICではありませんが、とてもシンプルで、PICに慣れているので簡単に理解できます。
アヌビス2013年

1
RBIE割り込みを使用する場合は、毎回以前の値をバッファリングし、XORを実行して変更内容を見つけることができます。実行はかなり速いはずです。
PeterJ 2013年

@PeterJ分かりませんでした。どの値をバッファリングしますか?
コードネームSC

@PeterJすばらしい!待機中...
コードネームSC SC

1
1つの方法は、外部8入力ゲート(昔の74LS30など)を使用して、外部信号を1つの割り込みピンに結合することです。74(HC)30はNANDゲートであるため、静止状態ですべての入力をハイにする必要があります。また、ポートを読み取ることによってアクティブな割り込みを特定できるように、ポートピンに接続する必要があります。
ブライアンドラモンド2013年

回答:


3

これは、1つのアイデアを説明するCの疑似コードです。排他的ORを使用して、変更されたピンを特定し、1つのRBIE割り込み内でさまざまなハンドラーを呼び出します。アプリケーションの重要度に応じて、割り込みの実行中にポートの変更などの状況をPICがどのように処理するかをチェックして、イベントを見逃さないようにすることができます。

int old_port_b;

void isr_handler()
{
    int new_port_b, changed_pins;
    new_port_b = read_port_b();
    changed_pins = new_port_b ^ old_port_b;
    if (changed_pins | 1)
        rb0_hander();
    if (changed_pins | 2)
        rb1_hander();
        // ... etc
    old_port_b = new_port_b;
}

int main()
{
    old_port_b = read_port_b();
    enable_interrupt();
}

わかりました、ありがとう!しかし、それは私が探している正確な答えではありません。この方法では、RB7:RB44つのピンのみを監視できます。しかし、私は8ピンを監視する方法を求めています。なにか提案を?
コードネームSC

上記が機能するはずのRB0-RB7を使用できない理由があると思いますか?そうでなければ、私は本当に方法を考えることができません。コードをすばやくトリガーすることが重要でなければ、タイマー割り込み(またはメインループのみ)で上記のスタイルのコードを使用できます。
PeterJ 2013年

そのPICの場合、これを行うために割り込みを使用する必要がある場合は、RB4:RB7でのXORトリックと、RB0:RB3での4つの割り込みが有効です。割り込みが不要な場合は、コードのポート全体をポーリングするか、ハードサンプリングレートが必要な場合はタイマー割り込みを使用してポーリングを処理します
Scott Seidman

and four interrupts for the RB0:RB3?PIC16F877はの割り込みをサポートしていませんRB1:RB3
コードネームSC

データシートで、ポート全体をカバーしているとは思っていませんでした。しかし、他のコメントは1秒に1回程度見たので、これをメインループで実行するだけの方がいいと思います。割り込みを使用すると、実行中の任意の時点で変数を更新し、割り込みの実行中にピンの変更を処理する方法に注意する必要があります。それは本当に本当の利益のためにそれを複雑にするだけのように本当に聞こえます。私が考えることができる唯一の例外は、割り込み時にスリープからのスリープ解除を使用したい場合で、その場合はハードウェアでMUXする必要があります。
PeterJ 2013年

1

その部分には、4つのピン変更割り込みと、選択したエッジに設定できる他のいくつかがあります。1つの戦略は、8ビット値の変化を外部で検出し、不一致で中断することです。これはハードウェアでは面倒になりますが、まさにあなたが望むものになります。

あなたが述べていない重要なパラメータは、ピンの変化にどのくらい速く応答する必要があるか、そしてピンの変化が有効になるためにピンの変化が持続する最小時間です。回答によっては、ファームウェアの定期的な割り込みに基づいてポーリングできます。16F877は5 MHzの命令レートで実行でき、変更のチェックには数命令しかかかりません。50命令ごとに割り込みを設定するとします。これは、プロセッサ時間のかなりの部分をフォアグラウンドコードに任せることになります。割り込みレートは100 kHzで、周期は10 µsです。もちろん、フォアグラウンドコードでも変更フラグを確認して何かを行う必要があるため、応答時間は10 µsを超えますが、変更が検出されたときに何をする必要があるかについては何も述べていません。これが人間の時間で応答する必要がある場合、


不足している詳細については申し訳ありません。期待される回答率once per secondで十分です。ピンの変化(1つのエッジのみ、たとえば立ち上がり)が検出された場合、カウンター(変数)をインクリメントする必要があります。メインループでは、カウンター値を監視する必要があり、特定の値よりも大きくなると、4バイトUSARTをPCに送信する必要があります。次に、関連するカウンタ値をゼロにリセットします。そのような単純な。ポーリングオプションはうまくいくと思いますか?
コードネームSC

2
1秒に1回!それでは、割り込みに対する苦痛は何ですか?これは、定期的なポーリングで簡単に実行できます。それで問題は何ですか?
Olin Lathrop、2013年

ええと...私はそれらが8つあり、また、応答を予測することはできないので最善ですが(しかし、その値は最小であると仮定することができます)。おい!人はミス、右.. :(行うことができます
コードネームSC

1

@Brian Drummondが述べたように、8入力ゲートNANDを使用して、INTピンで割り込みを立ち上げ、割り込みソースを「74HC165N」のような8ビットパラレルイン/シリアルアウトシフトレジスタに接続することができます。割り込みが発生した後、シフトレジスタからデータを読み取るだけで、実際の割り込みソースに関する情報が得られます...これは最速の方法ではないかもしれませんが、拡張が簡単で、5ピン以下を使用します。アドレス制御システム(MUX、LATCHなど)を追加した場合、割り込み通知に必要なパインは1つだけで、他のピンは異なるリソースに対して異なるタイミングで再利用できます;)

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.