« 2015年9月 | トップページ | 2015年11月 »

2015年10月の2件の記事

2015年10月31日 (土)

Tiny85のI2Cスレーブライブラリーのソースコード公開

 いま流行(はやり)の電子工作というのならArduinoなのだろうけど、こちらは今やイギリスの半導体メーカーに買収されてしまったAtmelの8ピンマイコンでソフトI2Cを自作している。こんな遊び方は、時代錯誤になりつつあると思うが、これが当人には結構面白く、ハマっている。

 I2Cは必要ラインが少なくてすみ(2線。グランドを入れて3線)、バス接続が出来るのでピン数の少ないマイコンでは定番の通信インターフェースである。専用のハードではなく普通のI/Oピン(GPIO)を使ってソフトウエアでこのI2Cを実現したのものをソフトI2Cと呼んでいる。

 ただ、GPIOによるI2Cインターフェースのソフトは、マスター側がほとんどで、スレーブ側の制作例は珍しい。マイコンがマスターになって、スレーブであるI2C機器を制御するというのが一般的だからだ。スレーブをソフトで作るというのは今度のように、I2Cのない周辺機器をI2C化するときくらいに限られる。

01pa307348  前記事までに、I2Cスレーブソフトは、目標のTiny85で一応動いたのだが、これは当面の目的である超音波距離測定ユニットHC-SR04を動かす部分の機能だけで、汎用的な用途にはまだ不安がある(連続データの送受信など)。

 前回、ソースコードを公開しなかったのは、せっかくここまで動いたのだから、もう少し、色々なところで使えるように機能を拡大してからと考えたためである。 追加の開発は楽に出来ると思っていたのだが、実は結構てこずった。

 ああでもない、こうでもない、と試行錯誤の結果、何とか安定して動くスレーブインターフェースの開発に成功した。もうソースコードを公開しても恥ずかしくないレベルに達したと思う。誰かが使ってくれると嬉しい。

I2Cスレーブはユーザーインターフェースが難しい(10/10/2015)
 I2Cインターフェースのスレーブ側は基本的には完全な受け身で自らは何も動き出さない。マスター側のトリガーをひたすら待ち続ける。スレーブのメインプログラムは無限ループでマスターからの信号を待ち、通信が始まったら、マスターの出すクロックの指示をすべて守らなければならない。

 こういうときは、マスターからの信号は割り込みで処理するのが一般的である。マスターからのデータはひとつも落とせないからである。このためにスレーブ側のメインプログラム(対象機器の制御、データの受け渡し)は、I2Cとのやりとりの合い間に動くバックグラウンドタスクとして、非同期で動かす必要がある。

 こうした方法の定番というのを分かりやすく解説している参考書やウェブの記事を、これまで見たことがない。どういうやりかたで作るのが良いのかいつも悩む。このあたりのロジックや、アルゴリズムは、マルチタスクを制御するOS(オペレーティングシステム)のしかけそのものなので、市販の参考書はそれを意識して、たいてい仰々しい書き方になっている。実務的にとても理解しにくい(初めて読む人にはわけがわからないだろう)。

 最近はOSをやさしく紹介する本がいくつか出ているが、実際のソースコードまで落としたものは少ないようだ。目的がOSを理解させることで、具体的にソフトを動かして何かの用を足すことを目的にしていないからである。

 前記事までのソフトI2Cスレーブのメインプログラムは、あくまでもHC-SR04を動かすために特化しており、このままでは他の用途に使いにくいし、汎用的に使うにはまだ機能が不足している。ちょうど良い機会なので、他にも応用が出来るような構造にし、併せて解説も少し足し、これから同じようなことに挑戦される方の参考になることを狙うことにした(誰もいないか)。

 現在のライブラリの形式は、I2Cインターフェースそのものはi2c_slave.cというソースファイル1本に集中させ(ヘッダーファイルは、i2c_slave.h)、アプリケーションに依存するコマンド解釈などの機器制御とデータの受け渡しは、メインプログラムi2c_SR04_85.cにまとめてある。

