Arduino返回的回复多于查询已发送的回复

时间:2012-04-16 11:54:11

标签: bash serial-port arduino stty

使用Arduino将数据发布到Pachube时出现问题。 Arduino配置为在发送't'时返回温度的JSON数据,并在发送'l'时返回亮度级别的JSON数据。这通过Arduino串行监视器完美地工作。然后我创建了两个bash脚本。一个人定期向Arduino发送't'和'l'命令,并在每个请求之间等待10秒。

while true; do
    echo -n t > /dev/ttyACM0
    echo "$(date): Queried Arduino for temperature."
    sleep 10
    echo -n l > /dev/ttyACM0
    echo "$(date): Queried Arduino for light."
    sleep 10
done

这很好用。我每隔10秒收到一条回音信息。另一个脚本从串口读取生成的JSON(我基本上是从某个Web页面复制它)。

ARDUINO_PORT=/dev/ttyACM0
ARDUINO_SPEED=9600
API_KEY='MY_PACHUBE_KEY'
FEED_ID='MY_FEED_ID'

# Set speed for usb
stty -F $ARDUINO_PORT ispeed $ARDUINO_SPEED ospeed $ARDUINO_SPEED raw
exec 6<$ARDUINO_PORT

# Read data from Arduino
while read -u 6 f ;do
    # Remove trailing carriage return character added
    # by println to satisfy stupid MS-DOS Computers
    f=${f:0:${#f} - 1}

    curl --request PUT --header "X-PachubeApiKey: $API_KEY" --data-binary "{ \"version\":\"1.0.0\", \"datastreams\":[ $f ] }" "http://api.pachube.com/v2/feeds/MY_FEED_ID"
    echo "$(date) $f was read."
done

不幸的是,这个脚本疯狂地回复消息告诉我,它每10秒就会向Pachube发送数据几次,尽管它应该每10秒执行一次(每当第一个脚本告诉Arduino创建JSON消息时)。我认为这可能是Arduino上缓冲消息的问题,但即使将其关闭再打开,问题仍然存在。有什么想法吗?提前谢谢。

1 个答案:

答案 0 :(得分:1)

我完全不熟悉Arduino以及你在这里做的其他一些事情,但这里有一些我看到的一般事项:

  • Bash几乎完全无法可靠地处理二进制数据。无法在Bash字符串中存储NUL字节。看起来你正在尝试提取一些技巧来使任意数据可读 - 希望你只是将字符数据发送到read,否则这不太可行。

  • read读取换行符分隔的输入(如果您的bash足够新,则读取-d的给定值)。我不知道while循环正在读取的格式,但它必须是换行符分隔的字符串。

  • 除非您希望解释转义序列,否则请使用read -r。 (您几乎总是希望-r使用read。)

  • 无条件剥离每个字符串末尾的字符并不是最好的。我使用:f=${f%+($'\r')},它会从f的末尾删除1个或多个相邻的\r。如果这不是默认值,请记住脚本顶部的shopt -s extglob

  • 这实际上不应该导致问题,但我不想使用exec,除非它真的需要 - 它不在这里。只需放置done <$ARDUINO_PORT来终止while循环并从-u 6中删除read参数(除非循环中的某些内容专门从stdin读取并且不能冲突,这不会看来是这样的。退出循环时,打开的FD将自动关闭。

  • 不要在脚本中创建自己的全部大写变量名称,因为它们是保留的,并且可能与环境中的变量冲突。至少使用一个小写字母。如果这些变量是由系统中的某些东西设置的,而您只是使用或修改它们,那么这当然不适用。