MOSFETによる双方向電圧レベルシフト回路の仕組み
電圧レベルシフトについて
ArduinoとRaspberry Piの間で通信をすることになった。
I2CとかSPIを使って通信することになった。
この二つを接続する時、直接接続してはいけないことに注意しないといけない。
Arduinoの信号レベルは5Vなのに対し、Raspberry Piの信号レベルは3.3V。
だから例えば両者を直接接続したとき、Arduinoからの5V信号がRaspberry Piに届くとRaspberry Piの基板が破壊される危険性がある。
これを防ぐためには、通信路の間に「電圧レベルシフト回路」というものを挟む必要がある。
今回紹介するのは、MOSFETによる双方向電圧レベルシフト回路。
これを使うと、信号のレベルが5Vから3.3Vへ、3.3Vが5Vへと双方向に変換されるので、基板を破壊する心配がなくなる。
この回路にはもう一つ利点があって、信号レベルを安定化させることが可能。
例えば両者を直接つないでいたとして、3.3V基板からHIGHを出力したとする。
5V駆動のArduinoでは、HIGH/LOWのスレッショルドが約2.5Vらしいので、3.3VでもHIGHと認識される。
しかし何らかの原因で3.3Vの出力がゆらいで2.5Vを下回ってしまった時、HIGHのはずがArduinoではLOWと認識されてしまう。
電圧レベルシフトを使うと、そのように揺らいだ電圧も変換して5Vまで引き上げられるので、Arduino側でLOWと認識されずに済む。
こんなに便利な回路だが、動作の仕組みがやや分かりにくくて、きちんと理解しようと思ったら少し詰まってしまった。
このサイトをみてやっと理解できたので、ここでも解説してみる。
分かりやすいサイトがあったおかげで知恵袋に質問する手間が省けてよかった。
回路
回路はこんな感じ。
今回はArduinoとRaspberry Piで使う予定だったので、3.3V側はRaspberry PiのGPIO、5V側はArduinoのIOを接続することを想定。
レベルシフトで重要なMOSFETは、NchエンハンスメントMOSFETである2N7000を使用。
3.3V→5V
HIGHになるとき
RPi_GPIOがHIGHのとき、ゲート-ソース間に電位差がないので、ドレイン-ソース間に電流が流れない。
よって、Arduino_IOが5V出力でプルアップされる。
つまりArduino_IOがHIGHになる。
ついついゲートに電圧かけるだけでFETがONになると考えちゃうけど、そーだった、ソースの電圧も高くなるとオフになるんだったわ。
相対的な電圧差でオンオフが切り替わるんだったな。
なるほど。
LOWになるとき
RPi_GPIOがLOWの時、ゲート-ソース間に電位差が生じるので、ドレイン-ソース間に電流が流れる。
この時、Arduino_IOがプルダウンされ、Arduino_IOはLOWになる。
5V→3.3V
HIGHになるとき
最初、RPi_GPIOは3.3Vでプルアップされているので、ドレイン-ソース間には電流が流れない。
Arduino_IOが5Vなので、結果的に両者がHIGHになる。
LOWになるとき
最初、RPi_GPIOは3.3Vでプルアップされているので、ドレイン-ソース間には電流が流れていない。
Arduino_IOがLOWになると、2N7000の寄生ダイオードに電流が流れ、RPi_GPIOの電圧が降下し始める。
すると、ゲート-ソース間に電位差が生じ、ドレイン-ソース間に電流が流れるようになる。
すると、RPi_GPIOがプルダウンされ、RPi_GPIOがLOWになる。
プルアップ抵抗は10Kで良いと思いますよ。
理由はご想像の通りです。
あ、周囲に激しいノイズ源が有るならやむなし。