02pa307350  従って、違う機器(LEDや、液晶表示装置、温度センサーなど)をI2C化するときは、このメインプログラムだけを目的に合わせて変更すれば良いようになっている。前にも触れたように、このあたりは定式化したやりかたがない(もちろん、知らないだけという可能性もある)ので、がた老AVR研究所なりの方法論で話を進めることをご了承願いたい。

 やり方は次の通りである。まず、使いそうな機能をいくつか想定して、実際にそれを実装する。このしくみを詳しく説明すれば、メインプログラムと、割り込み駆動のI2Cルーチンとの間の動きが明確になり、他への応用が容易になるのではないかという狙いである。

連続データの送受信が非同期で出来れば文句がないだろう(10/14/2015)

 どんな機能が役立つのかは、このI2Cスレーブを使う具体的な例を考えて、それを基に決める。色々検討したが、やっぱり今度のように非I2C機器をI2C化することが一番多いのではないかという結論になった。

 LCDなどの表示装置は既にI2C駆動のものも多いが、パラレル駆動のLCDや、LEDマトリックス、グラフィックLCDなどは、必要なI/Oピンを少なくできるのでI2C化するメリットは多い。ただ、これらの表示装置は、マスターからスレーブへの出力が殆どなので、I2Cとしてはそう難しくない。さらに、全体の処理速度を早くするために、多バイトのデータが一気に送れる機能があれば、もう文句はないだろう。

 一方、EEPROMやRTC(リアルタイマークロック)などの入力ディバイスは、スレーブからマスターへのデータ転送が必要になる。こういうディバイスには、マスターからコマンドを受け、すぐにリピートスタートで求められたデータをスレーブからマスターへ送り出す機能も必要になるだろう(この機能はこれまでの記事の通り開発済み)。

こうしたことから、汎用的なモデル機能を以下のようにまとめた。

(1) UARTコンソールのように、マスターから一定の長さのテキストを送り、スレーブ側で蓄積し、コマンドでそのデータを送り返す機能。

(2) スレーブ側に何らかのデータを用意し、マスターからのコマンドに応じたデータ値を1シーケンスでマスター側に送り返す機能。

(3) マスターからのコマンドによって、スレーブ側に接続した機器を制御する機能。これは(2)のバリエーションで、今回は、超音波距離センサーなどの起動トリガーコマンドがそれにあたる。

連続データのマスター書き込み(送信)は簡単に片付いた(10/15/2015)

 まず、(1)の擬似UART的な機能の送信の部分である。マスター側のコンソールから連続したデータ列をリターンキー(\r)を終端文字として一気にスレーブに送り、それをバッファーに一旦貯めた後、別のコマンドで一気にエコーバックさせる。

 これまでの開発で完動したのは、HC-SR04での、マスターからの1バイト送信と2バイト受信だけなので、今度は、スレーブの受信リングバッファーがオーバーフローしないように、スレーブのメインプログラムと割り込みルーチンがマルチタスク的に動く必要がある。

 メインプログラムで、割り込みルーチンのリングバッファーのポインターを常に調べ、割り込みルーチンでデータが入って、ポインターが進めば、すかさずデータを本体の配列に収容する。UARTなどでいつもやっている方式と同じである。

 マスター側のドライバーにコマンドを新設し、;(セミコロン)のあとの文字列が一気に送られるようなコードを加える。コーディングは簡単にすんだ。テストである。よーし、スレーブ側のデバッグ用のコンソールに送ったデータが綺麗に並んだ。これは問題なく動いた。

