R8C33C I2C通信について

お世話になっております。

R8C33Cマイコンにて、I2C通信を勉強しております。

R8C33Cマイコンとセンサーモジュール間でI2C通信を行い、データ値を読み取りたいのですが、レジスタ設定から迷走になっており困っております。

アドバイスを頂けると、大変助かります。

言語はC言語を使っており、開発環境はHEWを使用しています。

I2C通信を行うにあたって、現状私が理解しているのは、

・R8Cマイコンは、高速オンチップオシレータを使用し、20MHzのクロックで駆動。

・R8CマイコンのI2C通信のポート設定は、p3_7をSDA、p3_5をSCLを用いる。

・R8C33Cマイコン側は、マスタ側で受信のみ。

・センサーモジュールは、スレーブ側で送信をし続ける。

・モジュールのスレーブアドレスは0x39。

・モジュールからは1バイトずつ、データを受信したい。

R8C33CのハードウェアマニュアルのI2Cバスインターフェース章のレジスタ設定例を参照し、実装しているのですが、うまくできません。。

マイコン初心者のため、上記の記載だけでは、伝わりづらいのかと思うのですが、よろしくお願いいたします。

Parents
  •  RX621でプログラムを作りましたが、I2Cはハングアップし易い。

     ワイヤードオアなので、どれかがLレベルに引っ張ると、そこで固まってしまいます。

    オシロで波形を観測した方が良いですよ。ソフトだけで試行錯誤しても、動かない原因が分かりませんよ。

    NACKを出す処理が難しいのです。

    .

    1バイトと決まっているのなら、RX621を例に取ると.ICMR3 レジスタの WAIT,RDRFS、ACKWP を1にしておき、ACKBT にビットを書き手動でACKビットをコントロールします。

    .

    自動的にACKを返すようにしてあると、NACKを出す処理を間違えたときにングアップします。

    プログラムだけが再スタートしても、モジュール側が送信の途中で止まっていた場合は動かないでしょう。

    エラーでやり直すときは、モジュール側のハード・リセットも忘れずに。

    動くようになったら、ハングアップしたときの処理を考える事ですね。

  • プログラム見ないと何も言えないですが、

    > ・センサーモジュールは、スレーブ側で送信をし続ける。

    ここがちょっと気になります。I2C規格は、スレーブがマスターの指示なしに動く事はないです。あくまでマスターが「データくれ」って投げたら返事くれる、というモノですので、UARTのシリアルモニタのように、何もしないループで受信バッファを監視してフラグ立ったら表示、みたいなシンプルな記述では動かないです。

    今の動かないプログラム(出来れば回路図も)を貼られた方がいいかと。

  • こちらの質問、今回が初めてでございまして。

    添付ファイル等で、.cファイルを貼ることは不可能なのでしょうか?

  • アーカイブして .zip にするか、ファイル名の最後に拡張子 .txt を付加してテキストファイルのフリをするかすれば添付できますが、長くないものであれば「USE RICH FORMATTING」ボタンを押してリッチ書式を選択し、HTML で <pre>~</pre> で括って投稿するのがお手軽だと思います。

    void hogera(void)
    {
        hogera();
    }
    
    hogera.zip
  • zipファイルにしてからの操作を教えていただきたいです。(どのボタンを選択し、どのように貼り付けるのか)

    よろしくお願いいたします。

  • ご教授ありがとうございます。

    ちなみに、現在のソースファイルを貼り付けておきます。

    i2c.c、i2c.hに、現在実装しております。

    アドバイスよろしくお願いいたします。

    ソースファイル.zip
  • わわいです

    IICは2線だけの簡単なインターフェースなので、まずは、周辺デバイスを使わずにIOポートの操作で実装してみてはどうでしょう。

    SCLはクロック出力なので普通に出力をHigh/Lowにしていればいいです

    SDAはLow出力は出力、Highのときは入力ポートに設定して疑似的にオープンコレクタ出力を実装します。

    2CHのオシロスコープで双方の信号を見ながら通信波形を実装していけばそんなに難しくはないと思います

Reply
  • わわいです

    IICは2線だけの簡単なインターフェースなので、まずは、周辺デバイスを使わずにIOポートの操作で実装してみてはどうでしょう。

    SCLはクロック出力なので普通に出力をHigh/Lowにしていればいいです

    SDAはLow出力は出力、Highのときは入力ポートに設定して疑似的にオープンコレクタ出力を実装します。

    2CHのオシロスコープで双方の信号を見ながら通信波形を実装していけばそんなに難しくはないと思います

Children
  • ソースさらっと見ました。icdrt = 0x39 | 0x01とか合ってるのかなぁとも思いますが(I2Cのデバイスアドレスは7bitを左シフトしてW/R付加?)、そもそもI2Cはスレーブデバイスの仕様により通信フォーマットが変わるので、デバイスが何なのか判らないとデバッグ出来ないでした。デバイスは何でしょう?

    あと、よく罠にはまり易いのがReadするとき、Start→SlaveAddr(W)→DeviceReg→ReStart→SlaveAddr(R)→Dummy→Stop、という形式の場合に、RestartじゃなくてStop&Startしてしまうミスです。これは何度か見ました。

  • fluxさん>

    ご返答が遅くなり申し訳ありません。

    デバイスはTSL2561使用 照度センサーモジュールになります。

    なるほど。通信の手順工程ですね。気を付けます。

  • TSL2561。ググル先生に聞いたらadafruitの小基板が先頭に来た挙句、Arduinoのサンプルまであるんですね。GR-SAKURAあたりの方が勉強ラクなんじゃとも思いますがさておき。

    cdn-shop.adafruit.com/.../TSL2561.pdf

    ここの12-13ページあたりが通信フォーマットになりますが、これらのうちどれを実装されたんでしょう?(Figure10から17のどれ?)

    あと、ここの資料を見ると、

    strawberry-linux.com/.../tsl2561-manual.pdf

    「内部レジスタ 0xA0 に 0x03 を書き込むことでセンサが動作を開始」とか書かれてるので、センサ動かすにはおまじない等が必要と思われます。ついでにこの資料にアドレスも何やら書かれてますが、もしこれのOPENと同じ状態なら、0x39ではなくて、0x72|0x01か、0x72&0xFEな気がします。

    それと、オシロはお持ちですか?あるなら波形画像とって、それも載せてくれた方がデバグしやすいです。