2016-05-25 9 views
0

UART周辺機器を介してデータを送信する開発ボード(Beagle Bone Black)のアプリケーションを開発しています。開発ボードはLinux Kernel(一部のDebianディストリビューション、3.8.x Linuxカーネルバージョン)を実行します。 open()read()、およびwrite()家族機能:UART上でデータを送受信するためのUARTのシリアルデータが破損する

は私が標準UNIX APIを使用します。

baud ratestop/start bitsparityなど)の通信パラメータを設定するため、私は(termios.hから)termios構造を使用します。

  • fd_debug:デバッグ目的、ファイルへのリンクがあり
    fd_debug = open("output.out", O_CREAT | O_WRONLY, S_IRUSR | S_IWUSR); 
    
    fd_write = open(port.c_str(), O_WRONLY | O_NOCTTY | O_SYNC); 
    std::cout << std::endl << "I opened: " << port; 
    
    struct termios settings; 
    tcgetattr(fd_write, &settings); 
    
    cfsetospeed(&settings, B19200);   /* baud rate */ 
    settings.c_cflag &= ~PARENB;   /* no parity */ 
    settings.c_cflag &= ~CSTOPB;   /* 1 stop bit */ 
    settings.c_cflag &= ~CSIZE; 
    settings.c_cflag |= CS8 | CLOCAL;  /* 8 bits */ 
    settings.c_lflag = ICANON;    /* canonical mode */ 
    settings.c_oflag &= ~OPOST;    /* raw output */ 
    
    tcsetattr(fd_write, TCSANOW, &settings); /* apply the settings */ 
    tcflush(fd_write, TCOFLUSH); 
    

    は、私は2つのファイルディスクリプタをオープンしました:

    これは私がI/Oの設定を行い、いくつかの関連するコード配列です。

  • fd_write:UARTペリフェラル(特定のケースでは/dev/ttyO4)にリンクされています。

これは私がUART上で1つのバイトを送信したいときに実行される関数である:私は、送信データがUART上で正しく受信されたかどうかをチェックするために

int UARTIOHandler::write(uchar8 byte) { 
    auto tp = std::chrono::steady_clock::now(); 
    std::cout << std::endl << "[write] Timestamp: " << std::chrono::duration_cast<std::chrono::milliseconds>(tp.time_since_epoch()).count(); 
    ::write(fd_debug, &byte, 1); 
    return ::write(this->fd_write, &byte, 1); 
} 

、私はTXRXが接続されています私のボード上のピン(ループバックテスト)、およびその特定のUARTポートでminicomを実行します(私は送信データをバック受け取ることができるようにしたいので):

minicom -D /dev/ttyO4 -b 19200 -C test.test 

いくつかのデータを送信した後、2つのファイル(デバッグファイルとminicomによって生成された出力ファイル(UARTで受信したデータを含むはずです))を比較しました。問題は、データが同じではないということです!

これは(16進数で)送信され、実際のデータである。

55 33 02 04 06 08 0a 0c d5 55 0b 01 03 05 07 ef 55 3f 07 06 05 04 03 02 01 e3 55 16 01 02 03 04 05 06 07 08 db 55 3f 01 02 03 04 05 06 07 e3 

これは、デバッグファイルで受信したデータである(それは同じですので、これはいくつかのUART問題があることを確認):

55 33 02 04 06 08 0a 0c d5 55 0b 01 03 05 07 ef 55 3f 07 06 05 04 03 02 01 e3 55 16 01 02 03 04 05 06 07 08 db 55 3f 01 02 03 04 05 06 07 e3 

そして、これはminicomツール(それは同じUARTポートに耳を傾けるように設定し、同じ設定(baudparity、など)で受信したデータです。

55 33 02 04 06 08 0a d5 55 01 03 4d 69 6e 69 63 6f 6d 32 2e 36 2e 31 07 ef 55 3f 07 06 4d 69 6e 69 63 6f 6d 32 2e 36 2e 31 04 03 02 01 e3 55 16 01 02 03 04 4d 69 6e 69 63 6f 6d 32 2e 36 2e 31 06 07 08 db 55 3f 01 02 03 04 4d 69 6e 69 63 6f 6d 32 2e 36 2e 31 06 07 e3 

ポイントから見ると、すべてのデータが破損し、受信したバイト数が増えています。問題がある可能性がどのような

hexdump -ve '1/1 "%.2x "' test.test 

:私はこのようなhexdumpを使用し、出力ファイルから実際のデータをチェックするための

+0

C++はプログラミングしていないプログラミング言語を知っていれば役に立ちます。 – Lundin

+0

@Lundin 'unistd.h'と' termios.h'はCのPOSIXライブラリのコンポーネントなので、 'C'言語。 –

+0

minicomの設定、特にフロー制御(ハードウェアとソフトウェア)をチェックしましたか? – blatinox

答えて

1

これは、ENQ文字(0x05)に応答し、その応答をセッションキャプチャに記録するMinicomのようです。追加データは破損していないMinicom2.6.1です。ストリーム内の0x05ごとに置き換えられます。

+1

また、 '0c'と' 0b'をスキップしたようです。 –

+0

これは実際に問題になるかもしれませんが、私は実際に 'minicom'セッションで' Minicom2.6.1'文字列を見ることができます。私はこの置換を無効にする方法を見つけませんでした。 –

+0

@WeatherVaneはい。彼らは "垂直タブ"と "フォームフィード"であり、ミニコムはおそらくそれらを通過させるよりもむしろそれらに作用しているでしょう。昔、あなたのストリームの^ L(0x12)はあなたのハードコピー端末に新鮮なシートを提供します。 (なぜそれが 'vi'や' curses'のようなものでは再描画コマンドとして使われるのでしょうか?) – janm

関連する問題