Tiny85console
次のマスター連続受信(スレーブ送出)が難しい(10/16/2015)
(1)のもう一つの機能、マスター連続読み込み(受信)である。マスターからのコマンドによって、配列などに貯められたデータを一気にスレーブ側から、マスターに送り返す。スレーブ側は待つだけで、駆動するのはマスター側のクロックであり、スレーブはそれに従ってデータを載せて行く。

 ここで問題が発生した。書き込みのときは、コンソールのキーボードから打ちこまれた終端文字のリターンキー(\r)文字を見てマスターがストップコンディションを発行し、スレーブ側はこれを検知する機能があるので(前々記事参照)、問題なく通信が終了する。

 しかし、マスター読み込みの終了は、最終文字のACK/NACKビットでマスターがNACKをセットし、スレーブに返すことになっている。マスターが、送られてきた最終文字(リターンキー)のACK/NACKビットに、NACKをセットすることは時間的に不可能なので、マスターはリターンキーであることを知ったあと、ストップコンディションを挿入することになる。

 うーむ、困った。スレーブ側にはマスター読み込み時のストップコンディション検知機能がまだ実装されていない。固定量のデータならマスターが最終文字にNACKをつけるので正常に止められるが、このままでは、可変量の連続読み込みの送信終了は受け取れないことになる。どうしよう。

 ここまで来て、引き下がるわけにはいかない。乗りかかった船である。マスター読み込みのステートマシンに、ストップコンディションを検知するロジックを追加した。コードそのものは、マスター書き込みのところと同じなので簡単に出来た。ただ、フラッシュサイズは3Kバイトを超えた。

 しかし、これがどうやってもまともに動かないのだ。ストップコンディションを検知できなくて、すべての通信でタイムアウトしてしまう。ロジックアナライザーを再び引っ張り出して、ステートマシンをプローブして、原因がわかった。懸念していた通り、処理が次のクロック(SCL)パルスに食い込んでいる波形を発見した。クロックが8Mhzでは、今の50khzのI2Cが通らない。

 結局、マスター読み込み(スレーブ送信)でのストップコンディション検出はあきらめる。となると何か回避策を考えなければならない。良い方法を思いついた。

 リターンキーを受信したら、とにかくマスターはもう一文字受信し、この文字にマスターがNACKビットをつける。こうすると、スレーブに通信終了を知らせることが出来る。マスターはこの文字を捨てればよい。ちょっと姑息だけれどなかなか洒落た方法だ。

 スレーブ側の、NACKによる終了はこれまで正常に動いている。上機嫌で自信満々テストに臨んだ。ところが、これでも通信は正常に終わらない。つねにタイムアウトしてしまう。ロジアナで見ても正常な波形だ。もう調べるところがない。完全に暗礁に乗り上げてしまった。

旧友会が2回(10/18/2015)

 息抜きに、ここで、ちょっと電子工作以外の話題をご紹介する。同窓会の話題である。これまで、時々、話してきた小学校や高校の同窓会ではなく、珍しい古い友人からのお誘いが偶然に、続けて2つもあり、久しぶりに飲み会をやった。

 ひとつは、40年前、地方に転勤した時に一緒に仕事をした会社仲間の旧友会で、もうひとつは、同じ会社ではなく、20年前に仕事で親しくなった取引先の友人の同窓会である。どちらも10年くらい前までは頻繁に会っていたが、このところご無沙汰だった。

 それぞれ、出席者の殆どはもう現役を離れている。まず、会うなり「病気と、孫と、髪の毛の話は禁止」という宣言が出て大笑いした。良く見るとみんな相当な禿頭だ。まあ、それはともかく、昔話というのはいつになっても楽しいものだ。結論から言えば、どちらもとても楽しかった。

 会社の旧友会には実は余り顔を出したことがない。現役の頃の上下関係をいつまでも引きずる人間が少しでもいると周囲の雰囲気が悪くなり気分よく話が出来なくなるからだ。今回は幹事が、人を選んでくれたようで全く違和感なく昔話を楽しむことが出来た。

 こうした旧友会は、自分の人生を遠くから見るような解放感がある。この年になると、現役時代の熱い感情的な部分が削ぎ落とされて、自らを、良くも悪くも客観的にみている自分を発見する。今さら何が出来るわけでもない。達観した見方が出来るのだ。

 2つの会合とも、久しぶりに酒が進み、帰りが大変だった。まあ、何とか人の迷惑にならずに帰宅できたが、この年で深酒はほどほどにしておいた方が良い。自戒、自戒である。

