SerialPort and ZigBee: Use QThread and bump to 1.0.2.

This commit is contained in:
Mentalflow 2024-03-03 18:43:26 +08:00
parent 75bee1a451
commit 7bda54063c
Signed by: Mentalflow
GPG Key ID: 5AE68D4401A2EE71
21 changed files with 814 additions and 629 deletions

2
3rdparty/RibbonUI vendored

@ -1 +1 @@
Subproject commit aa3604579b8864efe9e777c7dec96209d7b8ee72 Subproject commit 43240eab1f351a90afdc843119743b0aca4d311c

View File

@ -1,6 +1,6 @@
cmake_minimum_required(VERSION 3.20) cmake_minimum_required(VERSION 3.20)
project(ProtocolParser_APP VERSION 0.1 LANGUAGES CXX) project(ProtocolParser_APP VERSION 1.0.2 LANGUAGES CXX)
add_definitions(-DFRAMELESSHELPER_CORE_NO_DEBUG_OUTPUT) add_definitions(-DFRAMELESSHELPER_CORE_NO_DEBUG_OUTPUT)
add_definitions(-DFRAMELESSHELPER_QUICK_NO_DEBUG_OUTPUT) add_definitions(-DFRAMELESSHELPER_QUICK_NO_DEBUG_OUTPUT)

View File

