シリアル通信について

解決


ぺんこ  2006-01-15 00:22:00  No: 60278

PCからPDAへシリアル通信(rs-232c)を使って送信するプログラムを作成しているのですが,PCからPDAに正しくテキストが送信されません.
PCからPDAへ"12345"と最初に送信したときは,
PDA側で"12345"と正しく出力されるのですが,
その後に,"abc"と送ると,PDAのほうでは"abc45"と出力されてしまいます.
前に送信したデータが残っているらしいのです.
PDAの受信プログラムはeMbedded Visual C++3.0  MFC  ダイアログベースを
使っています.タイマー関数を使って,0.1秒毎にポートの状態を調べて(ClearCommError),もしバッファにデータがあれば,それを読み込む(ReadFile)というプログラムを作成しました.非同期で受信していて,ストップビットは1,
パリティはなしです.
PCの送信プログラムはフリーソフト(Acknowrich)を使用しています.

以下に作成したプログラムを記述しますので,誰かご教授願えればと思います.
よろしくお願いいたします.

//rdBuf は  char rdBuf[516] = ""と宣言してあります.
//以下の関数を0.1秒毎に実行する  
void CTest1Dlg::OnTimer(UINT nIDEvent)

ClearCommError(hComm, &dwErrors, &ComStat); //ポートの状態を取得
     dwCount=ComStat.cbInQue;   // 受信バッファのバイト数の取得
   if(dwCount != 0 ){       
     ReadFile(hComm, rdBuf, dwCount , &dwRead, NULL);
     UpdateData(TRUE);
            m_b = rdBuf;
             PurgeComm(hComm , PURGE_RXABORT | PURGE_RXCLEAR );
            UpdateData(FALSE);

         }


επιστημη  2006-01-15 00:26:16  No: 60279

受信文字の末尾に'\0'がついてるわけでないから、あなたがくっつけてあげないと。

ReadFileの直後に rdBuf[dwCount] = '\0'; すればよさげ。


ぺんこ  2006-01-15 02:09:26  No: 60280

回答ありがとうございます.
プログラムのところで書き忘れた箇所がありました.すいません.
if(dwCount != 0 ){ 
の後で,
strcpy(rdBuf,"");
という部分があるのでrdBufはたぶん初期化できていると思います。
他に原因が考えられるでしょうか?


Blue  2006-01-15 02:28:27  No: 60281

> strcpy(rdBuf,"");
ではダメそうです。

おそらく、
rdBuf[ 0 ] = '\0';
という処理しかしていないかと。
(ウォッチやローカルウィンドウで確かめてみては)

よって、
rdBuf[ 0 ] = '1'
rdBuf[ 1 ] = '2'
rdBuf[ 2 ] = '3'
rdBuf[ 3 ] = '4'
rdBuf[ 4 ] = '5'
rdBuf[ 5 ] = '\0'

> strcpy(rdBuf,"");

rdBuf[ 0 ] = '\0'
rdBuf[ 1 ] = '2'
rdBuf[ 2 ] = '3'
rdBuf[ 3 ] = '4'
rdBuf[ 4 ] = '5'
rdBuf[ 5 ] = '\0'
となるだけなので、
> ReadFile(hComm, rdBuf, dwCount , &dwRead, NULL);

rdBuf[ 0 ] = 'a'
rdBuf[ 1 ] = 'b'
rdBuf[ 2 ] = 'c'
rdBuf[ 3 ] = '4'
rdBuf[ 4 ] = '5'
rdBuf[ 5 ] = '\0'
となっているというわけです。

初期化するならば、memset等で全てのバッファ内を'\0'で埋めるべきでしょう。
それか、επιστημηさんの指摘どおり
> ReadFileの直後に rdBuf[dwCount] = '\0'; すればよさげ。
とするか。


ぺんこ  2006-01-15 02:32:19  No: 60282

本当にありがとうございます.
rdBuf[dwCount]='\0'
を追加したところ,正しく送信した文字だけを受信できました.
ありがとうございました.


Blue  2006-01-15 02:53:45  No: 60283

ちなみに
> //rdBuf は  char rdBuf[516] = ""と宣言してあります.
のように宣言時に初期化させた場合は全ての領域が'\0'(0x00)で埋まります。
(文字を指定した場合は指定した文字列以降の領域が0で初期化される)

例)
char s1[10]="123";  // '1','2','3','\0',0,0,0,0,0,0
char s2[10]="";      // '\0',0,0,0,0,0,0,0,0,0
char s3[10]={0};    // 0,0,0,0,0,0,0,0,0,0
char s4[10]={'1'};  // '1',0,0,0,0,0,0,0,0,0
char s5[10];        // 初期化されない


επιστημη  2006-01-15 06:52:06  No: 60284

× 正しく送信した文字だけを受信できました.

○ 正しく送信した文字だけを表示できました.


※返信する前に利用規約をご確認ください。

※Google reCAPTCHA認証からCloudflare Turnstile認証へ変更しました。






  このエントリーをはてなブックマークに追加