マスター連続受信(スレーブ送り出し)終了条件の謎(10/21/2015)
 電子工作の話に戻ろう。いやあ、今回も解決までが長かったが、苦労の甲斐あって、これまで不安定な動きをしていたマスター読み込みは、完全にNO ERRORで動作するようになった。

 今回の不具合は、前のバグのように、お馬鹿なミスが原因ではなくて、複雑な要因で起きていたバグだったが、少しづつ事実を積み上げ、思い付いた仮説を検証しながら、最終的にバグの原因を解明できたので、すこぶる機嫌が良い。迷宮入り寸前の難事件を見事に解決した名探偵の気分である。

 マスターからの連続書き込みは簡単に成功したのに、マスターが連続して読み込む方は、どうも調子が悪い。マスター読み込みは、スレーブがデータを送った後、マスターからNACK/ACKビットが返ってくるので通信の終了はストップコンディションが出なくても通信終了になるはずなのに、現状は殆どの通信がタイムアウトになってしまう。

 気に入らないのが、すべてがうまくいかないのではなく、時々正常に終わるときがあることだ。何かのタイミングで起きたり止まったりするというのが、一番厄介なトラブルである。ステートマシンにプローブ(SR04のトリガーピンを流用)を入れて動きをロジアナで確かめる。

 確かに、NACK/ACKビットを調べるステップで、マスターはNACK(1)を返し、そこをステートマシンが通過していることは間違いない。それならタイムアウトフラグはここでクリアされ正常終了するはずだが、そうなっていない。

 そうだとすると問題はそのあとだ。一連の通信が終わったあと、割り込みルーチンはステートマシンを初期状態に戻し、割り込みをクロック(SCL)からデータ変化(SDA)に替えて、次のスタートコンディションを待つ。このあたりがうまくいっていない可能性が高い。

 しかし、マスターは、NACKを返した後、ストップコンディションを発行している。ロジアナにもはっきりした波形が出ている。たとえ、NACKでリセットできなくても、ここでストップコンディションによって割り込みルーチンは初期状態に戻り、リセットされるはずだ。それなのにタイムアウトになる。二重におかしい。

遂にマスター連続受信に成功。原因はNACK処理ではなかった(10/25/2015)

 謎は深まるばかりだ。そこで、今度は、ステートマシンではなくて、スタート/ストップコンディションを受ける初期状態のデータ(SDA)の割り込みにプローブをかけてみた。本当にリセットされてこの割り込みを受けているか確認するためである。

 確認したからと言って何か成算があるわけではないが物は試しである。半信半疑でロジアナを動かす。問題の通信終了のシーケンスを拡大する。おやあ、ACK/NACKビットを受けるステートマシンの直後に、スタート/ストップコンディションを受ける割り込みが2つも発生しているではないか。

Tiny85stop  先に触れたストップコンディションの時に発生するのは想定通りだが、その前の割り込みは何なのだ。あっあっあー、わかったぞ。マスターがストップコンディションを出すための準備に、SDAをLowにする準備の部分を拾ってスタートコンディションにしてしまっている!

 NACKのリセットのあと初期状態に戻るのが早い割に、実際にSDAの割り込み処理に来るオーバーヘッドが長すぎ(17μsもある)、次のSCLが立ち上がってしまってスタートコンディションと誤認してしまったのだ。

 しかも、一旦、スタートコンディションと認知してしまえば、割り込みはSDAからクロック(SCL)に移り、このあといくらストップコンディションが来ても無視される。時々動くのは、SCLの立ち上がりの前に割り込みルーチンに来るときがあるからだ。このときは問題なく動く。よーし、間違いない。すべては氷解した。

 原因はわかった。しかし、SDAの割り込み遅れを早くすることは出来ない。そもそもは、ACK/NACKビットのSCLの立ち上がり中にリセットしてSDA割り込みを待ち受けること自体が違反だ。ここはSCLが下がって次のステージに入ってから、スタートストップコンディションを待ち受ける体制にするべきなのだ。

I2cslave_85  ACK/NACKビットのステートマシンのところに、SCLが次のブロックに行くまで待つプロセスを入れて、これまでのタイムアウトは完全に解消された。連続データは勿論、(2)のリピートスタート処理も全く問題なく動く。

 いやあ素晴らしい。仮説に基づき、ロジアナで少しづつ事実を追いながら原因を突き止めた。「デバッグは外へ、外へ」という格言どおり、原因は意外なところに潜んでいたのである。

