まりぴよこのブログ

日々の日記。技術ネタでまとまりきってないものの記録、伝わる文章の書き方を練習とか。

ArduinoとMacでシリアル通信(C言語)

Arduinoはじめました

最近手を出してみた。リアル世界とつながるセンサーを使って、プログラミングしてみたい〜 ということでArduino始めました。

買った本

なんとなく参考書は2冊同時に買いたい派なので、以下の2冊をチョイス!

電子工作全くの初心者なので、今のところ「たのしい電子工作 Arduinoで電子工作をはじめよう!」ばかり開いています。「ボクのArduino工作ノート 改訂版」の方はレベルが高すぎるので、眺めてほえ〜んとするくらいです・・

照度センサーを使って明るさを測定

参考書の「たのしい電子工作 Arduinoで電子工作をはじめよう!」に載ってたそのままで、回路とスケッチを作成。

Arduino スケッチ

void setup() {
  Serial.begin(9600);
}

void loop() {
  int i;
  i = analogRead(0);
  Serial.print(i, DEC);
  Serial.print("\n");
  delay(1000);
}

1秒ごとにAnalog IN 0 (A0)に入ってくる、照度センサーからの数値を読み取り、10進数に変換して、シリアルポートに出力しているだけ。

シリアル通信でセンサーの値を読み込みたい

Arduino IDOのシリアルモニタを見ると、1秒ごとに数値がどんどん送信されていることが確認できる。

さて、ここで、数値の値によって処理をさせたくなってきたので、Arduinoと接続しているMacでシリアル通信プログラムを書いてみることに。。

とりあえず、送られてくる数値を読みたいだけなので、Cでいっかな、と思ってハマった。。

参考URL: LINUX間通信の準備

ここの参考URLのページのコードをいつものように1行ずつ写経・・・

シリアルポートのデバイス名を調べる

Arduino IDEで接続しているデバイス名はわかるけど、コンソールで調べる場合は・・

$ ls -al /dev/* | grep usb

macの場合、usbほにゃらら〜となってるので、grepで絞りこめる。

問題が・・

なぜか、

fd = open(DEV_NAME, O_RDWR);

でプログラムが止まる。 デバイス名をわざと間違えたりして色々調べたが、間違えてる場合はちゃんとエラー終了してくれる。 ずっとブロックするってなんなの・・・;;

解決

参考URL :

このページで紹介されてたツールソースコードを見て解決した。

先ほどの問題コードを

fd = open(DEV_NAME, O_RDWR | O_NONBLOCK );

に書き換えればOKだった。

O_NONBLOCKが鍵だったらしい。。

補足 O_NONBLOCKとは・・

参考URL: BeagleBoardでサバゲ!その19~シリアル通信プログラム解説~

O_NONBLOCK: ブロッキング制御をしない ブロッキング制御というのはシリアルモデムなんかで使われるモードのことで、(TX、RX以外の)制御信号でデータの送信完了を確認する時にセットします。

とのこと。。

つまり最初の書き方だと、送信完了を確認しようとして、ずっと待ってたってことなのかな・・?

完成したCのコードはこちら。

serial port read by c