From ad4b6ae8d6028a946adedbaddc2a36852a76429b Mon Sep 17 00:00:00 2001 From: gitea Date: Mon, 1 Jul 2024 14:09:47 +0800 Subject: [PATCH] =?UTF-8?q?v0.1.7.3(2024/07/01)=201.=20[APIs:=20openapi.py?= =?UTF-8?q?]=20=E7=BB=A7=E7=BB=AD=E5=AE=8C=E5=96=84=E5=B0=81=E5=8C=85?= =?UTF-8?q?=E8=A7=A3=E5=8C=85=E6=93=8D=E4=BD=9C=EF=BC=8C=E5=B9=B6=E4=BC=98?= =?UTF-8?q?=E5=8C=96=E4=BA=86=E6=89=80=E6=9C=89=E8=B0=83=E8=AF=95=E4=BF=A1?= =?UTF-8?q?=E6=81=AF=EF=BC=8C=E9=BB=98=E8=AE=A4=E6=89=93=E5=BC=80=E7=8A=B6?= =?UTF-8?q?=E6=80=81=EF=BC=8C=E7=9B=B4=E5=88=B0bug=E6=95=B0=E9=87=8F?= =?UTF-8?q?=E6=98=8E=E6=98=BE=E5=87=8F=E5=B0=91=202.=20[APIs:=20do=5Fcurre?= =?UTF-8?q?nt.py]=20=E4=BD=BF=E7=94=A8=E5=8E=9F=E5=B7=A5=E7=A8=8B=E7=9A=84?= =?UTF-8?q?=E5=B7=A5=E7=A8=8B=E5=90=8D=E8=BF=9B=E8=A1=8Cmove=E6=93=8D?= =?UTF-8?q?=E4=BD=9C=EF=BC=8C=E8=AF=AD=E4=B9=89=E6=9B=B4=E5=8A=A0=E6=98=8E?= =?UTF-8?q?=E7=A1=AE?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit > 目前看openapi.py封包解包没有任何问题了,但是所有的调试信息都默认打开,以便可以第一时间保留现场 --- aio/README.md | 11 +- aio/code/automatic_test/do_current.py | 6 +- aio/code/automatic_test/openapi.py | 315 +++++++++++++------------- 3 files changed, 173 insertions(+), 159 deletions(-) diff --git a/aio/README.md b/aio/README.md index 263b234..a021168 100644 --- a/aio/README.md +++ b/aio/README.md @@ -378,4 +378,13 @@ v0.1.7.2(2024/06/30) 1. 初步完成NB4h_R580_3BH7.zip工程的设计 2. 重新研究了解包操作,重新实现了一版 3. 修改openapi.pi中excution为execution函数 -4. 增减了解包原理性文档 \ No newline at end of file +4. 增加了解包原理性文档 + +v0.1.7.3(2024/07/01) +1. [APIs: openapi.py] 继续完善封包解包操作,并优化了所有调试信息,默认打开状态,直到bug数量明显减少 +2. [APIs: do_current.py] 使用原工程的工程名进行move操作,语义更加明确 + +> 目前看openapi.py封包解包没有任何问题了,但是所有的调试信息都默认打开,以便可以第一时间保留现场 + + + diff --git a/aio/code/automatic_test/do_current.py b/aio/code/automatic_test/do_current.py index 1e894c4..ba49752 100644 --- a/aio/code/automatic_test/do_current.py +++ b/aio/code/automatic_test/do_current.py @@ -71,13 +71,14 @@ def prj_to_xcore(prj_file): print(stdout.read().decode()) # 必须得输出一下stdout,才能正确执行sudo print(stderr.read().decode()) # 顺便也执行以下stderr - cmd = 'cd /home/luoshi/bin/controller/; sudo mv projects/target/_build/*.prj projects/target/_build/target.prj ' + _prj_name = prj_file.split('\\')[-1].removesuffix('.zip') + cmd = f'cd /home/luoshi/bin/controller/; ' + cmd += f'sudo mv projects/target/_build/{_prj_name}.prj projects/target/_build/target.prj ' stdin, stdout, stderr = ssh.exec_command(cmd, get_pty=True) stdin.write('luoshi2019' + '\n') stdin.flush() print(stdout.read().decode()) # 必须得输出一下stdout,才能正确执行sudo print(stderr.read().decode()) # 顺便也执行以下stderr - ssh.close() @@ -154,6 +155,7 @@ def run_rl(hr, w2t): _response = execution('diagnosis.open', hr, w2t, open=False, display_open=False) print(f"关闭诊断: {_response}") + _response = execution('rl_task.stop', hr, w2t, tasks=['brake']) _response = execution('state.switch_motor_off', hr, w2t) _response = execution('state.switch_manual', hr, w2t) diff --git a/aio/code/automatic_test/openapi.py b/aio/code/automatic_test/openapi.py index fc0c373..a5c7233 100644 --- a/aio/code/automatic_test/openapi.py +++ b/aio/code/automatic_test/openapi.py @@ -30,15 +30,17 @@ class HmiRequest(object): self.broke = 0 self.half = 0 self.half_length = 0 + self.index = 0 + self.reset_index = 0 self.sock_conn() self.t_heartbeat = Thread(target=self.heartbeat) self.t_heartbeat.daemon = True self.t_heartbeat.start() - self.t_unpackage = Thread(target=self.unpackage, args=(self.c, )) + self.t_unpackage = Thread(target=self.unpackage, args=(self.c,)) self.t_unpackage.daemon = True self.t_unpackage.start() - self.t_unpackage_xs = Thread(target=self.unpackage_xs, args=(self.c_xs, )) + self.t_unpackage_xs = Thread(target=self.unpackage_xs, args=(self.c_xs,)) self.t_unpackage_xs.daemon = True self.t_unpackage_xs.start() @@ -60,13 +62,6 @@ class HmiRequest(object): self.w2t("Connection success", 0, 0, 'green', tab_name=self.tab_name) with open(f"{current_path}/../../assets/templates/heartbeat", "w", encoding='utf-8') as f_hb: f_hb.write('1') - # print(f"打开诊断:") - # self.execution('diagnosis.open', open=True, display_open=True) - # display_pdo_params = [] - # print(f"执行采样") - # self.execution('diagnosis.set_params', display_pdo_params=display_pdo_params) - # print(f"关闭诊断") - # self.execution('diagnosis.open', open=False, display_open=False) except Exception as Err: self.w2t("Connection failed...", 0, 0, 'red', tab_name=self.tab_name) with open(f"{current_path}/../../assets/templates/heartbeat", "w", encoding='utf-8') as f_hb: @@ -76,45 +71,41 @@ class HmiRequest(object): if index + 8 < len(data): _frame_size = int.from_bytes(data[index:index+2], byteorder='big') _pkg_size = int.from_bytes(data[index+2:index+6], byteorder='big') - _protocol = int.from_bytes(data[index+6:index+7], byteorder='big') - _reserved = int.from_bytes(data[index+7:index+8], byteorder='big') + _protocol = int.from_bytes(data[index + 6:index + 7], byteorder='big') + _reserved = int.from_bytes(data[index + 7:index + 8], byteorder='big') if _reserved == 0 and _protocol == 2: - return index+8, _frame_size, _pkg_size + return index + 8, _frame_size, _pkg_size else: print(data) + print(f"index = {index}") + print(f"reserve = {_reserved}") + print(f"protocol = {_protocol}") print("head check 数据有误,需要确认") - self.w2t("", 0, 1, 'red', 'Automatic Test') + self.w2t("Header Check: 解包数据有误,需要确认!", 0, 1, 'red', tab_name=self.tab_name) else: - self.half_length = len(data)-index - if self.half_length == 1: - self.half = a2b_hex(str(hex(data[-1]))[2:].rjust(1, '0')) - else: - self.half = data[index:] + self.half_length = len(data) - index + self.half = data[index:] - print(f"in head check half data: {self.half}") + print(f"in head check half: {self.half}") print(f"in head check length: {self.half_length}") print(f"in head check data: {data}") self.broke = 100 index += MAX_FRAME_SIZE return index, 0, 0 - # except Exception as Err: - # print(data) - # print(f"Err = {Err}") - # print("无法读取数据,需要确认") def heartbeat(self): while self.t_bool: _id = self.execution('controller.heart') _flag = '0' if self.get_from_id(_id) is None else '1' print(f"hb = {_flag}", end=' ') + print(f"len(c_msg) = {len(self.c_msg)}", end=' ') with open(f"{current_path}/../../assets/templates/heartbeat", "w", encoding='utf-8') as f_hb: f_hb.write(_flag) if _flag == '0': self.w2t(f"心跳丢失,连接失败,重新连接中...", 0, 0, 'red', tab_name=self.tab_name) sleep(2) - print(len(self.c_msg), end=' ') # with open(f"{current_path}/../../assets/templates/c_msg.log", "w", encoding='utf-8') as f: # for msg in self.c_msg: # f.write(msg + '\n') @@ -132,60 +123,96 @@ class HmiRequest(object): # 流式获取单次请求的响应 if self.broke == 100: print("*****************************************") - print(f"half data: {self.half}") + print(f"in get_response if broke == 100 half = {self.half}") _half_1 = self.half - if self.half_length == 7: - _half_2 = a2b_hex(str(hex(data[0]))[2:].rjust(1, '0')) - else: - _half_2 = data[:8-self.half_length] + _half_2 = data[:8-self.half_length] _full = _half_1 + _half_2 - print(f"full data: {_full}") - _frame_size = _full[:2] + print(f"in get_response if broke == 100 _full = {_full}") + _frame_size = int.from_bytes(_full[:2], byteorder='big') _pkg_size = int.from_bytes(_full[2:6], byteorder='big') _protocol = int.from_bytes(_full[6:7], byteorder='big') _reserved = int.from_bytes(_full[7:8], byteorder='big') if _reserved != 0 or _protocol != 2: print(data) - print("数据有误,需要确认") - self.w2t("", 0, 1, 'red', 'Automatic Test') - self.pkg_size = _pkg_size - _index = 8 - self.half_length - else: - _index = 0 + self.w2t("in get_response: 解包数据有误,需要确认!", 0, 1, 'red', tab_name=self.tab_name) - while _index < len(data): + self.pkg_size = _pkg_size + self.index = 8 - self.half_length + print(f"broke == 100 index = {self.index}") + print(f"broke == 100 INIT pkg size = {self.pkg_size}") + print(f"broke == 100 data = {data}") + else: + if self.reset_index == 1: + self.index = 0 + + while self.index < len(data): # flag 为 0,则说明是一次新的请求对应的一次新的相应,也就是需要首次解包 if self.flag == 0: if self.broke == 100: self.broke = 0 else: - _index, _frame_size, self.pkg_size = self.header_check(_index, data) - if _index > MAX_FRAME_SIZE: + self.index, _frame_size, self.pkg_size = self.header_check(self.index, data) + print(f"broke == 0 index = {self.index-8}") + print(f"broke == 0 INIT pkg size = {self.pkg_size}") + print(f"broke == 0 data = {data}") + if self.index > MAX_FRAME_SIZE: break # 详见解包原理数据.txt,self.pkg_size 永远是除了当前data之外剩余未处理的数据大小 - print(f"INIT pkg size = {self.pkg_size}") - if self.pkg_size <= len(data) - _index: + if self.pkg_size <= len(data) - self.index: # 说明剩余部分的数据就在当前data内,没有被分割 - self.response = data[_index:_index+self.pkg_size].decode() + self.response = data[self.index:self.index + self.pkg_size].decode() self.msg_storage(flag=0, response=self.response) - _index += self.pkg_size + self.index += self.pkg_size print(f"in flag=0 if data = {data}") - print(f"in flag=0 if index = {_index}") + print(f"in flag=0 if index = {self.index}") print(f"in flag=0 if pkg size = {self.pkg_size}") print(f"in flag=0 if leftover = {self.leftover}") self.flag = 0 self.response = '' self.leftover = 0 - elif self.pkg_size > len(data) - _index: + self.pkg_size = 0 + self.reset_index = 0 if self.index < len(data) else 1 + elif self.pkg_size > len(data) - self.index: # 执行到这里说明该data是首包,且有有分包的情况发生了也就是该响应数据量稍微比较大 # 分散在了相邻的两个及以上的data中,需要flag=1的处理 self.flag = 1 - self.response = data[_index:].decode() - self.leftover = _frame_size - 6 - (len(data) - _index) # 这里的 _index 不一定是 0 - self.pkg_size -= (len(data) - _index) # 详见解包原理数据.txt,self.pkg_size + if self.index+_frame_size-6 < len(data): + self.response = data[self.index:self.index+_frame_size-6].decode() + self.index += (_frame_size-6) + self.pkg_size -= (_frame_size-6) # 详见解包原理数据.txt,self.pkg_size + self.reset_index = 0 + + if self.index + 2 < len(data): + self.leftover = int.from_bytes(data[self.index:self.index + 2], byteorder='big') + self.index += 2 + self.reset_index = 0 + else: + if self.index + 2 == len(data): + self.broke = 1 + self.half = data[-2:] + print(f"flag = 0 encounter broke == 1 - half = {self.half}") + elif self.index + 1 == len(data): + self.broke = 2 + self.half = data[-1:] + print(f"flag = 0 encounter broke == 2 - half = {self.half}") + elif self.index == len(data): + print('flag = 0 encounter broke == 3') + self.broke = 3 + + self.index += MAX_FRAME_SIZE + self.reset_index = 1 + break # 因为 index + 2 的大小超过 MAX_FRAME_SIZE + + elif self.index+_frame_size-6 > len(data): + self.response = data[self.index:].decode() + self.pkg_size -= (len(data) - self.index) # 详见解包原理数据.txt,self.pkg_size + self.leftover = (_frame_size-6-(len(data)-self.index)) + self.index += MAX_FRAME_SIZE + self.reset_index = 1 + print(f"in flag=0 else data = {data}") - print(f"in flag=0 else index = {_index}") + print(f"in flag=0 else index = {self.index}") print(f"in flag=0 else pkg size = {self.pkg_size}") print(f"in flag=0 else leftover = {self.leftover}") break @@ -193,127 +220,99 @@ class HmiRequest(object): # 继续处理之前为接收完的数据,处理完之后将flag重置为0 # !!!需要注意的是,包头/帧头也是有可能被分割开的!!!但是目前该程序未实现此种情况!!! if self.broke == 1: - self.leftover = int.from_bytes(int(self.half).to_bytes(1, byteorder='big') + data[0:1], byteorder='big') - _index = 1 - self.broke = 0 + self.index = 0 + self.leftover = int.from_bytes(self.half, byteorder='big') print(f"broke 1 leftover: {self.leftover}") - if self.broke == 2: - self.leftover = int.from_bytes(data[:2], byteorder='big') + elif self.broke == 2: + self.leftover = int.from_bytes(self.half+data[:1], byteorder='big') + self.index = 1 + self.broke = 0 print(f"broke 2 leftover: {self.leftover}") - _index = 2 + if self.broke == 3: + self.leftover = int.from_bytes(data[:2], byteorder='big') + print(f"broke 3 leftover: {self.leftover}") + self.index = 2 self.broke = 0 while self.pkg_size > 0: - print(f"flag = 1 INIT _index = {_index}") - if _index + self.leftover <= len(data): - self.response += data[_index:_index + self.leftover].decode() + if self.index + self.leftover <= len(data): + print(f"in pkg size > 0 loop before if data = {data}") + print(f"in pkg size > 0 loop before if index = {self.index}") + print(f"in pkg size > 0 loop before if pkg size = {self.pkg_size}") + print(f"in pkg size > 0 loop before if leftover = {self.leftover}") + if self.leftover < 0 or self.leftover > 1024: + self.w2t("", 0, 111, 'red') + self.response += data[self.index:self.index + self.leftover].decode() self.pkg_size -= self.leftover if self.pkg_size == 0: self.msg_storage(flag=0, response=self.response) - _index += self.leftover - print(f"break _index = {_index}") - print(data) + self.index += self.leftover self.flag = 0 self.response = '' self.leftover = 0 self.pkg_size = 0 + self.reset_index = 0 if self.index < len(data) else 1 + print(f"in pkg size > 0 loop break if data = {data}") + print(f"in pkg size > 0 loop break if index = {self.index}") + print(f"in pkg size > 0 loop break if pkg size = {self.pkg_size}") + print(f"in pkg size > 0 loop break if leftover = {self.leftover}") break - _index += self.leftover - if _index+2 <= len(data): - self.leftover = int.from_bytes(data[_index:_index+2], byteorder='big') - _index += 2 + self.index += self.leftover + if self.index + 2 < len(data): + self.leftover = int.from_bytes(data[self.index:self.index + 2], byteorder='big') + self.index += 2 + self.reset_index = 0 else: - self.leftover = 4096 - if _index == len(data) -1: + # self.leftover = 4096 + if self.index + 2 == len(data): self.broke = 1 - self.half = data[-1] - print(f"half = {self.half}") - print('+++++++++++++++++++++') - _index += MAX_FRAME_SIZE - elif _index == len(data): - _index += MAX_FRAME_SIZE + self.half = data[-2:] + print(f"flag = 1 encounter broke == 1 - half = {self.half}") + elif self.index + 1 == len(data): self.broke = 2 - print(f"in if data = {data}") - print(f"in if index = {_index}") - print(f"in if pkg size = {self.pkg_size}") - print(f"in if leftover = {self.leftover}") - if self.leftover > 1024: - print('============================') - else: - self.response += data[_index:].decode() - self.leftover -= (len(data) - _index) - self.pkg_size -= (len(data) - _index) - # if self.pkg_size == 0: - # self.msg_storage(flag=0, response=self.response) - # _index += MAX_FRAME_SIZE - # self.flag = 0 - # self.response = '' - # self.leftover = 0 - # break + self.half = data[-1:] + print(f"flag = 1 encounter broke == 2 - half = {self.half}") + elif self.index == len(data): + print('flag = 1 encounter broke == 3') + self.broke = 3 - _index += MAX_FRAME_SIZE - print(f"in else data = {data}") - print(f"in else index = {_index}") - print(f"in else pkg size = {self.pkg_size}") - print(f"in else leftover = {self.leftover}") - if self.leftover > 1024: - print('============================') - break + self.index += MAX_FRAME_SIZE + self.reset_index = 1 + break # 因为 index + 2 的大小超过 MAX_FRAME_SIZE + print(f"in pkg size > 0 loop after if data = {data}") + print(f"in pkg size > 0 loop after if index = {self.index}") + print(f"in pkg size > 0 loop after if pkg size = {self.pkg_size}") + print(f"in pkg size > 0 loop after if leftover = {self.leftover}") + if self.leftover < 0 or self.leftover > 1024: + self.w2t("", 0, 111, 'red') + else: + print(f"in pkg size > 0 loop before else data = {data}") + print(f"in pkg size > 0 loop before else index = {self.index}") + print(f"in pkg size > 0 loop before else pkg size = {self.pkg_size}") + print(f"in pkg size > 0 loop before else leftover = {self.leftover}") + if self.leftover < 0 or self.leftover > 1024: + self.w2t("", 0, 111, 'red') + self.response += data[self.index:].decode() + self.leftover -= (len(data) - self.index) + self.pkg_size -= (len(data) - self.index) + self.index += MAX_FRAME_SIZE + self.reset_index = 1 + print(f"in pkg size > 0 loop after else data = {data}") + print(f"in pkg size > 0 loop after else index = {self.index}") + print(f"in pkg size > 0 loop after else pkg size = {self.pkg_size}") + print(f"in pkg size > 0 loop after else leftover = {self.leftover}") + if self.leftover < 0 or self.leftover > 1024: + self.w2t("", 0, 111, 'red') + break # 该data内数据已经处理完毕,需要跳出大循环,通过break和index else: self.msg_storage(flag=0, response=self.response) self.flag = 0 self.response = '' self.leftover = 0 - _index -= 2 - # _index = 0 - # while _index < len(data): - # if self.flag == 0: - # _index, _frame_size, _pkg_size = self.header_check(_index, data) - # if _pkg_size <= len(data) - _index: - # # 说明剩余部分的数据正好就是完整的包数据 - # self.response = data[_index:_index+_pkg_size].decode() - # self.msg_storage(flag=0, response=self.response) - # _index += _pkg_size - # self.flag = 0 - # self.response = '' - # self.leftover = 0 - # elif _pkg_size > len(data) - _index: - # # 说有有分包的情况发生了,需要flag=1的处理 - # self.flag = 1 - # self.response = data[_index:].decode() - # self.leftover = _frame_size - 6 - (len(data) - _index) # 其实就是常量 2,其中 6 就是六个字节的包头 - # break - # - # elif self.flag == 1: - # # 处理完之后,将flag重置为0 - # _index = self.leftover - # self.response += data[:_index].decode() - # _index += 2 - # - # _frame_size = int.from_bytes(data[_index - 2:_index], byteorder='big') - # if _frame_size == 0: - # self.msg_storage(flag=0, response=self.response) - # self.flag = 0 - # self.response = '' - # self.leftover = 0 - # break - # - # if _frame_size == MAX_FRAME_SIZE: - # self.leftover = MAX_FRAME_SIZE - (len(data) - _index) - # self.response += data[_index:].decode() - # break - # else: - # if _index+_frame_size <= MAX_FRAME_SIZE: - # self.response += data[_index:_index+_frame_size].decode() - # self.msg_storage(flag=0, response=self.response) - # self.flag = 0 - # self.response = '' - # self.leftover = 0 - # break - # else: - # self.response += data[_index:].decode() - # self.leftover = _index + _frame_size - MAX_FRAME_SIZE - # break + self.pkg_size = 0 + self.index -= 2 + # self.reset_index = 1 + self.reset_index = 0 if (len(data) > self.index > 0) else 1 def get_response_xs(self, data): if self.flag_xs == 0: @@ -362,7 +361,7 @@ class HmiRequest(object): return None def package(self, cmd): - _frame_head = (len(cmd)+6).to_bytes(length=2, byteorder='big') + _frame_head = (len(cmd) + 6).to_bytes(length=2, byteorder='big') _pkg_head = len(cmd).to_bytes(length=4, byteorder='big') _protocol = int(2).to_bytes(length=1, byteorder='big') _reserved = int(0).to_bytes(length=1, byteorder='big') @@ -375,7 +374,7 @@ class HmiRequest(object): def to_read(conn): data = conn.recv(MAX_FRAME_SIZE) if data: - print(data) + # print(data) self.get_response(data) else: print('closing', sock) @@ -386,7 +385,11 @@ class HmiRequest(object): sel.register(sock, selectors.EVENT_READ, to_read) while self.t_bool: - events = sel.select() + try: + events = sel.select() + except: + sleep(1) + continue for key, mask in events: callback = key.data callback(key.fileobj) @@ -420,11 +423,11 @@ class HmiRequest(object): if flg == 0: # for old protocols req = None try: - with open(f'{current_path}/../../assets/templates/{command}.json', encoding='utf-8', mode='r') as f_json: + with open(f'{current_path}/../../assets/templates/{command}.json', encoding='utf-8', + mode='r') as f_json: req = load(f_json) except: - print(f"暂不支持 {command} 功能,或确认该功能存在...") - return 'NOT SUPPORT' + self.w2t(f"暂不支持 {command} 功能,或确认该功能存在...", 0, 1, 'red', tab_name=self.tab_name) match command: case 'state.set_tp_mode': @@ -449,7 +452,7 @@ class HmiRequest(object): cmd = dumps(req, separators=(',', ':')) try: self.c.send(self.package(cmd)) - sleep(1) + sleep(0.5) except Exception as Err: self.w2t(f"{cmd}\n请求发送失败...{Err}", 0, 0, 'red', tab_name=self.tab_name)