ソースコードの公開。readmeもつけた(10/30/2015)
 紙数が増えてきたので、(2)や、(3)の機能の説明は、添付するソースコードのフォルダーの中にあるreadme.txtにまとめて書いたので、そこを参照頂きたい。回路図も念のため掲載しておく。

 冒頭でも述べたが、このソースコードはSR04というセンサーユニットをI2Cで動かすための機能と、連続データの入出力などのテスト機能が入った、汎用的なモデル機能をデモするプログラムで余り実用的なものではない。

 このソースを参考に、ご自分の用途にあったI2Cスレーブのプログラムを開発されたい。そういう意味では、余計な機能や冗長なコードがまだ沢山残っており、余り自慢できるものではないが、少しでも参考になればと恥を忍んで公開することにする。

以下に、2つのファームウエアのフォルダーとreadme.txtなどをzipでかためたファイルを置きます。同じファイル名でも、以前に公開したファイルと内容は全く異なっていますのでご注意ください。  

「I2CslaveSet.zip」をダウンロード

上記のライブラリーは改訂されています。なるべくこれを使わず、新しい方をお使いください(新しいリンク先)

| | コメント (0) | トラックバック (0)

2015年10月 9日 (金)

Tiny85のI2Cスレーブライブラリー完成。今度もドジなミスで大騒ぎ

Tiny85への換装を考える(9/17/2015)
 Tiny861でI2Cのスレーブソフトが順調に動いたので、本来の目標、8ピンAVRへ換装する準備を始めた。超音波距離センサーHC-SR04が5Vなので、小さなブレークアウト基板に、DC-DCコンバーターと、8ピンAVR(Tiny85を予定)を載せ、EdisonやRasPiのI2Cで動かそうという計画である。

 同種のプロセッサーなのですぐ動くとは思うが、ピン数が少なく外部発振子は使えないので、クロックはこれまでの16Mhzではなく内蔵のCR発振の8Mhzになってしまう。動くかどうかは、やってみないとわからない。不安なのは、デバッグ用のISP-UARTが使えなくなることだ。動作確認が難しくなる。

 ただ、これから使うTiny85はフラッシュサイズが8KBもあるので、機能的にはまだ沢山実装できる余地がある。未開発のスレーブ送信(マスター受信)でのストップコンディション検知や、マスター受信のあとのリピートスタート機能も組み込もうとすれば楽勝だ。

01pa077329  いずれにしてもピン数が絶対的に足らない。ISPでプログラムすると完全に自由なピンは、わずか2本(GND、Vcc、RST、MISO、MOSI、SCKの残り)しかない。プログラムしたあとMISOなどが使えるとしても、全部で5本である。HR04のドライブに2本(エコーとトリガー)、I2Cに2本(SCL、SDA)使うとすると、残り1本しかデバッグ用に残されていない。

 パラレルにすれば、リセットピン(RST)が使え(Dragonも持っている)、1本増えるが、手慣れたISPからパラレルプログラミングにするのも難儀なことだ。というので、苦肉の策として、ISP-UARTの送信(MISO)だけをデバッグ用に残すことにした。ぎりぎりのリソース運用である(これが苦労の原因になるとは露知らず)。

 ここで訂正とお詫びである。前記事などで、8ピンAVRシリーズにはUSI(汎用シリアルインターフェース)がないと言っていたが、良く調べると、ないのは旧型の15や、最近の13などで、25,45,85には、ちゃんとUSIがついていた(ChaNさんのAtmelの紹介の表にあるIICは誤り)。失礼しました。とはいえ今さらUSIに戻るわけにもいかない。GPIOによるI2C化を進める。

秋月とAitendoで同じ超音波距離測定センサーを入手する(9/19/2015)
  このところご無沙汰だった秋葉原を久しぶりに訪れた。秋月電子の店内がすっかり模様替えしている。マルツと同じように部品棚が店内両側の高いところまで立ち並ぶ形式である。マルツと違って棚の奥に人が歩けるくらいのスペースが空いていて店員の補給路になっている。

 今日の目的は、秋月が同じ超音波距離測定センサー(HC-SR04)を、Parallaxのオリジナル品(¥3000近い。最近見たら¥3980に値上げ)と並行して売っているのを知ったのと、Aitendoにも同一品が出ているようなので、ついでに2つとも買ってしまおうというものだ。

 秋月のあと、足を伸ばしてAitendoの直営店に向かう。ここは秋葉原というより御徒町に近い。人気の少ないオフィス街を歩いて、エレベーターに乗り3階に着くと、意外な光景が広がっていた。

 土曜ということもあるが、店内が客で溢れているのだ。驚いたことにベビーカーが2台もはいっていて家族連れまでいる。自分のようなお年寄りから、おたくっぽいリュック姿の太目の若者まで、まさしく老若男女が真剣な目つきで部品を選んでいる。 02pa077338

 前にも書いたが、いかにも中国人らしい若い女性店員は意外にも商品知識が豊富で、SR04の展示場所を迷うことなく案内してくれた。面白そうなものが沢山あったが、広い店内(秋月より明らかに広い)と人に少し圧倒されてしまいSR04だけで帰ってきた。それにしても電子工作の裾野が広がっているようで喜ばしい。

