趣味のマイコンいじり

安価なマイコンを利用して作成したアプリの紹介です。

Arduino IDE からのコード書き込みを調べてみました

最近ArduinoでのESP系のチップのボードの利用を検討していて、それらに対する
コードの書き込み方法を調査してまとめて見ました。その状況は次の様なものです。

<スケッチコード書き込み動作の概要>
   USBポートからの書き込み機能を持たないボードとして、Arduino Pro Mini
   および ESP-xx のチップマウントボードが有ります。これらのボードへの
   Arduino IDEからのコードの書き込み方法を調査し、ESP-xx 用に関しては
   オリジナルの回路も作って見ました。 その時の状況は次の様なものでした。

 [Arduino Pro Mini の場合]
    イメージ 1

  1.リセットがかかると、まずブートローダが起動
  2.ブートローダIDEからの書き込み要求コマンドを待つ
  3.IDEからの書き込み要求が正当なものの場合は書き込み処理を実行
  4.IDEからの書き込み要求が無いか不当な時はユーザープログラムを実行
  5.IDEは書き込み開始時にDTR端子をLowに設定してリセットのタイミングを
          取る
  6.DTRの出力を持たないUSBtoTTLのデバイスでは、書き込み開始前に
      マニュアルでリセットして、ブートローダ期間にIDEからの書き込みが開始
        する様に調整する必要が有る。(リセットタイミングの調整は多少困難)

   <書き込み時のIDEからの出力>
      イメージ 2

 [ESP-xx の場合] 
    ESP-xxの場合はブートローダの方式では無く、チップを書き込みモードに設定
    して書き込みを行います。ただし、この書き込みモードへの移行を、USBtoTTL
    のデバイスの電源投入時の不安定なデバイスの出力に対して防ぐ必要が有り、
    多少厄介な処理となっています。その為、WeMos D1 と ESP-32系では、DTRと
    RTSの出力の組み合わせる次の様な回路で対応しています。
    イメージ 3

  1.書き込み処理の時、まずDTRをHi、RTSをLowに設定する
  2.この時、RES(RST)がLowとなる(ESP-32系ではEN)
  3.次に、DTRをLow、RTSをHiに設定する
  4.この時、GPIO0はLowとなるが、RESはコンデンサが有るためすこし遅れて
          Hiとなりリセット解除時にGPIO0をLowにする書き込みモードへの移行の
          条件が成立する
  5.その後、IDEから書き込みデータが送られれば書き込み処理が実行される
  6.なお、書き込みモードへの移行は、リセット解除時にGPIO0をLowにして
          おけば良く、マニュアルのスイッチ操作で行ってもそれ程難しくない
  7.この回路は WeMos D1 で採用されているもので、この回路を採用している
          ボードはボートの設定を WeMos D1 にすればIDEからの自動書き込み処理
          が実行される
  8.ESP8266系では、他のボードの設定にすると上記のDTRとRTSの出力
          タイミングが変わり、この回路が有効に働かない場合が有る
  9.ESP-32系のボード設定では、WeMos D1 のタイミングが採用され、この
          回路が有効に働いている様に思われる

   <WeMos D1 でのIDEからの出力>
     イメージ 4

  <ESP-32でのIDEからの出力>
     イメージ 11

<USBtoTTLデバイスの電源投入時>         
   USBtoTTLデバイスの電源投入時のコントロールポートからの出力は次に様な
   状況です。Arduino Pro Mini の様にブートローダ形式で有れば、リセットが
   複数回起きるだけで、問題なく利用できますが、ESP-xx の様に書き込みモード
   を持つものでは、静的な判断の処理だけでは書き込みモードに入って、リセット
   をしないと正常に起動しなくなる確率が非常に高くなります。 その点、
   WeMos D1 で採用されているのは、コントロールポートの時系列の変化を利用
   するものとなっていますので、不要な書き込みモードを避ける画期的なものだと
   思います。
   イメージ 5

<ESP8266系で自動書き込みの問題点> 
   ESP8266系で WeMos D1 のボードを選択して書き込みを行う場合には、上記の
   回路が利用できますが、他のボードを選択するとUSBtoTTLデバイス
   コントロールポートからの出力タイミングが異なってきます。以下は
   Generic ESP8266 Module を選択した場合です。
   イメージ 6

  1.書き込み処理の時、DTRとRTSの両方がLowになる
  2.次にRTSがHiとなり、その後DTRもHiとなる
  3.WeMos D1 の場合の様に時系列にコントロールポートを変更するもので
          ない為、USBtoTTLデバイスの電源投入時の不安定な動作で同様な
          タイミングが発生する可能性が高い

<作成したESP-xx用自動書き込み処理>
   以上の様にESP-xx全般で利用できるIDEからの自動書き込み処理は困難なのが
   判りましたが次の点を妥協したもので実現する方法を検討する事にしました。

  1.USBtoTTLデバイスの電源投入時の書き込みモードへの移行に対しては、
          頻度が少ないのでマニュアルのリセット処理で対応する。
  2.また、コード検討時とUSBからの電源利用時をショートジャンパーの
          切り替えで対応する。

    以上の点を考慮して検討したものが次の回路となります。 Arduino Pro Mini と
    同様にDTRの信号のみを利用したものとなっています。(回路用の材料は
    秋月電子から購入しました。)
    イメージ 7

      イメージ 8

<データ取得に利用した機材>
   以上のデータの取得に利用した機材は次のものです。
   イメージ 9


  1.24MHz/8CHロジックアナライザ
  2.WeMos D1
  3.USB to TTL

<作成したESP-xx用の書き込みツール>
   USBtoTTLのデバイスが3種類有りますので、それぞれに対するものを作って
   みました。なお、3.3Vの電源を搭載していない2種類に関しては、3.3V
   の電源も搭載しました。
   イメージ 10

<ESP-xxでの書き込み上の注意>
   ESP8266では、前に書き込んだコードの内容により、書き込み回路ではGPIO0が
   Lowにならないで書き込みモードに移行しない時が有る様です。(WeMos D1 で
   最初に経験)その時には、書き込みの時にGPIO0をジャンパー線でGNDに接続
   する事で解決しました。

<余談>
   以上の内容から、どうせリセットスイッチは付けるのだから、書き込み時には
   GPIO0をGNDに接続してリセットをかければ良いのではないかとの結論が出る
   かと思います。確かに、上記で作成した回路を組むのはそれなりに時間がかかり
   ますので、コード修正の頻度とIDEからの自動書き込みができると少し楽しい
   気分になる事に対する価値判断で、どうするかを決めるのが良いかと思います。
   英語の記事に書き込みシーケンス等に関する記述が詳しく書いて有ったので、
   自分なりにそれらを確認するつもりでまとめて見ました。