diff --git a/.cache/clangd/index/CoreService.cpp.4E2160035C5FBDAD.idx b/.cache/clangd/index/CoreService.cpp.4E2160035C5FBDAD.idx new file mode 100644 index 0000000..980ad9c Binary files /dev/null and b/.cache/clangd/index/CoreService.cpp.4E2160035C5FBDAD.idx differ diff --git a/.cache/clangd/index/CoreService.h.545B9643BE6343CF.idx b/.cache/clangd/index/CoreService.h.545B9643BE6343CF.idx new file mode 100644 index 0000000..ba420e5 Binary files /dev/null and b/.cache/clangd/index/CoreService.h.545B9643BE6343CF.idx differ diff --git a/.cache/clangd/index/DeviceBus.cpp.3FE983A42FE7A6A8.idx b/.cache/clangd/index/DeviceBus.cpp.3FE983A42FE7A6A8.idx new file mode 100644 index 0000000..1fa1bdb Binary files /dev/null and b/.cache/clangd/index/DeviceBus.cpp.3FE983A42FE7A6A8.idx differ diff --git a/.cache/clangd/index/DeviceBus.h.170EB5C1B9D8C650.idx b/.cache/clangd/index/DeviceBus.h.170EB5C1B9D8C650.idx new file mode 100644 index 0000000..8f603e6 Binary files /dev/null and b/.cache/clangd/index/DeviceBus.h.170EB5C1B9D8C650.idx differ diff --git a/.cache/clangd/index/DeviceBusManager.cpp.134168DDD210A4ED.idx b/.cache/clangd/index/DeviceBusManager.cpp.134168DDD210A4ED.idx new file mode 100644 index 0000000..865289c Binary files /dev/null and b/.cache/clangd/index/DeviceBusManager.cpp.134168DDD210A4ED.idx differ diff --git a/.cache/clangd/index/DeviceBusManager.h.4DAD625CA48C7EE3.idx b/.cache/clangd/index/DeviceBusManager.h.4DAD625CA48C7EE3.idx new file mode 100644 index 0000000..f4023f8 Binary files /dev/null and b/.cache/clangd/index/DeviceBusManager.h.4DAD625CA48C7EE3.idx differ diff --git a/.cache/clangd/index/DeviceTreeModel.cpp.D68EA11C8BBF4ADF.idx b/.cache/clangd/index/DeviceTreeModel.cpp.D68EA11C8BBF4ADF.idx new file mode 100644 index 0000000..1c855bc Binary files /dev/null and b/.cache/clangd/index/DeviceTreeModel.cpp.D68EA11C8BBF4ADF.idx differ diff --git a/.cache/clangd/index/DeviceTreeModel.h.A5637DBA59AB7F8A.idx b/.cache/clangd/index/DeviceTreeModel.h.A5637DBA59AB7F8A.idx new file mode 100644 index 0000000..c8c46f5 Binary files /dev/null and b/.cache/clangd/index/DeviceTreeModel.h.A5637DBA59AB7F8A.idx differ diff --git a/.cache/clangd/index/DriverCapabilityProvider.cpp.D9F40BD74EEBC885.idx b/.cache/clangd/index/DriverCapabilityProvider.cpp.D9F40BD74EEBC885.idx new file mode 100644 index 0000000..48c5aa0 Binary files /dev/null and b/.cache/clangd/index/DriverCapabilityProvider.cpp.D9F40BD74EEBC885.idx differ diff --git a/.cache/clangd/index/DriverCapabilityProvider.h.78F6C857AFED3B7D.idx b/.cache/clangd/index/DriverCapabilityProvider.h.78F6C857AFED3B7D.idx new file mode 100644 index 0000000..1e8e61b Binary files /dev/null and b/.cache/clangd/index/DriverCapabilityProvider.h.78F6C857AFED3B7D.idx differ diff --git a/.cache/clangd/index/IStreamDriver.h.7F77A7878AD58FDD.idx b/.cache/clangd/index/IStreamDriver.h.7F77A7878AD58FDD.idx new file mode 100644 index 0000000..3c2e111 Binary files /dev/null and b/.cache/clangd/index/IStreamDriver.h.7F77A7878AD58FDD.idx differ diff --git a/.cache/clangd/index/IpcDBus.cpp.F75762A8BF6179E0.idx b/.cache/clangd/index/IpcDBus.cpp.F75762A8BF6179E0.idx new file mode 100644 index 0000000..6a719fa Binary files /dev/null and b/.cache/clangd/index/IpcDBus.cpp.F75762A8BF6179E0.idx differ diff --git a/.cache/clangd/index/IpcDBus.h.DD48681835A8EA94.idx b/.cache/clangd/index/IpcDBus.h.DD48681835A8EA94.idx new file mode 100644 index 0000000..dd18520 Binary files /dev/null and b/.cache/clangd/index/IpcDBus.h.DD48681835A8EA94.idx differ diff --git a/.cache/clangd/index/SerialCapabilities.h.50ACDAA3497BB1F6.idx b/.cache/clangd/index/SerialCapabilities.h.50ACDAA3497BB1F6.idx new file mode 100644 index 0000000..a616aa3 Binary files /dev/null and b/.cache/clangd/index/SerialCapabilities.h.50ACDAA3497BB1F6.idx differ diff --git a/.cache/clangd/index/SerialQtDriver.cpp.E8F1085153E8E1E0.idx b/.cache/clangd/index/SerialQtDriver.cpp.E8F1085153E8E1E0.idx new file mode 100644 index 0000000..8990c78 Binary files /dev/null and b/.cache/clangd/index/SerialQtDriver.cpp.E8F1085153E8E1E0.idx differ diff --git a/.cache/clangd/index/SerialQtDriver.h.0D1EBDDF4831E0E3.idx b/.cache/clangd/index/SerialQtDriver.h.0D1EBDDF4831E0E3.idx new file mode 100644 index 0000000..037d162 Binary files /dev/null and b/.cache/clangd/index/SerialQtDriver.h.0D1EBDDF4831E0E3.idx differ diff --git a/.cache/clangd/index/logging.h.C8CBC4848C286E20.idx b/.cache/clangd/index/logging.h.C8CBC4848C286E20.idx new file mode 100644 index 0000000..be0a8bd Binary files /dev/null and b/.cache/clangd/index/logging.h.C8CBC4848C286E20.idx differ diff --git a/.cache/clangd/index/main.cpp.76A75E580B25A05E.idx b/.cache/clangd/index/main.cpp.76A75E580B25A05E.idx new file mode 100644 index 0000000..8168620 Binary files /dev/null and b/.cache/clangd/index/main.cpp.76A75E580B25A05E.idx differ diff --git a/.gitignore b/.gitignore index aa3808c..91ab649 100644 --- a/.gitignore +++ b/.gitignore @@ -1,82 +1,82 @@ -# This file is used to ignore files which are generated -# ---------------------------------------------------------------------------- - -*~ -*.autosave -*.a -*.core -*.moc -*.o -*.obj -*.orig -*.rej -*.so -*.so.* -*_pch.h.cpp -*_resource.rc -*.qm -.#* -*.*# -core -!core/ -tags -.DS_Store -.directory -*.debug -Makefile* -*.prl -*.app -moc_*.cpp -ui_*.h -qrc_*.cpp -Thumbs.db -*.res -*.rc -/.qmake.cache -/.qmake.stash - -# qtcreator generated files -*.pro.user* -*.qbs.user* -CMakeLists.txt.user* - -# xemacs temporary files -*.flc - -# Vim temporary files -.*.swp - -# Visual Studio generated files -*.ib_pdb_index -*.idb -*.ilk -*.pdb -*.sln -*.suo -*.vcproj -*vcproj.*.*.user -*.ncb -*.sdf -*.opensdf -*.vcxproj -*vcxproj.* - -# MinGW generated files -*.Debug -*.Release - -# Python byte code -*.pyc - -# Binaries -# -------- -*.dll -*.exe - -# Directories with generated files -.moc/ -.obj/ -.pch/ -.rcc/ -.uic/ -/build*/ +# This file is used to ignore files which are generated +# ---------------------------------------------------------------------------- + +*~ +*.autosave +*.a +*.core +*.moc +*.o +*.obj +*.orig +*.rej +*.so +*.so.* +*_pch.h.cpp +*_resource.rc +*.qm +.#* +*.*# +core +!core/ +tags +.DS_Store +.directory +*.debug +Makefile* +*.prl +*.app +moc_*.cpp +ui_*.h +qrc_*.cpp +Thumbs.db +*.res +*.rc +/.qmake.cache +/.qmake.stash + +# qtcreator generated files +*.pro.user* +*.qbs.user* +CMakeLists.txt.user* + +# xemacs temporary files +*.flc + +# Vim temporary files +.*.swp + +# Visual Studio generated files +*.ib_pdb_index +*.idb +*.ilk +*.pdb +*.sln +*.suo +*.vcproj +*vcproj.*.*.user +*.ncb +*.sdf +*.opensdf +*.vcxproj +*vcxproj.* + +# MinGW generated files +*.Debug +*.Release + +# Python byte code +*.pyc + +# Binaries +# -------- +*.dll +*.exe + +# Directories with generated files +.moc/ +.obj/ +.pch/ +.rcc/ +.uic/ +/build*/ diff --git a/CMakeLists.txt b/CMakeLists.txt index 3172efd..432f9ed 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,85 +1,116 @@ -cmake_minimum_required(VERSION 3.19) -project(soft_bus_daemon - LANGUAGES CXX - VERSION 1.0.0 -) - -set(CMAKE_EXPORT_COMPILE_COMMANDS ON) - -set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -g") -set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -g") - -# Output layout -set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_SOURCE_DIR}/bin) -set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${CMAKE_SOURCE_DIR}/bin/plugins) -set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${CMAKE_SOURCE_DIR}/bin/plugins) - -# 启用AddressSanitizer(仅在非Windows平台上) -if(NOT WIN32) - set(SANITIZE_FLAGS "-fsanitize=address") - set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${SANITIZE_FLAGS}") - set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${SANITIZE_FLAGS}") - set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} ${SANITIZE_FLAGS}") -else() - message(STATUS "AddressSanitizer disabled on Windows because the runtime is unavailable in the MinGW kit.") -endif() - -# 设置C++标准 -set(CMAKE_CXX_STANDARD 20) -set(CMAKE_CXX_STANDARD_REQUIRED ON) -set(CMAKE_AUTORCC ON) -set(CMAKE_AUTOMOC ON) -# 查找Qt6(守护进程只需要 Core/DBus/Network/SerialPort/Sql) -find_package(Qt6 6.5 REQUIRED COMPONENTS Core SerialPort Network Sql DBus) - -# 检测编译平台 -if("${CMAKE_SIZEOF_VOID_P}" STREQUAL "4") - set(PlatformDir "x86") -else() - set(PlatformDir "x64") -endif() - -qt_standard_project_setup() - -# 添加软总线模板库 -# 1. 日志库 -qt_add_library(softbus_template - src/utils/logs/logging.h - src/utils/logs/LogStream.h -) - -qt_add_executable(softbus_daemon - main.cpp - src/core/CoreService.cpp - - # api 接口 - - src/api/ipc_dbus/IpcDBus.h - src/api/ipc_dbus/IpcDBus.cpp - - -) - -target_include_directories(softbus_daemon - PRIVATE - ${CMAKE_SOURCE_DIR} -) - - - -target_link_libraries(softbus_daemon - PRIVATE - Qt::Core - Qt6::DBus - Qt6::SerialPort - Qt6::Network -) - -add_subdirectory(plugins) - - -install(TARGETS softbus_daemon - BUNDLE DESTINATION . - RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} - LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} -) +cmake_minimum_required(VERSION 3.19) +project(soft_bus_daemon + LANGUAGES CXX + VERSION 1.0.0 +) + +set(CMAKE_EXPORT_COMPILE_COMMANDS ON) + +set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -g") +set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -g") + +# Output layout +set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_SOURCE_DIR}/bin) +set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${CMAKE_SOURCE_DIR}/bin/plugins) +set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${CMAKE_SOURCE_DIR}/bin/plugins) + +# 启用AddressSanitizer(仅在非Windows平台上) +if(NOT WIN32) + set(SANITIZE_FLAGS "-fsanitize=address") + set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${SANITIZE_FLAGS}") + set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${SANITIZE_FLAGS}") + set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} ${SANITIZE_FLAGS}") +else() + message(STATUS "AddressSanitizer disabled on Windows because the runtime is unavailable in the MinGW kit.") +endif() + +# 设置C++标准 +set(CMAKE_CXX_STANDARD 20) +set(CMAKE_CXX_STANDARD_REQUIRED ON) +set(CMAKE_AUTORCC ON) +set(CMAKE_AUTOMOC ON) +# 查找Qt6(守护进程只需要 Core/DBus/Network/SerialPort/Sql) +find_package(Qt6 6.5 REQUIRED COMPONENTS Core SerialPort Network Sql DBus) + +# 检测编译平台 +if("${CMAKE_SIZEOF_VOID_P}" STREQUAL "4") + set(PlatformDir "x86") +else() + set(PlatformDir "x64") +endif() + +qt_standard_project_setup() + +# 添加软总线模板库 +# 1. 日志库 +qt_add_library(softbus_template + src/utils/logs/logging.h + src/utils/logs/LogStream.h +) + +qt_add_executable(softbus_daemon + main.cpp + src/core/CoreService.cpp + # core device types + src/core/device/DeviceTypes.h + src/core/device/DeviceTypes.cpp + + + # api 接口 + + src/api/ipc_dbus/IpcDBus.h + src/api/ipc_dbus/IpcDBus.cpp + + # hardware interfaces (Level 2) + src/hardware/interfaces/IStreamDriver.h + src/hardware/interfaces/IFrameDriver.h + src/hardware/interfaces/IDeviceWatcher.h + + # hardware drivers (Level 2) + src/hardware/drivers/serial/SerialQtDriver.h + src/hardware/drivers/serial/SerialQtDriver.cpp + src/hardware/drivers/serial/SerialCapabilities.h + + # device bus: tree & capabilities + src/device_bus/tree/DeviceTreeModel.h + src/device_bus/tree/DeviceTreeModel.cpp + src/device_bus/capabilities/DriverCapabilityProvider.h + src/device_bus/capabilities/DriverCapabilityProvider.cpp + + # device bus: facade & manager + src/device_bus/DeviceBus.h + src/device_bus/DeviceBus.cpp + src/device_bus/manager/DeviceBusManager.h + src/device_bus/manager/DeviceBusManager.cpp + + # device bus: registry skeleton + src/device_bus/registry/IDeviceRegistry.h + + # devices: base skeleton + src/devices/base/IDevice.h +) + +target_include_directories(softbus_daemon + PRIVATE + ${CMAKE_SOURCE_DIR} + ${CMAKE_SOURCE_DIR}/src +) + + + +target_link_libraries(softbus_daemon + PRIVATE + Qt::Core + Qt6::DBus + Qt6::SerialPort + Qt6::Network +) + +add_subdirectory(plugins) + + +install(TARGETS softbus_daemon + BUNDLE DESTINATION . + RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} + LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} +) diff --git a/bin/softbus_daemon b/bin/softbus_daemon index fc1ba60..63bc709 100755 Binary files a/bin/softbus_daemon and b/bin/softbus_daemon differ diff --git a/config/daemon_config.json b/config/daemon_config.json index 8b02b04..458aa64 100644 --- a/config/daemon_config.json +++ b/config/daemon_config.json @@ -1,5 +1,23 @@ -{ - "plugin_dir": "bin/plugins", - "device_tree": [], - "routes": [] -} +{ + "plugin_dir": "bin/plugins", + "device_tree": [ + { + "id": "serial_1", + "name": "Serial Device 1", + "type": "serial", + "endpoint": "/dev/ttyS1", + "driver": "hardware/drivers/serial/SerialQtDriver", + "capabilitiesRef": "src/hardware/drivers/serial/parameters.json", + "params": { + "baudRate": 115200, + "dataBits": 8, + "parity": "none", + "stopBits": 1, + "flowControl": "none" + }, + "children": [], + "enabled": true + } + ], + "routes": [] +} diff --git a/config/plugins_config.json b/config/plugins_config.json index 9581b98..4126bc7 100644 --- a/config/plugins_config.json +++ b/config/plugins_config.json @@ -2,4 +2,4 @@ "modbus_rtu": { "register_map": [] } -} +} diff --git a/main.cpp b/main.cpp index 92feb73..27d4e92 100644 --- a/main.cpp +++ b/main.cpp @@ -1,136 +1,136 @@ -#include -#include -#include -#include -#include -#include "src/utils/logs/logging.h" -#include "src/core/CoreService.h" -#include "src/api/ipc_dbus/IpcDBus.h" - -void signalHandler(int signal) -{ - LOG_INFO() << "Received signal:" << signal; - QCoreApplication::quit(); -} - -int main(int argc, char *argv[]) -{ - // ================================== - // 创建并配置 Qt 应用程序对象 - // ================================== - QCoreApplication app(argc, argv); - - app.setApplicationName("soft_bus_daemon"); - app.setApplicationVersion("1.0.0"); - app.setOrganizationName("soft_bus"); - - // ================================== - // 设置 Qt 应用程序信息 - // ================================== - QCommandLineParser parser; - parser.setApplicationDescription(QStringLiteral("Soft Bus Daemon")); - parser.addHelpOption(); - parser.addVersionOption(); - QCommandLineOption roleOption(QStringLiteral("role"), - QStringLiteral("Daemon role (CoreRouter, CollectorSerial, CollectorCan, Collector, SqlServer)"), - QStringLiteral("role"), - QStringLiteral("CoreRouter")); - parser.addOption(roleOption); - QCommandLineOption dbusBusOption(QStringLiteral("dbus-bus"), - QStringLiteral("DBus bus to use: system|session|auto (default: auto)"), - QStringLiteral("bus"), - QStringLiteral("auto")); - parser.addOption(dbusBusOption); - parser.process(app); - - - const QString roleString = parser.value(roleOption).trimmed(); - const QString dbusBus = parser.value(dbusBusOption).trimmed(); - CoreService::Role role = CoreService::Role::CoreRouter; // 默认角色 - if (roleString == QStringLiteral("CoreRouter")) { - role = CoreService::Role::CoreRouter; - } else if (roleString == QStringLiteral("CollectorSerial")) { - role = CoreService::Role::CollectorSerial; - } else if (roleString == QStringLiteral("CollectorCan")) { - role = CoreService::Role::CollectorCan; - } else if (roleString == QStringLiteral("Collector")) { - role = CoreService::Role::Collector; - } else if (roleString == QStringLiteral("SqlServer")) { - role = CoreService::Role::SqlServer; - } else { - LOG_ERROR() << "Invalid role:" << roleString - << "valid roles are: CoreRouter, CollectorSerial, CollectorCan, Collector, SqlServer"; - return 1; - } - - CoreService* coreService = CoreService::instance(); - if (!coreService->initialize()) { - LOG_ERROR() << "CoreService initialize failed"; - return 1; - } - QObject::connect(&app, &QCoreApplication::aboutToQuit, coreService, &CoreService::shutdown); - - // ======================================================================== - // 创建并注册 D-Bus 服务(仅在 CoreRouter 角色中启用) - // ======================================================================== - if (role == CoreService::Role::CoreRouter) { - const QString serviceName = QStringLiteral("com.softbus.Daemon"); - const QString objectPath = QStringLiteral("/com/softbus/Daemon"); - - IpcDBus* ipc = new IpcDBus(coreService, roleString, &app); - - auto pickConnection = [&]() -> QDBusConnection { - if (dbusBus == QStringLiteral("system")) { - return QDBusConnection::systemBus(); - } - if (dbusBus == QStringLiteral("session")) { - return QDBusConnection::sessionBus(); - } - // auto: 优先 system(更符合 daemon),失败则退回 session(方便本地开发) - QDBusConnection conn = QDBusConnection::systemBus(); - if (conn.isConnected()) { - return conn; - } - return QDBusConnection::sessionBus(); - }; - - QDBusConnection connection = pickConnection(); - if (!connection.isConnected()) { - LOG_ERROR() << "Cannot connect to D-Bus. system error=" - << QDBusConnection::systemBus().lastError().message() - << " session error=" << QDBusConnection::sessionBus().lastError().message(); - return 1; - } - - if (!connection.registerService(serviceName)) { - LOG_ERROR() << "Failed to register D-Bus service:" << serviceName - << "error=" << connection.lastError().message(); - return 1; - } - - if (!connection.registerObject(objectPath, - ipc, - QDBusConnection::ExportAllSlots | QDBusConnection::ExportAllSignals)) { - LOG_ERROR() << "Failed to register D-Bus object:" << objectPath - << "error=" << connection.lastError().message(); - return 1; - } - - LOG_INFO() << "D-Bus ready. bus=" - << (connection.name() == QDBusConnection::systemBus().name() ? "system" : "session") - << " service=" << serviceName - << " object=" << objectPath; - } - - - - // ================================== - // 处理系统信号,确保在接收到 SIGINT 或 SIGTERM 时能够优雅地退出 - // ================================== - - signal(SIGINT, signalHandler); - signal(SIGTERM, signalHandler); - - int ret = app.exec(); - return ret; -} +#include +#include +#include +#include +#include +#include "src/utils/logs/logging.h" +#include "src/core/CoreService.h" +#include "src/api/ipc_dbus/IpcDBus.h" + +void signalHandler(int signal) +{ + LOG_INFO() << "Received signal:" << signal; + QCoreApplication::quit(); +} + +int main(int argc, char *argv[]) +{ + // ================================== + // 创建并配置 Qt 应用程序对象 + // ================================== + QCoreApplication app(argc, argv); + + app.setApplicationName("soft_bus_daemon"); + app.setApplicationVersion("1.0.0"); + app.setOrganizationName("soft_bus"); + + // ================================== + // 设置 Qt 应用程序信息 + // ================================== + QCommandLineParser parser; + parser.setApplicationDescription(QStringLiteral("Soft Bus Daemon")); + parser.addHelpOption(); + parser.addVersionOption(); + QCommandLineOption roleOption(QStringLiteral("role"), + QStringLiteral("Daemon role (CoreRouter, CollectorSerial, CollectorCan, Collector, SqlServer)"), + QStringLiteral("role"), + QStringLiteral("CoreRouter")); + parser.addOption(roleOption); + QCommandLineOption dbusBusOption(QStringLiteral("dbus-bus"), + QStringLiteral("DBus bus to use: system|session|auto (default: auto)"), + QStringLiteral("bus"), + QStringLiteral("auto")); + parser.addOption(dbusBusOption); + parser.process(app); + + + const QString roleString = parser.value(roleOption).trimmed(); + const QString dbusBus = parser.value(dbusBusOption).trimmed(); + CoreService::Role role = CoreService::Role::CoreRouter; // 默认角色 + if (roleString == QStringLiteral("CoreRouter")) { + role = CoreService::Role::CoreRouter; + } else if (roleString == QStringLiteral("CollectorSerial")) { + role = CoreService::Role::CollectorSerial; + } else if (roleString == QStringLiteral("CollectorCan")) { + role = CoreService::Role::CollectorCan; + } else if (roleString == QStringLiteral("Collector")) { + role = CoreService::Role::Collector; + } else if (roleString == QStringLiteral("SqlServer")) { + role = CoreService::Role::SqlServer; + } else { + LOG_ERROR() << "Invalid role:" << roleString + << "valid roles are: CoreRouter, CollectorSerial, CollectorCan, Collector, SqlServer"; + return 1; + } + + CoreService* coreService = CoreService::instance(); + if (!coreService->initialize()) { + LOG_ERROR() << "CoreService initialize failed"; + return 1; + } + QObject::connect(&app, &QCoreApplication::aboutToQuit, coreService, &CoreService::shutdown); + + // ======================================================================== + // 创建并注册 D-Bus 服务(仅在 CoreRouter 角色中启用) + // ======================================================================== + if (role == CoreService::Role::CoreRouter) { + const QString serviceName = QStringLiteral("com.softbus.Daemon"); + const QString objectPath = QStringLiteral("/com/softbus/Daemon"); + + IpcDBus* ipc = new IpcDBus(coreService, roleString, &app); + + auto pickConnection = [&]() -> QDBusConnection { + if (dbusBus == QStringLiteral("system")) { + return QDBusConnection::systemBus(); + } + if (dbusBus == QStringLiteral("session")) { + return QDBusConnection::sessionBus(); + } + // auto: 优先 system(更符合 daemon),失败则退回 session(方便本地开发) + QDBusConnection conn = QDBusConnection::systemBus(); + if (conn.isConnected()) { + return conn; + } + return QDBusConnection::sessionBus(); + }; + + QDBusConnection connection = pickConnection(); + if (!connection.isConnected()) { + LOG_ERROR() << "Cannot connect to D-Bus. system error=" + << QDBusConnection::systemBus().lastError().message() + << " session error=" << QDBusConnection::sessionBus().lastError().message(); + return 1; + } + + if (!connection.registerService(serviceName)) { + LOG_ERROR() << "Failed to register D-Bus service:" << serviceName + << "error=" << connection.lastError().message(); + return 1; + } + + if (!connection.registerObject(objectPath, + ipc, + QDBusConnection::ExportAllSlots | QDBusConnection::ExportAllSignals)) { + LOG_ERROR() << "Failed to register D-Bus object:" << objectPath + << "error=" << connection.lastError().message(); + return 1; + } + + LOG_INFO() << "D-Bus ready. bus=" + << (connection.name() == QDBusConnection::systemBus().name() ? "system" : "session") + << " service=" << serviceName + << " object=" << objectPath; + } + + + + // ================================== + // 处理系统信号,确保在接收到 SIGINT 或 SIGTERM 时能够优雅地退出 + // ================================== + + signal(SIGINT, signalHandler); + signal(SIGTERM, signalHandler); + + int ret = app.exec(); + return ret; +} diff --git a/plugins/CMakeLists.txt b/plugins/CMakeLists.txt index 3e0ff6a..1466b74 100644 --- a/plugins/CMakeLists.txt +++ b/plugins/CMakeLists.txt @@ -3,4 +3,4 @@ cmake_minimum_required(VERSION 3.19) add_subdirectory(protocols/modbus_rtu) add_subdirectory(protocols/can_raw) add_subdirectory(protocols/custom_proto) -add_subdirectory(filters) +add_subdirectory(filters) diff --git a/plugins/filters/CMakeLists.txt b/plugins/filters/CMakeLists.txt index 7e81cdd..2288e4e 100644 --- a/plugins/filters/CMakeLists.txt +++ b/plugins/filters/CMakeLists.txt @@ -1 +1 @@ -# Placeholder for filter plugins +# Placeholder for filter plugins diff --git a/plugins/protocols/can_raw/CMakeLists.txt b/plugins/protocols/can_raw/CMakeLists.txt index 9ee7371..818c93b 100644 --- a/plugins/protocols/can_raw/CMakeLists.txt +++ b/plugins/protocols/can_raw/CMakeLists.txt @@ -1,3 +1,3 @@ # Placeholder for can_raw plugin add_library(can_raw SHARED) -set_target_properties(can_raw PROPERTIES OUTPUT_NAME "can_raw") +set_target_properties(can_raw PROPERTIES OUTPUT_NAME "can_raw") diff --git a/plugins/protocols/custom_proto/CMakeLists.txt b/plugins/protocols/custom_proto/CMakeLists.txt index 6bf80de..fe435e3 100644 --- a/plugins/protocols/custom_proto/CMakeLists.txt +++ b/plugins/protocols/custom_proto/CMakeLists.txt @@ -1,3 +1,3 @@ # Placeholder for custom_proto plugin add_library(custom_proto SHARED) -set_target_properties(custom_proto PROPERTIES OUTPUT_NAME "custom_proto") +set_target_properties(custom_proto PROPERTIES OUTPUT_NAME "custom_proto") diff --git a/plugins/protocols/modbus_rtu/CMakeLists.txt b/plugins/protocols/modbus_rtu/CMakeLists.txt index 9c8d48f..fc61891 100644 --- a/plugins/protocols/modbus_rtu/CMakeLists.txt +++ b/plugins/protocols/modbus_rtu/CMakeLists.txt @@ -1,3 +1,3 @@ # Placeholder for modbus_rtu plugin add_library(modbus_rtu SHARED) -set_target_properties(modbus_rtu PROPERTIES OUTPUT_NAME "modbus_rtu") +set_target_properties(modbus_rtu PROPERTIES OUTPUT_NAME "modbus_rtu") diff --git a/src/api/ipc_dbus/IpcDBus.cpp b/src/api/ipc_dbus/IpcDBus.cpp index 6238189..da1cc8b 100644 --- a/src/api/ipc_dbus/IpcDBus.cpp +++ b/src/api/ipc_dbus/IpcDBus.cpp @@ -1,75 +1,75 @@ -#include "IpcDBus.h" - -#include -#include -#include -#include - -#include "src/core/CoreService.h" - -IpcDBus::IpcDBus(CoreService* coreService, const QString& role, QObject* parent) - : QObject(parent), - m_coreService(coreService), - m_role(role) -{ -} - -IpcDBus::~IpcDBus() = default; - -bool IpcDBus::isRunning() const -{ - if (!m_coreService) { - return false; - } - return m_coreService->isInitialized(); -} - -QString IpcDBus::ping() const -{ - return QStringLiteral("pong"); -} - -QString IpcDBus::getVersion() const -{ - return QCoreApplication::applicationVersion(); -} - -QString IpcDBus::getStatus() const -{ - QJsonObject obj; - obj.insert(QStringLiteral("service"), QStringLiteral("com.softbus.Daemon")); - obj.insert(QStringLiteral("objectPath"), QStringLiteral("/com/softbus/Daemon")); - obj.insert(QStringLiteral("interface"), QStringLiteral("com.softbus.Daemon")); - obj.insert(QStringLiteral("pid"), static_cast(QCoreApplication::applicationPid())); - obj.insert(QStringLiteral("role"), m_role); - obj.insert(QStringLiteral("running"), isRunning()); - obj.insert(QStringLiteral("timestampMs"), static_cast(QDateTime::currentMSecsSinceEpoch())); - - const QJsonDocument doc(obj); - return QString::fromUtf8(doc.toJson(QJsonDocument::Compact)); -} - -qint64 IpcDBus::getPid() const -{ - return static_cast(QCoreApplication::applicationPid()); -} - -void IpcDBus::shutdown() -{ - if (m_coreService) { - m_coreService->shutdown(); - } - QCoreApplication::quit(); -} - -bool IpcDBus::reloadConfig() -{ - // 占位:后续移植配置系统时在这里触发 reload - return false; -} - -void IpcDBus::updateLoadInfo() -{ - // 预留:后续可在此周期性采样 CPU/内存/队列长度等指标,并通过 getStatus() 输出 -} - +#include "IpcDBus.h" + +#include +#include +#include +#include + +#include "src/core/CoreService.h" + +IpcDBus::IpcDBus(CoreService* coreService, const QString& role, QObject* parent) + : QObject(parent), + m_coreService(coreService), + m_role(role) +{ +} + +IpcDBus::~IpcDBus() = default; + +bool IpcDBus::isRunning() const +{ + if (!m_coreService) { + return false; + } + return m_coreService->isInitialized(); +} + +QString IpcDBus::ping() const +{ + return QStringLiteral("pong"); +} + +QString IpcDBus::getVersion() const +{ + return QCoreApplication::applicationVersion(); +} + +QString IpcDBus::getStatus() const +{ + QJsonObject obj; + obj.insert(QStringLiteral("service"), QStringLiteral("com.softbus.Daemon")); + obj.insert(QStringLiteral("objectPath"), QStringLiteral("/com/softbus/Daemon")); + obj.insert(QStringLiteral("interface"), QStringLiteral("com.softbus.Daemon")); + obj.insert(QStringLiteral("pid"), static_cast(QCoreApplication::applicationPid())); + obj.insert(QStringLiteral("role"), m_role); + obj.insert(QStringLiteral("running"), isRunning()); + obj.insert(QStringLiteral("timestampMs"), static_cast(QDateTime::currentMSecsSinceEpoch())); + + const QJsonDocument doc(obj); + return QString::fromUtf8(doc.toJson(QJsonDocument::Compact)); +} + +qint64 IpcDBus::getPid() const +{ + return static_cast(QCoreApplication::applicationPid()); +} + +void IpcDBus::shutdown() +{ + if (m_coreService) { + m_coreService->shutdown(); + } + QCoreApplication::quit(); +} + +bool IpcDBus::reloadConfig() +{ + // 占位:后续移植配置系统时在这里触发 reload + return false; +} + +void IpcDBus::updateLoadInfo() +{ + // 预留:后续可在此周期性采样 CPU/内存/队列长度等指标,并通过 getStatus() 输出 +} + diff --git a/src/api/ipc_dbus/IpcDBus.h b/src/api/ipc_dbus/IpcDBus.h index 731a4f2..0945c80 100644 --- a/src/api/ipc_dbus/IpcDBus.h +++ b/src/api/ipc_dbus/IpcDBus.h @@ -1,70 +1,70 @@ -/** - * @file Ipc_dbus.h - * @brief D-Bus 服务接口 - 提供核心服务状态和负载查询 - */ - -#ifndef IPC_DBUS_H -#define IPC_DBUS_H - -#include - -#include -// 前向声明 -class CoreService; -/** - * @brief D-Bus 服务适配器 - 暴露核心服务接口 - */ -class IpcDBus : public QObject -{ - Q_OBJECT - Q_CLASSINFO("D-Bus Interface", "com.softbus.Daemon") - -public: - explicit IpcDBus(CoreService* coreService, const QString& role, QObject* parent = nullptr); - ~IpcDBus(); - -public slots: - /** - * @brief 检查核心服务是否运行 - * @return true 如果核心服务正在运行 - */ - bool isRunning() const; - - QString ping() const; - - QString getVersion() const; - - /** - * @brief 获取核心服务状态信息 - * @return JSON 格式的状态信息 - */ - QString getStatus() const; - - - /** - * @brief 获取守护进程的进程ID - * @return 进程ID,如果无法获取则返回0 - */ - qint64 getPid() const; - - /** - * @brief 关闭守护进程 - */ - void shutdown(); - - bool reloadConfig(); - - - - - -private slots: - void updateLoadInfo(); - -private: - CoreService* m_coreService{nullptr}; // non-owning - QString m_role; -}; - -#endif // IPC_DBUS_H - +/** + * @file Ipc_dbus.h + * @brief D-Bus 服务接口 - 提供核心服务状态和负载查询 + */ + +#ifndef IPC_DBUS_H +#define IPC_DBUS_H + +#include + +#include +// 前向声明 +class CoreService; +/** + * @brief D-Bus 服务适配器 - 暴露核心服务接口 + */ +class IpcDBus : public QObject +{ + Q_OBJECT + Q_CLASSINFO("D-Bus Interface", "com.softbus.Daemon") + +public: + explicit IpcDBus(CoreService* coreService, const QString& role, QObject* parent = nullptr); + ~IpcDBus(); + +public slots: + /** + * @brief 检查核心服务是否运行 + * @return true 如果核心服务正在运行 + */ + bool isRunning() const; + + QString ping() const; + + QString getVersion() const; + + /** + * @brief 获取核心服务状态信息 + * @return JSON 格式的状态信息 + */ + QString getStatus() const; + + + /** + * @brief 获取守护进程的进程ID + * @return 进程ID,如果无法获取则返回0 + */ + qint64 getPid() const; + + /** + * @brief 关闭守护进程 + */ + void shutdown(); + + bool reloadConfig(); + + + + + +private slots: + void updateLoadInfo(); + +private: + CoreService* m_coreService{nullptr}; // non-owning + QString m_role; +}; + +#endif // IPC_DBUS_H + diff --git a/src/core/CoreService.cpp b/src/core/CoreService.cpp index eb5aff0..0650aa1 100644 --- a/src/core/CoreService.cpp +++ b/src/core/CoreService.cpp @@ -1,5 +1,14 @@ #include "CoreService.h" -#include "../utils/logs/logging.h" + +#include +#include +#include +#include +#include +#include + +#include "utils/logs/logging.h" +#include "device_bus/DeviceBus.h" CoreService* CoreService::instance() { @@ -26,6 +35,34 @@ bool CoreService::initialize() } LOG_INFO() << "CoreService initializing"; + + // 1. 解析配置路径(放在用户 home 下的相对固定目录:~/softbus/config) + const QString configPath = + QDir::homePath() + QStringLiteral("/softbus/config/daemon_config.json"); + + QFile f(configPath); + if (!f.open(QIODevice::ReadOnly | QIODevice::Text)) { + LOG_ERROR() << "CoreService: failed to open" << configPath; + return false; + } + + const QByteArray data = f.readAll(); + f.close(); + + QJsonParseError pe; + const QJsonDocument doc = QJsonDocument::fromJson(data, &pe); + if (pe.error != QJsonParseError::NoError || !doc.isObject()) { + LOG_ERROR() << "CoreService: invalid JSON in" << configPath << ":" << pe.errorString(); + return false; + } + + const QJsonObject root = doc.object(); + + // 2. 初始化 device_bus(交给 DeviceBus facade 处理具体设备) + if (!softbus::device_bus::DeviceBus::instance().initialize(root)) { + return false; + } + m_initialized = true; return true; } @@ -38,6 +75,7 @@ void CoreService::shutdown() } LOG_INFO() << "CoreService shutting down"; + softbus::device_bus::DeviceBus::instance().shutdown(); m_initialized = false; } diff --git a/src/core/CoreService.h b/src/core/CoreService.h index a6888b4..8ddd081 100644 --- a/src/core/CoreService.h +++ b/src/core/CoreService.h @@ -2,6 +2,7 @@ #include + class CoreService : public QObject { Q_OBJECT diff --git a/src/core/device/DeviceTypes.cpp b/src/core/device/DeviceTypes.cpp new file mode 100644 index 0000000..1aa9d2e --- /dev/null +++ b/src/core/device/DeviceTypes.cpp @@ -0,0 +1,39 @@ +#include "core/device/DeviceTypes.h" + +namespace softbus::core::device +{ + +DeviceKind kindFromType(const QString& typeStr) +{ + const QString t = typeStr.trimmed().toLower(); + if (t == QStringLiteral("serial")) return DeviceKind::Serial; + if (t == QStringLiteral("can")) return DeviceKind::Can; + if (t == QStringLiteral("ethernet") || t == QStringLiteral("network")) return DeviceKind::Network; + if (t == QStringLiteral("virtual")) return DeviceKind::Virtual; + if (t == QStringLiteral("distributed")) return DeviceKind::Distributed; + return DeviceKind::Unknown; +} + +DeviceKind inferDeviceKindFromEndpoint(const QString& endpoint) +{ + const QString ep = endpoint.trimmed(); + if (ep.startsWith(QStringLiteral("/dev/tty"))) return DeviceKind::Serial; + if (ep.startsWith(QStringLiteral("can"))) return DeviceKind::Can; + if (ep.startsWith(QStringLiteral("tcp://")) || ep.startsWith(QStringLiteral("udp://"))) return DeviceKind::Network; + return DeviceKind::Unknown; +} + +QString driverKeyFor(DeviceKind kind) +{ + switch (kind) { + case DeviceKind::Serial: return QStringLiteral("serial_qt"); + case DeviceKind::Can: return QStringLiteral("can_socketcan"); + case DeviceKind::Network: return QStringLiteral("tcp_qt"); + case DeviceKind::Virtual: return QStringLiteral("virtual_device"); + case DeviceKind::Distributed: return QStringLiteral("distributed_node"); + default: return QStringLiteral("unknown"); + } +} + +} // namespace softbus::core::device + diff --git a/src/core/device/DeviceTypes.h b/src/core/device/DeviceTypes.h new file mode 100644 index 0000000..e829b73 --- /dev/null +++ b/src/core/device/DeviceTypes.h @@ -0,0 +1,69 @@ +#pragma once + +#include +#include +#include +#include + +namespace softbus::core::device +{ + +enum class DeviceKind { + Serial, + Can, + Network, + Virtual, + Distributed, + Unknown, +}; + +struct DeviceInfo +{ + int id{0}; + QString endpoint; + QString name; + QString type; // "serial" / "can" / "network" / ... + int address{0}; + QString protocol; + QString protocolDetail; + QJsonObject properties; + QString status{QStringLiteral("online")}; + bool isActive{true}; + QDateTime lastSeen; + + QString toJson() const + { + QJsonObject obj; + obj[QStringLiteral("id")] = id; + obj[QStringLiteral("endpoint")] = endpoint; + obj[QStringLiteral("name")] = name; + obj[QStringLiteral("type")] = type; + obj[QStringLiteral("address")] = address; + obj[QStringLiteral("protocol")] = protocol; + obj[QStringLiteral("protocol_detail")] = protocolDetail; + obj[QStringLiteral("properties")] = properties; + obj[QStringLiteral("status")] = status; + obj[QStringLiteral("isActive")] = isActive; + if (lastSeen.isValid()) { + obj[QStringLiteral("lastSeen")] = lastSeen.toString(Qt::ISODate); + } + const QJsonDocument doc(obj); + return QString::fromUtf8(doc.toJson(QJsonDocument::Compact)); + } +}; + +struct BusMessage +{ + QString id; + QString source; + QString destination; + QJsonObject payload; + qint64 timestamp{0}; +}; + +DeviceKind kindFromType(const QString& typeStr); +DeviceKind inferDeviceKindFromEndpoint(const QString& endpoint); +QString driverKeyFor(DeviceKind kind); + +} // namespace softbus::core::device + diff --git a/src/core/memory/LockFreeQueue.h b/src/core/memory/LockFreeQueue.h index 077122c..633da49 100644 --- a/src/core/memory/LockFreeQueue.h +++ b/src/core/memory/LockFreeQueue.h @@ -4,4 +4,4 @@ class LockFreeQueue { public: LockFreeQueue() = default; -}; +}; diff --git a/src/core/memory/MemoryPool.h b/src/core/memory/MemoryPool.h index 2c1ef88..47f07cf 100644 --- a/src/core/memory/MemoryPool.h +++ b/src/core/memory/MemoryPool.h @@ -4,4 +4,4 @@ class MemoryPool { public: MemoryPool() = default; -}; +}; diff --git a/src/core/metadata/DataTrace.h b/src/core/metadata/DataTrace.h index 9ecbce0..87c9e41 100644 --- a/src/core/metadata/DataTrace.h +++ b/src/core/metadata/DataTrace.h @@ -2,4 +2,4 @@ // Placeholder for data trace model. struct DataTrace { -}; +}; diff --git a/src/core/metadata/Metadata.h b/src/core/metadata/Metadata.h index 8a06787..3150c20 100644 --- a/src/core/metadata/Metadata.h +++ b/src/core/metadata/Metadata.h @@ -2,4 +2,4 @@ // Placeholder for metadata model. struct Metadata { -}; +}; diff --git a/src/core/plugin_system/IProtocolPlugin.h b/src/core/plugin_system/IProtocolPlugin.h index 6404102..ab70877 100644 --- a/src/core/plugin_system/IProtocolPlugin.h +++ b/src/core/plugin_system/IProtocolPlugin.h @@ -4,4 +4,4 @@ class IProtocolPlugin { public: virtual ~IProtocolPlugin() = default; -}; +}; diff --git a/src/core/plugin_system/PluginManager.h b/src/core/plugin_system/PluginManager.h index 64946c1..251dae4 100644 --- a/src/core/plugin_system/PluginManager.h +++ b/src/core/plugin_system/PluginManager.h @@ -4,4 +4,4 @@ class PluginManager { public: PluginManager() = default; -}; +}; diff --git a/src/device_bus/DeviceBus.cpp b/src/device_bus/DeviceBus.cpp new file mode 100644 index 0000000..6cfeabb --- /dev/null +++ b/src/device_bus/DeviceBus.cpp @@ -0,0 +1,30 @@ +#include "device_bus/DeviceBus.h" + +#include "device_bus/manager/DeviceBusManager.h" + +namespace softbus::device_bus { + +class DeviceBus::Impl { +public: + DeviceBusManager manager; +}; + +DeviceBus &DeviceBus::instance() { + static DeviceBus inst; + return inst; +} + +DeviceBus::DeviceBus() : d(new Impl()) {} + +DeviceBus::~DeviceBus() { + delete d; + d = nullptr; +} + +bool DeviceBus::initialize(const QJsonObject &rootConfig) { + return d->manager.initialize(rootConfig); +} + +void DeviceBus::shutdown() { d->manager.shutdown(); } + +} // namespace softbus::device_bus diff --git a/src/device_bus/DeviceBus.h b/src/device_bus/DeviceBus.h new file mode 100644 index 0000000..694044f --- /dev/null +++ b/src/device_bus/DeviceBus.h @@ -0,0 +1,24 @@ +#pragma once + +#include + +namespace softbus::device_bus { + +class DeviceBus { +public: + static DeviceBus &instance(); + + bool initialize(const QJsonObject &rootConfig); + void shutdown(); + +private: + DeviceBus(); + ~DeviceBus(); + DeviceBus(const DeviceBus &) = delete; + DeviceBus &operator=(const DeviceBus &) = delete; + + class Impl; + Impl *d; +}; + +} // namespace softbus::device_bus diff --git a/src/device_bus/capabilities/DriverCapabilityProvider.cpp b/src/device_bus/capabilities/DriverCapabilityProvider.cpp new file mode 100644 index 0000000..bec6595 --- /dev/null +++ b/src/device_bus/capabilities/DriverCapabilityProvider.cpp @@ -0,0 +1,77 @@ +#include "device_bus/capabilities/DriverCapabilityProvider.h" + +#include +#include +#include + +#include "utils/logs/logging.h" + +bool DriverCapabilityProvider::loadFromFile(const QString& jsonPath, QString* errorMessage) +{ + m_defaults = QJsonObject(); + m_enums = QJsonObject(); + + QFile f(jsonPath); + if (!f.open(QIODevice::ReadOnly | QIODevice::Text)) { + if (errorMessage) { + *errorMessage = QStringLiteral("Failed to open capability file: %1").arg(jsonPath); + } + return false; + } + + const QByteArray data = f.readAll(); + f.close(); + + QJsonParseError pe; + const QJsonDocument doc = QJsonDocument::fromJson(data, &pe); + if (pe.error != QJsonParseError::NoError || !doc.isObject()) { + if (errorMessage) { + *errorMessage = QStringLiteral("Invalid JSON in capability file %1: %2") + .arg(jsonPath, pe.errorString()); + } + return false; + } + + const QJsonObject root = doc.object(); + m_defaults = root.value(QStringLiteral("defaults")).toObject(); + m_enums = root.value(QStringLiteral("enums")).toObject(); + + LOG_INFO() << "DriverCapabilityProvider loaded from" << jsonPath; + return true; +} + +QJsonObject DriverCapabilityProvider::mergeAndValidateParams(const QJsonObject& nodeParams) const +{ + // 1. 从 defaults 拷贝一份出来 + QJsonObject result = m_defaults; + + // 2. 覆盖节点里的显式参数 + for (auto it = nodeParams.constBegin(); it != nodeParams.constEnd(); ++it) { + const QString key = it.key(); + const QJsonValue value = it.value(); + + // 如果存在枚举限制,则先校验 + const QJsonValue enumVal = m_enums.value(key); + if (enumVal.isArray()) { + const QJsonArray arr = enumVal.toArray(); + bool ok = false; + for (const QJsonValue& candidate : arr) { + if (candidate == value) { + ok = true; + break; + } + } + if (!ok) { + LOG_WARNING() << "DriverCapabilityProvider: param" << key + << "value" << value.toVariant() + << "not in allowed enum, keep default"; + continue; // 不覆盖默认值 + } + } + + result.insert(key, value); + } + + return result; +} + diff --git a/src/device_bus/capabilities/DriverCapabilityProvider.h b/src/device_bus/capabilities/DriverCapabilityProvider.h new file mode 100644 index 0000000..a740974 --- /dev/null +++ b/src/device_bus/capabilities/DriverCapabilityProvider.h @@ -0,0 +1,21 @@ +#pragma once + +#include +#include + +// 负责加载 drivers 下的 parameters.json,并对节点 params 做默认值合并与简单枚举校验 + +class DriverCapabilityProvider +{ +public: + // 从给定路径加载能力描述(如 "src/hardware/drivers/serial/parameters.json") + bool loadFromFile(const QString& jsonPath, QString* errorMessage = nullptr); + + // 将节点 params 与 defaults 合并,并按 enums 做简单校验 + QJsonObject mergeAndValidateParams(const QJsonObject& nodeParams) const; + +private: + QJsonObject m_defaults; + QJsonObject m_enums; +}; + diff --git a/src/device_bus/manager/DeviceBusManager.cpp b/src/device_bus/manager/DeviceBusManager.cpp new file mode 100644 index 0000000..e24e104 --- /dev/null +++ b/src/device_bus/manager/DeviceBusManager.cpp @@ -0,0 +1,124 @@ +#include "device_bus/manager/DeviceBusManager.h" + +#include +#include + +#include "hardware/drivers/serial/SerialCapabilities.h" +#include "core/device/DeviceTypes.h" +#include "utils/logs/logging.h" + +using softbus::hardware::drivers::serial::SerialQtDriver; +namespace serial_cap = softbus::hardware::drivers::serial::capabilities; + +bool DeviceBusManager::initialize(const QJsonObject& rootConfig) +{ + // 加载设备树 + QString treeError; + if (!m_treeModel.loadFromDaemonConfig(rootConfig, &treeError)) { + LOG_ERROR() << "DeviceBusManager: failed to load device_tree:" << treeError; + return false; + } + + const auto nodes = m_treeModel.nodes(); + for (const auto& n : nodes) { + if (!n.enabled) continue; + auto kind = softbus::core::device::kindFromType(n.type); + if (kind == softbus::core::device::DeviceKind::Unknown) { + kind = softbus::core::device::inferDeviceKindFromEndpoint(n.endpoint); + } + + if (kind == softbus::core::device::DeviceKind::Serial) { + initializeSerialDriver(n.endpoint, n.params); + m_deviceEndpointsMap.insert(n.endpoint, QStringLiteral("serial")); + } else { + LOG_WARNING() << "DeviceBusManager: skip unsupported kind for endpoint=" << n.endpoint + << "type=" << n.type; + } + } + + return true; +} + +void DeviceBusManager::shutdown() +{ + // 关闭并销毁所有串口驱动 + const auto keys = m_serialDriversMap.keys(); + for (const auto& endpoint : keys) { + shutdownSerialDriver(endpoint); + } +} + +void DeviceBusManager::initializeSerialDriver(const QString& endpoint,const QJsonObject& params) +{ + if (m_serialDriversMap.contains(endpoint)) { + LOG_WARNING() << "DeviceBusManager: serial driver already exists for" << endpoint; + return; + } + + // 合并参数(defaults + enum 校验) + serial_cap::SerialDefaults def = serial_cap::kDefaults; + + int baud = params.value(QStringLiteral("baudRate")).toInt(def.baudRate); + if (!serial_cap::isValidBaud(baud)) baud = def.baudRate; + + int dataBits = params.value(QStringLiteral("dataBits")).toInt(def.dataBits); + if (!serial_cap::isValidDataBits(dataBits)) dataBits = def.dataBits; + + QString parityStr = params.value(QStringLiteral("parity")).toString(QLatin1String(def.parity)); + if (!serial_cap::isValidParity(parityStr)) parityStr = QLatin1String(def.parity); + + int stopBitsVal = params.value(QStringLiteral("stopBits")).toInt(def.stopBits); + if (!serial_cap::isValidStopBits(stopBitsVal)) stopBitsVal = def.stopBits; + + QString flowStr = params.value(QStringLiteral("flowControl")).toString(QLatin1String(def.flowControl)); + if (!serial_cap::isValidFlowControl(flowStr)) flowStr = QLatin1String(def.flowControl); + + QJsonObject merged; + merged.insert(QStringLiteral("baudRate"), baud); + merged.insert(QStringLiteral("dataBits"), dataBits); + merged.insert(QStringLiteral("parity"), parityStr); + merged.insert(QStringLiteral("stopBits"), stopBitsVal); + merged.insert(QStringLiteral("flowControl"), flowStr); + + LOG_INFO() << "DeviceBusManager: init serial endpoint=" << endpoint + << "params=" << QJsonDocument(merged).toJson(QJsonDocument::Compact); + + auto driver = new SerialQtDriver(nullptr); + driver->SetBaudRate(static_cast(baud)); + driver->SetDataBits(static_cast(dataBits)); + + QSerialPort::Parity parity = QSerialPort::NoParity; + if (parityStr == QStringLiteral("even")) { + parity = QSerialPort::EvenParity; + } else if (parityStr == QStringLiteral("odd")) { + parity = QSerialPort::OddParity; + } + driver->SetParity(parity); + + QSerialPort::StopBits stopBits = (stopBitsVal == 2) ? QSerialPort::TwoStop : QSerialPort::OneStop; + driver->SetStopBits(stopBits); + + QSerialPort::FlowControl flow = QSerialPort::NoFlowControl; + if (flowStr == QStringLiteral("hardware")) { + flow = QSerialPort::HardwareControl; + } else if (flowStr == QStringLiteral("software")) { + flow = QSerialPort::SoftwareControl; + } + driver->SetFlowControl(flow); + + // 按你当前策略:初始化时就打开串口 + driver->Open(endpoint.toStdString()); + + m_serialDriversMap.insert(endpoint, driver); + m_serialDriversList.push_back(driver); +} + +void DeviceBusManager::shutdownSerialDriver(const QString& endpoint) +{ + auto driver = m_serialDriversMap.take(endpoint); + if (driver) { + driver->Close(); + delete driver; + m_serialDriversList.removeAll(driver); + } +} \ No newline at end of file diff --git a/src/device_bus/manager/DeviceBusManager.h b/src/device_bus/manager/DeviceBusManager.h new file mode 100644 index 0000000..e6c811a --- /dev/null +++ b/src/device_bus/manager/DeviceBusManager.h @@ -0,0 +1,42 @@ +#pragma once + +#include +#include +#include +#include +#include + +#include "device_bus/tree/DeviceTreeModel.h" +#include "hardware/drivers/serial/SerialQtDriver.h" + +class DeviceBusManager +{ +public: + bool initialize(const QJsonObject& rootConfig); + void shutdown(); + +private: + void initializeSerialDriver(const QString& endpoint, const QJsonObject& params); + void shutdownSerialDriver(const QString& endpoint); + // void initializeCanDriver(); + // void shutdownCanDriver(); + // void initializeTcpDriver(); + // void shutdownTcpDriver(); + // void initializeUdpDriver(); + // void shutdownUdpDriver(); + + + +private: + DeviceTreeModel m_treeModel; + // 添加map来记住所有设备的endpoint和type的映射 + QMap m_deviceEndpointsMap; + + QMap m_serialDriversMap; + QList m_serialDriversList; + + // std::vector m_canDrivers; + // std::vector m_tcpDrivers; + // std::vector m_udpDrivers; +}; + diff --git a/src/device_bus/registry/IDeviceRegistry.h b/src/device_bus/registry/IDeviceRegistry.h new file mode 100644 index 0000000..e6c7a14 --- /dev/null +++ b/src/device_bus/registry/IDeviceRegistry.h @@ -0,0 +1,24 @@ +#pragma once + +#include +#include + +#include "core/device/DeviceTypes.h" + +namespace softbus::device_bus::registry +{ + +class IDeviceRegistry +{ +public: + virtual ~IDeviceRegistry() = default; + + virtual void registerDevice(const softbus::core::device::DeviceInfo& info) = 0; + virtual void unregisterDevice(int id) = 0; + + virtual std::optional findById(int id) const = 0; + virtual std::vector listDevices() const = 0; +}; + +} // namespace softbus::device_bus::registry + diff --git a/src/device_bus/tree/DeviceTreeModel.cpp b/src/device_bus/tree/DeviceTreeModel.cpp new file mode 100644 index 0000000..ca55915 --- /dev/null +++ b/src/device_bus/tree/DeviceTreeModel.cpp @@ -0,0 +1,84 @@ +#include "device_bus/tree/DeviceTreeModel.h" + +#include + +#include "utils/logs/logging.h" + +bool DeviceTreeModel::loadFromDaemonConfig(const QJsonObject& root, QString* errorMessage) +{ + m_nodes.clear(); + m_indexById.clear(); + + if (!root.contains(QStringLiteral("device_tree"))) { + if (errorMessage) { + *errorMessage = QStringLiteral("daemon_config.json missing 'device_tree' field"); + } + return false; + } + + const QJsonValue treeVal = root.value(QStringLiteral("device_tree")); + if (!treeVal.isArray()) { + if (errorMessage) { + *errorMessage = QStringLiteral("'device_tree' must be an array"); + } + return false; + } + + const QJsonArray arr = treeVal.toArray(); + m_nodes.reserve(arr.size()); + + for (const QJsonValue& v : arr) { + if (!v.isObject()) { + LOG_WARNING() << "DeviceTreeModel: skip non-object node in device_tree"; + continue; + } + const QJsonObject obj = v.toObject(); + + DeviceTreeNode node; + node.id = obj.value(QStringLiteral("id")).toString(); + node.name = obj.value(QStringLiteral("name")).toString(); + node.type = obj.value(QStringLiteral("type")).toString(); + node.endpoint = obj.value(QStringLiteral("endpoint")).toString(); + node.driver = obj.value(QStringLiteral("driver")).toString(); + node.capabilitiesRef = obj.value(QStringLiteral("capabilitiesRef")).toString(); + node.params = obj.value(QStringLiteral("params")).toObject(); + node.enabled = obj.value(QStringLiteral("enabled")).toBool(true); + + // children: array of ids + const QJsonValue childrenVal = obj.value(QStringLiteral("children")); + if (childrenVal.isArray()) { + const QJsonArray childrenArr = childrenVal.toArray(); + for (const QJsonValue& c : childrenArr) { + if (c.isString()) { + node.childrenIds.push_back(c.toString()); + } + } + } + + if (node.id.isEmpty()) { + LOG_WARNING() << "DeviceTreeModel: node without id, skipping"; + continue; + } + + const int index = m_nodes.size(); + m_nodes.push_back(node); + m_indexById.insert(node.id, index); + } + + LOG_INFO() << "DeviceTreeModel loaded" << m_nodes.size() << "nodes from daemon_config"; + return true; +} + +const DeviceTreeNode* DeviceTreeModel::findById(const QString& id) const +{ + const auto it = m_indexById.constFind(id); + if (it == m_indexById.constEnd()) { + return nullptr; + } + const int index = it.value(); + if (index < 0 || index >= m_nodes.size()) { + return nullptr; + } + return &m_nodes.at(index); +} + diff --git a/src/device_bus/tree/DeviceTreeModel.h b/src/device_bus/tree/DeviceTreeModel.h new file mode 100644 index 0000000..7c5ea48 --- /dev/null +++ b/src/device_bus/tree/DeviceTreeModel.h @@ -0,0 +1,37 @@ +#pragma once + +#include +#include +#include +#include + +// 轻量级设备树模型:从 daemon_config.json 的 device_tree 字段加载 + +struct DeviceTreeNode +{ + QString id; + QString name; + QString type; + QString endpoint; + QString driver; + QString capabilitiesRef; + QJsonObject params; + QVector childrenIds; + bool enabled{true}; +}; + +class DeviceTreeModel +{ +public: + // 从给定的 JSON 根对象(包含 device_tree 字段)加载 + bool loadFromDaemonConfig(const QJsonObject& root, QString* errorMessage = nullptr); + + const QVector& nodes() const { return m_nodes; } + + const DeviceTreeNode* findById(const QString& id) const; + +private: + QVector m_nodes; + QHash m_indexById; +}; + diff --git a/src/devices/base/IDevice.h b/src/devices/base/IDevice.h new file mode 100644 index 0000000..1d75dd6 --- /dev/null +++ b/src/devices/base/IDevice.h @@ -0,0 +1,17 @@ +#pragma once + +#include "core/device/DeviceTypes.h" + +namespace softbus::devices +{ + +class IDevice +{ +public: + virtual ~IDevice() = default; + + virtual softbus::core::device::DeviceInfo deviceInfo() const = 0; +}; + +} // namespace softbus::devices + diff --git a/src/devices/devicesType.h b/src/devices/devicesType.h new file mode 100644 index 0000000..2f0c0ae --- /dev/null +++ b/src/devices/devicesType.h @@ -0,0 +1,14 @@ +#pragma once + +#include + +namespace softbus::devices::physical +{ + enum class Type + { + Serial, + Can, + Tcp, + Udp, + }; +} \ No newline at end of file diff --git a/src/hardware/drivers/serial/SerialCapabilities.h b/src/hardware/drivers/serial/SerialCapabilities.h new file mode 100644 index 0000000..1058b0a --- /dev/null +++ b/src/hardware/drivers/serial/SerialCapabilities.h @@ -0,0 +1,67 @@ +#pragma once + +#include +#include + +namespace softbus::hardware::drivers::serial::capabilities +{ + +struct SerialDefaults +{ + int baudRate = 115200; + int dataBits = 8; + const char* parity = "none"; + int stopBits = 1; + const char* flowControl = "none"; +}; + +inline constexpr SerialDefaults kDefaults{}; + +inline constexpr std::array kBaudRates{9600, 19200, 38400, 57600, 115200}; +inline constexpr std::array kDataBits{5, 6, 7, 8}; +inline constexpr std::array kParity{"none", "even", "odd"}; +inline constexpr std::array kStopBits{1, 2}; +inline constexpr std::array kFlowControl{"none", "hardware", "software"}; + +inline bool isValidBaud(int v) +{ + for (int b : kBaudRates) { + if (b == v) return true; + } + return false; +} + +inline bool isValidDataBits(int v) +{ + for (int b : kDataBits) { + if (b == v) return true; + } + return false; +} + +inline bool isValidParity(const QString& s) +{ + for (const char* p : kParity) { + if (s == QLatin1String(p)) return true; + } + return false; +} + +inline bool isValidStopBits(int v) +{ + for (int b : kStopBits) { + if (b == v) return true; + } + return false; +} + +inline bool isValidFlowControl(const QString& s) +{ + for (const char* f : kFlowControl) { + if (s == QLatin1String(f)) return true; + } + return false; +} + +} // namespace softbus::hardware::drivers::serial::capabilities + diff --git a/src/hardware/drivers/serial/SerialQtDriver.cpp b/src/hardware/drivers/serial/SerialQtDriver.cpp new file mode 100644 index 0000000..a427535 --- /dev/null +++ b/src/hardware/drivers/serial/SerialQtDriver.cpp @@ -0,0 +1,138 @@ +#include "hardware/drivers/serial/SerialQtDriver.h" + +#include + +#include "utils/logs/logging.h" + +namespace softbus::hardware::drivers::serial +{ + +SerialQtDriver::SerialQtDriver(QObject* parent) + : QObject(parent), + m_port(this) +{ + connect(&m_port, &QSerialPort::readyRead, this, &SerialQtDriver::handleReadyRead); + connect(&m_port, &QSerialPort::errorOccurred, this, &SerialQtDriver::handleError); +} + +SerialQtDriver::~SerialQtDriver() +{ + Close(); +} + +bool SerialQtDriver::Open(const std::string& endpoint) +{ + if (m_port.isOpen()) { + return true; + } + + m_port.setPortName(QString::fromStdString(endpoint)); + if (!m_port.open(QIODevice::ReadWrite)) { + if (m_errorCallback) { + m_errorCallback(m_port.errorString().toStdString()); + } + LOG_WARNING() << "SerialQtDriver: failed to open port" << m_port.portName() << ":" << m_port.errorString(); + return false; + } + + LOG_DEBUG() << "SerialQtDriver: opened port" << m_port.portName(); + return true; +} + +void SerialQtDriver::Close() +{ + if (m_port.isOpen()) { + const QString name = m_port.portName(); + m_port.close(); + LOG_DEBUG() << "SerialQtDriver: closed port" << name; + } +} + +bool SerialQtDriver::Write(const std::vector& data) +{ + if (!m_port.isOpen()) { + return false; + } + + const QByteArray bytes(reinterpret_cast(data.data()), static_cast(data.size())); + const qint64 written = m_port.write(bytes); + if (written != bytes.size()) { + LOG_WARNING() << "SerialQtDriver: partial write on" << m_port.portName() << "written" << written << "of" + << bytes.size(); + return false; + } + return true; +} + +void SerialQtDriver::SetReadCallback(ReadCallback cb) +{ + m_readCallback = std::move(cb); +} + +void SerialQtDriver::SetErrorCallback(ErrorCallback cb) +{ + m_errorCallback = std::move(cb); +} + +void SerialQtDriver::SetBaudRate(QSerialPort::BaudRate baud) +{ + m_port.setBaudRate(baud); +} + +void SerialQtDriver::SetDataBits(QSerialPort::DataBits bits) +{ + m_port.setDataBits(bits); +} + +void SerialQtDriver::SetParity(QSerialPort::Parity parity) +{ + m_port.setParity(parity); +} + +void SerialQtDriver::SetStopBits(QSerialPort::StopBits stopBits) +{ + m_port.setStopBits(stopBits); +} + +void SerialQtDriver::SetFlowControl(QSerialPort::FlowControl flow) +{ + m_port.setFlowControl(flow); +} + +void SerialQtDriver::handleReadyRead() +{ + if (!m_readCallback) { + const QByteArray data = m_port.readAll(); + LOG_DEBUG() << "SerialQtDriver: dropped" << data.size() << "bytes on" << m_port.portName() + << "because no read callback is set"; + return; + } + + const QByteArray data = m_port.readAll(); + if (data.isEmpty()) { + return; + } + + std::vector buffer(reinterpret_cast(data.constData()), + reinterpret_cast(data.constData()) + data.size()); + m_readCallback(buffer); +} + +void SerialQtDriver::handleError(QSerialPort::SerialPortError error) +{ + if (error == QSerialPort::NoError) { + return; + } + + const QString msg = + QStringLiteral("SerialQtDriver error on %1: %2").arg(m_port.portName(), m_port.errorString()); + + LOG_WARNING() << msg; + + if (m_errorCallback) { + m_errorCallback(msg.toStdString()); + } +} + +} // namespace softbus::hardware::drivers::serial + diff --git a/src/hardware/drivers/serial/SerialQtDriver.h b/src/hardware/drivers/serial/SerialQtDriver.h new file mode 100644 index 0000000..03fe2ec --- /dev/null +++ b/src/hardware/drivers/serial/SerialQtDriver.h @@ -0,0 +1,85 @@ +#pragma once + +#include +#include +#include + +#include "hardware/interfaces/IStreamDriver.h" + +// 这里的串口的唯一标识是串口的端口名,如 /dev/ttyUSB0, can0, tcp://... +// 串口的endpoint是串口的端口名,如 /dev/ttyUSB0, can0, tcp://... +// 使用说明: +// 1. 创建一个SerialQtDriver对象 +// 2. 调用Open方法打开串口 +// 3. 调用Write方法写数据 +// 4. 调用SetReadCallback方法设置读回调 +// 5. 调用SetErrorCallback方法设置错误回调 +// 6. 调用Close方法关闭串口 +// 7. 调用SetBaudRate方法设置波特率 +// 8. 调用SetDataBits方法设置数据位 +// 9. 调用SetParity方法设置校验位 +// 10. 调用SetStopBits方法设置停止位 +// 11. 调用SetFlowControl方法设置流控制 +// eg: +// SerialQtDriver driver; +// driver.Open("/dev/ttyUSB0"); +// driver.Write({0x01, 0x02, 0x03}); +// driver.SetReadCallback([](const std::vector& data) { +// std::cout << "read data: " << data << std::endl; +// }); +// driver.SetErrorCallback([](const std::string& error) { +// std::cout << "error: " << error << std::endl; +// }); +// driver.Close(); +// 12. 调用SetBaudRate方法设置波特率 +// 13. 调用SetDataBits方法设置数据位 +// 14. 调用SetParity方法设置校验位 +// 15. 调用SetStopBits方法设置停止位 +// 16. 调用SetFlowControl方法设置流控制 +// eg: +// driver.SetBaudRate(QSerialPort::Baud115200); +// driver.SetDataBits(QSerialPort::Data8); +// driver.SetParity(QSerialPort::NoParity); +// driver.SetStopBits(QSerialPort::OneStop); +// driver.SetFlowControl(QSerialPort::NoFlowControl); +// driver.Close(); + +namespace softbus::hardware::drivers::serial +{ + +// 基于 Qt 的串口驱动实现:只负责串口 open/read/write,不包含设备注册、数据库或协议逻辑 +class SerialQtDriver : public QObject, public softbus::hardware::interfaces::IStreamDriver +{ + Q_OBJECT + +public: + explicit SerialQtDriver(QObject* parent = nullptr); + ~SerialQtDriver() override; + + bool Open(const std::string& endpoint) override; + void Close() override; + + bool Write(const std::vector& data) override; + + void SetReadCallback(ReadCallback cb) override; + void SetErrorCallback(ErrorCallback cb) override; + + // 允许上层配置串口参数(最小集合) + void SetBaudRate(QSerialPort::BaudRate baud); + void SetDataBits(QSerialPort::DataBits bits); + void SetParity(QSerialPort::Parity parity); + void SetStopBits(QSerialPort::StopBits stopBits); + void SetFlowControl(QSerialPort::FlowControl flow); + +private slots: + void handleReadyRead(); + void handleError(QSerialPort::SerialPortError error); + +private: + QSerialPort m_port; + ReadCallback m_readCallback; + ErrorCallback m_errorCallback; +}; + +} // namespace softbus::hardware::drivers::serial + diff --git a/src/hardware/interfaces/IDeviceWatcher.h b/src/hardware/interfaces/IDeviceWatcher.h new file mode 100644 index 0000000..978759a --- /dev/null +++ b/src/hardware/interfaces/IDeviceWatcher.h @@ -0,0 +1,37 @@ +#pragma once + +#ifdef __cplusplus + +#include +#include + +namespace softbus::hardware::interfaces +{ + +struct DiscoveredDevice +{ + std::string id; // 稳定 ID(如序列号、路径) + std::string endpoint; // 打开所需的 endpoint(如 /dev/ttyUSB0, can0, tcp://...) + std::string type; // 设备类型:serial / can / ethernet / usb 等 +}; + +// 设备发现 / 监控接口:负责发现插拔事件,不负责创建设备或驱动实例 +class IDeviceWatcher +{ +public: + using DeviceAttachedCallback = std::function; + using DeviceDetachedCallback = std::function; + + virtual ~IDeviceWatcher() = default; + + virtual bool Start() = 0; + virtual void Stop() = 0; + + virtual void SetDeviceAttachedCallback(DeviceAttachedCallback cb) = 0; + virtual void SetDeviceDetachedCallback(DeviceDetachedCallback cb) = 0; +}; + +} // namespace softbus::hardware::interfaces + +#endif // __cplusplus + diff --git a/src/hardware/interfaces/IFrameDriver.h b/src/hardware/interfaces/IFrameDriver.h new file mode 100644 index 0000000..91c28ec --- /dev/null +++ b/src/hardware/interfaces/IFrameDriver.h @@ -0,0 +1,41 @@ +#pragma once + +#ifdef __cplusplus + +#include +#include +#include +#include + +namespace softbus::hardware::interfaces +{ + +struct Frame +{ + std::vector payload; + std::uint32_t id{0}; // 如 CAN ID + std::uint64_t timestamp{0}; +}; + +// 面向帧设备(如 CAN 总线)的统一驱动接口 +class IFrameDriver +{ +public: + using FrameCallback = std::function; + using ErrorCallback = std::function; + + virtual ~IFrameDriver() = default; + + virtual bool Open(const std::string& endpoint) = 0; + virtual void Close() = 0; + + virtual bool WriteFrame(const Frame& frame) = 0; + + virtual void SetFrameCallback(FrameCallback cb) = 0; + virtual void SetErrorCallback(ErrorCallback cb) = 0; +}; + +} // namespace softbus::hardware::interfaces + +#endif // __cplusplus + diff --git a/src/hardware/interfaces/IStreamDriver.h b/src/hardware/interfaces/IStreamDriver.h new file mode 100644 index 0000000..8874221 --- /dev/null +++ b/src/hardware/interfaces/IStreamDriver.h @@ -0,0 +1,34 @@ +#pragma once + +#ifdef __cplusplus + +#include +#include +#include +#include + +namespace softbus::hardware::interfaces +{ + +// 面向字节流设备的统一驱动接口:串口 / TCP / UDP 等 +class IStreamDriver +{ +public: + using ReadCallback = std::function&)>; + using ErrorCallback = std::function; + + virtual ~IStreamDriver() = default; + + virtual bool Open(const std::string& endpoint) = 0; + virtual void Close() = 0; + + virtual bool Write(const std::vector& data) = 0; + + virtual void SetReadCallback(ReadCallback cb) = 0; + virtual void SetErrorCallback(ErrorCallback cb) = 0; +}; + +} // namespace softbus::hardware::interfaces + +#endif // __cplusplus + diff --git a/src/message_bus/pipeline/PipelineContext.h b/src/message_bus/pipeline/PipelineContext.h index 0a2db3e..c597f7a 100644 --- a/src/message_bus/pipeline/PipelineContext.h +++ b/src/message_bus/pipeline/PipelineContext.h @@ -4,4 +4,4 @@ class PipelineContext { public: PipelineContext() = default; -}; +}; diff --git a/src/message_bus/pipeline/PipelineEngine.h b/src/message_bus/pipeline/PipelineEngine.h index 83d21c4..2d51e69 100644 --- a/src/message_bus/pipeline/PipelineEngine.h +++ b/src/message_bus/pipeline/PipelineEngine.h @@ -4,4 +4,4 @@ class PipelineEngine { public: PipelineEngine() = default; -}; +}; diff --git a/src/utils/logs/LogStream.h b/src/utils/logs/LogStream.h index 1dd8767..170bd18 100644 --- a/src/utils/logs/LogStream.h +++ b/src/utils/logs/LogStream.h @@ -4,4 +4,4 @@ class LogStream { public: LogStream() = default; -}; +}; diff --git a/src/utils/logs/logging.h b/src/utils/logs/logging.h index 25cce3d..2c8ef09 100644 --- a/src/utils/logs/logging.h +++ b/src/utils/logs/logging.h @@ -1,36 +1,36 @@ -#ifndef LOGGING_H -#define LOGGING_H - -#include -#include -#include -#include - - -/** - * @file logging.h - * @brief 日志宏定义,提供带文件名和函数名的日志输出,并异步存储到数据库 - */ - -// 获取文件名(不含路径) -#define __FILENAME__ (strrchr(__FILE__, '/') ? strrchr(__FILE__, '/') + 1 : __FILE__) - -// 构建来源字符串的辅助宏 -// #define __LOG_SOURCE__ (QString(__FILENAME__) + "." + QString(__FUNCTION__)) - -// 日志宏,格式:[文件名.函数名] 消息 - -#define LOG_DEBUG() \ - qDebug() << "[" << __FILENAME__ << "/" << __FUNCTION__ << "]" - -#define LOG_ERROR() \ - qCritical() << "[" << __FILENAME__ << "/" << __FUNCTION__ << "]" - -#define LOG_INFO() \ - qInfo() << "[" << __FILENAME__ << "/" << __FUNCTION__ << "]" - -#define LOG_WARNING() \ - qWarning() << "[" << __FILENAME__ << "/" << __FUNCTION__ << "]" - -#endif // LOGGING_H - +#ifndef LOGGING_H +#define LOGGING_H + +#include +#include +#include +#include + + +/** + * @file logging.h + * @brief 日志宏定义,提供带文件名和函数名的日志输出,并异步存储到数据库 + */ + +// 获取文件名(不含路径) +#define __FILENAME__ (strrchr(__FILE__, '/') ? strrchr(__FILE__, '/') + 1 : __FILE__) + +// 构建来源字符串的辅助宏 +// #define __LOG_SOURCE__ (QString(__FILENAME__) + "." + QString(__FUNCTION__)) + +// 日志宏,格式:[文件名.函数名] 消息 + +#define LOG_DEBUG() \ + qDebug() << "[" << __FILENAME__ << "/" << __FUNCTION__ << "]" + +#define LOG_ERROR() \ + qCritical() << "[" << __FILENAME__ << "/" << __FUNCTION__ << "]" + +#define LOG_INFO() \ + qInfo() << "[" << __FILENAME__ << "/" << __FUNCTION__ << "]" + +#define LOG_WARNING() \ + qWarning() << "[" << __FILENAME__ << "/" << __FUNCTION__ << "]" + +#endif // LOGGING_H +