2線式シリアル・インターフェース(TWI)は、マイクロコントローラーが使われる多くの用途に適した理想的なインターフェースです。 TWIのプロトコルでは、わずか二本の双方向バス・ライン、クロック(SCL)とデータ(SDA)、だけを使用して、128個までの異なるデバイスを接続するシステム設計が可能です。 外付けで必要なハードウェアはTWIバス・ラインそれぞれに接続する一本ずつのプルアップ抵抗だけです。 バスに接続されたデバイスは全て個々のアドレスをもち、バス競合を解決するしくみはTWIプロトコル内に実装されています。
下の表は、この章で頻繁に用いる用語の定義です。
用語 | 説明 |
---|---|
マスター |
データ転送の開始と終了を行うデバイス。 マスターはSCLクロックの生成も行います。 |
スレーブ | マスターによってアドレス指定されるデバイス |
送信(デバイス) | バス上にデータを送り出す(デバイス) |
受信(デバイス) | バス上からデータを受け取る(デバイス) |
2線式インターフェースを有効にするためには、「消費電力を最小にするために」(p.40)の説明にあるPRTWIビットをゼロにしておく必要があります。
Figure 21-1に描かれているように、二本のバス・ラインはプルアップ抵抗を通して電源のプラス側に接続します。 TWI互換のデバイスのバス・ドライバは全て、オープン・ドレイン、あるいはオープン・コレクタ出力になっています。 この接続により、2線式インターフェースの動作に不可欠なワイアードAND機能が実装されています。 一つ以上のTWIデバイスがゼロを出力しているときに、バス・ラインがLow状態になります。 すべてのTWIデバイスがハイ・インピーダンス出力になっているとき、プルアップ抵抗がバスをHighに引き上げ、バス・ラインがHigh状態になります。 TWIバスに接続されるAVRデバイスは全て、バス操作を行う場合、必ず電源を供給されていなければなりません。
バスに接続できるデバイスの数の上限は、バスの容量成分の制限である400pFと、7ビットのスレーブ用アドレス空間によってのみ制限されます。 TWIの詳細な電気的特性の仕様については、「2線式シリアル・インターフェースの特性」(p.307)に記載されています。 バス・スピードが100kHz未満の場合に適用されるものと、400kHzまでの条件で適用される、二種類の異なる仕様があります。
TWIバス上では、各データのビットはクロック・ライン上のパルスをともなって転送されます。 データ・ラインの電圧レベルはクロック・ラインがHighのときには安定していなければなりません。 唯一の例外はスタート・コンディション、ストップ・コンディションが発生する場合です。
マスターがデータ転送の開始と終了を行います。 マスターがスタート・コンディションをバス上に発効するときが転送の開始であり、マスターがストップ・コンディションを発効するときが転送の終了です。 スタート・コンディションとストップ・コンディションの間の時間帯は、バスはビジー状態であるとみなされ、他のマスターはバスの制御権を取得しようとするべきではありません。 スタート・コンディションとストップ・コンディションの間に、新たなスタート・コンディションが発効される特別な場合があります。 これは、再スタート・コンディションといい、マスターがバスの制御権を放棄せずに、新たな転送を行おうとする場合に使われます。 再スタート・コンディションの直後から、次にストップ・コンディションが現れるまで、バスはビジー状態とみなされます。 これは、スタート・コンディション時の動作と同一であり、したがって、この章の以後の部分では「スタート・コンディション」と記載されている部分では、特に記載の無い場合、スタート・コンディションと再スタート・コンディションの両方についての説明とします。 下記の図のとおり、スタート・コンディションとストップ・コンディションはSCLラインがHighのときにSDAラインのレベルを変化させることにより伝達されます。
TWIバス上のアドレス・パケットはすべて9ビットの長さを持ち、7ビットのアドレス・ビット、1ビットのリード/ライト・コントロール、1ビットのアクノレッジ・ビットから成り立っています。 リード/ライト・ビットがセットされているときはリード動作が行われ、そうでない場合はライト動作が行われます。 スレーブ・デバイスがアドレス指定を受けたと認識した場合、SCLの第9サイクル(ACK)にSDAをLowにします。 アドレス指定を受けたスレーブがビジー状態であるか、他の理由によりマスターからの要求に応答できない場合、ACKクロック・サイクルでSDAラインをHighのままにしておきます。 その後、マスターはストップ・コンディションを送信するか、再スタート・コンディションを送信して、新しいデータ転送を開始します。 スレーブ・アドレスとリードまたはライト・ビットから成るアドレス・パケットをそれぞれ、SLA+R、SLA+Wとよびます。
アドレス・バイトでは、MSBから送信が行われます。スレーブ・アドレスは設計者により自由に値を割り当てることができますが、0000 000のアドレスは、ジェネラル・コールとして予約されています。
ジェネラル・コールが送信された場合、すべてのスレーブ・デバイスはACKサイクルでSDAラインをLowにして応答しなければなりません。 ジェネラル・コールは、システム上の複数のスレーブに同一のメッセージを送信しようとする場合に使います。 バス上にジェネラル・コールが送信され、それにライト・ビットが続いている場合、ジェネラル・コールに応答するよう設定されている全てのスレーブは、ACKサイクルでSDAラインをLowにします。
ライト・ビットをともなうジェネラル・コールに続いて送信されるデータ・パケットは、ジェネラル・コールに応答したスレーブ全てが受信します。 なお、ジェネラル・コール・アドレスにリード・ビットを続けて送信することには意味がありません。複数のスレーブが異なるデータの送信を開始するとバス競合が発生するからです。
1111 xxxの形式を持つアドレスは全て将来のための予約となっています。
TWIバス上で転送されるデータ・パケットは全て9ビットの長さを持ち、1バイトのデータ・バイトと1ビットのアクノレッジ・ビットが含まれています。 データ転送中は、マスターはクロック信号とスタート・コンディション、ストップ・コンディションを生成し、受信デバイスは受信に対するアクノレッジ(確認動作)を行う必要があります。 アクノレッジ(ACK)の発信は、受信デバイスが第9SCLサイクルにおいてSDAラインをLowに下げることにより行われます。 受信デバイスがSDAラインをHighのままにしている場合は、NACKが発信されたことになります。 受信デバイスが最後のバイトを受信したとき、あるいは、何らかの理由によりそれ以上のバイト・データを受けとることができない場合、最後のバイト・データを受信した後に、送信デバイスに対してNACKを発信して知らせる必要があります。 データ・バイトはMSBから先に送信されます。
データの転送は、基本的にスタート・コンディション、SLA+R/W、一つ以上のデータ・パケット、そしてストップ・コンディションで構成されています。 スタート・コンディションの直後にストップ・コンディションが続く、空のメッセージは不正な動作とみなされます。 SCLラインのワイアードAND接続によって、マスターとスレーブのハンド・シェーク動作を実装することができます。 スレーブはSCLラインをLowに下げて、SCL = Lowの時間を延長することができます。 マスターが設定しているクロック・スピードがスレーブにとって速すぎる場合や、スレーブがデータ転送とデータ転送の間で処理を行うための時間が必要な場合に、この動作を利用することができます。 スレーブによるSCLのLow期間の延長は、SCLのHigh期間の動作に影響しません。これは、マスターによって制御されるからです。 結果的に、スレーブはSCLのデューティー比を延長することによってTWIのデータ転送速度を下げることができます。
Figure 21-6に一般的によく用いられるデータ転送の例を示します。 なお、アプリケーション・ソフトウェアによるプロトコルの実装に応じて、SLA+R/Wとストップ・コンディションの間では複数のデータ・バイトが転送できます。
TWIプロトコルでは、バス・システム上に複数のマスターが存在することが可能です。 二つ以上のマスターが同時に転送を開始したとしても、データ転送が通常どおりに行われるように、特別な設計上の配慮がなされています。 マルチ・マスター・システムでは二つの問題が発生します。
全てのマスターが、データを出力してから絶えずSDAラインを監視することにより、バス調停が行われます。 SDAラインから読み取った値がマスターから出力した値と一致していない場合、そのマスターは調停によりバス権を得られなかったと判断します。 あるマスターが調停によりバス権を放棄させられる条件は、そのマスターがSDAにHighを出力している時に他のマスターがLowを出力している場合だけです。 バス調停で権利を放棄したマスターは即座にスレーブ・モードに移行し、バス権を得たマスターによってアドレス指定されているかどうかをチェックしなければなりません。 SDAラインはHighのままにしておく必要がありますが、バス権を得ることができなかったマスターは、その時点で出力していたデータ・パケットやアドレス・パケットの終了までクロック信号を生成することが容認されています。 バス調停動作は、マスターが一つだけになるまで続行され、この動作には多数のビットが消費される可能性があります。 複数のマスターが同一アドレスのスレーブを指定しようとしている場合、調停動作はデータ・パケットまで続くことになります。
なお、下記の場合における調停動作は許可されていません。
これらの不正な条件での調停動作が絶対に行われないように、ユーザー・ソフトウェアを設計する必要があります。 このことは、マルチ・マスターのシステムでは全てのデータ転送はSLA+R/Wとデータ・パケットからなる同一の構成を使用しなければならないということです。 別の言い方をすると、全てのデータ転送は同じ数のデータ・パケットを含んでいなければならず、そうしないと調停動作の結果が不定となってしまいます。
Figure 21-9に示すとおり、TWIモジュールはいくつかのサブ・モジュールから成り立っています。 太線で描かれたレジスタは全てAVRデータ・バスからアクセス可能なものです。
これらの端子はTWIバスとMCUシステムの他の部分とのインターフェースの役割をもっています。 出力ドライバには、TWIの仕様に準拠するためのスルーレートの制限が設けられています。 入力側にはスパイク・ノイズ抑制ユニットがあり、50nSよりも短いスパイク・ノイズを除去します。 なお、I/Oポートの章で説明されているように、AVRの外部接続端子の内蔵プルアップ抵抗を、SC、SDA端子に対応する各ポートの設定ビットによって有効にすることができます。 この内蔵ブルアップ抵抗を使うことで、外付けの抵抗が不要になる場合もあります。
このユニットは、マスター・モード動作でのSCLの周期を制御します。 SCLの周期はTWIビットレート・レジスタ(TWBR)の設定値と、TWIステータス・レジスタ(TWSR)の分周比設定ビットによって設定します。 スレーブ動作では、ビットレートや分周比の設定は関係ありませんが、スレーブ・デバイスのCPUクロック周波数は少なくともSCLクロック周波数の16倍よりも大きな値でなければなりません。 なお、スレーブはSCLのLow期間を延長することでTWIバスのクロック周期の平均値を下げることができます。 SCLクロックの周波数は下記の式により計算されます。
このユニットには、データ・アドレスのシフト・レジスタ(TWDR)、スタート/ストップ制御、およびバス調停検出を行うハードウェアが含まれます。 TWDRレジスタには、送信するアドレスやデータ・バイトや受信したアドレスやデータ・バイトが格納されます。 8ビットのTWDRに加えて、バス・インターフェース・ユニットには送信または受信する(N)ACKビットを格納するレジスタがあります。 この(N)ACKビット・レジスタはアプリケーション・ソフトウェアから直接アクセスすることができません。 ただし、受信時にTWIコントロール・レジスタ(TWCR)を操作することによってセット/クリアすることができます。 送信モードでは、受信した(N)ACKビットの値は、TWSRレジスタの値によって判定できます。
スタート/ストップ制御回路の役割は、スタート・コンディション、再スタート・コンディションおよびストップ・コンディションの生成と検出です。 AVR MCUのスリープ・モードでは、スタート/ストップ制御回路がスタート・コンディション、ストップ・コンディションの検出を行うことができ、マスターによってアドレス指定を受けたときにスリープ・モードからMCUをウェークアップすることができます。
TWIモジュールがマスターとしてデータ転送を開始した場合、バス調停検出ハードウェアは転送状態を絶えず監視して、バス調停が発生したかどうか判定します。 TWIモジュールが調停によりバス権を失った場合、そのことがコントロール・ユニットに伝達されて適正な動作が行われ、適切なステータス・コードが生成されます。
アドレス・マッチ・ユニットは、受信したアドレス・バイトがTWIアドレス・レジスタ(TWAR)に設定されている7ビットのアドレスと一致しているかどうかをチェックします。 TWARレジスタのTWIジェネラル・コール検出機能有効(TWGCE)ビットが1にセットされている場合は、全ての受信アドレス・ビットとジェネラル・コール・アドレスとの比較も行います。 アドレス・マッチが発生すると、コントロール・ユニットに伝達され、適正な動作が行われます。 アドレスに対するTWIモジュールのアクノレッジ動作は、TWCRレジスタの設定に応じて、する場合としない場合があります。
アドレス・マッチ・ユニットはAVR MCUがスリープ・モードにある場合でもアドレス比較を行うことができ、マスターからアドレス指定を受けた際にMCUをウェークアップすることが可能です。 スリープ中のTWIアドレス・マッチとCPUのウェークアップ中に他の割込み(例えば、INT0)が発生した場合、TWIは動作を中断して待機状態に戻ります。 この動作によって問題が発生する場合は、パワーダウン・モードに入る際にTWIアドレス・マッチだけが有効な割込みになっているように設定してください。
コントロール・ユニットはTWIバスを監視し、TWIコントロール・レジスタ(TWCR)の設定に応じた応答を行います。 アプリケーションが注意する必要のあるイベントがTWIバス上で発生した場合、TWI割込みフラグ(TWINT)がセットされます。 それにつづくクロック・サイクルで、TWIステータス・レジスタ(TWSR)が更新され、発生したイベントを特定するステータス・コードが格納されます。 TWSRレジスタは、TWI割込みフラグが発効(セット)された時点でのステータス情報のみを保存しています。 それ以外の時間では、TWSRレジスタには、特に相当するステータス情報が無いことを示すコードが格納されています。 TWINTフラグがセットされている間、SCLラインはLowのままになります。 この動作により、TWIのデータ転送の続行される前にアプリケーション・ソフトウェアが必要な処理を完了することができます。
TWINTフラグは、以下の状況でセットされます。
AVR TWIインターフェースは、バイト単位で動作し、割り込みによって使用するように設計されています。 割り込みは全てのバス・イベント、例えば、1バイト受信や、スタート・コンディションの転送の直後に発生します。 TWIインターフェースは割り込みを使って動作するので、アプリケーション・ソフトウェアは、TWIがバイト・データを転送している間、他の処理を行うことができます。 なお、TWCRレジスタのTWI割り込み有効(TWIE)ビットとSREGのグローバル割り込み有効ビットの設定によって、TWINTフラグによって割り込み要求を発生させるかどうかをアプリケーションが決定することができます。 TWIEビットがクリアされている場合、TWINTフラグをポーリング処理して、TWIバス上で行われている動作をアプリケーションが検出しなければなりません。
TWINTフラグが発効されると、TWIインターフェースは現在の動作を完了してアプリケーションによる応答を待ちます。 この場合、TWIステータス・レジスタ(TWSR)には、TWIバスの現在のステータスを示す値が保存されています。 アプリケーション・ソフトウェアは、TWCRレジスタとTWDRレジスタを操作することにより、次のTWIバス・サイクルでTWIインターフェースがどのような動作を行うかを決定することができます。
Figure 21-10は、アプリケーションがTWIのハードウェアとどのようなやりとりを行うことができるかを簡潔に示した例です。 この例では、マスターは1バイトのデータ・バイトをスレーブに送ろうとしています。 この図は非常に抽象的に描かれていますが、より詳しい説明が本章の後半にあります。 目的とする操作をどのように実装するか、についての簡潔なコーディング例も掲載されています。
1. TWIの転送の最初の手順は、スタート・コンディションの送信から始まります。 これは、TWCRレジスタに特定の値を書き込むことによって行われ、TWIハードウェアにスタート・コンディションの送信を行うよう命令します。 具体的にどのような値を書き込むかについては後述しますが、ここで重要なのは、TWINTビットが書き込む値においてセットされていることです。 TWINTビットに1を書き込むことにより、同フラグをクリアします。 TWCRレジスタのTWINTビットがセットされている間は、TWIはいかなる動作も開始しません。 アプリケーションがTWINTビットをクリアすると、直ちにTWIはスタート・コンディションの転送を開始します。
2. スタート・コンディションが転送されると、TWCRレジスタのTWINTフラグがセットされ、TWSRレジスタにスタート・コンディションが正しく送信されたことを示すステータス・コードが書き込まれます。
3. 次にアプリケーション・ソフトウェアはTWSRレジスタの値を検査し、スタート・コンディションが正しく送信されたことを確認します。 TWSRレジスタが異常を示している場合、アプリケーション・ソフトウェアがエラー処理を行うなど、特別な操作をしなければならない場合があります。 ステータス・コードが期待通りであった場合、アプリケーションはSLA+WパケットをTWDRレジスタに書き込む必要があります。 TWDRレジスタはアドレスとデータの両方に使用されることにご注意ください。 TWDRに送信するSLA+Wパケットをロードした後、TWCRレジスタに特定の値を書き込み、TWDRレジスタに格納されているSLA+Wパケットを送信するようTWIハードウェアに命令します。 具体的にどのような値を書き込むかについては後述します。
ここで重要なのは、TWINTビットが書き込む値においてセットされていることです。 TWINTビットに1を書き込むことにより、同フラグをクリアします。 TWCRレジスタのTWINTビットがセットされている間は、TWIはいかなる動作も開始しません。 アプリケーションがTWINTビットをクリアすると、直ちにTWIはアドレス・パケットの転送を開始します。
4. アドレス・パケットが転送されると、TWCRレジスタのTWINTフラグがセットされ、アドレス・パケットが正しく送信されたことを示すステータス・コードがTWSRレジスタに格納されます。 このステータス・コードには、スレーブによってパケットがアクノレッジされたかどうかについての情報も含まれています。
5. 次にアプリケーション・ソフトウェアはTWSRレジスタの値を検査してアドレス・パケットが正しく送信されて、ACKビットが期待していた値になっていることを確認する必要があります。 TWSRレジスタが異常を示している場合、アプリケーション・ソフトウェアがエラー処理を行うなど、特別な操作をしなければならない場合があります。 ステータス・コードが期待通りであった場合、アプリケーションはデータ・パケットをTWDRレジスタに書き込む必要があります。 ひきつづき、TWCRレジスタに特定の値を書き込み、TWDRレジスタに格納されているデータ・パケットを送信するよう、TWIハードウェアに命令します。 具体的にどのような値を書き込むかについては後述しますが、ここで重要なのは、TWINTビットが書き込む値においてセットされていることです。 TWINTビットに1を書き込むことにより、同フラグをクリアします。 TWCRレジスタのTWINTビットがセットされている間は、TWIはいかなる動作も開始しません。 アプリケーションがTWINTビットをクリアすると、直ちにTWIはデータ・パケットの転送を開始します。
6. データ・パケットが転送されると、TWCRレジスタのTWINTフラグがセットされ、データ・パケットが正しく送信されたことを示すステータス・コードがTWSRレジスタに格納されます。 このステータス・コードには、スレーブによってパケットがアクノレッジされたかどうかについての情報も含まれています。
7. 次にアプリケーション・ソフトウェアはTWSRレジスタの値を検査してデータ・パケットが正しく送信されて、ACKビットが期待していた値になっていることを確認する必要があります。 TWSRレジスタが異常を示している場合、アプリケーション・ソフトウェアがエラー処理を行うなど、特別な操作をしなければならない場合があります。 ステータス・コードが期待通りであった場合、アプリケーションはTWCRレジスタに特定の値を書き込み、ストップ・コンディションを送信するよう、TWIハードウェアに命令します。 具体的にどのような値を書き込むかについては後述しますが、ここで重要なのは、TWINTビットが書き込む値においてセットされていることです。 TWINTビットに1を書き込むことにより、同フラグをクリアします。 TWCRレジスタのTWINTビットがセットされている間は、TWIはいかなる動作も開始しません。 アプリケーションがTWINTビットをクリアすると、直ちにTWIはストップ・コンディションの転送を開始します。 ストップ・コンディションの送信の後では、TWINTはセットされないことにご注意ください。
この例は簡潔ではあるものの、TWIにおける全ての転送動作の動作原理について示しています。
以上の動作は、下記のように要約することができます。
下記には、アセンブリ言語とC言語による実装例が示されています。 以下のコードでは、インクルード・ファイルなどにより、必要な定数の定義が行われているものと仮定しています。
アセンブリ言語の例 | C言語の例 | 説明 | |
---|---|---|---|
1 |
ldi r16, (1<<TWINT)|(1<<TWSTA)|(1<<TWEN) out TWCR, r16 |
TWCR = (1<<TWINT)|(1<<TWSTA)|(1<<TWEN); |
スタート・コンディションの送信 |
2 |
wait1: in r16, TWCR sbrs r16, TWINT rjmp wait1 |
while (!(TWCR & (1<<TWINT))) ; |
TWINTフラグがセットされるのを待つ。 同フラグはスタート・コンディションが送信されたことを表す。 |
3 |
in r16, TWSR andi r16, 0xF8 cpi r16, START brne ERROR |
if ((TWSR & 0xF8) != START) ERROR(); |
TWIステータス・レジスタを検査。 分周比設定ビットをマスクする。 ステータスがSTARTと異なっていたらエラー。 |
ldi r16, SLA_W out TWDR, r16 ldi r16, (1<<TWINT)|(1<<TWEN) out TWCR, r16 |
TWDR = SLA_W; TWCR = (1<<TWINT)|(1<<TWEN); |
SLA_WをTWDRレジスタにロード。 TWCRレジスタのTWINTフラグをクリアして、アドレス・パケットの転送開始。 | |
4 |
wait2: in r16, TWCR sbrs r16, TWINT rjmp wait2 |
while (!(TWCR & (1<<TWINT))) ; |
TWINTフラグがセットされるのを待つ。 同フラグはSLA+Wパケットがが送信され、ACK/NACKが受信されたことを表す。 |
5 |
in r16, TWSR andi r16, 0xF8 cpi r16, MT_SLA_ACK brne ERROR |
if ((TWSR & 0xF8) != MT_SLA_ACK) ERROR(); |
WIステータス・レジスタを検査。 分周比設定ビットをマスクする。 ステータスがMT_SLA_ACKと異なっていたらエラー。 |
ldi r16, DATA out TWR, r16 ldi r16, (1<<TWINT)|(1<<TWEN) out TWCR, r16 |
TWDR = DATA; TWCR = (1<<TWINT)|(1<<TWEN); |
DATAをTWDRレジスタにロード。 TWCRレジスタのTWINTフラグをクリアし、データ・パケットの転送開始。 | |
6 |
wait3: in r16, TWCR sbrs r16, TWINT rjmp wait3 |
while (!(TWCR & (1<<TWINT))) ; |
TWINTフラグがセットされるのを待つ。 同フラグはデータ・パケットがが送信され、ACK/NACKが受信されたことを表す。 |
7 |
in r16, TWSR andi r16, 0xF8 cpi r16, MT_DATA_ACK brne ERROR |
if ((TWSR & 0xF8) != MT_DATA_ACK) ERROR(); |
TWIステータス・レジスタを検査。 分周比設定ビットをマスクする。 ステータスがMT_DATA_ACKと異なっていたらエラー。 |
ldi r16, (1<<TWINT) | (1<<TWEN) | (1<<TWSTO) out TWCR, r16 |
TWCR = (1<<TWINT) | (1<<TWEN) | (1<<TWSTO); |
ストップ・コンディションの送信 |
TWIインターフェースは、主要な4つのモードのいずれかで動作します。 このモードには、マスター送信(MT)、マスター受信(MR)、スレーブ送信(ST)、スレーブ受信(SR)があります。 同一のアプリケーション内で複数のモードを使うことができます。 たとえば、TWIのMTモードを用いてTWI EEPROMにデータを書き込み、MRモードを用いてEEPROMからデータを読み戻す、といった使い方です。 システム上に他のマスターが存在し、そのデバイスがTWIにデータを送信する場合には、SRモードを用いることになります。 どのモードを用いるのが適正であるかは、アプリケーション・ソフトウェアの判断により決まります。
この節の以降の部分では、それぞれのモードについて説明をします。 各モードでのデータ転送の詳細図とともに、発生する可能性のあるステータス・コードが説明されています。 この図では、以下の省略記号が使われています。
S: | スタート・コンディション |
Rs: | 再スタート・コンディション |
R: | リード・ビット (SDAはHighレベル) |
W: | ライト・ビット (SDAはLowレベル) |
A: | アクノレッジ・ビット (SDAはLowレベル) |
A: | ノット・アクノレッジ・ビット (SDAはHighレベル) |
Data: | 8ビットのデータ・バイト |
P: | ストップ・コンディション |
SLA: | スレーブ・アドレス |
Figure 21-12からFigure 21-18では、丸い記号が描かれている部分でTWINTフラグがセットされることを表しています。 丸の中の数字はTWSRレジスタに格納されるステータス・コードを、分周比設定ビットをゼロにマスクした値で表しています。 この時点で、TWI転送を続行するか完了するかの動作をアプリケーションが行う必要があります。 TWINTフラグがソフトウェアによってクリアされるまで、TWI転送は中断されたままになります。
TWINTフラグがセットされたとき、TWSRレジスタのステータス・コードを用いてアプリケーション・ソフトウェアの動作を決定します。 それぞれのステータス・コードについて、必要なソフトウェア処理と、それに引き続いて行われるシリアル転送の詳細がTable 21-2とTable 21-5に掲載されています。 各テーブル中では分周比設定ビットはゼロにマスクされていることにご注意ください。
マスター送信モードでは、複数のデータ・バイトがスレーブ受信デバイスへ転送されます(Figure 21-11を参照)。 マスター・モードを開始するには、スタート・コンディションを送信する必要があります。
続いて転送されるアドレス・パケットによって、マスター送信(MT)モードとマスター受信(MR)モードのどちらを開始するかが決まります。 SLA+Wパケットが送信された場合MTモードとなり、SLA+Rパケットが送信された場合MRモードとなります。 この節では、ステータス・コードについての説明はすべて、分周比設定ビットをゼロに設定、またはゼロにマスクしたものという前提で書かれています。
スタート・コンディションは、下記の値をTWCRレジスタに書き込むことで送信されます。
TWCR | TWINT | TWEA | TWSTA | TWSTO | TWWC | TWEN | - | TWIE |
---|---|---|---|---|---|---|---|---|
値 | 1 | X | 1 | 0 | X | 1 | 0 | X |
2線式シリアル・インターフェースを有効にするため、TWENビットを1にします。 TWSTAビットには、スタート・コンディションを送信するため1を書き込み、TWINTビットに1を書き込んでTWINTフラグをクリアします。 この書き込みにより、TWIは2線式シリアル・バスの状態を調べ、バスが開放されると直ちにスタート・コンディションを生成します。 スタート・コンディションが送信された後、TWINTフラグがハードウェアによってセットされ、TWSRレジスタのステータス・コードは0x08 (Table 21-2を参照)になります。 MTモードを開始するためには、SLA+Wパケットを送信するため、TWDRレジスタにSLA+Wを書き込む必要があります。 その後、TWINTビットを(1を書き込むことによって)クリアして転送を続行します。 TWCRレジスタに下記の値を書き込むことにより、この動作が行われます。
TWCR | TWINT | TWEA | TWSTA | TWSTO | TWWC | TWEN | - | TWIE |
---|---|---|---|---|---|---|---|---|
値 | 1 | X | 0 | 0 | X | 1 | 0 | X |
SLA+Wパケットが送信されアクノレッジ・ビットを受信すると、TWINTビットが再びセットされ、TWSRレジスタのステータス・コードは状態に応じた値となります。 マスター・モードで可能性のあるステータス・コードは、0x18、0x20、0x38です。 それぞれのステータス・コードに対して行うべき動作の詳細を、Table 21-2に説明します。
SLA+Wパケットが正しく送信された場合、データ・パケットを送信するため、TWDRレジスタにデータ・バイトを書き込みます。 TWDRレジスタへの書き込みを行ってよいのは、TWINTビットがHighになっている間だけです。 それ以外の場合、同レジスタへのアクセスは破棄され、TWCRレジスタの書き込み衝突ビット(TWWC)がセットされます。 TWDRレジスタを更新した後、TWINTビットを(1を書き込むことによって)クリアし、転送を続行します。 TWCRレジスタに下記の値を書き込むことにより、この動作が行われます。
TWCR | TWINT | TWEA | TWSTA | TWSTO | TWWC | TWEN | - | TWIE |
---|---|---|---|---|---|---|---|---|
値 | 1 | X | 0 | 0 | X | 1 | 0 | X |
この一連の動作は、最後のバイトが送信され、ストップ・コンディションや再スタートコンディションの生成により転送が終了するまで繰り返されます。 ストップ・コンディションは、TWCRレジスタに下記の値を書き込むことによって生成することができます。
TWCR | TWINT | TWEA | TWSTA | TWSTO | TWWC | TWEN | - | TWIE |
---|---|---|---|---|---|---|---|---|
値 | 1 | X | 0 | 1 | X | 1 | 0 | X |
再スタート・コンディションは、TWCRレジスタに下記の値を書き込むことによって生成することができます。
TWCR | TWINT | TWEA | TWSTA | TWSTO | TWWC | TWEN | - | TWIE |
---|---|---|---|---|---|---|---|---|
値 | 1 | X | 1 | 0 | X | 1 | 0 | X |
再スタート・コンディション(ステート 0x10)の後では、2線式シリアル・インターフェースは、ストップ・コンディションを送ることなく、同じスレーブに再びアクセスするか、別のスレーブにアクセスすることができます。 再スタート・コンディションの使用により、マスターがバス権を失うことなく、スレーブを変更してデータを送信したり、マスター送信モードとマスター受信モードを切り換えたりできます。
ステータス・コード(TWSR) 分数比設定ビットはゼロ |
2線式シリアル・バス、およびハードウェアの状態 | ソフトウェアによる応答 | TWIハードウェアにより行われる次の動作 | ||||
---|---|---|---|---|---|---|---|
TWDRレジスタの読み書き | TWCRレジスタへの書き込み | ||||||
STA | STO | TWINT | TWEA | ||||
0x08 | スタート・コンディションが送信された | SLA+Wをロード | 0 | 0 | 1 | X | SLA+Wパケットを送信、ACK/NOT ACKを受信 |
0x10 | 再スタート・コンディションが送信された | SLA+Wをロード | 0 | 0 | 1 | X | SLA+Wパケットを送信、ACK/NACKを受信 |
SLA+Rをロード | 0 | 0 | 1 | X | SLA+Rパケットを送信、マスター受信に切り換え | ||
0x18 | SLA+Wパケットが送信され、ACKを受信した | データ・バイトをロード | 0 | 0 | 1 | X | データ・バイトを送信し、ACK/NACKを受信 |
TWDRの操作なし | 1 | 0 | 1 | X | 再スタート・コンディションを送信 | ||
TWDRの操作なし | 0 | 1 | 1 | X | ストップ・コンディションを送信し、TWSTOフラグをリセット | ||
TWDRの操作なし | 1 | 1 | 1 | X | ストップ・コンディションに続けてスタート・コンディションを送信し、TWSTOフラグをリセット | ||
0x20 | SLA+Wパケットを送信し、NACKを受信した | データ・バイトをロード | 0 | 0 | 1 | X | データ・バイトを送信し、ACK/NACKを受信 |
TWDRの操作なし | 1 | 0 | 1 | X | 再スタート・コンディションを送信 | ||
TWDRの操作なし | 0 | 1 | 1 | X | ストップ・コンディションを送信し、TWSTOフラグをリセット | ||
TWDRの操作なし | 1 | 1 | 1 | X | ストップ・コンディションに続けてスタート・コンディションを送信し、TWSTOフラグをリセット | ||
0x28 | データ・パケットを送信し、ACKを受信した | データ・バイトをロード | 0 | 0 | 1 | X | データ・バイトを送信し、ACK/NACKを受信 |
TWDRの操作なし | 1 | 0 | 1 | X | 再スタート・コンディションを送信 | ||
TWDRの操作なし | 0 | 1 | 1 | X | ストップ・コンディションを送信し、TWSTOフラグをリセット | ||
TWDRの操作なし | 1 | 1 | 1 | X | ストップ・コンディションに続けてスタート・コンディションを送信し、TWSTOフラグをリセット | ||
0x30 | データ・パケットを送信し、NACKを受信した | データ・バイトをロード | 0 | 0 | 1 | X | データ・バイトを送信し、ACK/NACKを受信 |
TWDRの操作なし | 1 | 0 | 1 | X | 再スタート・コンディションを送信 | ||
TWDRの操作なし | 0 | 1 | 1 | X | ストップ・コンディションを送信し、TWSTOフラグをリセット | ||
TWDRの操作なし | 1 | 1 | 1 | X | ストップ・コンディションに続けてスタート・コンディションを送信し、TWSTOフラグをリセット | ||
0x38 | SLA+Wパケット、またはデータ・パケット中に調停動作によりバス権が失われた | TWDRの操作なし | 0 | 0 | 1 | X | 2線式シリアル・バスを開放、アドレス指定を受けていない状態のスレーブ・モードになる |
TWDRの操作なし | 1 | 0 | 1 | X | バスが開放されたときに、スタート・コンディションを送信する |
マスター受信モードでは、複数のデータ・バイトがスレーブ送信デバイスから転送されます(Figure 21-13を参照)。 マスター・モードを開始するには、スタート・コンディションを送信する必要があります。
続いて転送されるアドレス・パケットによって、マスター送信(MT)モードとマスター受信(MR)モードのどちらを開始するかが決まります。 SLA+Wパケットが送信された場合MTモードとなり、SLA+Rパケットが送信された場合MRモードとなります。 この節では、ステータス・コードについての説明はすべて、分周比設定ビットをゼロに設定、またはゼロにマスクしたものという前提で書かれています。
スタート・コンディションは、下記の値をTWCRレジスタに書き込むことで送信されます。
TWCR | TWINT | TWEA | TWSTA | TWSTO | TWWC | TWEN | - | TWIE |
---|---|---|---|---|---|---|---|---|
値 | 1 | X | 1 | 0 | X | 1 | 0 | X |
2線式シリアル・インターフェースを有効にするため、TWENビットを1にします。 TWSTAビットには、スタート・コンディションを送信するため1を書き込み、TWINTビットに1を書き込んでTWINTフラグをクリアします。 この書き込みにより、TWIは2線式シリアル・バスの状態を調べ、バスが開放されると直ちにスタート・コンディションを生成します。 スタート・コンディションが送信された後、TWINTフラグがハードウェアによってセットされ、TWSRレジスタのステータス・コードは0x08 (Table 21-2を参照)になります。 MRモードを開始するためには、SLA+Rパケットを送信するため、TWDRレジスタにSLA+Rを書き込む必要があります。 その後、TWINTビットを(1を書き込むことによって)クリアして転送を続行します。 TWCRレジスタに下記の値を書き込むことにより、この動作が行われます。
TWCR | TWINT | TWEA | TWSTA | TWSTO | TWWC | TWEN | - | TWIE |
---|---|---|---|---|---|---|---|---|
値 | 1 | X | 0 | 0 | X | 1 | 0 | X |
SLA+Rパケットが送信されアクノレッジ・ビットを受信すると、TWINTビットが再びセットされ、TWSRレジスタのステータス・コードは状態に応じた値となります。 マスター・モードで可能性のあるステータス・コードは、0x38、0x40、0x48です。 それぞれのステータス・コードに対して行うべき動作の詳細を、Table 21-3に説明します。 TWINTフラグがハードウェアによりセットされているとき、受信したデータをTWDRレジスタから読み取ることができます。 この手順を最後のバイトを受信するまで繰り返します。
最後のバイトを受信した後、マスター受信デバイス(MR)は、NACKを最後の受信データ・バイトを送ってスレーブ送信デバイス(ST)に通知する必要があります。 データ転送はストップ・コンディション、または再スタート・コンディションを生成することで終了します。 ストップ・コンディションは、TWCRレジスタに下記の値を書き込むことによって生成することができます。
TWCR | TWINT | TWEA | TWSTA | TWSTO | TWWC | TWEN | - | TWIE |
---|---|---|---|---|---|---|---|---|
値 | 1 | X | 0 | 1 | X | 1 | 0 | X |
再スタート・コンディションは、TWCRレジスタに下記の値を書き込むことによって生成することができます。
TWCR | TWINT | TWEA | TWSTA | TWSTO | TWWC | TWEN | - | TWIE |
---|---|---|---|---|---|---|---|---|
値 | 1 | X | 1 | 0 | X | 1 | 0 | X |
再スタート・コンディション(ステート 0x10)の後では、2線式シリアル・インターフェースは、ストップ・コンディションを送ることなく、同じスレーブに再びアクセスするか、別のスレーブにアクセスすることができます。 再スタート・コンディションの使用により、マスターがバス権を失うことなく、スレーブを変更してデータを送信したり、マスター送信モードとマスター受信モードを切り換えたりできます。
ステータス・コード(TWSR) 分数比設定ビットはゼロ |
2線式シリアル・バス、およびハードウェアの状態 | ソフトウェアによる応答 | TWIハードウェアにより行われる次の動作 | ||||
---|---|---|---|---|---|---|---|
TWDRレジスタの読み書き | TWCRレジスタへの書き込み | ||||||
STA | STO | TWINT | TWEA | ||||
0x08 | スタート・コンディションが送信された | SLA+Rをロード | 0 | 0 | 1 | X | SLA+Rパケットを送信、ACK/NOT ACKを受信 |
0x10 | 再スタート・コンディションが送信された | SLA+Rをロード | 0 | 0 | 1 | X | SLA+Rパケットを送信、ACK/NACKを受信 |
SLA+Wをロード | 0 | 0 | 1 | X | SLA+Wパケットを送信、マスター送信に切り換え | ||
0x38 | SLA+Rパケット中のバス調停、またはNACKによりバス権が失われた | TWDRの操作なし | 0 | 0 | 1 | X | 2線式シリアル・バスを開放、アドレス指定を受けていない状態のスレーブ・モードになる |
TWDRの操作なし | 1 | 0 | 1 | X | バスが開放されたときに、スタート・コンディションを送信する | ||
0x40 | SLA+Rパケットが送信され、ACKを受信した | TWDRの操作なし | 0 | 0 | 1 | 0 | データ・バイトを受信し、NACKを返す |
TWDRの操作なし | 0 | 0 | 1 | 1 | データバイトを受信し、ACKを返す | ||
0x48 | SLA+Rパケットが送信され、NACKを受信した | TWDRの操作なし | 1 | 0 | 1 | X | 再スタート・コンディションを送信 |
TWDRの操作なし | 0 | 1 | 1 | X | ストップ・コンディションを送信し、TWSTOフラグをリセット | ||
TWDRの操作なし | 1 | 1 | 1 | X | ストップ・コンディションに続けてスタート・コンディションを送信し、TWSTOフラグをリセット | ||
0x50 | データ・バイトを受信し、ACKを返信した | データ・バイトの読みとり | 0 | 0 | 1 | 0 | データ・バイトを受信し、NACKを返信する |
データ・バイトの読みとり | 0 | 0 | 1 | 1 | データバイトを受信し、ACKを返信する | ||
0x58 | データ・バイトを受信し、NACKを返信した | データ・バイトの読みとり | 1 | 0 | 1 | X | 再スタート・コンディションを送信 |
データ・バイトの読みとり | 0 | 1 | 1 | X | ストップ・コンディションを送信し、TWSTOフラグをリセット | ||
データ・バイトの読みとり | 1 | 1 | 1 | X | ストップ・コンディションに続けてスタート・コンディションを送信し、TWSTOフラグをリセット |
スレーブ受信モードでは、複数のデータ・バイトがマスター送信デバイスから転送されます(Figure 21-15を参照)。 この節では、ステータス・コードについての説明はすべて、分周比設定ビットをゼロに設定、またはゼロにマスクしたものという前提で書かれています。
スレーブ受信モードを開始するには、TWARレジスタ、TWCRレジスタを下記のように初期化する必要があります。
TWAR | TWA6 | TWA5 | TWA4 | TWA3 | TWA2 | TWA1 | TWA0 | TWGCE |
---|---|---|---|---|---|---|---|---|
値 | デバイス自身のスレーブ・アドレス |
上位7ビットは2線式インターフェースがマスターにアドレス指定を受けて応答するためのアドレス設定です。 LSBがセットされている場合、TWIはジェネラル・コール・アドレス(0x00)に応答し、セットされていない場合はジェネラル・コールを無視します。
TWCR | TWINT | TWEA | TWSTA | TWSTO | TWWC | TWEN | - | TWIE |
---|---|---|---|---|---|---|---|---|
値 | 0 | 1 | 0 | 0 | 0 | 1 | 0 | X |
2線式シリアル・インターフェースを有効にするため、TWENビットを1にします。 TWEAビットに1を書き込み、デバイス自身のスレーブ・アドレスやジェネラル・コール・アドレスに対するアクノレッジの応答を有効にします。 TWSTAビット、TWSTOビットには0を書き込んでください。
TWARレジスタ、TWCRレジスタを初期化すると、TWIはデバイス自身のスレーブ・アドレス(または、有効であればジェネラル・コール・アドレス)によりアドレス指定を受け、データ方向ビットを受信するまで待機します。 方向ビットが"0"(ライト)の場合、TWIはスレーブ受信(SR)モードの動作を開始し、そうでない場合はスレーブ送信(ST)モードを開始します。 デバイス自身のスレーブ・アドレスとライト・ビットを受信した後、TWINTフラグがセットされ、TWSRレジスタにセットされたステータス・コードを読み取ることができます。 ステータス・コードを用いて、ソフトウェアがどのような応答をする必要があるか判断します。 各ステータス・コードに対する適切な応答動作については、Table 21-4に詳細が記載されています。
スレーブ受信モードは、TWIがマスター動作を行っているときに調停動作によりバス権を失った場合に、開始される場合があります(ステータス 0x68と0x78を参照)。
TWEAビットが転送動作中にリセットされた場合、TWIインターフェースはその直後の受信データ・バイトの末尾に「ノット・アクノレッジ(NACK、"1")」をSDAラインに返信します。 この動作を用いてスレーブがこれ以上データ・バイトを受信できないことを通知することができます。 TWEAビットが0になっている間、TWIインターフェースは、デバイス自身のスレーブ・アドレスのアクノレッジ動作を行いません。 ただし、2線式シリアル・バスの監視は継続され、TWEAをセットした時点でアドレス認識を再開することができます。 つまり、TWEAビットを使うことによって、TWIインターフェースを2線式シリアル・バスから一時的に切り離すことができます。
アイドル・モード以外の全てのスリープ・モードにおいて、TWIインターフェースへのクロック供給は停止しています。 TWEAビットがセットされている場合、TWIインターフェースは2線式シリアル・バスのクロックで動作することによって、デバイス自身のスレーブ・アドレスやジェネラル・コール・アドレスの認識動作をすることができます。 アドレスが一致すると、デバイスはスリープ・モードからウェークアップ動作を行い、ウェークアップが完了してTWINTフラグを(1を書き込むことにより)クリアするまで、TWIインターフェースはSCLクロックをLowのまま保持します。 AVRのクロックが通常どおり動作を開始すれば、以降のデータ受信は通常どおり行われます。 AVRに長いスタートアップ時間を設定している場合、SCLラインが長時間にわたってLowに保持され、その間バス上で他のデータ転送ができなくなるので、ご注意ください。
各スリープ・モードからウェークアップしたとき、2線式シリアル・インターフェース・データ・レジスタ(TWDR)には、スリープ前にバス上にあったバイト値が保存されていないことにご注意ください。
ステータス・コード(TWSR) 分数比設定ビットはゼロ |
2線式シリアル・バス、およびハードウェアの状態 | ソフトウェアによる応答 | TWIハードウェアにより行われる次の動作 | ||||
---|---|---|---|---|---|---|---|
TWDRレジスタの読み書き | TWCRレジスタへの書き込み | ||||||
STA | STO | TWINT | TWEA | ||||
0x60 | デバイス自身を指定するSLA+Wパケットを受信し、 ACKを返信した | TWDRの操作なし | X | 0 | 1 | 0 | データ・バイトを受信し、NACKを返信する |
TWDRの操作なし | X | 0 | 1 | 1 | データ・バイトを受信し、ACKを返信する | ||
0x68 | マスター動作中のSLA+R/Wパケットで調停によりバス権を失い、 自身を指すSLA+Wパケットを受信した。 ACKを返信した。 | TWDRの操作なし | X | 0 | 1 | 0 | データ・バイトを受信し、NACKを返信する |
TWDRの操作なし | X | 0 | 1 | 1 | データ・バイトを受信し、ACKを返信する | ||
0x70 | ジェネラル・コール・アドレスを受信し、ACKを返信した | TWDRの操作なし | X | 0 | 1 | 0 | データ・バイトを受信し、NACKを返信する |
TWDRの操作なし | X | 0 | 1 | 1 | データ・バイトを受信し、ACKを返信する | ||
0x78 | マスター動作中のSLA+R/Wパケットで調停によりバス権を失い、 ジェネラル・コール・アドレスを受信した。 ACKを返信した。 | TWDRの操作なし | X | 0 | 1 | 0 | データ・バイトを受信し、NACKを返信する |
TWDRの操作なし | X | 0 | 1 | 1 | データ・バイトを受信し、ACKを返信する | ||
0x80 | すでにSLA+Wパケットでアドレス指定を受けている。 データ・パケットを受信した。 ACKを返信した。 | データ・バイトを読みとる | X | 0 | 1 | 0 | データ・バイトを受信し、NACKを返信する |
TWDRの操作なし | X | 0 | 1 | 1 | データ・バイトを受信し、ACKを返信する | ||
0x88 | すでにSLA+Wパケットでアドレス指定を受けている。 データ・パケットを受信した。 NACKを返信した。 | データ・バイトを読みとる | 0 | 0 | 1 | 0 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定やジェネラル・コール・アドレスの認識をしない。 |
データ・バイトを読みとる | 0 | 0 | 1 | 1 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定の認識を行う。 TWGCE = 1ならば、ジェネラル・コール・アドレスの認識も行う。 | ||
データ・バイトを読みとる | 1 | 0 | 1 | 0 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定やジェネラル・コール・アドレスの認識をしない。 バスが開放されたら、スタート・コンディションを送信する | ||
データ・バイトを読みとる | 1 | 0 | 1 | 1 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定の認識を行う。 TWGCE = 1ならば、ジェネラル・コール・アドレスの認識も行う。 バスが開放されたら、スタート・コンディションを送信する | ||
0x90 | すでにジェネラル・コールによるアドレス指定をうけている。 データ・パケットを受信し、ACKを返信した。 | データ・バイトを読みとる | X | 0 | 1 | 0 | データ・バイトを受信し、NACKを返信する |
データ・バイトを読みとる | X | 0 | 1 | 1 | データ・バイトを受信し、ACKを返信する | ||
0x98 | すでにジェネラル・コールによるアドレス指定をうけている。 データ・パケットを受信し、NACKを返信した。 | データ・バイトを読みとる | 0 | 0 | 1 | 0 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定やジェネラル・コール・アドレスの認識をしない。 |
データ・バイトを読みとる | 0 | 0 | 1 | 1 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定の認識を行う。 TWGCE = 1ならば、ジェネラル・コール・アドレスの認識も行う。 | ||
データ・バイトを読みとる | 1 | 0 | 1 | 0 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定やジェネラル・コール・アドレスの認識をしない。 バスが開放されたら、スタート・コンディションを送信する | ||
データ・バイトを読みとる | 1 | 0 | 1 | 1 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定の認識を行う。 TWGCE = 1ならば、ジェネラル・コール・アドレスの認識も行う。 バスが開放されたら、スタート・コンディションを送信する | ||
0xA0 | スレーブとしてアドレス指定を受けている状態で、 ストップ・コンディション、または再スタート・コンディションを受信した。 | 操作なし | 0 | 0 | 1 | 0 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定やジェネラル・コール・アドレスの認識をしない。 |
0 | 0 | 1 | 1 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定の認識を行う。 TWGCE = 1ならば、ジェネラル・コール・アドレスの認識も行う。 | |||
1 | 0 | 1 | 0 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定やジェネラル・コール・アドレスの認識をしない。 バスが開放されたら、スタート・コンディションを送信する | |||
1 | 0 | 1 | 1 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定の認識を行う。 TWGCE = 1ならば、ジェネラル・コール・アドレスの認識も行う。 バスが開放されたら、スタート・コンディションを送信する |
スレーブ送信モードでは、複数のデータ・バイトがマスター受信デバイスへ転送されます(Figure 21-17を参照)。 この節では、ステータス・コードについての説明はすべて、分周比設定ビットをゼロに設定、またはゼロにマスクしたものという前提で書かれています。
スレーブ送信モードを開始するには、TWARレジスタ、TWCRレジスタを下記のように初期化する必要があります。
TWAR | TWA6 | TWA5 | TWA4 | TWA3 | TWA2 | TWA1 | TWA0 | TWGCE |
---|---|---|---|---|---|---|---|---|
値 | デバイス自身のスレーブ・アドレス |
上位7ビットは2線式インターフェースがマスターにアドレス指定を受けて応答するためのアドレス設定です。 LSBがセットされている場合、TWIはジェネラル・コール・アドレス(0x00)に応答し、セットされていない場合はジェネラル・コールを無視します。
TWCR | TWINT | TWEA | TWSTA | TWSTO | TWWC | TWEN | - | TWIE |
---|---|---|---|---|---|---|---|---|
値 | 0 | 1 | 0 | 0 | 0 | 1 | 0 | X |
2線式シリアル・インターフェースを有効にするため、TWENビットを1にします。 TWEAビットに1を書き込み、デバイス自身のスレーブ・アドレスやジェネラル・コール・アドレスに対するアクノレッジの応答を有効にします。 TWSTAビット、TWSTOビットには0を書き込んでください。
TWARレジスタ、TWCRレジスタを初期化すると、TWIはデバイス自身のスレーブ・アドレス(または、有効であればジェネラル・コール・アドレス)によりアドレス指定を受け、データ方向ビットを受信するまで待機します。 方向ビットが"1"(リード)の場合、TWIはスレーブ受信(ST)モードの動作を開始し、そうでない場合はスレーブ送信(SR)モードを開始します。 デバイス自身のスレーブ・アドレスとライト・ビットを受信した後、TWINTフラグがセットされ、TWSRレジスタにセットされたステータス・コードを読み取ることができます。 ステータス・コードを用いて、ソフトウェアがどのような応答をする必要があるか判断します。 各ステータス・コードに対する適切な応答動作については、Table 21-5に詳細が記載されています。
スレーブ送信モードは、TWIがマスター動作を行っているときに調停動作によりバス権を失った場合に、開始される場合があります(ステータス 0xB0を参照)。
データ転送中にTWEAビットに0が書き込まれた場合、TWIインターフェースは最後の転送バイトを送信します。 最後のバイト送信に対してマスター受信デバイスがNACKを返信したか、ACKを返信したかにより、ステータスは0xC0、または0xC8になります。 TWIインターフェースはアドレス指定を受けていない状態のスレーブ・モードに切り換わり、マスターが転送を継続していても無視します。 したがって、この場合、マスター受信デバイスは全ビットが"1"のシリアル・データを受けとることになります。 スレーブが最終バイトを送信した(TWEAビットを0にして、マスターからのNACKを待っている状態)にもかかわらず、マスターがデータ・バイトをさらに要求している場合(ACKを返信している場合)、ステータスは0xC8になります。
TWEAビットが0になっている間、TWIインターフェースは、デバイス自身のスレーブ・アドレスへの応答動作を行いません。 ただし、2線式シリアル・バスの監視は継続され、TWEAをセットした時点でアドレス認識を再開することができます。 つまり、TWEAビットを使うことによって、TWIインターフェースを2線式シリアル・バスから一時的に切り離すことができます。
アイドル・モード以外の全てのスリープ・モードにおいて、TWIインターフェースへのクロック供給は停止しています。 TWEAビットがセットされている場合、TWIインターフェースは2線式シリアル・バスのクロックで動作することによって、デバイス自身のスレーブ・アドレスやジェネラル・コール・アドレスの認識動作をすることができます。 アドレスが一致すると、デバイスはスリープ・モードからウェークアップ動作を行い、ウェークアップが完了してTWINTフラグを(1を書き込むことにより)クリアするまで、TWIインターフェースはSCLクロックをLowのまま保持します。 AVRのクロックが通常どおり動作を開始すれば、以降のデータ受信は通常どおり行われます。 AVRに長いスタートアップ時間を設定している場合、SCLラインが長時間にわたってLowに保持され、その間バス上で他のデータ転送ができなくなるので、ご注意ください。
各スリープ・モードからウェークアップしたとき、2線式シリアル・インターフェース・データ・レジスタ(TWDR)には、スリープ前にバス上にあったバイト値が保存されていないことにご注意ください。
ステータス・コード(TWSR) 分数比設定ビットはゼロ |
2線式シリアル・バス、およびハードウェアの状態 | ソフトウェアによる応答 | TWIハードウェアにより行われる次の動作 | ||||
---|---|---|---|---|---|---|---|
TWDRレジスタの読み書き | TWCRレジスタへの書き込み | ||||||
STA | STO | TWINT | TWEA | ||||
0xA8 | デバイス自身を指すSLA+Rパケットを受信し、ACKを返信した | データ・バイトをロード | X | 0 | 1 | 0 | 最後のデータ・バイトを送信し、NACKの返信を待つ |
データ・バイトをロード | X | 0 | 1 | 1 | データ・バイトを送信し、ACKの返信を待つ | ||
0xB0 | マスター動作中のSLA+R/Wパケットで調停によりバス権を失い、 SLA+Rによるアドレス指定を受けた。 ACKを返信した。 | データ・バイトをロード | X | 0 | 1 | 0 | 最後のデータ・バイトを送信し、NACKの返信を待つ |
データ・バイトをロード | X | 0 | 1 | 1 | データ・バイトを送信し、ACKの返信を待つ | ||
0xB8 | TWDRのデータ・バイトを送信し、ACKを受信した | データ・バイトをロード | X | 0 | 1 | 0 | 最後のデータ・バイトを送信し、NACKの返信を待つ |
データ・バイトをロード | X | 0 | 1 | 1 | データ・バイトを送信し、ACKの返信を待つ | ||
0xC0 | TWDRのデータ・バイトを送信し、NACKを受信した | TWDRの操作なし | 0 | 0 | 1 | 0 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定やジェネラル・コール・アドレスの認識をしない。 |
TWDRの操作なし | 0 | 0 | 1 | 1 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定の認識を行う。 TWGCE = 1ならば、ジェネラル・コール・アドレスの認識も行う。 | ||
TWDRの操作なし | 1 | 0 | 1 | 0 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定やジェネラル・コール・アドレスの認識をしない。 バスが開放されたら、スタート・コンディションを送信する | ||
TWDRの操作なし | 1 | 0 | 1 | 1 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定の認識を行う。 TWGCE = 1ならば、ジェネラル・コール・アドレスの認識も行う。 バスが開放されたら、スタート・コンディションを送信する | ||
0xC8 | TWDRの最終データ・バイトを送信(TWEA = "0")し、 ACKを受信した。 | TWDRの操作なし | 0 | 0 | 1 | 0 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定やジェネラル・コール・アドレスの認識をしない。 |
TWDRの操作なし | 0 | 0 | 1 | 1 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定の認識を行う。 TWGCE = 1ならば、ジェネラル・コール・アドレスの認識も行う。 | ||
TWDRの操作なし | 1 | 0 | 1 | 0 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定やジェネラル・コール・アドレスの認識をしない。 バスが開放されたら、スタート・コンディションを送信する | ||
TWDRの操作なし | 1 | 0 | 1 | 1 | アドレス指定を受けていないスレーブ・モードへ切り換え、 自身のアドレス指定の認識を行う。 TWGCE = 1ならば、ジェネラル・コール・アドレスの認識も行う。 バスが開放されたら、スタート・コンディションを送信する |
TWIで定義されているどの状態にも当てはまらないステータス・コードが二つあります。Table 21-6を参照してください。
ステータス 0xF8は、TWINTフラグがセットされていないので有効な情報が存在しないことを表します。 この状態は、他のステータスとステータスの間の時間帯において、TWIインターフェースがシリアル・転送に関わっていない場合に発生します。
ステータス 0x00は、2線式シリアル・バスの転送動作中にバス・エラーが発生したことを表します。 バス・エラーはスタート・コンディションやストップ・コンディションがフレーム・フォーマットの不正な位置で発生した場合に起こります。
不正な位置の例としては、アドレス・バイト、データ・バイト、アクノレッジ・ビットのシリアル転送中があげられます。 バス・エラーが発生した場合、TWINTがセットされます、 バス・エラーから復帰するためには、TWSTOフラグをセットし、TWINTフラグに1を書き込んでクリアしなければなりません。 この操作により、TWIインターフェースはアドレス指定を受けていない状態のスレーブ・モードとなり、TWSTOフラグがクリアされます(TWCRレジスタの他のビットに影響はありません)。 SDAとSCLラインが開放され、ストップ・コンディションの送信は行われません。
ステータス・コード(TWSR) 分数比設定ビットはゼロ |
2線式シリアル・バス、およびハードウェアの状態 | ソフトウェアによる応答 | TWIハードウェアにより行われる次の動作 | ||||
---|---|---|---|---|---|---|---|
TWDRレジスタの読み書き | TWCRレジスタへの書き込み | ||||||
STA | STO | TWINT | TWEA | ||||
0xF8 | 有効なステータス情報なし。TWINT="0" | TWDRの操作なし | TWCRの操作なし | 待機、または現在の転送動作を継続する | |||
0x00 | 不正なスタート・コンディション、またはストップ・コンディションによるバス・エラー | TWDRの操作なし | 0 | 1 | 1 | X | 内部のハードウェアだけの動作。ストップ・コンディションの送信はしない。どの状態であっても、バスを開放し、TWSTOビットをクリアする。 |
大抵の場合、TWIの複数のモードを組み合わせて、目的とする動作を行います。
シリアルEEPROMからデータを読みとる場合を考えてみましょう。 一般に、このデータ転送には下記のような手順が含まれています。
複数のマスター・デバイスが同一のバス上に接続されている場合、転送動作が一つ以上のマスターにより同時に開始される可能性があります。 このような場合、マスターのうち一つだけが転送を許可され、データが転送動作の途中で失われないように、TWIの規格にしたがって確実に処理します。 バス調停が起こる状況の例を下記に示します。ここでは、二つのマスター・デバイスが、スレーブ受信デバイスにデータの送信をしようとしています。
下記のように、バス調停ではいくつかの異なるシナリオが想定されます。
この動作をFigure 21-21にまとめます。 ステータス・コードがとりうる値は丸の中に記されています。
ビット | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 | |
(0xB8) | TWBR7 | TWBR6 | TWBR5 | TWBR4 | TWBR3 | TWBR2 | TWBR1 | TWBR0 | TWBR |
Read/Write | R/W | R/W | R/W | R/W | R/W | R/W | R/W | R/W | |
初期値 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
TWBRレジスタにより、ビット・レート生成器の分周比を設定します。 ビット・レート生成器は、マスター・モードにおけるSCLクロックの周波数を決定する分周器です。 ビット・レートの計算式については、「ビット・レート生成ユニット」(p.215)を参照してください。
ビット | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 | |
(0xBC) | TWINT | TWEA | TWSTA | TWSTO | TWWC | TWEN | - | TWIE | TWCR |
Read/Write | R/W | R/W | R/W | R/W | R | R/W | R | R/W | |
初期値 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
TWCRレジスタを使って、TWIの動作を制御します。 TWIインターフェースの有効化、スタート・コンディションをバス上に送ることによるマスター動作の開始、受信モードでのアクノレッジの生成、ストップ・コンディションの生成、TWDRレジスタに送信データを書き込んでいる間のバスの停止を行うためにTWCRレジスタを使用します。 TWDRレジスタへのアクセス不可の状態で書き込みを行おうとした場合に起こる書き込み衝突の有無も表しています。
このビットは、TWIが現在の動作を完了しアプリケーション・ソフトウェアによる応答を待つ場合にセットされます。 SREGのIビットがセットされていて、TWCRレジスタのTWIEビットがセットされると、MCUはあTWIインターフェース割り込みベクトルにジャンプします。 TWINTフラグがセットされている間、SCLのLow期間が延長されます。 TWINTフラグは、ソフトウェアによって1を書き込みクリアする必要があります。 このフラグは、割り込み処理の実行によってハードウェアが自動的にクリアしないことに、ご注意ください。 また、このフラグをクリアするとTWIインターフェースが動作を開始するので、TWIアドレス・レジスタ(TWAR)、TWIステータス・レジスタ(TWSR)、TWIデータ・レジスタ(TWDR)へのアクセスは、このフラグのクリアより前に完了していなければなりません。
TWEAビットはアクノレッジ・ビットの生成を制御します。 TWEAビットに1を書き込むと、下記の場合に、TWIバスにACKビットが生成されます。
TWEAビットに0を書き込むことにより、デバイスを2線式シリアル・バスから一時的に切り離した状態にすることができます。 TWEAビットに再度1を書き込むとアドレス認識が再開されます。
2線式シリアル・バスのマスターとして動作を開始する場合、アプリケーション・ソフトウェアによりTWSTAビットに1を書き込みます。 TWIハードウェアは、バスが利用できる状態かどうかチェックし、バスが開放されていればスタート・コンディションを生成します。 ただし、バスが開放されていない場合、TWIインターフェースはストップ・コンディションが検出されるまで待機し、新たにスタート・コンディションを生成してバス・マスターになることを要求します。 スタート・コンディションが送信されたら、ソフトウェアによってTWSTAビットをクリアしなければなりません。
マスター・モードでTWSTOビットに1を書き込むと、ストップ・コンディションを2線式シリアル・バス上に生成します。 ストップ・コンディションがバス上に生成されると、TWSTOビットは自動的にクリアされます。 スレーブ・モードでは、TWSTOビットをセットして、エラー状態からの復帰をするのに使うことができます。
この場合、ストップ・コンディションは生成されませんが、TWIインターフェースはアドレス指定を受けていない状態のスレーブ・モードに復帰し、SCLとSDAラインをハイ・インピーダンスにして開放します。
TWINTビットがLowのときにTWIデータ・レジスタ(TWDR)に書き込みを行おうとした場合、TWWCビットがセットされます。 このフラグは、TWINTフラグがHighのときにTWDRレジスタに書き込みを行うことでクリアされます。
TWENビットにより、TWIの動作が有効になり、TWIインターフェースが使用できる状態になります。 TWENビットに1を書き込むと、TWIインターフェースがSCLとSDAの入出力端子を制御し、スルーレート制限とスパイク・ノイズ・フィルターが有効になります。 このビットに0を書き込むと、TWIインターフェースはオフとなり、全てのTWI転送は現在の動作状態に関係なく、終了されます。
このビットは予約となっており、リード時に常に0となります。
このビットに1がセットされ、SREGのIビットがセットされている場合、TWINTフラグがHighとなっているときにTWI割り込み要求が発生します。
ビット | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 | |
(0xB9) | TWS7 | TWS6 | TWS5 | TWS4 | TWS3 | - | TWPS1 | TWPS0 | TWSR |
Read/Write | R | R | R | R | R | R | R/W | R/W | |
初期値 | 1 | 1 | 1 | 1 | 1 | 0 | 0 | 0 |
この5ビットに、TWI制御回路と2線式シリアル・バスのステータスが反映されます。 各ステータス・コードについては、この節中に説明があります。 TWSRレジスタから読み出した値には、5ビットのステータス値と2ビットの分周比設定ビットが含まれていることにご注意ください。 アプリケーション・ソフトウェアの設計では、ステータス・ビットをチェックするときに、分周比設定ビットを0にマスクする必要があります。 このビット・マスク操作によって、分周比の設定値に関係なく、ステータスをチェックすることができます。 このデータシート中では、特に記載のないかぎり、このビット・マスクを行っているものとします。
このビットは予約となっており、リード時に常に0となります。
このビットは読み書きが可能で、ビット・レート分周器の設定を行います。
TWPS1 | TWPS0 | 分周比 |
---|---|---|
0 | 0 | 1 |
0 | 1 | 4 |
1 | 0 | 16 |
1 | 1 | 64 |
ビット・レートの計算式については、「ビット・レート生成ユニット」(p.215)を参照してください。 TWPS1..0の値が式中に使用されています。
ビット | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 | |
(0xBB) | TWD7 | TWD6 | TWD5 | TWD4 | TWD3 | TWD2 | TWD1 | TWD0 | TWDR |
Read/Write | R/W | R/W | R/W | R/W | R/W | R/W | R/W | R/W | |
初期値 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 |
送信モードでは、TWDRレジスタには次に送信するバイトが格納されます。 受信モードでは、TWDRレジスタに最後に受信したバイトが保存されます。 TWIインターフェースがバイトのシフト操作を行っていないとき、このレジスタに書き込みができます。
TWI割り込みフラグ(TWINT)がハードウェアによってセットされることで、レジスタへの書き込みが可能になります。 データ・レジスタは最初の割り込みが発生するまでは、ユーザーによって初期化することができないことにご注意ください。 TWDRレジスタ中のデータはTWINTビットがセットされている限り、変化することなく保持されます。 データがシフト出力されている間、バス上のデータが同時にシフト入力されます。 スリープ・モードからTWI割り込みでウェークアップした場合をのぞき、TWDRレジスタには常にバス上にあった最後のバイトが保存されています。 ウェークアップ時のTWDRレジスタの内容は未定義状態です。 調停によりバス権を失った場合でも、マスターからスレーブへのステータス移行によってデータが失われることはありません。 ACKビットの処理はTWI制御回路により自動的に行われており、CPUが直接ACKビットにアクセスすることは出来ません。
この8ビットには、次に送信されるデータ・バイトが含まれているか、または、2線式シリアル・バス上から最後に受信したデータ・バイトが保存されています。
ビット | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 | |
(0xBA) | TWA6 | TWA5 | TWA4 | TWA3 | TWA2 | TWA1 | TWA0 | TWGCE | TWAR |
Read/Write | R/W | R/W | R/W | R/W | R/W | R/W | R/W | R/W | |
初期値 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 0 |
TWARレジスタには、TWIインターフェースがスレーブ送信(ST)モード、スレーブ受信(SR)モードとして応答する場合に用いる、7ビットのスレーブ・アドレス(TWARレジスタの上位7ビット)をロードします。 このアドレスはマスター・モードの動作では必要ありません。 複数のマスターが存在するシステムでは、他のマスターからスレーブとしてアドレス指定を受けるために、マスターにTWARレジスタを設定する必要があります。
TWARレジスタのLSBは、ジェネラル・コール・アドレス(0x00)の認識を有効にするために使用します。 受信したシリアル・アドレス中のスレーブ・アドレス(または、有効になっていれば、ジェネラル・コール・アドレス)を監視するアドレス比較回路があり、アドレスの一致を検出した場合、割り込み要求が発生します。
この7ビットは、TWIユニットのスレーブ・アドレスとなります。
このビットがセットされている場合、2線式シリアル/バス上のジェネラル・コールの認識が有効になります。
ビット | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 | |
(0xBD) | TWAM[6:0] | - | TWAMR | ||||||
Read/Write | R/W | R/W | R/W | R/W | R/W | R/W | R/W | R | |
初期値 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
TWAMRレジスタには、7ビットのスレーブ・アドレス・マスクを設定します。 TWAMRレジスタの各ビットによって、TWIアドレス・レジスタ(TWAR)の対応するビットをマスク(無効に)することができます。 マスク・ビットが1にセットされている場合、アドレス一致検出回路は、それに対応する受信したアドレス・ビットとTWARレジスタのビットの比較結果を無視します。 Figure 21-22にアドレス一致検出回路の詳細を示します。
このビットはATmega48/88/168では未使用であり、リード時には常に0になります。