2バイトでのArduinoとPSoCのI2C通信をしてみました。
PSoCではI2CHWブロックを使い、Arduinoがマスタ、PSoCがスレーブというように設定しました。
ここで注意すべきことがありまして、
たとえばPSoC側を
dat = 1234; //16進数で4D2になります
buf_tx[0] = dat >> 8; //この場合0x04になります
buf_tx[1] = dat; //この場合0xD2になります
(buf_tx[n]とは送信するためのバッファ変数です。またdatはintでbuf_txはBYTEです。)
(PSoCマイコンではバッファ変数に送りたいものをあらかじめ入れておいて、マスタから送信しなさいと言われたら何も考えずにバッファ変数の内容を答えます。だから、マスタからいつ「送信しなさい!」といわれても良いようにあらかじめ言うことを準備しておきます。これらは、その準備のコードです。)
というコードにして、Arduino側で
Wire.requestFrom(18,2);//1バイト要求することを宣言
rd_data[1] = Wire.receive();//受信してrd_data[1]に代入
rd_data[0] = Wire.receive();//受信してrd_data[0]に代入
という風に受信すると、
rd_data[1]には0x04が入り、rd_data[0]には0xD2が入ります。
つまり、PSoCでは「変数名[0]」にMSBを入れて、「変数名[n]」にLSBを入れなければいけないと考えられます。
普通上位バイトから受信して、後で下位バイトを受信すると思い込んでいるのですが、ArduinoのWire関数は少々ブラックボックス化されているので、確実ではありません。
ただ、PSoCのバッファ変数の[0]は、Arduinoでは最初に受信されるのは確かです。
配列の[n]のnが少ないほうが下位バイトで後から送信するのだと思っていた僕は混乱しました。
ともかく、Wire.receive();で最初に返されたデーター(つまり最初に何らかの変数に代入したデーター)は、I2Cで実際に最初に受信したデーターであるということがはっきりすればこれらが確実になるということでございます。
分かりにくい文章ですみませんが、Wire.receive();で最初に返されたデーターが、I2Cで実際に最初に受信したデーターであるかどうか分かる方は御教授ください。お願いします。
さて、ちなみに僕がなぜこんなにPSoCマイコンとArduinoとのI2C通信をやっているかというと、
IRセンサー ― PSoC ========== Arduino (===はI2Cでつなぐと思ってください)
という感じでつないで、
利点①Arduinoの少ないアナログ入力を節約でき、1つのArduinoでたくさんのIRセンサーと2本の線だけでつなぐことができる
利点②アナログでないので、(PSoCとArduinoの間の線が長くても)モーターからの外部ノイズの影響を受けにくい(たぶん・・)
利点③外付け部品がほとんどいらない
と考えているからです。
といいながら想像だけでIRセンサー部分がまったくできていないのですが・・・
早くI2C通信を終えてLPF(ローパスフィルタ)に移りたいと思います。
最近のコメント