3種のSR04の比較テストでは意外な結果が出た(9/20/2015)
 超音波距離測定センサーHC-SR04が、はからずも3種類そろった。せっかくなので、3つの比較テストをした。結果は、
Aitendoで買ったもの>アマゾンで以前買ったもの>秋月電子で買ったもの
の順で、機能に大きな差が出た(値段はすべて¥400近辺)。

 秋月電子のSR04はスイッチサイエンスが告知した通りの不具合品で、一定の期間の距離測定では問題ないが、一旦、3mを超す距離を測定しようとすると、echoパルスがHighのままとなり、triggerパルスを出しても元に戻らない。電源を切って再投入する必要がある。

 アマゾンで買ったものは、3mを超すとエコーパルスがHighのままになるが、トリガーをかけると復帰する。一方、Aitendoのものは、距離が長くてもエコーパルスがHighのままになることはなく必ず復帰する(パルスはある距離を超えると一定の長さになる)。

 不思議なことに秋月のものでも物理的なショックを与えると、正常に戻る。アマゾンで買ったものと、秋月のものとは基板のパターンは、スイッチサイエンスの言う駄目なロットと同じように見えるが、良く調べてみると微妙なところに違いがある。

 例えば、秋月の製品は、クリスタルのところの小容量のコンデンサーが省かれており(パターンもない)、パスコンもいくつか省略されている。Aitendoのものはシルク印刷の状況から見るとスイッチサイエンスのいう正常な旧製品と同じように見える。

 しかし、買ってきたものが、それぞれひとつだけなので、すべての商品が上記のようになると断定は出来ない。たまたま所長の買ってきたものが、そうだったというだけである。誤解のないように。まあ、実用に使うなら秋月のオリジナルのParallax社のものが間違いないだろう(高価だが)。もっとも秋月のものでもFETか何かでタイムアウトをとりリセットすれば使えないわけではない。

プリンターを買い換えて、旧型をリサイクルセンターへ葬る(9/21/2015)
 珍しく仕事が入って、プリンターを使う機会が増えた。10年近く前に買ったカラーレーザー(コニカミノルタ 2530DL)は、印刷機能はまだ十分働くのに、最近は紙送りが不調で、最初の一枚か二枚を必ず失敗する。

 だましだまし使っていたのだが、遂にエラーが復帰せず、3枚以上の印刷が不能になった(必ず3枚目で紙送りエラーになる)。使い始めてからの年数を正確に調べてみた。8年と11ヶ月、およそ9年である。微妙な年数だ。ウェブで調べると、同程度のプリンターなら1万円台で入手可能だ。ドラムがそろそろ寿命だし、修理に出しても、軽くこれ以上の修理代金をとられる可能性は高い。

 大分前から迷っていたのだが、結局新しいプリンターに更新する決意を固めた。買うことは造作がないが、困るのは古いプリンターの処分である。20kg近い重量があり、地下から1階に上げるだけでも大仕事である。

 それに、まだ十分動く(恐らく紙送りのセンサーあたりを交換するだけ)のに粗大ゴミに出すのはあまりにも忍びない。地球環境にやさしくない。ウェブで探してみると沢山の廃棄処理業者のサイトが出てきた。送料だけで無料で引き取ってくれるらしい。

 直接持ち込めば梱包もいらないという、ある業者のコピーに惹かれて東村山にあるリサイクルセンターに車で持ち込むことにする。 あと始末に困っていたが助かった。ただ20キロ近い箱を運ぶのは、地下から玄関を出て車に入れるだけで一大事業だった。海外旅行に使ったカートが思わぬところで役に立った。何とか腰を痛めずに車のトランクに入れる。

 自宅から小一時間で現場の処分場に着く。雑木林に囲まれた倉庫のようなところで愛想の良いおねえちゃんが迎えてくれる。あらかじめかけた電話も親切だった。レーザープリンターのほかに、自作のデスクトップPC、長女のこわれたノートパソコン3点も一緒に引き取って貰った。

 すべて無料である。身元を証明するものは不要(無料だからか)で、控えに住所氏名を書くだけである。部品どりが沢山行われることを祈って現場を後にした。合掌。

