-
Notifications
You must be signed in to change notification settings - Fork 9
/
Copy pathDL-LPW.py
72 lines (56 loc) · 1.99 KB
/
DL-LPW.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
# -*- coding: utf-8 -*-
# https://www.decentlab.com/products/linear-position-/-way-for-lorawan
from __future__ import absolute_import
from __future__ import division
from __future__ import print_function
from __future__ import unicode_literals
import struct
from math import log, floor
from base64 import binascii
PROTOCOL_VERSION = 2
SENSORS = [
{'length': 2,
'values': [{'name': 'Potentiometer position',
'convert': lambda x: ((x[0] + x[1]*65536) / 8388608 - 1) * 1 * 100,
'unit': '%'}]},
{'length': 1,
'values': [{'name': 'Battery voltage',
'convert': lambda x: x[0] / 1000,
'unit': 'V'}]}
]
def decode(msg, hex=False):
"""msg: payload as one of hex string, list, or bytearray"""
bytes_ = bytearray(binascii.a2b_hex(msg)
if hex
else msg)
version = bytes_[0]
if version != PROTOCOL_VERSION:
raise ValueError("protocol version {} doesn't match v2".format(version))
devid = struct.unpack('>H', bytes_[1:3])[0]
bin_flags = bin(struct.unpack('>H', bytes_[3:5])[0])
flags = bin_flags[2:].zfill(struct.calcsize('>H') * 8)[::-1]
words = [struct.unpack('>H', bytes_[i:i + 2])[0]
for i
in range(5, len(bytes_), 2)]
cur = 0
result = {'Device ID': devid, 'Protocol version': version}
for flag, sensor in zip(flags, SENSORS):
if flag != '1':
continue
x = words[cur:cur + sensor["length"]]
cur += sensor["length"]
for value in sensor['values']:
if 'convert' not in value:
continue
result[value['name']] = {'value': value['convert'](x),
'unit': value.get('unit', None)}
return result
if __name__ == '__main__':
import pprint
payloads = [
b'0211110003409a00860c54',
b'02111100020c54',
]
for pl in payloads:
pprint.pprint(decode(pl, hex=True))
print("")