-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathcreate_functions.py
382 lines (303 loc) · 9.1 KB
/
create_functions.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
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
#mStart = 0, mEnd = -1, Width = 8, mCheck = -1, foldOp = add, finalOp = xor, magicVal = 0x55.
# calculate the checksum
import operator
import functools
width = 8
def calc(msg, fold_op, final_op, magic_val):
res = functools.reduce(fold_op, msg, 0)
if final_op is not None:
if magic_val is None:
res = final_op(res) # unary operation
else:
res = final_op(res, magic_val) # binary operation
# make sure it fits in width bits
return res & ((1 << width) - 1)
data = """806FA30102B00818
806FA30300800040
806FA30200800041
806FA30400800043
806FA30101810848
806FA30102800848
806FA30100810849
806FA3010480084A
806FA3010080084E
806FA30102A00868
806FA30101A2086B
806FA30102880870
806FA30106800874
806FA30100880876
806FA30102900878
806FA30112800878
1003A30001003806739C9B9400121202
1003A3000100380A74A08E9400121206
1003A30001004006729E99940012120B
1003A30001003007729B9A8E00121212
1003A30001003804747778CC01121212
1003A30001003007719B999000121212
1003A300010030076F9F929400121213
1003A300010030076EA18C9400121214
1003A300010030076EA08E9400121217
1003A30001003007729B9A900012121C
1003A3000100300672A191940012121C
1003A30001003007729B99900012121D
1003A30001003007709C98940012121F
1003A30001003805747677000012122C
1003A3000100B4036C3E3A0000120031""".strip()
# make a list out of the messages
def hexToList(data,pad):
msgs = []
if width == 8:
for m in data.split("\n"):
if pad and len(m) % 2 != 0:
m = m + "0"
msgs.append([x for x in bytes.fromhex(m)])
else: # it's 16
for m in data.split("\n"):
if pad and len(m) % 4 != 0:
m = m + (4 - (len(m) % 4)) * "0"
msgs.append([int(m[i:i+4], 16) for i in range(0, len(m)-3, 4)])
return msgs
# Given a set of bytes, calculate the checksum
def calculate_checksum(payload):
#res = functools.reduce(operator.add, payload, 0)
res = 0
checksum = 0
for byte in payload:
checksum=checksum+byte
if operator.xor is not None:
if 0x55 is None:
res = operator.xor(res,0) # unary operation
else:
res = operator.xor(res, 0x55) # binary operation
# make sure it fits in width bits
checksum = checksum ^ 0x55
return checksum & ((1 << width) - 1)
#return res & ((1 << width) - 1)
def calculate_checksum(payload):
#res = functools.reduce(operator.add, payload, 0)
magicValue = 0x55
checksum = 0
for byte in payload:
checksum= (checksum+byte)
checksum = (checksum ^ magicValue)
return checksum & ((1 << width) - 1)
#return res & ((1 << width) - 1)
def mk_calculate_checksum(mask,foldOp,finalOp,magicValue):
print(mask)
f= f""" checksum = 0
for byte in payload:
checksum = checksum {foldOp} byte
"""
if finalOp:
if magicValue:
f = f" magicValue = {str(magicValue)}\n" + f + f" checksum = checksum {finalOp} magicValue\n"
else:
f = f + f" checksum = {finalOp} checksum\n"
f = f + f" return checksum & {str(mask)}"
return "def calculate_checksum(payload):\n" +f
def mk(mask,foldOp,finalOp,magicValue,mStart,mEnd,cIdx,csumW):
lines = [f"def calculate_checksum(payload):"]
lines+= [f" checksum = 0"]
if magicValue:
lines+= [f" magicValue = {magicValue}"]
lines+= [f" for byte in payload:"]
lines+= [f" checksum = checksum {foldOp} byte"]
if finalOp:
if magicValue:
lines+= [f" checksum = checksum {finalOp} magicValue"]
else:
lines+= [f" checksum = {finalOp}checksum"]
lines+= [f" return checksum & {mask}"]
lines+= [""]
lines+= [f"def validate_message(msg):"]
lines+= [f" msgStart = {mStart}"]
lines+= [f" msgEnd = {mEnd}"]
lines+= [f" payload = msg[msgStart:msgEnd]"]
lines+= [f" checksumStart = {cIdx}"]
lines+= [f" checksum = msg[checksumStart]"]
# if cIdx+csumW != 0:
# lines+= [f" checksumEnd = {cIdx+csumW}"]
# lines+= [f" checksum_bytes = bytes(msg[checksumStart:checksumEnd])"]
# else:
# lines+= [f" checksumBytes = bytes(msg[checksumStart:])"]
# lines+= [f" checksum = int.from_bytes(checksumBytes,byteorder='big')"]
lines+= [f" return calculate_checksum(payload) == checksum"]
lines+= [""]
lines+= [f"assert(validate_message([1,2,3]+[calculate_checksum([1,2,3])])==True)"]
return "\n".join(lines)
def xcalculate_checksum(payload):
magicValue = 0x55
checksum = 0
for byte in payload:
checksum = checksum + byte
checksum = checksum ^ magicValue
return checksum & 255
def xcalculate_checksum(payload):
magicValue = 85
checksum = 0
for byte in payload:
checksum = checksum + byte
checksum = checksum ^ magicValue
return checksum & 255
# Given a msg, validate that no errors have been introduced.
def validate_checksum(msg):
mStart = 0
mEnd = -1
payload = msg[mStart:mEnd]
checksum = msg[mEnd:]
return calculate_checksum(payload) == checksum
for msg in hexToList(data,False):
#mStart = 0, mEnd = -1, Width = 8, mCheck = -1, foldOp = add, finalOp = xor, magicVal = 0x55.
v= calc(msg[:-1],operator.add,operator.xor,0x55)
v2 = calculate_checksum(msg[:-1])
v3 = xcalculate_checksum(msg[:-1])
print(msg,v,v2,v3)
def opname2function(name):
if name == "add":
return "+"
elif name == "twosComp":
return "-"
elif name =="xor":
return "^"
elif name == "":
pass
ftxt = mk_calculate_checksum(str(0xFF),"+","^",str(0x55))
print(ftxt)
ftxt = mk(0xffff,"-","+",0xfffd,0,0,5,2)
print(ftxt)
print("*"*80)
# def calculate_checksum(payload):
# checksum = 0
# magicValue = 85
# for byte in payload:
# checksum = checksum + byte
# checksum = checksum ^ magicValue
# return checksum & 255
# def validate_message(msg):
# msgStart = 0
# msgEnd = -1
# payload = msg[msgStart:msgEnd]
# checksumStart = -1
# checksumBytes = bytes(msg[checksumStart:])
# checksum = int.from_bytes(checksumBytes,byteorder='big')
# return calculate_checksum(payload) == checksum
# assert(validate_message([1,2,3]+[calculate_checksum([1,2,3])])==True)
# assert(validate_message([1,2,3]+[calculate_checksum([1,2,3])])==True)
print("""
def pad(xs,w):
n = len(xs)
target_n = (-(-n//w)) * w
delta = target_n - n
xs_padded = xs+[0]*delta
return xs_padded
def chunk(xs,w):
xs_chunked = [xs[i:i+w] for i in range(0,len(xs),w)]
return xs_chunked
def to_int(x):
return int.from_bytes(bytes(x),'big')
def preprocess(xs,w):
xs_padded = pad(xs,w)
xs_chunked = chunk(xs_padded,w)
xs_ints = [to_int(x) for x in xs_chunked]
return xs_int
""")
def test(msgStart,msgEnd,checksumPos,width,foldOp,finalOp,magicValue,mask):
def pad(xs,w):
n = len(xs)
target_n = (-(-n//w)) * w
delta = target_n - n
xs_padded = xs+[0]*delta
return xs_padded
def chunk(xs,w):
xs_chunked = [xs[i:i+w] for i in range(0,len(xs),w)]
return xs_chunked
def to_int(x):
return int.from_bytes(bytes(x),'big')
def preprocess(xs,w):
xs_padded = pad(xs,w)
xs_chunked = chunk(xs_padded,w)
xs_ints = [to_int(x) for x in xs_chunked]
return xs_ints
def calculate_checksum(payload):
magicValue = 65533
mask = 0xFFFF
checksum = 0
for element in payload:
checksum = checksum - element
checksum = checksum + magicValue
return checksum & mask
def validate_message(rawmsg):
msgStart = {0}
msgEnd = 0
checksumPos =5
width = 2
msg = preprocess(rawmsg,width)
payload = msg[msgStart:]
checksum = msg[checksumPos]
payload[checksumStart] = 0
return calculate_checksum(payload) == checksum
def stest(msgStart,msgEnd,checksumPos,width,foldOp,finalOp,magicValue,mask):
if finalOp != None:
if magicValue != None:
magicValue_str = f""" magicValue = {magicValue}"""
finalOp_str = f""" checksum = checksum {finalOp} magicValue"""
else:
magicValue_str = ""
finalOp_str = f""" checksum = {finalOp}checksum"""
else:
magicValue_str = ""
finalOp_str = ""
if msgEnd == 0:
payload_str = f" payload = msg[msgStart:]"
else:
payload_str = f" payload = msg[msgStart:{msgEnd}]"
res = f"""
def pad(xs,w):
n = len(xs)
target_n = (-(-n//w)) * w
delta = target_n - n
xs_padded = xs+[0]*delta
return xs_padded
def chunk(xs,w):
xs_chunked = [xs[i:i+w] for i in range(0,len(xs),w)]
return xs_chunked
def to_int(x):
return int.from_bytes(bytes(x),'big')
def preprocess(xs,w):
xs_padded = pad(xs,w)
xs_chunked = chunk(xs_padded,w)
xs_ints = [to_int(x) for x in xs_chunked]
return xs_ints
def calculate_checksum(payload):
{magicValue_str}
mask = {mask}
checksum = 0
for element in payload:
checksum = checksum {foldOp} element
{finalOp_str}
return checksum & mask
def validate_message(rawmsg):
msgStart = {msgStart}
msgEnd = {msgEnd}
checksumPos ={checksumPos}
width = {width}
msg = preprocess(rawmsg,width)
{payload_str}
checksum = msg[checksumPos]
payload[checksumStart] = 0
return calculate_checksum(payload) == checksum"""
return res
data = """4500002894d00000710654cc0d6b8809c0a80a17
450000282ba700007106bdf50d6b8809c0a80a17
45000028bd27000071062c750d6b8809c0a80a17
4500012c000040004006d998c0a80a170d6b8809
45000052000040004006da72c0a80a170d6b8809
450000de4ef50000391197f28efa406ec0a80a17"""
for msg in hexToList(data,False):
#mStart = 0, mEnd = -1, Width = 8, mCheck = -1, foldOp = add, finalOp = xor, magicVal = 0x55.
#print(msg,validate_message(msg),preprocess(msg,2))
pass
gender = "male"
s = "At least, that's what {pronoun} told {subject}.".format(pronoun="he" if gender == "male" else "she",subject="he" if gender == "male" else "she")
print(s)
print(stest(0,0,5,2,"-","+",65533,0xFFFF))