Nec5750c_2  新しいレーザープリンターは正価が8万近くするが、何故かネットで1万前後で売られているNECの5750Cを選んだ。DTP屋さんが、べた褒めしているサイトが検索上位にランクし、思わずポチッとしてしまった。値段は肩の力の抜けるこれまでの1/3の¥13,500。2日ほどで届いた。

 早速テストする。何の問題もなく動いた。前のコニカミノルタに較べると少し大きいが静かだし、早い。画質は確かに良くなった。文字も綺麗だ。もっとも、この間には10年近い年月が流れている。これぐらいの進歩は当たり前なのだろう。

久しぶりの家族旅行。世界遺産の白川郷へ(9/27/2015)
03p9257251_2

 次も、電子工作ではない話である。長女夫婦が岐阜に転勤になったので、家族と一緒に車で岐阜に遊びに行った。暫くぶりの長距離ドライブである。また第二東名を飛ばす。かなりの雨だったが、第二東名の路面からは全く水しぶきがあがらない。高速走行での雨は路面に溜まった水がハイドロプレーニング現象などを起こすので神経を遣うのだが、その心配もなく実に快適だった。

 岐阜に着いて少し早めの夕食の後、長女たちの案内で鵜飼を初めて鑑賞した。鵜匠たちが宮内庁職員だったとはこれまで知らなかった。格調が高いのである。ただ鵜飼そのものは、雨で川が増水して流れが速かったせいか、あっという間に通り過ぎ、ちょっと物足らなかった。

02p9277313_3 04p9277312_2

 鵜飼の写真を載せたが、すべて手ブレとピンボケでまともな写真にはならない。そりゃそうだ。動く舟の上から、篝火だけの光源では無理だ。ストロボもよほど強力でなければ効かない(恐らく禁止しているだろう)。雰囲気だけでも感じていただきたい。

 次の日は明治村を何十年ぶりかで再訪問し、最終日は世界遺産の白川郷まで足を伸ばした。このあたりは、40年近く前に、自動車(オンボロ自家用車)で通ったことがある。もちろん白川郷までは行けず、深い谷筋を延々と辿ってやっとのことで通り抜けた記憶がよみがえる。 01p9277326_2

 しかし、今は岐阜から白川郷まで自動車専用道路だけで行けるのだ。スイスアルプスにあるような山間(やまあい)に雄大な曲線を描くインターチェンジを通り、10キロを越す長大トンネルを抜けて目的地に着く。道路網の進歩には驚くばかりである。まさしく隔世の感である。

 初めて訪れた世界遺産の白川郷は、外人観光客であふれかえっていた。コスモスと稲穂が合掌造りの民家に良く映えていた。紅葉や積雪時も美しいだろう。ただ残念なのは合掌造りの家が着実に減っていることだ。昔の写真と較べると良くわかる。まあ、ここは完全な保護区ではないので無理と言えば無理な話だが。

Tiny85のI2Cがうまく動かない(10/2/2015)
 旅行から帰って、電子工作を再開する。Tiny85への換装は仕様をまとめただけで実際の作業は始めていない。小さなブレッドボードにTiny85を載せてテストボードを追加する。861から85 へのソフトの変更は、クロック変更によるタイマー設定の変更、GPIOピンの再設定ぐらいである。テスト用のUARTは送信部分だけ残し、受信側は省略する。

