R8Cでハードフロー制御を行いたい時

こんにちは、NAKAと言います。

初歩的な質問かもしれませんが........

ハードフロー制御機能を持たない、R8Cのようなマイコンでハードフロー制御を行いたい場合
接続先のRTSをINPUTピンでモニタしながら行いたいと思っています。
マイコン側から割り込みを使った、TX(送信)を行おうと思いますが、接続先のRTSの準備ができて
いない場合、
①割り込み関数の中で、RTSがOKになるまで待つ(While(RTS)というように)
②接続先が準備できていないので受け取れないことを期待し、再度、送信空割り込みを発生させる
 ため、ダミーデータを送信レジスタに書いて、割り込み処理を抜ける。


を考えたのですが、

①の方法はRTSが準備できる間、CPUはその部分で止まってしまう。
②はダミーデータを送信レジスタに書いた直後にRTSが準備できた場合、不要なデータを送ってしまう。
というデメリットがあります。

一般的には、どのような方法を取るのでしょうか?

 

  • NAKAさんおひさです。

    RTSをエッジ割り込みで使えば、RTSが変化するまでCPUは別の処理ができるのでいいのかなと思います。

  • Kirinさんおひさです。

    相変わらず大活躍ですね!流石ぁ~!僕の先生!

    すいません!まだ呑み込めてません.......涙

    RTS信号を外部割り込み(INT)のエッジ動作を使うという意味?

    ドライバーの作り方が悪いのかなぁ~?? 

    こんな感じで送信してます。(コード貼った方がいいのかな?)

    ◎送信関数

    送信レジスタに1つ目のデータ書き込み

    残りをバッファに書き込み

       ↓

    送信レジスタが送信して"空"割り込み発生

       ↓

    ◎送信"空"割り込み関数

    バッファが最後でないなら

    次のバッファの内容を送信レジスタに書き込み

    割り込みを抜ける

       ↓

    送信レジスタが送信して"空"割り込み発生

    バッファの最後まで送信空割り込み関数が回りつづける

    どのタイミングでRTSのエッジ割り込みをかけて、送信を止める

    のか理解できてない感じです...........はずかしー!!

    途中で止めちゃったら、"空"割り込みが次から発生しなくなる?

    RTSのエッジ割り込みの中で、どんな処理するんだろう?

    P.S.

    久しぶりの書き込みでしたので、聞きたい部分だけ(いきなりハードフロー制御とか)

    書いちゃいました。調歩同期のシリアル通信で....とか書くべきでしたね!

    LogINしておらず、NewPOSTボタンも探しちゃいました.....汗)

  • NAKAさん

    思いついたら自動返信ですから(笑)

    NAKAさんの処理にエッジ割り込みを足してみました。

    ◎送信関数
    全データをバッファに書き込み
    RTSをチェックしてOKなら、送信レジスタに1つ目のデータ書き込み、バッファのポインタをインクリメントして関数から抜ける。
    RTSがNGなら、何も送信せずに関数から抜ける。
       ↓
    送信空割り込み もしくは エッジ割り込み発生
       ↓
    ◎送信"空"割り込み関数とエッジ割り込み関数から共通のサブルーチンをコール
    RTSをチェックしてOKなら、
    バッファが最後でないなら次のバッファの内容を送信レジスタに書き込み割り込みを抜ける。
    RTSがNGならなにもせず割り込みから抜ける。
       ↓
    送信空割り込み もしくは エッジ割り込み発生

    バッファの最後まで送信空割り込み関数もしくはエッジ割り込み関数(から呼ばれる共通サブルーチン関数)が回りつづける。

    こんな感じでいかがでしょう?

  • Kirinさんこんばんは!

    考えてみました。

    接続先からのRTS信号(INT外部割り込み)の立上がりエッジで、送信"空"割り込み関数を中断して(送信せずに)関数を抜けて、

    次に立下りエッジで再度バッファの続きのデータを送信レジスタに書き込み、処理を再開させる。

    という意味だったのでしょうか?

    なるほどぉー。気づかんかった!!!疲れとる!

    p.s.

    そうそう、USBシリアルのブリッジICってあるじゃないですか?

    メーカによってハードフロー制御の動作が違うような記事がありました。

    FTDIのデバイスは、RTSが"H"になっててもデータが送られちゃうことがあるようです。

    ProLificのICはちゃんと待っててくれるそうです。

    bluegiga.zendesk.com/.../23143152--REFERENCE-Using-or-bypassing-flow-control-with-UART-communication

  • きゃは!!

    考えて、文章打っている間に、回答きちゃった!!

    送信関数で、1つ目のデータを送信レジスタに書いちゃった後に、RTSが「待ってくれぇ~」となっちゃったらとか考えちゃいました。

    心配しすぎですかね?........笑)

  • NAKAさん

    そうですねー、RTSの応答時間は相手次第なので、送信前に0.1msecくらいウエイトを入れてから、RTSの判定をするのがいいかもしれませんね。0.1msecを10msecにすればもっと安全になりそうですけれども、スループットが悪くなるので、適切なタイミングを見つけてくださいね!
    タイマー割り込みなんかも加わって、送信処理が大変そうですけども・・・・

  • Kirinさん

    ありがとうございました。

    Kirinさんとやり取りしてると、ちょー楽し~ぃ!!!

    いかん!いかん!仕事しよっと! それでは。

  • NAKAさん
    私もNAKAさんとおしゃべりしていると現実逃避できて幸せです♡

    RTSを考えると、送信"空"割り込みよりも、送信完了割り込みの方がいいかもしれませんね。
    送信バッファ空割り込みを使うと、RTS NGを検出した後に1バイト余分に出てしまうので、実送信が完了する毎にRTSをチェックすれば、より安全になりそうですよ。

  •  昔の通信LSIの8251には、RTS、CTS、DTR、DSRが有ります。CTS以外は信号名に捉われず汎用の入出力ポートとして使えます。

     CTSはハード的に送信の制御を行います。

     RTSでは無く、CTSを見て制御するべきだと思います。

     常時送信可であれば、CTSはONに固定です。だからエッジ割り込みと言う訳には行きません。

     送信しようとした時にOFFだったので、ONになったタイミングで知らせてくれと言う割り込みなら分かりますが。

     アスキーコードの制御信号でON/OFFする場合、OFFを送っても相手が読んでから止めるので、直ぐには止まりません。

    予備実験が必要です。OFFを送った後10バイトじゃ足らない。予備実験無しで勘で設計するなら、止まるまで30~60バイトぐらいの余裕が必要です。

  • チョコです。

    リカルドさん、8251ですか。懐かしいUSARTですね。(UARTではなく、インテルは

    USARTと呼んでました。)

    モデム関係者によると、RTS、CTS、DTR、DSRでの制御はおかしいとの話でしたが、

    マイコンの世界では、RTSとCTSによるハンドシェイクが定着してしまいましたね。

    リカルドさんのおっしゃるように、DTE(端末)側での送信制御はCTSを使うのが正しい

    やり方ですね。

    X-OFFでの送信停止要求でもそうですが、中にはCTSでの送信禁止からでも10

    バイト以上必要なUNIXシステムもありましたね。