@ -1,6 +1,6 @@
cmake_minimum_required(VERSION 3.21) cmake_minimum_required(VERSION 3.21)
project(ProtocolParser VERSION 1.0.1 LANGUAGES CXX) project(ProtocolParser VERSION ${CMAKE_PROJECT_VERSION} LANGUAGES CXX)
set(CMAKE_AUTOMOC ON) set(CMAKE_AUTOMOC ON)
set(CMAKE_CXX_STANDARD_REQUIRED ON) set(CMAKE_CXX_STANDARD_REQUIRED ON)
@ -13,8 +13,8 @@ set(PROJECT_COMPANY "Mentalflow's Lab")
set(PROJECT_COPYRIGHT "Copyright (c) 2023 Mentalflow's Lab. All rights reserved.") set(PROJECT_COPYRIGHT "Copyright (c) 2023 Mentalflow's Lab. All rights reserved.")
set(PROJECT_DOMAIN "dev.ourdocs.cn.protocolparser") set(PROJECT_DOMAIN "dev.ourdocs.cn.protocolparser")
set(PROJECT_BUNDLE_NAME ${PROJECT_NAME}) set(PROJECT_BUNDLE_NAME ${PROJECT_NAME})
set(version_str "${CMAKE_PROJECT_VERSION_MAJOR},${CMAKE_PROJECT_VERSION_MINOR},${CMAKE_PROJECT_VERSION_PATCH}")
add_definitions(-DPROTOCOLPARSER_VERSION=1,0,1) add_definitions(-DPROTOCOLPARSER_VERSION=${version_str})
find_package(Qt6 COMPONENTS Quick SerialPort LinguistTools REQUIRED) find_package(Qt6 COMPONENTS Quick SerialPort LinguistTools REQUIRED)
@ -24,8 +24,18 @@ set(
include/zigbeeparser.h source/zigbeeparser.cpp source/crypto.cpp include/crypto.h include/zigbeeparser.h source/zigbeeparser.cpp source/crypto.cpp include/crypto.h
include/protocol.h source/protocol.cpp include/protocol_data.h include/protocol.h source/protocol.cpp include/protocol_data.h
include/config.h source/config.cpp include/config.h source/config.cpp
include/serialdataresolver.h source/serialdataresolver.cpp
include/zigbeedataresolver.h source/zigbeedataresolver.cpp
languages/zh_CN.ts languages/en_US.ts languages/zh_CN.ts languages/en_US.ts
# dlln3x_handler.h dlln3x_handler.cpp )
set(
qml_files qml/Main.qml qml/components/RibbonWindow.qml qml/components/ZigBeeFrame.qml
qml/components/RibbonMessageListView.qml qml/components/RibbonMessage.qml
qml/components/ZigBeeMessage.qml qml/components/SerialPortAssistant.qml
qml/components/ZigBeeDataView.qml qml/components/TabBar.qml qml/components/CenterView.qml
qml/components/ListTable.qml qml/components/DeviceList.qml qml/components/KeysList.qml
qml/components/EventsHistoryList.qml
) )
INCLUDE_DIRECTORIES(dlln3x include) INCLUDE_DIRECTORIES(dlln3x include)
@ -43,19 +53,19 @@ if (WIN32)
${sources_files} ${sources_files}
resources/icon.rc resources/icon.rc
) )
file(TO_CMAKE_PATH "/" PATH_SEPARATOR) file(TO_CMAKE_PATH "/" PATH_SEPARATOR)
if(CMAKE_CXX_COMPILER_ID STREQUAL "MSVC") if(CMAKE_CXX_COMPILER_ID STREQUAL "MSVC")
set(DLLPATH ../3rdparty/msvc/*.dll) set(DLLPATH ../3rdparty/msvc/*.dll)
else() else()
set(DLLPATH ../3rdparty/mingw/*.dll) set(DLLPATH ../3rdparty/mingw/*.dll)
endif() endif()
string(REPLACE "/" ${PATH_SEPARATOR} DLLPATH "${DLLPATH}") string(REPLACE "/" ${PATH_SEPARATOR} DLLPATH "${DLLPATH}")
file(GLOB DLL_FILES ${DLLPATH}) file(GLOB DLL_FILES ${DLLPATH})
add_custom_command(TARGET ${PROJECT_NAME} POST_BUILD add_custom_command(TARGET ${PROJECT_NAME} POST_BUILD
COMMAND ${CMAKE_COMMAND} -E copy COMMAND ${CMAKE_COMMAND} -E copy
${DLL_FILES} ${DLL_FILES}
${CMAKE_RUNTIME_OUTPUT_DIRECTORY} ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}
) )
elseif(APPLE) elseif(APPLE)
set(MACOSX_BUNDLE_ICON_FILE AppIcon) set(MACOSX_BUNDLE_ICON_FILE AppIcon)
set(App_ICON "resources/imgs/AppIcon.icns") set(App_ICON "resources/imgs/AppIcon.icns")
@ -71,15 +81,16 @@ else ()
) )
endif () endif ()
foreach(qmlfile ${qml_files})
string(REPLACE "qml/" "" fixedfile ${qmlfile})
set_source_files_properties(${qmlfile} PROPERTIES QT_RESOURCE_ALIAS ${fixedfile})
endforeach(qmlfile)
qt_add_qml_module(${PROJECT_NAME} qt_add_qml_module(${PROJECT_NAME}
URI ${PROJECT_NAME} URI ${PROJECT_NAME}
VERSION 1.0 QML_FILES ${qml_files}
QML_FILES qml/Main.qml qml/components/RibbonWindow.qml qml/components/ZigBeeFrame.qml RESOURCE_PREFIX "/qt/qml/"
qml/components/RibbonMessageListView.qml qml/components/RibbonMessage.qml VERSION ${CMAKE_PROJECT_VERSION_MAJOR}.${CMAKE_PROJECT_VERSION_MINOR}
qml/components/ZigBeeMessage.qml qml/components/SerialPortAssistant.qml
qml/components/ZigBeeDataView.qml qml/components/TabBar.qml qml/components/CenterView.qml
qml/components/ListTable.qml qml/components/DeviceList.qml qml/components/KeysList.qml
qml/components/EventsHistoryList.qml
) )
set_target_properties(${PROJECT_NAME} PROPERTIES set_target_properties(${PROJECT_NAME} PROPERTIES
@ -94,9 +105,9 @@ set_target_properties(${PROJECT_NAME} PROPERTIES
) )
qt_add_translations(${PROJECT_NAME} qt_add_translations(${PROJECT_NAME}
TS_FILES languages/zh_CN.ts languages/en_US.ts TS_FILES languages/zh_CN.ts languages/en_US.ts
RESOURCE_PREFIX "/translations" RESOURCE_PREFIX "/translations"
) )
if(RIBBONUI_BUILD_STATIC_LIB) if(RIBBONUI_BUILD_STATIC_LIB)
add_definitions(-DRIBBONUI_BUILD_STATIC_LIB) add_definitions(-DRIBBONUI_BUILD_STATIC_LIB)

View File

@ -7,7 +7,6 @@ using namespace zigbee_protocol;
DLLN3X::DLLN3X(QObject *parent) DLLN3X::DLLN3X(QObject *parent)
: QObject{parent} : QObject{parent}
{ {
} }
DLLN3X* DLLN3X::instance(){ DLLN3X* DLLN3X::instance(){
@ -60,6 +59,8 @@ ZigbeeFrame DLLN3X::recv(bool non_blocked)
bool DLLN3X::send(ZigbeeFrame zf) bool DLLN3X::send(ZigbeeFrame zf)
{ {
if(!_DSerial->isOpen())
return false;
bool status = false; bool status = false;
uint8_t len = zf.size(); uint8_t len = zf.size();
if (zf.getSrcPort() < 0x80 || len > 66) if (zf.getSrcPort() < 0x80 || len > 66)
@ -281,7 +282,7 @@ enum DLLN3X::PIN_CONTROL DLLN3X::pin_control(PIN pin, PIN_CONTROL cmd)
void DLLN3X::loop() void DLLN3X::loop()
{ {
if (_DSerial->bytesAvailable() > 7 && !_recv_lock) { if (_DSerial && _DSerial->bytesAvailable() > 7 && !_recv_lock) {
ZigbeeFrame zf = recv(); ZigbeeFrame zf = recv();
printf("Message: "); printf("Message: ");
for (int i = 0; i < zf.size(); i++) { for (int i = 0; i < zf.size(); i++) {
@ -303,7 +304,8 @@ int DLLN3X::readBytesUntil(uint8_t delimiter, uint8_t* buffer, qint64 maxSize)
{ {
QByteArray data; QByteArray data;
qint64 bytesRead = 0; qint64 bytesRead = 0;
if(!_DSerial->isOpen())
return bytesRead;
if (_DSerial->bytesAvailable() || _DSerial->waitForReadyRead(2000)) if (_DSerial->bytesAvailable() || _DSerial->waitForReadyRead(2000))
while (bytesRead < maxSize) while (bytesRead < maxSize)
{ {

View File

@ -17,6 +17,8 @@ private:
const QSerialPort::BaudRate _baud_rate_list[7] = {QSerialPort::Baud2400, QSerialPort::Baud4800, QSerialPort::Baud9600, const QSerialPort::BaudRate _baud_rate_list[7] = {QSerialPort::Baud2400, QSerialPort::Baud4800, QSerialPort::Baud9600,
QSerialPort::Baud19200, QSerialPort::Baud38400, QSerialPort::Baud57600, QSerialPort::Baud115200}; QSerialPort::Baud19200, QSerialPort::Baud38400, QSerialPort::Baud57600, QSerialPort::Baud115200};
QSerialPort* _DSerial; QSerialPort* _DSerial;
explicit DLLN3X(QObject *parent = nullptr);
Q_DISABLE_COPY_MOVE(DLLN3X)
void (*_callback)(ZigbeeFrame& zf) = nullptr; void (*_callback)(ZigbeeFrame& zf) = nullptr;
int readBytesUntil(uint8_t delimiter, uint8_t* buf, qint64 maxSize); int readBytesUntil(uint8_t delimiter, uint8_t* buf, qint64 maxSize);
void _sleep(int msec); void _sleep(int msec);
@ -33,7 +35,6 @@ public:
}; };
enum PIN_CONTROL{ OUT_HIGH = 0x11, OUT_LOW = 0x10, READ_PIN = 0x12}; enum PIN_CONTROL{ OUT_HIGH = 0x11, OUT_LOW = 0x10, READ_PIN = 0x12};
enum PIN{ DLLN3X_PIN4 = 0x44, DLLN3X_PIN5 = 0x45}; enum PIN{ DLLN3X_PIN4 = 0x44, DLLN3X_PIN5 = 0x45};
explicit DLLN3X(QObject *parent = nullptr);
static DLLN3X* instance(); static DLLN3X* instance();
void init(QSerialPort* DSerial, uint32_t baudrate = 115200); void init(QSerialPort* DSerial, uint32_t baudrate = 115200);
ZigbeeFrame recv(bool non_blocked = true); ZigbeeFrame recv(bool non_blocked = true);

View File

@ -21,6 +21,7 @@ public:
private: private:
Config(QString qstrfilename = ""); Config(QString qstrfilename = "");
~Config(void); ~Config(void);
Q_DISABLE_COPY_MOVE(Config)
QString m_qstrFileName; QString m_qstrFileName;
QSettings *m_psetting=nullptr; QSettings *m_psetting=nullptr;
}; };

View File

@ -1,31 +0,0 @@
#ifndef DLLN3X_HANDLER_H
#define DLLN3X_HANDLER_H
#include <QObject>
#include <QQmlEngine>
#include <QSerialPort>
#include "DLLN3X.h"
#include "3rdparty/RibbonUI/lib_source/definitions.h"
class DLLN3X_Handler : public QObject
{
Q_OBJECT
QML_ELEMENT
QML_SINGLETON
QML_NAMED_ELEMENT(DLLN3XHandler)
Q_PROPERTY_RW(bool, handle_serial);
Q_PROPERTY_RW(QSerialPort*, serial);
public:
explicit DLLN3X_Handler(QObject *parent = nullptr);
Q_INVOKABLE bool send(QString data);
signals:
void zigbee_recved(QByteArray data, QByteArray sender);
private:
zigbee_protocol::DLLN3X* _zigbee=nullptr;
void zigbee_callback(zigbee_protocol::ZigbeeFrame zframe);
void close();
};
#endif // DLLN3X_HANDLER_H

View File

@ -33,6 +33,7 @@ public:
Q_INVOKABLE void unreg_event(Event* event); Q_INVOKABLE void unreg_event(Event* event);
private: private:
explicit EventsBus(QObject *parent = nullptr); explicit EventsBus(QObject *parent = nullptr);
Q_DISABLE_COPY_MOVE(EventsBus);
QList<Event*> _events; QList<Event*> _events;
}; };

View File

@ -35,6 +35,7 @@ public:
private: private:
Protocol(); Protocol();
~Protocol(); ~Protocol();
Q_DISABLE_COPY_MOVE(Protocol)
Config* _config = nullptr; Config* _config = nullptr;
}; };
} }

View File

@ -0,0 +1,53 @@
#ifndef SERIALDATARESOLVER_H
#define SERIALDATARESOLVER_H
#include <QObject>
#include <QMutex>
#include <QSerialPort>
#include "DLLN3X.h"
class SerialDataResolver : public QObject
{
Q_OBJECT
public:
enum class SendType{
Blank=0,
WithCarriageEnter=1,
WithLineFeed=2,
WithCarriageEnterAndLineFeed=3
};
Q_ENUM(SendType)
void open(QString port_name, QString baudrate, QString databits,
QString parity, QString stopbits);
void close();
bool handled_by_manager();
void handled_by_manager(bool handled_by_manager);
bool recv_hex();
void recv_hex(bool recv_hex);
bool serial_opened();
static SerialDataResolver* instance();
public slots:
void write_data(QString data, SendType type, bool send_hex);
private:
explicit SerialDataResolver(QObject *parent = nullptr);
~SerialDataResolver();
Q_DISABLE_COPY_MOVE(SerialDataResolver)
void readHandler();
void zigbee_callback(zigbee_protocol::ZigbeeFrame zframe);
void serial_opened(bool serial_opened);
zigbee_protocol::DLLN3X* _zigbee=nullptr;
QSerialPort* _serial=nullptr;
bool _quit = false, _handled_by_manager = false, _recv_hex = false,
_serial_opened = false,_serial_want_open = false;
signals:
void error(const QString &s);
void recved(const QByteArray &data);
void recved_zframe(zigbee_protocol::ZigbeeFrame zframe);
void handled_by_managerChanged();
void recv_hexChanged();
void serial_openedChanged();
};
#endif // SERIALDATARESOLVER_H

View File

@ -5,9 +5,9 @@
#include <QQmlEngine> #include <QQmlEngine>
#include <QTimer> #include <QTimer>
#include <QSerialPort> #include <QSerialPort>
#include "DLLN3X.h" #include <QThread>
#include "serialdataresolver.h"
#include "../3rdparty/RibbonUI/lib_source/definitions.h" #include "../3rdparty/RibbonUI/lib_source/definitions.h"
#include "zigbeeparser.h"
#include "eventsbus.h" #include "eventsbus.h"
class SerialPortManager : public QObject class SerialPortManager : public QObject
@ -27,10 +27,8 @@ public:
WithCarriageEnterAndLineFeed=3 WithCarriageEnterAndLineFeed=3
}; };
Q_ENUM(SendType) Q_ENUM(SendType)
Q_PROPERTY_RW(int, available_ports_count) Q_PROPERTY_RW(int, available_ports_count)
Q_PROPERTY_RW(bool, opened) Q_PROPERTY_RW(bool, opened)
Q_PROPERTY_RW(bool, closed)
Q_PROPERTY_RW(bool, readyRead) Q_PROPERTY_RW(bool, readyRead)
Q_PROPERTY_RW(bool, handledBymanager) Q_PROPERTY_RW(bool, handledBymanager)
Q_PROPERTY_RW(bool, recv_hex) Q_PROPERTY_RW(bool, recv_hex)
@ -41,25 +39,30 @@ public:
static SerialPortManager* instance(); static SerialPortManager* instance();
static SerialPortManager* create(QQmlEngine *qmlEngine, QJSEngine *jsEngine){return instance();} static SerialPortManager* create(QQmlEngine *qmlEngine, QJSEngine *jsEngine){return instance();}
QList<QString> available_ports(); QList<QString> available_ports();
Q_INVOKABLE bool open(QString port_name, QString baudrate, QString databits, Q_INVOKABLE void open(QString port_name, QString baudrate, QString databits,
QString parity, QString stopbits); QString parity, QString stopbits);
Q_INVOKABLE void close(); Q_INVOKABLE void close();
Q_INVOKABLE QByteArray read(); Q_INVOKABLE void write(QString data);
Q_INVOKABLE bool write(QString data);
Q_INVOKABLE QSerialPort* get_serial();
signals: signals:
void available_portsChanged(QList<QString> ports); void available_portsChanged(QList<QString> ports);
void recved(QString data);
void serial_open(QString port_name, QString baudrate, QString databits,
QString parity, QString stopbits);
void serial_close();
void serial_write(QString data, SerialDataResolver::SendType type, bool send_hex);
private: private:
explicit SerialPortManager(QObject *parent = nullptr); explicit SerialPortManager(QObject *parent = nullptr);
~SerialPortManager(); ~SerialPortManager();
Q_DISABLE_COPY_MOVE(SerialPortManager)
QTimer _serial_port_scanner; QTimer _serial_port_scanner;
QSerialPort _serial_port;
zigbee_protocol::DLLN3X* _zigbee=nullptr;
void _ready_for_read();
void zigbee_callback(zigbee_protocol::ZigbeeFrame zframe);
Event _event; Event _event;
EventsBus* _bus = nullptr; EventsBus* _bus = nullptr;
SerialDataResolver* _resolver = nullptr;
QThread* _thread = nullptr;
private slots:
void zigbee_callback(zigbee_protocol::ZigbeeFrame zframe);
}; };
#endif // SERIALPORTMANAGER_H #endif // SERIALPORTMANAGER_H

View File

@ -0,0 +1,32 @@
#ifndef ZIGBEEDATARESOLVER_H
#define ZIGBEEDATARESOLVER_H
#include <QObject>
#include <QJsonObject>
#include "zigbeeframe.h"
#include "protocol.h"
class ZigBeeDataResolver : public QObject
{
Q_OBJECT
public:
static ZigBeeDataResolver* instance();
public slots:
void message_parser(QJsonObject message, QString self_addr, QList<uint16_t> allow_list, QList<uint16_t> deny_list, QList<uint16_t> wait_queue);
private:
explicit ZigBeeDataResolver(QObject *parent = nullptr);
~ZigBeeDataResolver();
Q_DISABLE_COPY_MOVE(ZigBeeDataResolver)
void data_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo = false);
void src_port_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo = false);
void des_port_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo = false);
void remote_addr_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo = false);
zigbee_protocol::Protocol* _protocol = nullptr;
QString _self_addr;
QMap<uint16_t, QPair<device,device>> nodes;
QList<uint16_t> _allow_list,_deny_list,_wait_queue;
signals:
void data_send(QString type, QJsonObject data, QList<uint16_t> allow_list, QList<uint16_t> deny_list, QList<uint16_t> wait_queue);
};
#endif // ZIGBEEDATARESOLVER_H

View File

@ -11,6 +11,7 @@
#include "protocol.h" #include "protocol.h"
#include "eventsbus.h" #include "eventsbus.h"
#include "config.h" #include "config.h"
#include "zigbeedataresolver.h"
class ZigBeeParser : public QObject class ZigBeeParser : public QObject
{ {
@ -30,24 +31,25 @@ public:
void setHmac_verify_key(QString key){ _config->Set("Protocol","hmac_verify_key",key); _protocol->hmac_verify_key = key;emit hmac_verify_keyChanged();}; void setHmac_verify_key(QString key){ _config->Set("Protocol","hmac_verify_key",key); _protocol->hmac_verify_key = key;emit hmac_verify_keyChanged();};
QStringList pre_hmac_verify_key(){ return _protocol->pre_hmac_verify_key;}; QStringList pre_hmac_verify_key(){ return _protocol->pre_hmac_verify_key;};
void setPre_hmac_verify_key(QStringList keys){ _config->SetArray("Protocol","pre_hmac_verify_key",keys); _protocol->pre_hmac_verify_key = keys;emit pre_hmac_verify_keyChanged();}; void setPre_hmac_verify_key(QStringList keys){ _config->SetArray("Protocol","pre_hmac_verify_key",keys); _protocol->pre_hmac_verify_key = keys;emit pre_hmac_verify_keyChanged();};
void data_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo = false);
void message_parser(QJsonObject message);
static ZigBeeParser* instance(); static ZigBeeParser* instance();
static ZigBeeParser* create(QQmlEngine *qmlEngine, QJSEngine *jsEngine){return instance();} static ZigBeeParser* create(QQmlEngine *qmlEngine, QJSEngine *jsEngine){return instance();}
void message_parser(QJsonObject message);
signals: signals:
void hmac_verify_keyChanged(); void hmac_verify_keyChanged();
void pre_hmac_verify_keyChanged(); void pre_hmac_verify_keyChanged();
void message_recved(QJsonObject message, QString self_addr, QList<uint16_t> allow_list, QList<uint16_t> deny_list, QList<uint16_t> wait_queue);
private: private:
explicit ZigBeeParser(QObject *parent = nullptr); explicit ZigBeeParser(QObject *parent = nullptr);
~ZigBeeParser(); ~ZigBeeParser();
void src_port_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo = false); Q_DISABLE_COPY_MOVE(ZigBeeParser)
void des_port_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo = false);
void remote_addr_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo = false);
QMap<uint16_t, QPair<device,device>> nodes;
Event _event; Event _event;
EventsBus *_bus = nullptr; EventsBus *_bus = nullptr;
zigbee_protocol::Protocol* _protocol = nullptr; zigbee_protocol::Protocol* _protocol = nullptr;
QString _self_addr = QString::number(DEFAULT_SELF_ADDR,16).toUpper(); QString _self_addr = QString::number(DEFAULT_SELF_ADDR,16).toUpper();
Config* _config = nullptr; Config* _config = nullptr;
ZigBeeDataResolver* _resolver = nullptr;
QThread *_thread = nullptr;
private slots:
void bus_data_send(QString type, QJsonObject data, QList<uint16_t> allow_list, QList<uint16_t> deny_list, QList<uint16_t> wait_queue);
}; };
#endif // ZIGBEEPARSER_H #endif // ZIGBEEPARSER_H

View File

@ -32,16 +32,13 @@ Item{
} }
Connections{ Connections{
target: SerialPortManager target: SerialPortManager
function onReadyReadChanged(){ function onRecved(data)
if (control.handle_serial && SerialPortManager.readyRead) {
{ serial_view.message_model.append({
var d = SerialPortManager.read() time: Qt.formatDateTime(new Date(), "yyyy-MM-dd hh:mm:ss.zzz"),
serial_view.message_model.append({ note_text: data.toString(),
note_text: d.toString(), recieved: true,
recieved: true, })
})
}
} }
} }
} }
@ -188,13 +185,14 @@ Item{
SerialPortManager.send_hex = tab_bar.send_hex SerialPortManager.send_hex = tab_bar.send_hex
SerialPortManager.send_type = serial_send_type_combo.currentText === "无" ? SerialPortManager.Blank SerialPortManager.send_type = serial_send_type_combo.currentText === "无" ? SerialPortManager.Blank
: serial_send_type_combo.currentText === "回车" ? SerialPortManager.WithCarriageEnter : serial_send_type_combo.currentText === "回车" ? SerialPortManager.WithCarriageEnter
: serial_send_type_combo.currentText === "换行" ? SerialPortManager.WithLineFeed : serial_send_type_combo.currentText === "换行" ? SerialPortManager.WithLineFeed
: SerialPortManager.WithCarriageEnterAndLineFeed : SerialPortManager.WithCarriageEnterAndLineFeed
SerialPortManager.write(message_sender_textbox.text) SerialPortManager.write(message_sender_textbox.text)
serial_view.message_model.append({ serial_view.message_model.append({
note_text: message_sender_textbox.text, time: Qt.formatDateTime(new Date(), "yyyy-MM-dd hh:mm:ss.zzz"),
recieved: false, note_text: message_sender_textbox.text,
}) recieved: false,
})
message_sender_textbox.textedit.clear() message_sender_textbox.textedit.clear()
} }

View File

@ -37,7 +37,7 @@ RibbonTabBar {
} }
icon_source: RibbonIcons.SerialPort icon_source: RibbonIcons.SerialPort
currentIndex: 0 currentIndex: 0
enabled: SerialPortManager.closed enabled: !SerialPortManager.opened
Connections{ Connections{
target: SerialPortManager target: SerialPortManager
function onAvailable_portsChanged(ports){ function onAvailable_portsChanged(ports){
@ -70,7 +70,7 @@ RibbonTabBar {
ListElement { text: "57600" } ListElement { text: "57600" }
ListElement { text: "115200" } ListElement { text: "115200" }
} }
enabled: SerialPortManager.closed enabled: !SerialPortManager.opened
currentIndex: 6 currentIndex: 6
icon_source: RibbonIcons.NumberSymbol icon_source: RibbonIcons.NumberSymbol
} }
@ -91,7 +91,7 @@ RibbonTabBar {
ListElement { text: "7" } ListElement { text: "7" }
ListElement { text: "8" } ListElement { text: "8" }
} }
enabled: SerialPortManager.closed enabled: !SerialPortManager.opened
currentIndex: 3 currentIndex: 3
icon_source: RibbonIcons.DataWhisker icon_source: RibbonIcons.DataWhisker
} }
@ -121,7 +121,7 @@ RibbonTabBar {
ListElement { text: qsTr("EVEN") } ListElement { text: qsTr("EVEN") }
ListElement { text: qsTr("ODD") } ListElement { text: qsTr("ODD") }
} }
enabled: SerialPortManager.closed enabled: !SerialPortManager.opened
icon_source: RibbonIcons.DataWhisker icon_source: RibbonIcons.DataWhisker
} }
} }
@ -140,7 +140,7 @@ RibbonTabBar {
ListElement { text: "1.5" } ListElement { text: "1.5" }
ListElement { text: "2" } ListElement { text: "2" }
} }
enabled: SerialPortManager.closed enabled: !SerialPortManager.opened
icon_source: RibbonIcons.DataWhisker icon_source: RibbonIcons.DataWhisker
} }
} }
@ -150,12 +150,13 @@ RibbonTabBar {
Layout.alignment: Qt.AlignVCenter Layout.alignment: Qt.AlignVCenter
icon_source: RibbonIcons.Open icon_source: RibbonIcons.Open
show_tooltip: false show_tooltip: false
text: SerialPortManager.closed ? qsTr("打开串口") : qsTr("关闭串口") text: SerialPortManager.opened ? qsTr("关闭串口") : qsTr("打开串口")
onClicked: SerialPortManager.open(serial_port_combo.currentText, onClicked: !SerialPortManager.opened ? SerialPortManager.open(serial_port_combo.currentText,
serial_baudrate_combo.currentText, serial_baudrate_combo.currentText,
serial_databits_combo.currentText, serial_databits_combo.currentText,
serial_parity_combo.currentText, serial_parity_combo.currentText,
serial_stopbits_combo.currentText) serial_stopbits_combo.currentText) :
SerialPortManager.close()
} }
} }
} }

View File

@ -1,56 +0,0 @@
#include "dlln3x_handler.h"
DLLN3X_Handler::DLLN3X_Handler(QObject *parent)
: QObject{parent}
{
_zigbee = zigbee_protocol::DLLN3X::instance();
handle_serial(false);
serial(nullptr);
connect(this, &DLLN3X_Handler::handle_serialChanged, this, [=](){
if (_handle_serial&&_serial!=nullptr)
{
_zigbee->init(_serial, _serial->baudRate());
connect(_zigbee, &zigbee_protocol::DLLN3X::recved, this, &DLLN3X_Handler::zigbee_callback);
connect(_serial, &QSerialPort::readyRead, _zigbee, &zigbee_protocol::DLLN3X::loop);
connect(_serial, &QSerialPort::aboutToClose, this, &DLLN3X_Handler::close);
}
else
{
close();
}
});
}
void DLLN3X_Handler::zigbee_callback(zigbee_protocol::ZigbeeFrame zframe)
{
QByteArray zf = QByteArray((char *)zframe.data(),zframe.size());
QByteArray hex = zf.toHex(' ');
QByteArray data = hex.toUpper();
QByteArray num = QByteArray::number(zframe.getRemoteAddr(),16);
QByteArray sender = num.toUpper();
emit zigbee_recved(data, sender);
}
void DLLN3X_Handler::close()
{
disconnect(_zigbee, &zigbee_protocol::DLLN3X::recved, this, &DLLN3X_Handler::zigbee_callback);
disconnect(_serial, &QSerialPort::readyRead, _zigbee, &zigbee_protocol::DLLN3X::loop);
disconnect(_serial, &QSerialPort::aboutToClose, this, &DLLN3X_Handler::close);
}
bool DLLN3X_Handler::send(QString data)
{
if (_handle_serial)
{
QByteArray bdata;
QStringList td = data.split(' ');
for (auto item : td)
bdata += QByteArray::fromHex(item.toLatin1());
zigbee_protocol::ZigbeeFrame zf(bdata.data(),bdata.length());
return _zigbee->send(zf);
}
else
return false;
}

View File

@ -35,7 +35,7 @@ int main(int argc, char *argv[])
#ifdef RIBBONUI_BUILD_STATIC_LIB #ifdef RIBBONUI_BUILD_STATIC_LIB
engine.addImportPath("qrc:/"); engine.addImportPath("qrc:/");
#endif #endif
const QUrl url(u"qrc:/ProtocolParser/qml/Main.qml"_qs); const QUrl url(u"qrc:/qt/qml/ProtocolParser/Main.qml"_qs);
QObject::connect(&engine, &QQmlApplicationEngine::objectCreated, QObject::connect(&engine, &QQmlApplicationEngine::objectCreated,
&app, [url](QObject *obj, const QUrl &objUrl) { &app, [url](QObject *obj, const QUrl &objUrl) {
if (!obj && url == objUrl) if (!obj && url == objUrl)

View File

@ -0,0 +1,246 @@
#include "serialdataresolver.h"
#include "protocol.h"
#include <QThread>
SerialDataResolver::SerialDataResolver(QObject *parent)
: QObject{parent}
{
//qDebug()<<__FUNCTION__<<"Thread: "<<QThread::currentThread();
_serial = new QSerialPort(this);
_zigbee = zigbee_protocol::DLLN3X::instance();
recv_hex(false);
handled_by_manager(true);
connect(this, &SerialDataResolver::handled_by_managerChanged, this, [=](){
if (!_handled_by_manager && _serial->isOpen())
{
_zigbee->init(_serial, _serial->baudRate());
zigbee_protocol::Protocol::getInstance()->self_addr = _zigbee->read_addr();
connect(_zigbee, &zigbee_protocol::DLLN3X::recved, this, &SerialDataResolver::zigbee_callback);
}
else
{
disconnect(_zigbee, &zigbee_protocol::DLLN3X::recved, this, &SerialDataResolver::zigbee_callback);
}
});
}
SerialDataResolver::~SerialDataResolver()
{
close();
delete _serial;
}
SerialDataResolver* SerialDataResolver::instance()
{
//qDebug()<<__FUNCTION__<<"Thread: "<<QThread::currentThread();
static QMutex mutex;
QMutexLocker locker(&mutex);
static SerialDataResolver *singleton = nullptr;
if (!singleton) {
singleton = new SerialDataResolver();
}
return singleton;
}
void SerialDataResolver::open(QString port_name, QString baudrate, QString databits,
QString parity, QString stopbits)
{
//qDebug()<<__FUNCTION__<<"Thread: "<<QThread::currentThread();
QMutex mutex;
const QMutexLocker locker(&mutex);
_serial->setPortName(port_name);
if (!_serial->open(QIODevice::ReadWrite))
{
emit error(tr("串口%1打开失败, 错误代码:%2")
.arg(port_name).arg(_serial->error()));
return;
}
else
{
serial_opened(true);
_serial->setBaudRate(baudrate.toInt());
switch (databits.toInt())
{
case 5:
_serial->setDataBits( QSerialPort::Data5 ); // 设置数据位(数据位为5位)
break;
case 6:
_serial->setDataBits( QSerialPort::Data6 ); // 设置数据位(数据位为6位)
break;
case 7:
_serial->setDataBits( QSerialPort::Data7 ); // 设置数据位(数据位为7位)
break;
case 8:
_serial->setDataBits( QSerialPort::Data8 ); // 设置数据位(数据位为8位)
break;
default:
break;
}
if (parity=="NONE")
{
_serial->setParity( QSerialPort::NoParity ); // 设置校验位(无校验位)
}
else if (parity=="EVEN")
{
_serial->setParity( QSerialPort::EvenParity ); // 设置校验位(奇校验位)
}
else
{
_serial->setParity( QSerialPort::OddParity ); // 设置校验位(偶校验位)
}
if (stopbits=="1")
{
_serial->setStopBits( QSerialPort::OneStop ); // 设置停止位(停止位为1)
}
else if (stopbits=="1.5")
{
_serial->setStopBits( QSerialPort::OneAndHalfStop ); // 设置停止位(停止位为1.5)
}
else
{
_serial->setStopBits( QSerialPort::TwoStop ); // 设置停止位(停止位为2)
}
_serial->setFlowControl( QSerialPort::NoFlowControl ); // 设置流控制(无数据流控制)
connect(_serial,&QSerialPort::aboutToClose, this, &SerialDataResolver::close);
connect(_serial,&QSerialPort::readyRead, this, &SerialDataResolver::readHandler);
if (!_handled_by_manager)
{
_zigbee->init(_serial, _serial->baudRate());
zigbee_protocol::Protocol::getInstance()->self_addr = _zigbee->read_addr();
connect(_zigbee, &zigbee_protocol::DLLN3X::recved, this, &SerialDataResolver::zigbee_callback);
}
}
}
bool SerialDataResolver::handled_by_manager()
{
return _handled_by_manager;
}
void SerialDataResolver::handled_by_manager(bool handled_by_manager)
{
QMutex mutex;
const QMutexLocker locker(&mutex);
_handled_by_manager = handled_by_manager;
emit handled_by_managerChanged();
}
bool SerialDataResolver::recv_hex()
{
return _recv_hex;
}
void SerialDataResolver::recv_hex(bool recv_hex)
{
QMutex mutex;
const QMutexLocker locker(&mutex);
_recv_hex = recv_hex;
emit recv_hexChanged();
}
bool SerialDataResolver::serial_opened()
{
return _serial_opened;
}
void SerialDataResolver::serial_opened(bool serial_opened)
{
QMutex mutex;
const QMutexLocker locker(&mutex);
_serial_opened = serial_opened;
emit serial_openedChanged();
}
void SerialDataResolver::readHandler()
{
//qDebug()<<__FUNCTION__<<"Thread: "<<QThread::currentThread();
if (_handled_by_manager)
{
QByteArray bdata;
if (_serial->isOpen() && _handled_by_manager)
{
while(true){
bdata += _serial->readAll();
if (!_serial->waitForReadyRead(20))
break;
}
if (_recv_hex)
{
emit recved(bdata.toHex(' ').toUpper());
}
else
emit recved(bdata);
}
else
emit recved(bdata);
}
else
_zigbee->loop();
}
void SerialDataResolver::close()
{
//qDebug()<<__FUNCTION__<<"Thread: "<<QThread::currentThread();
serial_opened(false);
disconnect(_serial,&QSerialPort::aboutToClose,this,&SerialDataResolver::close);
disconnect(_zigbee, &zigbee_protocol::DLLN3X::recved, this, &SerialDataResolver::zigbee_callback);
if(_serial->isOpen())
{
_serial->clear();
_serial->close();
}
}
void SerialDataResolver::write_data(QString data, SendType type, bool send_hex)
{
//qDebug()<<__FUNCTION__<<"Thread: "<<QThread::currentThread();
QByteArray bdata;
if (!_serial->isOpen())
return;
if (!_handled_by_manager)
{
QStringList td = data.split(' ');
for (auto item : td)
bdata += QByteArray::fromHex(item.toLatin1());
zigbee_protocol::ZigbeeFrame zf;
zf.load_package((uint8_t*)bdata.data(),bdata.length());
_zigbee->send(zf);
return;
}
if(send_hex)
{
QStringList td = data.split(' ');
for (auto item : td)
bdata += QByteArray::fromHex(item.toLatin1());
}
else
bdata = data.toUtf8();
switch(type)
{
case SendType::WithCarriageEnter:
bdata += "\n";
break;
case SendType::WithLineFeed:
bdata += "\r";
break;
case SendType::WithCarriageEnterAndLineFeed:
bdata += "\r\n";
break;
case SendType::Blank:
default:
break;
}
_serial->write(bdata);
_serial->flush();
return;
}
void SerialDataResolver::zigbee_callback(zigbee_protocol::ZigbeeFrame zframe)
{
emit recved_zframe(zframe);
}

View File

@ -1,48 +1,62 @@
#include "serialportmanager.h" #include "serialportmanager.h"
#include <QSerialPortInfo> #include <QSerialPortInfo>
#include <QMutex> #include <QMutex>
#include "zigbeeparser.h"
SerialPortManager::SerialPortManager(QObject *parent) SerialPortManager::SerialPortManager(QObject *parent)
: QObject{parent} : QObject{parent}
{ {
_zigbee = zigbee_protocol::DLLN3X::instance(); _resolver = SerialDataResolver::instance();
_thread = new QThread();
_resolver->moveToThread(_thread);
_bus = EventsBus::instance(); _bus = EventsBus::instance();
ZigBeeParser::instance(); // 让ZigBeeParser在QML引擎中实例化 ZigBeeParser::instance(); // 让ZigBeeParser在QML引擎中实例化
_event.type("serial_port"); _event.type("serial_port");
_bus->reg_event(&_event); _bus->reg_event(&_event);
closed(true);
opened(false); opened(false);
handledBymanager(true); handledBymanager(true);
recv_hex(false); recv_hex(false);
send_hex(false); send_hex(false);
send_type(SendType::Blank); send_type(SendType::Blank);
_serial_port_scanner.setInterval(1000);
_serial_port_scanner.start();
connect(&_serial_port_scanner, &QTimer::timeout, this, [=](){ connect(&_serial_port_scanner, &QTimer::timeout, this, [=](){
available_ports(); available_ports();
}); });
connect(this, &SerialPortManager::handledBymanagerChanged, this, [=](){
if (!_handledBymanager && _serial_port.isOpen())
{
_zigbee->init(&_serial_port, _serial_port.baudRate());
zigbee_protocol::Protocol::getInstance()->self_addr = _zigbee->read_addr();
connect(_zigbee, &zigbee_protocol::DLLN3X::recved, this, &SerialPortManager::zigbee_callback);
}
else
{
disconnect(_zigbee, &zigbee_protocol::DLLN3X::recved, this, &SerialPortManager::zigbee_callback);
}
});
connect(&_event, &Event::triggered, this, [=](QJsonObject data){ connect(&_event, &Event::triggered, this, [=](QJsonObject data){
write(data["text"].toString()); write(data["text"].toString());
}); });
connect(_resolver,&SerialDataResolver::recved, this, [=](const QByteArray &data){
emit recved(data);
});
connect(_resolver,&SerialDataResolver::recved_zframe, this, &SerialPortManager::zigbee_callback);
connect(this, &SerialPortManager::recv_hexChanged, this, [=](){
_resolver->recv_hex(recv_hex());
});
connect(this, &SerialPortManager::handledBymanagerChanged, this, [=](){
_resolver->handled_by_manager(handledBymanager());
});
connect(_resolver,&SerialDataResolver::serial_openedChanged, this, [=](){
opened(_resolver->serial_opened());
});
connect(this, &SerialPortManager::serial_close, _resolver, &SerialDataResolver::close);
connect(this, &SerialPortManager::serial_open, _resolver, &SerialDataResolver::open);
connect(this, &SerialPortManager::serial_write, _resolver, &SerialDataResolver::write_data);
connect(_thread, &QThread::finished, this, [=](){
_thread->deleteLater();
_resolver->deleteLater();
});
_serial_port_scanner.setInterval(1000);
_serial_port_scanner.start();
_thread->start();
} }
SerialPortManager::~SerialPortManager() SerialPortManager::~SerialPortManager()
{ {
close(); close();
_bus->unreg_event(&_event); _bus->unreg_event(&_event);
if(_thread->isRunning())
{
_thread->quit();
}
} }
SerialPortManager* SerialPortManager::instance(){ SerialPortManager* SerialPortManager::instance(){
@ -68,182 +82,29 @@ QList<QString> SerialPortManager::available_ports(){
return newPortStringList; return newPortStringList;
} }
bool SerialPortManager::open(QString port_name, QString baudrate, QString databits, void SerialPortManager::open(QString port_name, QString baudrate, QString databits,
QString parity, QString stopbits) QString parity, QString stopbits)
{ {
_serial_port.setPortName(port_name); emit serial_open(port_name,baudrate,databits,parity,stopbits);
if (_serial_port.isOpen())
{
close();
return false;
}
else
{
if (_serial_port.open(QIODevice::ReadWrite))
{
_serial_port.setBaudRate(baudrate.toInt());
switch (databits.toInt())
{
case 5:
_serial_port.setDataBits( QSerialPort::Data5 ); // 设置数据位(数据位为5位)
break;
case 6:
_serial_port.setDataBits( QSerialPort::Data6 ); // 设置数据位(数据位为6位)
break;
case 7:
_serial_port.setDataBits( QSerialPort::Data7 ); // 设置数据位(数据位为7位)
break;
case 8:
_serial_port.setDataBits( QSerialPort::Data8 ); // 设置数据位(数据位为8位)
break;
default:
return false;
}
if (parity=="NONE")
{
_serial_port.setParity( QSerialPort::NoParity ); // 设置校验位(无校验位)
}
else if (parity=="EVEN")
{
_serial_port.setParity( QSerialPort::EvenParity ); // 设置校验位(奇校验位)
}
else
{
_serial_port.setParity( QSerialPort::OddParity ); // 设置校验位(偶校验位)
}
if (stopbits=="1")
{
_serial_port.setStopBits( QSerialPort::OneStop ); // 设置停止位(停止位为1)
}
else if (stopbits=="1.5")
{
_serial_port.setStopBits( QSerialPort::OneAndHalfStop ); // 设置停止位(停止位为1.5)
}
else
{
_serial_port.setStopBits( QSerialPort::TwoStop ); // 设置停止位(停止位为2)
}
_serial_port.setFlowControl( QSerialPort::NoFlowControl ); // 设置流控制(无数据流控制)
// 当下位机中有数据发送过来时就会响应这个槽函数
connect(&_serial_port,&QSerialPort::readyRead,this,&SerialPortManager::_ready_for_read);
connect(&_serial_port,&QSerialPort::aboutToClose,this,&SerialPortManager::close);
opened(true);
closed(false);
return true;
}
else
return false;
}
} }
void SerialPortManager::close() void SerialPortManager::close()
{ {
disconnect(&_serial_port,&QSerialPort::aboutToClose,this,&SerialPortManager::close); emit serial_close();
disconnect(&_serial_port,&QSerialPort::readyRead,this,&SerialPortManager::_ready_for_read);
disconnect(_zigbee, &zigbee_protocol::DLLN3X::recved, this, &SerialPortManager::zigbee_callback);
if(_opened)
{
_serial_port.clear();
_serial_port.close();
}
readyRead(false);
closed(true);
opened(false);
} }
QByteArray SerialPortManager::read() void SerialPortManager::write(QString data)
{ {
QByteArray bdata; emit serial_write(data,static_cast<SerialDataResolver::SendType>(send_type()),send_hex());
if (_opened && _handledBymanager)
{
readyRead(false);
while(true){
bdata += _serial_port.readAll();
if (!_serial_port.waitForReadyRead(20))
break;
}
if (_recv_hex)
{
return bdata.toHex(' ').toUpper();
}
else
return bdata;
}
else
return bdata;
} }
void SerialPortManager::_ready_for_read() void SerialPortManager::zigbee_callback(zigbee_protocol::ZigbeeFrame zframe)
{
if (_handledBymanager)
readyRead(true);
if (!_handledBymanager)
_zigbee->loop();
}
bool SerialPortManager::write(QString data)
{
if (_closed)
return false;
if ( !_handledBymanager)
{
QByteArray bdata;
QStringList td = data.split(' ');
for (auto item : td)
bdata += QByteArray::fromHex(item.toLatin1());
zigbee_protocol::ZigbeeFrame zf;
zf.load_package((uint8_t*)bdata.data(),bdata.length());
return _zigbee->send(zf);
}
QByteArray bdata;
if(_send_hex)
{
QStringList td = data.split(' ');
for (auto item : td)
bdata += QByteArray::fromHex(item.toLatin1());
}
else
bdata = data.toUtf8();
switch(_send_type)
{
case SendType::WithCarriageEnter:
bdata += "\n";
break;
case SendType::WithLineFeed:
bdata += "\r";
break;
case SendType::WithCarriageEnterAndLineFeed:
bdata += "\r\n";
break;
case SendType::Blank:
default:
break;
}
bool status = _serial_port.write(bdata);
status = _serial_port.flush();
return status;
}
void SerialPortManager::zigbee_callback(zigbee_protocol::ZigbeeFrame zframe)
{ {
QJsonObject object; QJsonObject object;
QByteArray zf = QByteArray((char *)zframe.data(),zframe.size()); QByteArray zf = QByteArray((char *)zframe.data(),zframe.size());
QByteArray hex = zf.toHex(' '); QByteArray hex = zf.toHex(' ');
QByteArray data = hex.toUpper(); QByteArray data = hex.toUpper();
readyRead(false);
object.insert("data_hex", QJsonValue(QString(data))); object.insert("data_hex", QJsonValue(QString(data)));
object.insert("type","zigbee_raw_data"); object.insert("type","zigbee_raw_data");
_bus->push_data("zigbee_parser", object); _bus->push_data("zigbee_parser", object);
} }
QSerialPort* SerialPortManager::get_serial()
{
if (!_handledBymanager)
return &_serial_port;
else
return nullptr;
}

View File

@ -0,0 +1,325 @@
#include "zigbeedataresolver.h"
#include "crypto.h"
#include <QRandomGenerator>
#include <QMutex>
ZigBeeDataResolver::ZigBeeDataResolver(QObject *parent)
: QObject{parent}
{
_protocol = zigbee_protocol::Protocol::getInstance();
}
ZigBeeDataResolver::~ZigBeeDataResolver()
{
}
ZigBeeDataResolver* ZigBeeDataResolver::instance()
{
static QMutex mutex;
QMutexLocker locker(&mutex);
static ZigBeeDataResolver *singleton = nullptr;
if (!singleton) {
singleton = new ZigBeeDataResolver();
}
return singleton;
}
void ZigBeeDataResolver::data_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo)
{
src_port_parser(zframe,is_demo);
des_port_parser(zframe, is_demo);
remote_addr_parser(zframe, is_demo);
}
void ZigBeeDataResolver::src_port_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo)
{
switch (zframe.getSrcPort()) {
case 0x81:
break;
default:
break;
}
}
void ZigBeeDataResolver::des_port_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo)
{
if (zframe.size() <= 7)
{
qDebug()<<"ZigBee: recved package is corrupted, dropped.";
return;
}
void *frame = nullptr;
base_frame *bframe=nullptr;
hmac_frame *hframe=nullptr;
crypto_zdata_frame *czdata = nullptr;
data_frame *ddata = nullptr;
QByteArray zdata((char *)zframe.data(), zframe.size());
QString sender = QString::number(((base_frame *)zframe.getData().data())->ori_addr,16).toUpper();
device temp,self;
QPair<device,device>* node = nullptr;
memset(&temp,0,sizeof(temp));
memset(&temp,0,sizeof(self));
self.addr = _protocol->self_addr;
if (!nodes.contains(((base_frame *)zframe.getData().data())->ori_addr))
{
temp.addr=((base_frame *)zframe.getData().data())->ori_addr;
temp.id = 0;
temp.online = 1;
temp.rand_num = 0;
temp.verified = 0;
nodes.insert(temp.addr,qMakePair(temp,self));
}
node = &nodes[((base_frame *)zframe.getData().data())->ori_addr];
bframe = (base_frame*)zframe.getData().data();
if (is_demo || bframe->des_addr == _protocol->self_addr && (node->first.id == 0||bframe->reset_num==0xDD||((bframe->id > node->first.id && bframe->id<=BASE_FRAME_RESET_NUM))))
{
node->first.addr = bframe->ori_addr;
node->first.id = bframe->id;
node->first.rand_num = bframe->rand_num;
frame = (void*)bframe->data;
}
else
{
QJsonObject object;
object.insert("text",QJsonValue(QString(zdata.toHex(' ').toUpper())));
object.insert("note_text",QJsonValue("请注意节点0x"+QString::number(node->first.addr,16).toUpper()+"发送的该数据包损坏"));
object.insert("recieved", true);
object.insert("sender", sender);
object.insert("type","zigbee_identify_data");
emit data_send("zigbee_identify_data_view",object,_allow_list,_deny_list,_wait_queue);
return;
}
switch (zframe.getDesPort()) {
case 0x81:
{
hframe = (hmac_frame*)frame;
QJsonObject object;
object.insert("text",QJsonValue(QString(zdata.toHex(' ').toUpper())));
object.insert("sender", sender);
object.insert("note_text",QJsonValue("收到节点0x"+ sender +"发送的验证信息"));
object.insert("recieved", true);
object.insert("type","zigbee_identify_data");
emit data_send("zigbee_identify_data_view",object,_allow_list,_deny_list,_wait_queue);
if (_allow_list.contains(node->first.addr))
{
u8 hmac[33]="";
QByteArray key = QByteArray::fromHex(_protocol->hmac_verify_key.toLatin1());
Crypto::getInstance()->SM3_HMAC((u8 *)key.data(),16,&hframe->value,1,hmac);
if (_protocol->bytecmp(hframe->hmac,hmac,32))
{
new_data_frame(15) data;
memset(&data, 0, sizeof(data));
_protocol->protocal_wrapper((data_frame *)&data, 0, 10, (u8 *)"Identified", 0);
node->first.verified = 1;
new_base_frame(15 + DATA_FRAME_PREFIX_LEN + BASE_FRAME_PREFIX_LEN) bframe;
memset(&bframe, 0, sizeof(bframe));
_protocol->base_frame_maker(&data, (base_frame *)&bframe, node->first.addr,&node->second);
zigbee_protocol::ZigbeeFrame zf(zframe.getSrcPort(),zframe.getDesPort(),zframe.getRemoteAddr(),(uint8_t *)&bframe,bframe.length);
QByteArray bdata((char *)&bframe, bframe.length);
QByteArray zdata((char *)zf.data(), zf.size());
QJsonObject object;
object.insert("baseframe_data",QJsonValue(QString(bdata.toHex(' ').toUpper())));
object.insert("text",QJsonValue(QString(zdata.toHex(' ').toUpper())));
object.insert("note_text",QJsonValue("向0x"+QString::number(node->first.addr,16).toUpper()+"节点发送验证通过回复信息"));
object.insert("recieved", false);
object.insert("sender", QString::number(_protocol->self_addr,16).toUpper());
object.insert("type","zigbee_identify_data");
emit data_send("zigbee_identify_data_view",object,_allow_list,_deny_list,_wait_queue);
if(!is_demo)
emit data_send("serial_port",object,_allow_list,_deny_list,_wait_queue);
}
else
{
u8 hmac[33]="";
QJsonObject object;
QByteArray latest_key = QByteArray::fromHex(_protocol->hmac_verify_key.toLatin1());
for (auto key_str : _protocol->pre_hmac_verify_key)
{
QByteArray key = QByteArray::fromHex(key_str.toLatin1());
Crypto::getInstance()->SM3_HMAC((u8 *)key.data(),16,&hframe->value,1,hmac);
if (_protocol->bytecmp(hframe->hmac,hmac,32))
{
zigbee_protocol::ZigbeeFrame zf(0x82,0x82,node->first.addr);
new_crypto_zdata_frame(32) zdata;
memset(&zdata, 0, sizeof(zdata));
_protocol->zigbee_data_encrypt((u8*)latest_key.data(), 16, (crypto_zdata_frame *)&zdata, Crypto::SM4_encrypt, key_str);
new_base_frame(sizeof(zdata) + BASE_FRAME_PREFIX_LEN) bframe;
memset(&bframe, 0, sizeof(bframe));
_protocol->base_frame_maker(&zdata, (base_frame *)&bframe, node->first.addr, &node->second);
zf.setData((u8 *)&bframe, bframe.length);
QByteArray bdata((char *)&bframe, bframe.length);
QByteArray zfdata((char *)zf.data(), zf.size());
object.insert("baseframe_data",QJsonValue(QString(bdata.toHex(' ').toUpper())));
object.insert("text",QJsonValue(QString(zfdata.toHex(' ').toUpper())));
object.insert("note_text",QJsonValue("节点0x"+QString::number(node->first.addr,16).toUpper()+"正在使用旧密钥,发送密钥更新指令"));
object.insert("recieved", false);
object.insert("sender", QString::number(_protocol->self_addr,16).toUpper());
object.insert("type","zigbee_identify_data");
emit data_send("zigbee_identify_data_view",object,_allow_list,_deny_list,_wait_queue);
if(!is_demo)
emit data_send("serial_port",object,_allow_list,_deny_list,_wait_queue);
return;
}
}
object.insert("note_text",QJsonValue("节点0x"+QString::number(node->first.addr,16).toUpper()+"验证不通过,请考虑移出认证列表"));
object.insert("recieved", true);
object.insert("sender", sender);
object.insert("type","zigbee_identify_data");
emit data_send("zigbee_identify_data_view",object,_allow_list,_deny_list,_wait_queue);
}
}
else if(_deny_list.contains(node->first.addr))
{
object.insert("sender", sender);
object.insert("text","");
object.insert("note_text",QJsonValue("节点0x"+QString::number(((base_frame *)zframe.getData().data())->ori_addr,16).toUpper()+"被禁止接入"));
object.insert("recieved", true);
object.insert("type","zigbee_identify_data");
emit data_send("zigbee_identify_data_view",object,_allow_list,_deny_list,_wait_queue);
}
else {
if (!_wait_queue.contains(node->first.addr))
{
_wait_queue.append(node->first.addr);
object.insert("sender", sender);
object.insert("text","");
object.insert("note_text",QJsonValue("节点0x"+QString::number(((base_frame *)zframe.getData().data())->ori_addr,16).toUpper()+"进入等待队列"));
object.insert("recieved", true);
object.insert("type","zigbee_identify_data");
emit data_send("zigbee_identify_data_view",object,_allow_list,_deny_list,_wait_queue);
}
else
{
object.insert("sender", sender);
object.insert("text","");
object.insert("note_text",QJsonValue("节点0x"+QString::number(((base_frame *)zframe.getData().data())->ori_addr,16).toUpper()+"已在等待队列"));
object.insert("recieved", true);
object.insert("type","zigbee_identify_data");
emit data_send("zigbee_identify_data_view",object,_allow_list,_deny_list,_wait_queue);
}
}
break;
}
case 0x82:
{
}
case 0x83:
{
QJsonObject object;
if (node->first.verified)
{
zigbee_protocol::ZigbeeFrame dzf = zframe;
new_data_frame(72) ndata;
uint8_t data_len = 0;
memset(&ndata,0,sizeof(ndata));
if (*(u16 *)frame == CRYPTO_ZDATA_FRAME_HEAD)
{
czdata = (crypto_zdata_frame*)frame;
_protocol->zigbee_data_dectypt((uint8_t*)&ndata, &data_len, czdata, Crypto::SM4_decrypt);
dzf.setData((char*)&ndata,ndata.data_length + DATA_FRAME_PREFIX_LEN);
zdata = QByteArray((char *)dzf.data(), dzf.size());
object.insert("decrypted_text", QJsonValue(QString(zdata.toHex(' ').toUpper())));
}
object.insert("sender", sender);
object.insert("text",QJsonValue(QString(zdata.toHex(' ').toUpper())));
object.insert("note_text",QJsonValue("收到节点0x"+sender+"发送的数据"));
object.insert("recieved", true);
object.insert("type","zigbee_recv_data");
if (QRandomGenerator::global()->bounded(2)!=0 && is_demo)
object.insert("decrypted_text", QJsonValue(QString(zdata.toHex(' ').toUpper())));
emit data_send("zigbee_recv_data_view",object,_allow_list,_deny_list,_wait_queue);
}
else
{
object.insert("sender", sender);
object.insert("text",QJsonValue(QString(zdata.toHex(' ').toUpper())));
object.insert("note_text",QJsonValue("收到节点0x"+sender+"发送的数据,但节点并未认证"));
object.insert("recieved", true);
object.insert("type","zigbee_recv_data");
emit data_send("zigbee_recv_data_view",object,_allow_list,_deny_list,_wait_queue);
node->second.id=0;
new_data_frame(5) dframe;
memset(&dframe,0,sizeof (dframe));
_protocol->protocal_wrapper((data_frame *)&dframe, 0, 5, (u8 *)"RESET", false);
new_base_frame(5 + DATA_FRAME_PREFIX_LEN + BASE_FRAME_PREFIX_LEN) bframe;
memset(&bframe, 0, sizeof(bframe));
_protocol->base_frame_maker(&dframe, (base_frame *)&bframe, node->first.addr,&node->second);
zigbee_protocol::ZigbeeFrame zf(0x83,0x83,node->first.addr,(char *)&bframe,bframe.length);
QByteArray zfdata((char *)zf.data(),zf.size());
QJsonObject object;
object.insert("sender", QString::number(_protocol->self_addr,16).toUpper());
object.insert("text",QJsonValue(QString(zfdata.toHex(' ').toUpper())));
object.insert("note_text",QJsonValue("向节点0x"+sender+"发送重置命令"));
object.insert("recieved", false);
object.insert("type","zigbee_recv_data");
emit data_send("zigbee_recv_data_view",object,_allow_list,_deny_list,_wait_queue);
}
}
default:
break;
}
}
void ZigBeeDataResolver::remote_addr_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo)
{
switch (zframe.getRemoteAddr()) {
case 0xAAAA:
break;
default:
break;
}
}
void ZigBeeDataResolver::message_parser(QJsonObject message, QString self_addr, QList<uint16_t> allow_list, QList<uint16_t> deny_list, QList<uint16_t> wait_queue)
{
_self_addr = self_addr;
_allow_list = allow_list;
_deny_list = deny_list;
_wait_queue = wait_queue;
if (message["type"] == "demo_verify_request")
{
hmac_frame frame;
frame.value = QRandomGenerator::global()->bounded(256);
frame.head = HMAC_FRAME_HEAD;
frame.length = 32 + HMAC_FRAME_PREFIX_LEN;
QByteArray key = QByteArray::fromHex(_protocol->hmac_verify_key.toLatin1());
Crypto::getInstance()->SM3_HMAC((u8 *)key.data(), 16, &frame.value, 1, frame.hmac);
new_base_frame(50 + BASE_FRAME_PREFIX_LEN) bframe;
device test;
test.addr = 0x5656;
_protocol->base_frame_maker(&frame, (base_frame *)&bframe, _protocol->self_addr, &test);
zigbee_protocol::ZigbeeFrame zf(0x81,0x81,0x5656,(char*)&bframe,bframe.length);
data_parser(zf, true);
}
if (message["type"] == "demo_verify_key_update")
{
hmac_frame frame;
frame.value = QRandomGenerator::global()->bounded(256);
frame.head = HMAC_FRAME_HEAD;
frame.length = 32 + HMAC_FRAME_PREFIX_LEN;
QByteArray key = QByteArray::fromHex(_protocol->pre_hmac_verify_key[QRandomGenerator::global()->bounded(_protocol->pre_hmac_verify_key.length())].toLatin1());
Crypto::getInstance()->SM3_HMAC((u8 *)key.data(), 16, &frame.value, 1, frame.hmac);
new_base_frame(50 + BASE_FRAME_PREFIX_LEN) bframe;
device test;
test.addr = 0x5656;
_protocol->base_frame_maker(&frame, (base_frame *)&bframe, _protocol->self_addr, &test);
zigbee_protocol::ZigbeeFrame zf(0x81,0x81,0x5656,(char*)&bframe,bframe.length);
data_parser(zf, true);
}
if (message["type"] == "demo_recv_data" || message["type"] == "zigbee_raw_data")
{
QString data = message["data_hex"].toString();
QByteArray bdata;
QStringList td = data.split(' ');
for (auto item : td)
bdata += QByteArray::fromHex(item.toLatin1());
zigbee_protocol::ZigbeeFrame zf;
zf.load_package((uint8_t*)bdata.data(),bdata.length());
data_parser(zf, message["type"] == "demo_recv_data");
}
}

View File

@ -1,23 +1,38 @@
#include "zigbeeparser.h" #include "zigbeeparser.h"
#include "crypto.h" #include "crypto.h"
#include <QMutex> #include <QMutex>
#include <QThread>
#include <QRandomGenerator> #include <QRandomGenerator>
ZigBeeParser::ZigBeeParser(QObject *parent) ZigBeeParser::ZigBeeParser(QObject *parent)
: QObject{parent} : QObject{parent}
{ {
_config = Config::instance();
_protocol = zigbee_protocol::Protocol::getInstance(); _protocol = zigbee_protocol::Protocol::getInstance();
_thread = new QThread();
_resolver = ZigBeeDataResolver::instance();
_resolver->moveToThread(_thread);
_config = Config::instance();
_bus = EventsBus::instance(); _bus = EventsBus::instance();
_event.type("zigbee_parser"); _event.type("zigbee_parser");
_bus->reg_event(&_event); _bus->reg_event(&_event);
connect(&_event,&Event::triggered,this,&ZigBeeParser::message_parser); connect(&_event,&Event::triggered,this,&ZigBeeParser::message_parser);
connect(this, &ZigBeeParser::message_recved, _resolver, &ZigBeeDataResolver::message_parser);
connect(_resolver, &ZigBeeDataResolver::data_send, this, &ZigBeeParser::bus_data_send);
connect(_thread, &QThread::finished, this, [=](){
_thread->deleteLater();
_resolver->deleteLater();
});
_thread->start();
} }
ZigBeeParser::~ZigBeeParser() ZigBeeParser::~ZigBeeParser()
{ {
_bus->unreg_event(&_event); _bus->unreg_event(&_event);
disconnect(&_event,&Event::triggered,this,&ZigBeeParser::message_parser); disconnect(&_event,&Event::triggered,this,&ZigBeeParser::message_parser);
if(_thread->isRunning())
{
_thread->quit();
}
} }
ZigBeeParser* ZigBeeParser::instance() ZigBeeParser* ZigBeeParser::instance()
@ -32,296 +47,15 @@ ZigBeeParser* ZigBeeParser::instance()
return singleton; return singleton;
} }
void ZigBeeParser::data_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo)
{
src_port_parser(zframe,is_demo);
des_port_parser(zframe, is_demo);
remote_addr_parser(zframe, is_demo);
}
void ZigBeeParser::src_port_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo)
{
switch (zframe.getSrcPort()) {
case 0x81:
break;
default:
break;
}
}
void ZigBeeParser::des_port_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo)
{
if (zframe.size() <= 7)
{
qDebug()<<"ZigBee: recved package is corrupted, dropped.";
return;
}
void *frame = nullptr;
base_frame *bframe=nullptr;
hmac_frame *hframe=nullptr;
crypto_zdata_frame *czdata = nullptr;
data_frame *ddata = nullptr;
QByteArray zdata((char *)zframe.data(), zframe.size());
QString sender = QString::number(((base_frame *)zframe.getData().data())->ori_addr,16).toUpper();
device temp,self;
QPair<device,device>* node = nullptr;
memset(&temp,0,sizeof(temp));
memset(&temp,0,sizeof(self));
self.addr = _protocol->self_addr;
if (!nodes.contains(((base_frame *)zframe.getData().data())->ori_addr))
{
temp.addr=((base_frame *)zframe.getData().data())->ori_addr;
temp.id = 0;
temp.online = 1;
temp.rand_num = 0;
temp.verified = 0;
nodes.insert(temp.addr,qMakePair(temp,self));
}
node = &nodes[((base_frame *)zframe.getData().data())->ori_addr];
bframe = (base_frame*)zframe.getData().data();
if (is_demo || bframe->des_addr == _protocol->self_addr && (node->first.id == 0||bframe->reset_num==0xDD||((bframe->id > node->first.id && bframe->id<=BASE_FRAME_RESET_NUM))))
{
node->first.addr = bframe->ori_addr;
node->first.id = bframe->id;
node->first.rand_num = bframe->rand_num;
frame = (void*)bframe->data;
}
else
{
QJsonObject object;
object.insert("text",QJsonValue(QString(zdata.toHex(' ').toUpper())));
object.insert("note_text",QJsonValue("请注意节点0x"+QString::number(node->first.addr,16).toUpper()+"发送的该数据包损坏"));
object.insert("recieved", true);
object.insert("sender", sender);
object.insert("type","zigbee_identify_data");
_bus->push_data("zigbee_identify_data_view",object);
return;
}
switch (zframe.getDesPort()) {
case 0x81:
{
hframe = (hmac_frame*)frame;
QJsonObject object;
object.insert("text",QJsonValue(QString(zdata.toHex(' ').toUpper())));
object.insert("sender", sender);
object.insert("note_text",QJsonValue("收到节点0x"+ sender +"发送的验证信息"));
object.insert("recieved", true);
object.insert("type","zigbee_identify_data");
_bus->push_data("zigbee_identify_data_view",object);
if (_allow_list.contains(node->first.addr))
{
u8 hmac[33]="";
QByteArray key = QByteArray::fromHex(_protocol->hmac_verify_key.toLatin1());
Crypto::getInstance()->SM3_HMAC((u8 *)key.data(),16,&hframe->value,1,hmac);
if (_protocol->bytecmp(hframe->hmac,hmac,32))
{
new_data_frame(15) data;
memset(&data, 0, sizeof(data));
_protocol->protocal_wrapper((data_frame *)&data, 0, 10, (u8 *)"Identified", 0);
node->first.verified = 1;
new_base_frame(15 + DATA_FRAME_PREFIX_LEN + BASE_FRAME_PREFIX_LEN) bframe;
memset(&bframe, 0, sizeof(bframe));
_protocol->base_frame_maker(&data, (base_frame *)&bframe, node->first.addr,&node->second);
zigbee_protocol::ZigbeeFrame zf(zframe.getSrcPort(),zframe.getDesPort(),zframe.getRemoteAddr(),(uint8_t *)&bframe,bframe.length);
QByteArray bdata((char *)&bframe, bframe.length);
QByteArray zdata((char *)zf.data(), zf.size());
QJsonObject object;
object.insert("baseframe_data",QJsonValue(QString(bdata.toHex(' ').toUpper())));
object.insert("text",QJsonValue(QString(zdata.toHex(' ').toUpper())));
object.insert("note_text",QJsonValue("向0x"+QString::number(node->first.addr,16).toUpper()+"节点发送验证通过回复信息"));
object.insert("recieved", false);
object.insert("sender", QString::number(_protocol->self_addr,16).toUpper());
object.insert("type","zigbee_identify_data");
_bus->push_data("zigbee_identify_data_view",object);
if(!is_demo)
_bus->push_data("serial_port",object);
}
else
{
u8 hmac[33]="";
QJsonObject object;
QByteArray latest_key = QByteArray::fromHex(_protocol->hmac_verify_key.toLatin1());
for (auto key_str : _protocol->pre_hmac_verify_key)
{
QByteArray key = QByteArray::fromHex(key_str.toLatin1());
Crypto::getInstance()->SM3_HMAC((u8 *)key.data(),16,&hframe->value,1,hmac);
if (_protocol->bytecmp(hframe->hmac,hmac,32))
{
zigbee_protocol::ZigbeeFrame zf(0x82,0x82,node->first.addr);
new_crypto_zdata_frame(32) zdata;
memset(&zdata, 0, sizeof(zdata));
_protocol->zigbee_data_encrypt((u8*)latest_key.data(), 16, (crypto_zdata_frame *)&zdata, Crypto::SM4_encrypt, key_str);
new_base_frame(sizeof(zdata) + BASE_FRAME_PREFIX_LEN) bframe;
memset(&bframe, 0, sizeof(bframe));
_protocol->base_frame_maker(&zdata, (base_frame *)&bframe, node->first.addr, &node->second);
zf.setData((u8 *)&bframe, bframe.length);
QByteArray bdata((char *)&bframe, bframe.length);
QByteArray zfdata((char *)zf.data(), zf.size());
object.insert("baseframe_data",QJsonValue(QString(bdata.toHex(' ').toUpper())));
object.insert("text",QJsonValue(QString(zfdata.toHex(' ').toUpper())));
object.insert("note_text",QJsonValue("节点0x"+QString::number(node->first.addr,16).toUpper()+"正在使用旧密钥,发送密钥更新指令"));
object.insert("recieved", false);
object.insert("sender", QString::number(_protocol->self_addr,16).toUpper());
object.insert("type","zigbee_identify_data");
_bus->push_data("zigbee_identify_data_view",object);
if(!is_demo)
_bus->push_data("serial_port",object);
return;
}
}
object.insert("note_text",QJsonValue("节点0x"+QString::number(node->first.addr,16).toUpper()+"验证不通过,请考虑移出认证列表"));
object.insert("recieved", true);
object.insert("sender", sender);
object.insert("type","zigbee_identify_data");
_bus->push_data("zigbee_identify_data_view",object);
}
}
else if(_deny_list.contains(node->first.addr))
{
object.insert("sender", sender);
object.insert("text","");
object.insert("note_text",QJsonValue("节点0x"+QString::number(((base_frame *)zframe.getData().data())->ori_addr,16).toUpper()+"被禁止接入"));
object.insert("recieved", true);
object.insert("type","zigbee_identify_data");
_bus->push_data("zigbee_identify_data_view",object);
}
else {
if (!_wait_queue.contains(node->first.addr))
{
_wait_queue.append(node->first.addr);
object.insert("sender", sender);
object.insert("text","");
object.insert("note_text",QJsonValue("节点0x"+QString::number(((base_frame *)zframe.getData().data())->ori_addr,16).toUpper()+"进入等待队列"));
object.insert("recieved", true);
object.insert("type","zigbee_identify_data");
_bus->push_data("zigbee_identify_data_view",object);
}
else
{
object.insert("sender", sender);
object.insert("text","");
object.insert("note_text",QJsonValue("节点0x"+QString::number(((base_frame *)zframe.getData().data())->ori_addr,16).toUpper()+"已在等待队列"));
object.insert("recieved", true);
object.insert("type","zigbee_identify_data");
_bus->push_data("zigbee_identify_data_view",object);
}
}
break;
}
case 0x82:
{
}
case 0x83:
{
QJsonObject object;
if (node->first.verified)
{
zigbee_protocol::ZigbeeFrame dzf = zframe;
new_data_frame(72) ndata;
uint8_t data_len = 0;
memset(&ndata,0,sizeof(ndata));
if (*(u16 *)frame == CRYPTO_ZDATA_FRAME_HEAD)
{
czdata = (crypto_zdata_frame*)frame;
_protocol->zigbee_data_dectypt((uint8_t*)&ndata, &data_len, czdata, Crypto::SM4_decrypt);
dzf.setData((char*)&ndata,ndata.data_length + DATA_FRAME_PREFIX_LEN);
zdata = QByteArray((char *)dzf.data(), dzf.size());
object.insert("decrypted_text", QJsonValue(QString(zdata.toHex(' ').toUpper())));
}
object.insert("sender", sender);
object.insert("text",QJsonValue(QString(zdata.toHex(' ').toUpper())));
object.insert("note_text",QJsonValue("收到节点0x"+sender+"发送的数据"));
object.insert("recieved", true);
object.insert("type","zigbee_recv_data");
if (QRandomGenerator::global()->bounded(2)!=0 && is_demo)
object.insert("decrypted_text", QJsonValue(QString(zdata.toHex(' ').toUpper())));
_bus->push_data("zigbee_recv_data_view",object);
}
else
{
object.insert("sender", sender);
object.insert("text",QJsonValue(QString(zdata.toHex(' ').toUpper())));
object.insert("note_text",QJsonValue("收到节点0x"+sender+"发送的数据,但节点并未认证"));
object.insert("recieved", true);
object.insert("type","zigbee_recv_data");
_bus->push_data("zigbee_recv_data_view",object);
node->second.id=0;
new_data_frame(5) dframe;
memset(&dframe,0,sizeof (dframe));
_protocol->protocal_wrapper((data_frame *)&dframe, 0, 5, (u8 *)"RESET", false);
new_base_frame(5 + DATA_FRAME_PREFIX_LEN + BASE_FRAME_PREFIX_LEN) bframe;
memset(&bframe, 0, sizeof(bframe));
_protocol->base_frame_maker(&dframe, (base_frame *)&bframe, node->first.addr,&node->second);
zigbee_protocol::ZigbeeFrame zf(0x83,0x83,node->first.addr,(char *)&bframe,bframe.length);
QByteArray zfdata((char *)zf.data(),zf.size());
QJsonObject object;
object.insert("sender", QString::number(_protocol->self_addr,16).toUpper());
object.insert("text",QJsonValue(QString(zfdata.toHex(' ').toUpper())));
object.insert("note_text",QJsonValue("向节点0x"+sender+"发送重置命令"));
object.insert("recieved", false);
object.insert("type","zigbee_recv_data");
_bus->push_data("zigbee_recv_data_view",object);
}
}
default:
break;
}
}
void ZigBeeParser::remote_addr_parser(zigbee_protocol::ZigbeeFrame &zframe, bool is_demo)
{
switch (zframe.getRemoteAddr()) {
case 0xAAAA:
break;
default:
break;
}
}
void ZigBeeParser::message_parser(QJsonObject message) void ZigBeeParser::message_parser(QJsonObject message)
{ {
if (message["type"] == "demo_verify_request") emit message_recved(message, _self_addr, _allow_list, _deny_list, _wait_queue);
{ }
hmac_frame frame;
frame.value = QRandomGenerator::global()->bounded(256); void ZigBeeParser::bus_data_send(QString type, QJsonObject data, QList<uint16_t> allow_list, QList<uint16_t> deny_list, QList<uint16_t> wait_queue)
frame.head = HMAC_FRAME_HEAD; {
frame.length = 32 + HMAC_FRAME_PREFIX_LEN; _bus->push_data(type, data);
QByteArray key = QByteArray::fromHex(_protocol->hmac_verify_key.toLatin1()); _allow_list = allow_list;
Crypto::getInstance()->SM3_HMAC((u8 *)key.data(), 16, &frame.value, 1, frame.hmac); _deny_list = deny_list;
new_base_frame(50 + BASE_FRAME_PREFIX_LEN) bframe; _wait_queue = wait_queue;
device test;
test.addr = 0x5656;
_protocol->base_frame_maker(&frame, (base_frame *)&bframe, _protocol->self_addr, &test);
zigbee_protocol::ZigbeeFrame zf(0x81,0x81,0x5656,(char*)&bframe,bframe.length);
data_parser(zf, true);
}
if (message["type"] == "demo_verify_key_update")
{
hmac_frame frame;
frame.value = QRandomGenerator::global()->bounded(256);
frame.head = HMAC_FRAME_HEAD;
frame.length = 32 + HMAC_FRAME_PREFIX_LEN;
QByteArray key = QByteArray::fromHex(_protocol->pre_hmac_verify_key[QRandomGenerator::global()->bounded(_protocol->pre_hmac_verify_key.length())].toLatin1());
Crypto::getInstance()->SM3_HMAC((u8 *)key.data(), 16, &frame.value, 1, frame.hmac);
new_base_frame(50 + BASE_FRAME_PREFIX_LEN) bframe;
device test;
test.addr = 0x5656;
_protocol->base_frame_maker(&frame, (base_frame *)&bframe, _protocol->self_addr, &test);
zigbee_protocol::ZigbeeFrame zf(0x81,0x81,0x5656,(char*)&bframe,bframe.length);
data_parser(zf, true);
}
if (message["type"] == "demo_recv_data" || message["type"] == "zigbee_raw_data")
{
QString data = message["data_hex"].toString();
QByteArray bdata;
QStringList td = data.split(' ');
for (auto item : td)
bdata += QByteArray::fromHex(item.toLatin1());
zigbee_protocol::ZigbeeFrame zf;
zf.load_package((uint8_t*)bdata.data(),bdata.length());
data_parser(zf, message["type"] == "demo_recv_data");
}
} }