I2c_85full  大した作業ではない。ほどなく完成して、早速テストに入る。CRクロックなのでUARTの速度を少し落とす(38400 -> 19200)。UARTは無事Welcomeメッセージを出した。しかしI2Cの方は、どうも安定しない。マスター書き込みは何とか動いているが、読み込みが全くだめだ。

 デバッグ用のUARTメッセージだけでは原因がつかめない。得意のロジアナへのプローブは一本たりとも使えない。読み込みのステートマシン部にカウンターを設けて、UARTで動作を確認していくが、いくつもの不審な動きを見せて安定しない。

 まず、マスター受信バッファーとデータ配列の順番がおかしい。データはSR04の距離データを使っているのだが、1バイトずれている(これはいつのまにか直ってしまった)。それに、マスター受信のビットの送り込み回数が本来の24回(3バイト)のはずが、もう1バイト多い32回になっている(あとになってみれば、それは現状を正しく表現していたのだが、このときはわからない)。

 I2Cそのものの波形をロジアナでとってみると奇妙なことばかりだ。想定もしないところにストップコンディションが発生して通信が中断されているし、データはもともと全く狂っている。しかし化け方に規則性があるのが悔しい。ロジックで間違っていることは明らかだ。

今度も馬鹿馬鹿しいミスで、1週間を無駄にした(10/6/2015)
 ソースを追っかけては、メモ用紙にSCL、SDAのチャートを描き、動作を検証する。しかし間違っているところを見つけられない。第一、861では何の問題なく動いていたのだ(クロックは1/2になっているが)。Tiny861からTiny85への移植だけで、こんなにトラブルになる理由がわからない。

 何度か、ステートメントを換えて(SCLクロックを割り込みではなくwaitで待つなど)、動かしてみたが改善されない。クロック遅れで起きるのなら、状態が時々変わりそうなものだが、データの化け方は一定している。これが悔しい。

 いい加減、嫌気がさして(大きな目標があるわけでもない)、そろそろTiny85でスレーブを作るをもう止めようと思い始めた。それでも最後に、プログラムの動きを探るプローブ点を一つだけ作って、動きを確認し、それでもだめなら潔くTiny85を諦めることにする。

 マスター読み込みルーチンの動きだけでも調べれば何かがわかるだろう。テスト用にSR04のトリガーピンを使っても当面問題はなさそうだ(ユニットが勝手に動くだけ)。というので最後の手段、トリガーピンのGPIOにデバッグ用のプローブステートメントを当て、テストしてみた。

I2c_85lowintpt  これが大当たりだったのである。ロジアナの画面には目を疑う波形が現れた。何ということだ。最初のSCLの立下りのあと、複数の割り込みが入っている波形がでてきたのだ。何だ、何だ、これは何だ。ロジアナに記録されないSCLの動きがあるのか。暫く考えて、いや違う、もっととんでもないことに気が付いた。

 なに、SCLの割り込み設定をやっているか?あ、あ、あっ、861から移植するとき、UARTの受信ピンに合わせて削除したままなのではないか(861の外部割込み設定は共通)。その通りだった。外部割込み設定を未定義のビット0、0「Low割り込み」のまま動かしている。

 それにしてもなぜこれに気が付かなかったのだろう。マスター書き込みは、1バイトだけで間隔が狭いので、「Low割り込み」でも問題なく動いたのだ。一方、マスター読み込みは、多バイトで、マスターは1バイトづつ関数で送るので、バイトとバイトの間に少し間が開く。で、ここで複数回の割り込みが起きてトラブルになっていた。受信回数が想定より多いのは、このせいだったのである。あああ、もう少し深く考えれば、この状況を解明できたかもしれない。

 外部割込みの設定を(0,0)ではなく立下りの(1.0)にして、Tiny85は何ごともなかったようにI2Cのマスター読み込みを実現した。何度やってもエラーは全く起きない。タイムアウトもない。ああ、良かった。あきらめずに頑張って本当に良かった。このまま挫折していたら電子工作そのものの熱も冷めるところだった。

Pa097340  やれやれ、今度のドタバタ劇も、幕を開ければ、実にくだらないミスだった。しかし、こういう解決は、変な話だが妙にすがすがしい。これまでの暗雲が、すっかり晴れて、人生が明るくなる。これまで暗かった周りの世界が一変し、ものみなすべてが自分に対して好意を持ってくれるかのような変化だ。これだから電子工作はやめられない。

| | コメント (0) | トラックバック (0)

« 2015年9月 | トップページ | 2015年11月 »