ワレコ
このところArduinoやAVRマイコンを学習中だ。
その過程でATmega328Pチップにプログラムを書き込めなくなるトラブルに何度か遭遇した。
当記事では、その解決方法が分ったので記事にしてみた。
では、本題に入ろう。
ArduinoとAVRの関係
ワテの場合、ArduinoやAVRに関してはまだまだ初心者なのだが、ある程度は理解出来て来た部分もあるので備忘録としてまとめておこう。あくまでワテの理解なので間違いや勘違いもあるかも知れないが。その時は末尾のコメント欄から教えて頂けると有難いです。
まずArduino UNOとはこんなやつだ(下写真)。
Arduino UNOはパソコンとはUSB接続で簡単につなぐ事が出来て、デジタルやアナログの入出力ポートが幾つかある。専用の開発環境Arduino IDEが無料で公開されているので、誰でも簡単にマイコンプログラミングが出来るのだ。
Arduinoには幾つかの種類があるがArduino UNOや小型のArduino Nano(下写真)が一般的だ。
もしArduino Unoを買うなら、単品で買うよりも下写真のような初心者キットを買うと良い。
各種センサー、モーター、抵抗、ブレッドボードなど多数の電子パーツがセットになっているので、これ一つで各種の実験が可能だ。
Arduino UNOの基板
Arduino UNO基板の写真を以下に示す。
写真 Arduino UNOの入出力端子
引用元 https://forum.arduino.cc/t/can-i-reassign-spi-pins-on-an-arduino-uno/510012
上写真のArduino UNOの基板には二つのAVRマイコンが搭載されている。
一つはDIP28ピンソケットに刺さっている大型のATMEGA328P-PUと、もう一つはUSBソケットの右にある正方形で四辺に端子が出ているQFP(Quad Flat Package) 32タイプのATMEGA16U2-MU(R) だ。
下のURLで示すArduino公式サイトにArduino UNOの回路図があるので参考にして頂きたい。
https://content.arduino.cc/assets/UNO-TH_Rev3e_sch.pdf
Arduinoの開発環境であるArduino IDEを使ってプログラム(スケッチと呼ぶ)を作成した場合には、そのプログラムはDIP28ピンソケットに刺さっているATMEGA328P-PUに書き込まれる。
一方、USBソケットの近くにあるLQFP-32パッケージのATMEGA16U2-MU(R) はArduino UNOがパソコンとUSB接続する為に入っている。つまりUSBシリアル変換の動作をするプログラム(ファームウェア)が書き込まれている。
このATMEGA16U2-MU(R) がUSBシリアル変換の機能を提供するので、Arduino UNOとパソコンはUSB接続出来るのだ。
その結果、Arduino IDEの開発環境でATMEGA328P-PUに何らかのプログラミングをして動作をさせた場合には、Arduino IDEのシリアルモニタ画面に文字を表示するなどが可能だ。逆に、COMポート経由でパソコンからArduino UNOへデータを送信する事も出来る。
と言う訳でワテの理解ではArduino UNOとは、メインのAVRマイコンであるATMEGA328P-PUと、サブのAVRマイコン(USBシリアル変換機能として動く)が合体したようなものだ。
AVRマイコンを単体で使う
一方、AVRマイコン(例 ATMEGA328P-PU)を単体で使う事も出来る。実際ワテも先日AVRマイコン単体でLチカ実験などやってみた(下記事)。
AVRマイコン単体の場合にはそのままではパソコンとは直接に接続出来ないのでAVRのライターとかデバッガーと呼ばれる機器を間に入れる。
具体的にはワテが使っているのは下写真のATMEL-ICEだ。
或いは下写真のような製品もある。
これらの機器とAVRマイコンとの接続は6pinのフラットケーブルを使い、AVRマイコンにある以下の六つのピンに接続する。
2 VCC
3 SCK
4 MOSI
5 /RESET
6 GND
この六つのピンは上で示したArduino UNOにもありICSP端子と呼ばれている。ICSPとは In Circuit Serial Programmingの略だ。
Arduino UNOの場合にはATMEGA328P-PUとATMEGA16U2-MU(R)の二つのAVRマイコンが搭載されているので、先ほど上で示したArduino UNO写真にはICSP端子も二つあるのが分かるだろう。
AVRマイコン単体では文字を表示出来ない
ワテの場合はMicrochip Studioと言う開発環境を使ってAVRマイコン単体でLEDチカチカくらいしか成功していないのだが、一つ気付いた点がある。
それはAVRマイコンを単体で使ってMicrochip Studioでプログラミングする場合、printf() みたいなコマンドで変数の値を画面に表示出来るのかなと思ったら、それが出来ないようなのだ。
一般にプログラミングする場合にはC言語系ならprintf、C#ならConsole.WriteLineやDebug.WriteLineなどのメソッドを使えば簡単に文字列や数字を画面に表示出来る。
ところがAVRマイコン単体だとそれが出来ないようなので、もしATMEL-ICEを使ってデバッグ中に変数の値を確認したい場合には、例えばデバッガーでブレークポイントで停止させて変数の値をユーザーが手作業で確認するなどの作業が必要になる。
何だか面倒くさいぞ。
じゃあAVRマイコン単体でプログラミングする場合に、画面に文字を表示させたい場合にはどうすれば良いかと言うと、例えばLCDパネルを接続しておいてそこに出力するなどの案が浮かぶ。
ワテも先日、AVRマイコンを単体で使ってLCDパネルに文字出力は出来た(下記事)。
あるいは、USBシリアル変換モジュールと言ったパーツを買ってAVRマイコンと組み合わせて使う方式でも良いだろう。
例えば上写真の製品の場合、6ピンが出ているが商品説明には以下の記述がある。
本品 - AVR
RI - RESET
RSD - SCK
CST - MISO
DCD - MOSI
GND - GND
VCC - VCC
要するにこの6ピンを使えばAVRマイコンのICSP端子の6ピンとそのままつなぐだけでAVRマイコンをUSB経由でパソコンと接続出来るはずだ。
そうすればCOMポートのモニタ画面を出して文字出力するなどが可能だろうと思う(たぶん)。
でもAVRマイコンにUSBシリアル変換モジュールを接続して使うと言うのは、それはArduino UNOを使うみたいなもんだろ!?
それなら最初から素直にArduino UNOを使う方が良いのかも知れない。
動かなくなったATmega328Pを復活させる
さてArduinoやAVRマイコンを学習中のワテであるが、Arduino UNOに刺さっているATmega328Pマイコンを抜いて単体でブレッドボードに挿して、ATMEL-ICEとICSP接続してMicrochip Studioの環境でいじくり回していると当然ながらブートローダーも消えてしまう。
そのATmega328Pマイコンを再びArduino UNOに挿して再びArduino IDEの環境でスケッチを書き込もうとしても、エラーで失敗。
それならブートローダーを再び書き込めば回復するはずだ。
ブートローダー書き込みシールドを使う案
ネット検索するとブートローダーが書き込まれていない新品のATmega328Pチップを買って来て、それにArduino用のブートローダーを書き込むやり方は沢山の解説記事がある。
その一つに、Arduino UNOを使って新品のATmega328Pチップにブートローダーを書き込むやり方がある。
具体的にはブレッドボードに新品のATmega328Pチップを挿して、Arduino Unoとはジャンパーワイヤーで接続しておく。
一方、Arduino UNOにはブートローダーを書き込む為のスケッチが用意されているので、それを実行するのだ。
要するにこの方法では正常動作するArduino UNOが一台は必要になる。それを使って別のATmega328Pチップにブートローダーを書き込むのだ。
ワテもそれをやってみようかなと思ったのだが、ATmega328Pチップにブートローダーを書き込む作業が必要になる度に毎回ブレッドボードにジャンパーワイヤーで配線するのは面倒だし。
そんなめんどくさがり屋のワテはこんな製品を見付けた(下写真)。
まあ要するに、ブレッドボードにジャンパーワイヤーで配線しなくても、このブートローダ書き込み用基板(シールドと呼ばれる)をArduino Unoに重ねて挿し込めば良いのだ。その基板にはゼロプレッシャーソケットがあるので、そこにATmega328Pチップを挿しておけば良い。
実際にワテはこの製品を使って新品のATmega328Pにブートローダーを書き込む事に成功した。そのATmega328Pは正常動作しているArduino UnoのATmega328Pと差し替えても無事にArduino Unoとして動かす事も出来た。
一方、Arduino IDEやMicrochip Studioを使ってArduino UnoやAVR単体マイコンをプログラミングしていじくり回して訳分からなくなったATmega328Pもこの方法でブートローダーの書き込みに成功して再びArduino Unoで利用出来るようになったものもある。
でも中には、ブートローダーの書き込み時にエラーして書き込めないものもあった。エラーの詳細は未確認だ。もう訳分からんw。
たぶんFUSE BIT(ヒューズビット)と言うやつが関係しているようなのだが、ワテの場合、まだヒューズビットは良く理解出来ていない。
その結果、使えなくなったATmega328Pチップが三個くらいある。
どうにかしないと使えないチップが溜まる一方だ。
ATMEL-ICEとICSP接続して復活させる案
そんな時にイチケンさんのYouTube動画を見付けた。
動画 Arduino UNOを自作しました。 How to Make your own Arduino UNO
引用元 イチケンさんのYouTube
この動画では、世間に公開されているArduino UNOの基板データを使ってイチケンさんがプリント基板を外注して、その基板にパーツを半田付けして、Arduino UNO互換機を製作している。
製作した互換機にはファームウェアとブートローダーを書き込む事で初めてArduino Unoとして動作するのだが、ワテもその部分を参考にして動かなくなったATmega328Pにブートローダーを書き込む事が出来た。
以下、その手順を紹介したい。やっている事は上のイチケンさん動画と全く同じだが。
ファームウェアを書き込む
Arduino Uno用のファームウェアとブートローダーは以下のフォルダで見付けた。
“C:\Program Files (x86)\Arduino\hardware\arduino\avr\bootloaders\optiboot\optiboot_atmega328.hex”
まずはATMEGA16U2-MU(R)にファームウェアを書き込む。
具体的には下写真のようにATMEGA16U2-MU(R)のICSP端子にATMEL-ICEを6Pのデバッグワイヤーで接続する。
写真 Arduino Uno基板にあるATMEGA16U2-MU(R)のICSP端子にATMEL-ICEを接続
なおイチケンさんが使っているAVRライターは白いATMEL-ICEでは無くて青色ケースに入っている他のタイプだ。でもまあたぶんICSPの6端子で接続するライターならどれでも良いと思う。
下写真はそのATMEGA16U2-MU(R)マイコンのICSP端子拡大。
写真 Arduino Uno基板のATMEGA16U2-MU(R)のICSP端子拡大
以下ではMicrochip Studioを起動してこのATMEGA16U2-MU(R)にファームウェアを書き込む。
なお、動かなくなったATMEGA328Pを回復させるならATMEGA328Pにブートローダーを書き込むだけで良さそうだが、ワテが試した限りではそれではダメな場合もあった。
そこでファームウェアの書き込みを行い次にブートローダーの書き込みを行ったところ、無事にATMEGA328Pを復活させる事が出来たので、以下でもその手順を行う。
Microchip Studioの空のソリューションを開く
下図のようにMicrochip Studioの新規プロジェクトメニューを開く。
図 Microchip Studioの新規プロジェクトメニューを開く
下図のように新しいプロジェクト画面が開くので、空のソリューションを選ぶ。
図 新しいプロジェクト画面が開くので空のソリューションを選ぶ
空のソリューションが開いたら下図のようにツールメニューのDevice Programmingを開く。
図 ツールメニューのDevice Programmingを開く
ファームウェア書き込み用ヒューズビット設定
下図のようにファームウェア書き込み用のヒューズビットを設定する。
図 ファームウェア書き込み用のヒューズビットを設定する
上図に於いて、ワテの場合はLOWの部分が初期状態では0xFFだったので、それをイチケンさん動画に従って0xEFに変更した。
その意味は良く分かっていないので今後、調査したい。
ファームウェア書き込みを実行
あとは、下図のようにファームウェアファイルを指定して、Programボタンを押せば良い。
図 ファームウェアファイルを指定してProgramボタンを押す
上図のようにProgramボタンをクリックして、ステータス欄に幾つかのOKの表示が出れば成功だ。
これで無事にファームウェアが書き込めた。
ブートローダーを書き込む
次はATMEGA328P本体にブートローダーを書き込む。
下図のように6PデバッグワイヤーをICSP端子に接続する。
図 6PデバッグワイヤーをATMEGA328PチップのICSP端子に接続する
この6ピンのICSP端子は向きがどっちなのか良く混乱するので、ワテの場合は下写真のようにデバッグワイヤー側の6Pソケットの凸形状の絵を描いている。
写真 ICSP端子にデバッグワイヤーソケットの凸側の向きを絵に描いて挿し間違い防止
ブートローダー書き込み用ヒューズビット設定
イチケンさん動画を参考にしてブートローダー書き込み用のヒューズビットを設定する。
図 ブートローダー書き込み用のヒューズビットを設定
上図に於いて、ワテの環境ではヒューズビットの初期状態は上図の通りで、それはイチケンさん動画の設定値と同じだった。なのでワテは何も変更していない。
ブートローダー書き込みを実行
あとは下図のようにブートローダーファイルを指定してProgramボタンをクリックすれば良い。
図 ブートローダーファイルを指定してProgramボタンをクリック
上図のようにProgramボタンをクリックして、OKが表示されれば成功だ。
これでブートローダーの書き込みが完了した。
ブートローダーを書き込んだATMEGA328PをArduino Unoで試す
無事にブートローダーの書き込みに成功したので、次はこのATMEGA328Pが載っているArduino Unoが正常に動作するか試してみる。
まずはATMEL-ICEは取り外し、Arduino UNO基板にあるUSB端子を使ってパソコンと接続する。
次にArduino IDEを起動して、サンプルにあるスケッチ「Blink」を実行してみる。
図 Arduino IDEを起動してサンプルスケッチのBlinkを開く
シリアルポートはワテの環境では下図のようにCOM3に設定している。
図 シリアルポートをCOM3に設定した
そして下図のようにスケッチを書き込んだ。
図 LEDチカチカのスケッチを書き込む
その結果、Arduino Uno基板上にあるLEDが点灯1秒、消灯1秒の間隔で点滅を繰り返している。
いい感じだ。
これで使えなくなっていたATMEGA328Pマイコンチップを無事に復活させる事が出来た(はずだ)。
まとめ
ワレコ
最近ようやくArduinoとAVRの関係が分かって来た。
でもヒューズビットに関しては何も分かっていないワテである。
あかんがなw
当記事では、Arduino IDEやMicrochip Studioを使って弄くり回してArduinoとしてプログラミング不能になってしまったAVRマイコンATMEGA328Pを復活させる手法をまとめてみた。
最初に試したのがブートローダー書き込みシールドを使う方式だ。新品のATMEGA328Pマイコンはこの方式でブートローダーを書き込めた。でも弄くり回しておかしくなっているATMEGA328Pマイコンの中にはこの方法では復活出来なかったものも有った。
その理由は不明だ。たぶんヒューズビットと言うのが関係していると思う。
たしかヒューズビットを書き換えるにはArduino IDEでは出来なくて、ATMEL-ICEなどのライターが必要だった思うが確証は無い。
そしてATMEL-ICEを使ってファームウェアとブートローダーを書き込んだら無事にATMEGA328Pマイコンが復活出来た。
そのATMEGA328Pマイコンが載っているArduino Uno基板はサンプルのLEDチカチカスケッチを動作させる事が出来た。
なお、この手順に於いてブートローダーの書き込みだけでなく、先にファームウェアも書き込む必要性に関しては良く分からないがワテの場合はファームウェア書き込まずにブートローダーを書き込んだだけではArduino UNOが正常動作しなかった場合があった。
具体的には、Blinkスケッチを書き込む時にエラーしたのかな?忘れた。あかんがな。兎に角動かなかったのだ。
なので当記事ではファームウェアとブートローダーの両方を書き込む手順を紹介している。
もしかすると、ブートローダーのみを書き込んだ場合には、Arduinoをリセットするとか電源を入れ直すなどすれば良かったのかも知れない。
Arduinoを学ぶ
(続く)
コメント