Help us understand the problem. What is going on with this article?

pythonでTWE-Liteのシリアルを受け取る

More than 3 years have passed since last update.

安価で低消費電力の無線マイコン、TWE-LiteのシリアルデータをRaspberry Pi上のpythonで受け取るメモ。

構成

  | TWE-Lite | - | raspberry Pi |

まず、Raspberry Piのシリアルを使えるようにする。
この辺を見るといいです。
http://qiita.com/ryugyoku/items/bf5fd10512c84a55d030

テスト

TWE-LiteのTX,RDをRaspberry Piのシリアルポートに接続します。
試しにminicomで読み込んでみましょう。

$ sudo minicom -b 115200 -o -D /dev/ttyAMA0

minicomはsudo apt-get install minicomでインストールできます。

-Dオプションがターミナルの場所。
USBシリアル変換を使用している場合はここを/dev/ttyUSB0とかに変えればいいです。

minicom へようこそ 2.7

オプション: I18n
コンパイルされた日時は:  Jan 12 2014, 05:42:53.
ポート /dev/ttyAMA0, 01:54:51

CTRL-A Z を押すと、説明画面になります。

:0F8115015481012CFB00A387000BB0150101FFFFFFFFFF66
:0F8115015181012CFB00A389000BB0150101FFFFFFFFFF67
:0F8115015481012CFB00A38B000BAC150101FFFFFFFFFF66
:0F8115015181012CFB00A38D000BAC150101FFFFFFFFFF67
:0F8115015481012CFB00A38F000BB0150101FFFFFFFFFF5E
:0F8115014E81012CFB00A393000BAC150101FFFFFFFFFF64

このような物が出たら接続は正常です。
Ctrl+A,Qで終了。

こいつをPythonで受け取ってパースしましょう

シリアル受け取り

シリアルの取得はpyserialを使用します。

$ pip3 install pyserial

Python 3.4.2 (default, Oct 19 2014, 13:31:11)
[GCC 4.9.1] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> import serial
>>> ser = serial.Serial('/dev/ttyAMA0',115200)
>>> ser.readline()
b':0F8115014E81012CFB00A437000BAC150101FFFFFFFFFFBF'
>>> ser.close()
<bound method Serial.close of Serial<id=0xb68fd550, open=True>(port='/dev/ttyAMA0', baudrate=115200, bytesize=8, parity='N', stopbits=1, timeout=None, xonxoff=False, rtscts=False, dsrdtr=False)>
>>>

チェックサム計算

公式によると、コードの最後の1バイトがチェックサムとなっています。
計算方法は、先頭行から1バイトずつ加算していき、和の下位1バイトの補数がチェックサムとなっています。
つまり、':0F8115014E81012CFB00A437000BAC150101FFFFFFFFFFBF'の場合のチェックサムは最後のBFで、
0x0f+0x81+....0xff+0xff = 0x941 これの下1バイトの0x41 + 0xBF = 0xa00となります。

ということは、最初の":"を除く全桁を1バイトずつ加算した総和の下1バイトはかならず0になるということです。

python的な計算をすると、

Python 3.5.2 (default, Jun 28 2016, 08:46:01) 
[GCC 6.1.1 20160602] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> string = ':0F8115014E81012CFB00A437000BAC150101FFFFFFFFFFBF'
>>> string = string[1:] #冒頭の:を除く
>>> lst = [ int(string[i:i+2], 16) for i in range(0, len(string), 2) ] #二桁ずつ切り取って16進数として数値化
>>> s = sum(lst) #総和を取る
>>> hex(s & 0b1111)
'0x0'
>>>

0になりましたね。話のわかるやつだ

パース

データフォーマットはマニュアルを参照。

# coding: utf-8
#!/usr/bin/env python3

def parse(string):
    if string[-2:] == b"\r\n"  : string = string[:-2]
    if string[0]   == ord(':') : string = string[1:]
    lst = [ int(string[i:i+2], 16) for i in range(0, len(string), 2) ]
    if sum(lst) & 0xff == 0:
        return lst

    return False

if __name__ == '__main__':
    import serial
    s = serial.Serial('/dev/ttyAMA0',115200)

    l = s.readline()
    lst = parse(l)

    print (lst)

    SOURCE_DEVIDE = lst[0]
    COMMAND = lst[1]
    PACKET = lst[2]
    PROTOCOL = lst[3]
    LQI = (7 * lst[4] - 1970 ) / 20
    SN = lst[5] << 24 | lst[6] << 16 | lst[7] << 8 | lst[8]
    DESTINATION_ID = lst[9]
    TIMESTAMP = lst[10] << 8 | lst[11]
    RELATED = True if lst[15] % 1 else False
    VOLTAGE = lst[13] << 8 | lst[14]
    NONE = 0
    DIN = lst[16]
    DCHANGE = lst[17]
    ACOMP = lst[22]
    AD1 = (lst[18] * 4 + ACOMP) * 4
    AD2 = (lst[19] * 4 + ACOMP) * 4
    AD3 = (lst[20] * 4 + ACOMP) * 4
    AD4 = (lst[21] * 4 + ACOMP) * 4
    SUM = lst[-1]

    D1 = True if lst[16] & 0b0001 else False
    D2 = True if lst[16] & 0b0010 else False
    D3 = True if lst[16] & 0b0100 else False
    D4 = True if lst[16] & 0b1000 else False

あとはご自由に。

ライブラリですが、今見たら酷い出来だったのでそのうち改造します

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Comments
No comments
Sign up for free and join this conversation.
If you already have a Qiita account
Why do not you register as a user and use Qiita more conveniently?
You need to log in to use this function. Qiita can be used more conveniently after logging in.
You seem to be reading articles frequently this month. Qiita can be used more conveniently after logging in.
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
ユーザーは見つかりませんでした