PDG2 にて生成した RIIC スレーブの送信について

ryokkei と申します。


RX210 のプログラムを作成しています。
周辺機能の設定は PDG2 で生成したコードを使用しているのですが、
RIIC0 のスレーブ動作がうまくいきません。
主な設定は RIIC タブにて、

・I2C フォーマット 標準モード
・スレーブ
・全データの受信完了、スレーブリード要求、ストップ条件検出を関数呼び出しで通知する
・関数によりデータを送信する

です。

リファレンスマニュアルの通り、R_PG_I2C_SlaveMonitor_C0 関数にて
モニタを開始した後、スレーブアドレスへのアクセスを検知して
IIC0SlaveFunc 関数が呼ばれます。その後、Read 要求であることを確認して
R_PG_I2C_SlaveSend_C0 関数にてデータを 254 バイト送信するのですが、
どうもバッファの最初の 1 バイトのみが繰り返し送信されているようです (オシロにて確認)。

リファレンスマニュアルの使用例は変数や関数が間違っていたり、
ちょっと R_IIC_SlaveSendAll 関数のソースを見てみると、コールバック関数が
ない方の処理 (143 行あたり) に、なにやら気になるコメントがあったりと
いったところが気になり、「もしや未完成?」などと勘ぐったりしてしまいます。

このあたりについてなにかご存じの方は、助言いただけるとありがたく存じます。

Parents
  • ryokkei です。

    送信できるようになりました。
    とりあえずコードです。

    uint8_t recv_data[254];
    uint8_t send_data[254];
    bool is_sent;

    void func(void)
    {
    R_PG_Clock_Set();
    R_PG_I2C_Set_C0();
    R_PG_I2C_SlaveMonitor_C0(recv_data, 254);
    is_sent = false;
    }

    void IIC0SlaveFunc(void)
    {
    bool transmit, timeout, start, stop;
    bool addr0;
    R_PG_I2C_GetEvent_C0(0, &stop, &start, 0, &timeout);
    R_PG_I2C_GetTR_C0(&transmit);
    R_PG_I2C_GetDetectedAddress_C0(&addr0, 0, 0, 0, 0, 0);
    if (stop) {
    R_PG_I2C_SlaveMonitor_C0(recv_data, 254);
    is_sent = false;
    return;
    }
    if (addr0) {
    if (!is_sent && transmit) {
    R_PG_I2C_SlaveSend_C0(&send_data, 254);
    is_sent = true;
    }
    }
    }

    IIC0SlaveFunc は、送信データエンプティ割り込みからも呼びまくられるので、
    そのたびにバッファの先頭を設定するような形になっていたようです。
    なので、is_sent フラグを使い、1度だけ送信処理をするようにしました。
    stop コンディションの検出にて再びモニタの指定、フラグのクリアを行います。
    リファレンスマニュアルの使用例は、間違いではないのかもしれませんが、
    その通りやっても正常に動かないといったところでしょうか。

    また、SCI の受信もなのですが、継続的に受信したい場合は (これがほとんどだと思うのですが)
    毎回モニタするための関数を呼ばなければならないことが記述されていなかったりと
    肝心な説明が抜けている印象です。
Reply
  • ryokkei です。

    送信できるようになりました。
    とりあえずコードです。

    uint8_t recv_data[254];
    uint8_t send_data[254];
    bool is_sent;

    void func(void)
    {
    R_PG_Clock_Set();
    R_PG_I2C_Set_C0();
    R_PG_I2C_SlaveMonitor_C0(recv_data, 254);
    is_sent = false;
    }

    void IIC0SlaveFunc(void)
    {
    bool transmit, timeout, start, stop;
    bool addr0;
    R_PG_I2C_GetEvent_C0(0, &stop, &start, 0, &timeout);
    R_PG_I2C_GetTR_C0(&transmit);
    R_PG_I2C_GetDetectedAddress_C0(&addr0, 0, 0, 0, 0, 0);
    if (stop) {
    R_PG_I2C_SlaveMonitor_C0(recv_data, 254);
    is_sent = false;
    return;
    }
    if (addr0) {
    if (!is_sent && transmit) {
    R_PG_I2C_SlaveSend_C0(&send_data, 254);
    is_sent = true;
    }
    }
    }

    IIC0SlaveFunc は、送信データエンプティ割り込みからも呼びまくられるので、
    そのたびにバッファの先頭を設定するような形になっていたようです。
    なので、is_sent フラグを使い、1度だけ送信処理をするようにしました。
    stop コンディションの検出にて再びモニタの指定、フラグのクリアを行います。
    リファレンスマニュアルの使用例は、間違いではないのかもしれませんが、
    その通りやっても正常に動かないといったところでしょうか。

    また、SCI の受信もなのですが、継続的に受信したい場合は (これがほとんどだと思うのですが)
    毎回モニタするための関数を呼ばなければならないことが記述されていなかったりと
    肝心な説明が抜けている印象です。
Children
  • こんにちは。
    ryokkeiさんの意図した動作を実現するためには、
    何か処理、または設定等を間違えているような気がします(もしくはマスタの動作?)。
    もし、送信データエンプティが発生した場合、
    Interrupt_IIC.cのInterrupt_IIC_ICTXI0割り込み関数が実行され、
    stateがIIC_SLAVE_SEND_DATAの状態と考えられ、送信データの更新しかしないのではないかと思います。
    (送信データエンプティの要因では、IIC0SlaveFuncをコールしていないように見えます)

    SCIの受信もということですが、
    ちょうどRX210でPDGを使用したSCIの調歩同期式通信についての投稿がありますので、
    参考にしてみてはいかがでしょうか?
     ↓
    japan.renesasrulz.com/.../rx210-sci

  • こんにちは、ryokkei です。

    circle さん、お付き合いいただきありがとうございます。
    ご指摘のとおり、送信データエンプティ割り込みは無罪でした。すみません。
    修正したコードは次のとおりです。

    void IIC0SlaveFunc(void)
    {
    bool transmit, timeout, start, stop;
    bool addr0;
    R_PG_I2C_GetEvent_C0(0, &stop, &start, 0, &timeout);
    R_PG_I2C_GetTR_C0(&transmit);
    R_PG_I2C_GetDetectedAddress_C0(&addr0, 0, 0, 0, 0, 0);
    if (stop) {
    R_PG_I2C_SlaveMonitor_C0(recv_data, 254);
    return;
    }
    if (addr0) {
    if (transmit) {
    R_PG_I2C_SlaveSend_C0(send_data, 254);
    }
    }
    }

    ミソは stop コンディション検出時の R_PG_I2C_SlaveMonitor_C0 です。
    うまくいっていなかった頃のコードは、IIC0SlaveFunc の最後で必ず R_PG_I2C_SlaveMonitor_C0 を
    呼んでしまっていたので、ライブラリ内のステートが IIC_SLAVE_MONITOR になってしまい、
    何度も呼び出されていたようです。

    やはりこの辺はもう少し説明が欲しいところですね。
  • 解決してよかったです。
    マニュアルで不明な部分がある場合、
    実際に動作させる環境があれば、
    色々と試してみるのが早いですね。

    採用されるか、されないかは分かりませんが、
    かふぇルネはルネサスの方も御覧になっているようですので、
    要望事項は書いておいて損はないかもしれません。