network_manager.cpp 33 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084
  1. #include "network_manager.h"
  2. #include "network_data_buffer.h"
  3. #include "network_storage_thread.h"
  4. #include "network_parser_thread.h"
  5. #include "devices/network/NetworkPortWatcher.h"
  6. #include "protocol_plugin/ProtocolPluginManager.h"
  7. #include "utils/logging.h"
  8. #include <QDateTime>
  9. #include <QJsonDocument>
  10. #include <QJsonArray>
  11. #include <QJsonObject>
  12. #include <QQueue>
  13. #include <QNetworkInterface>
  14. #include <QHostAddress>
  15. #include <QProcess>
  16. #include <algorithm>
  17. NetworkManager::NetworkManager(DeviceBusCore *busCore, QObject *parent)
  18. : QObject(parent),
  19. m_busCore(busCore),
  20. m_portWatcher(new devices::network::NetworkPortWatcher(this)),
  21. m_discoveryTimer(new QTimer(this)),
  22. m_storageThread(nullptr),
  23. m_parserThread(nullptr),
  24. m_pluginManager(nullptr)
  25. {
  26. // 连接定时器信号
  27. connect(m_discoveryTimer, &QTimer::timeout, this, &NetworkManager::discoverNetworkInterfaces);
  28. // 连接网络端口监视器信号
  29. connect(m_portWatcher, &devices::network::NetworkPortWatcher::networkDeviceArrived,
  30. this, &NetworkManager::onNetworkDeviceArrived);
  31. connect(m_portWatcher, &devices::network::NetworkPortWatcher::networkDeviceRemoved,
  32. this, &NetworkManager::onNetworkDeviceRemoved);
  33. // 启动网络端口监视器
  34. m_portWatcher->startWatching();
  35. // 初始化线程
  36. initThreads();
  37. }
  38. NetworkManager::~NetworkManager()
  39. {
  40. stopDiscovery();
  41. closeAllConnections();
  42. cleanupThreads();
  43. }
  44. void NetworkManager::startDiscovery(int intervalMs)
  45. {
  46. // 立即执行一次发现
  47. discoverNetworkInterfaces();
  48. // 启动定时器
  49. if (intervalMs > 0)
  50. {
  51. m_discoveryTimer->start(intervalMs);
  52. }
  53. }
  54. void NetworkManager::stopDiscovery()
  55. {
  56. m_discoveryTimer->stop();
  57. }
  58. bool NetworkManager::openNetworkConnection(const QString &interfaceName, const ConnectionConfig &config)
  59. {
  60. // 如果连接已经打开,直接返回成功
  61. if (m_openedInterfaces.contains(interfaceName))
  62. {
  63. return true;
  64. }
  65. bool success = false;
  66. if (config.protocol.toLower() == QStringLiteral("tcp"))
  67. {
  68. // 创建TCP连接
  69. QTcpSocket *socket = new QTcpSocket(this);
  70. // 连接信号
  71. connect(socket, &QTcpSocket::readyRead, this, &NetworkManager::onTcpReadyRead);
  72. connect(socket, QOverload<QAbstractSocket::SocketError>::of(&QAbstractSocket::errorOccurred),
  73. this, &NetworkManager::onTcpSocketError);
  74. connect(socket, &QTcpSocket::connected, this, &NetworkManager::onTcpConnected);
  75. connect(socket, &QTcpSocket::disconnected, this, &NetworkManager::onTcpDisconnected);
  76. // 尝试连接
  77. socket->connectToHost(config.remoteAddress, config.remotePort);
  78. if (socket->waitForConnected(5000))
  79. {
  80. m_tcpSockets.insert(interfaceName, socket);
  81. m_openedInterfaces.insert(interfaceName);
  82. m_connectionConfigs.insert(interfaceName, config);
  83. success = true;
  84. // 为接口创建数据缓冲区
  85. if (!m_dataBuffers.contains(interfaceName))
  86. {
  87. NetworkDataBuffer *buffer = new NetworkDataBuffer(interfaceName, this);
  88. m_dataBuffers.insert(interfaceName, buffer);
  89. // 注册到解析线程
  90. if (m_parserThread)
  91. {
  92. m_parserThread->registerBuffer(interfaceName, buffer);
  93. }
  94. }
  95. LOG_DEBUG() << "Opened TCP connection for" << interfaceName
  96. << "to" << config.remoteAddress << ":" << config.remotePort;
  97. }
  98. else
  99. {
  100. LOG_WARNING() << "Failed to connect TCP for" << interfaceName
  101. << ":" << socket->errorString();
  102. delete socket;
  103. }
  104. }
  105. else if (config.protocol.toLower() == QStringLiteral("udp"))
  106. {
  107. // 创建UDP连接
  108. QUdpSocket *socket = new QUdpSocket(this);
  109. // 绑定本地端口
  110. QHostAddress bindAddress = QHostAddress::AnyIPv4;
  111. quint16 bindPort = config.localPort > 0 ? config.localPort : 0;
  112. if (socket->bind(bindAddress, bindPort))
  113. {
  114. // 连接信号
  115. connect(socket, &QUdpSocket::readyRead, this, &NetworkManager::onUdpReadyRead);
  116. m_udpSockets.insert(interfaceName, socket);
  117. m_openedInterfaces.insert(interfaceName);
  118. m_connectionConfigs.insert(interfaceName, config);
  119. success = true;
  120. // 为接口创建数据缓冲区
  121. if (!m_dataBuffers.contains(interfaceName))
  122. {
  123. NetworkDataBuffer *buffer = new NetworkDataBuffer(interfaceName, this);
  124. m_dataBuffers.insert(interfaceName, buffer);
  125. // 注册到解析线程
  126. if (m_parserThread)
  127. {
  128. m_parserThread->registerBuffer(interfaceName, buffer);
  129. }
  130. }
  131. LOG_DEBUG() << "Opened UDP connection for" << interfaceName
  132. << "on port" << socket->localPort();
  133. }
  134. else
  135. {
  136. LOG_WARNING() << "Failed to bind UDP for" << interfaceName
  137. << ":" << socket->errorString();
  138. delete socket;
  139. }
  140. }
  141. else
  142. {
  143. LOG_WARNING() << "Unsupported protocol:" << config.protocol;
  144. }
  145. return success;
  146. }
  147. void NetworkManager::closeNetworkConnection(const QString &interfaceName)
  148. {
  149. if (m_tcpSockets.contains(interfaceName))
  150. {
  151. QTcpSocket *socket = m_tcpSockets.take(interfaceName);
  152. socket->disconnectFromHost();
  153. if (socket->state() != QAbstractSocket::UnconnectedState)
  154. {
  155. socket->waitForDisconnected(3000);
  156. }
  157. delete socket;
  158. m_openedInterfaces.remove(interfaceName);
  159. m_connectionConfigs.remove(interfaceName);
  160. // 清理数据缓冲区
  161. if (m_dataBuffers.contains(interfaceName))
  162. {
  163. NetworkDataBuffer *buffer = m_dataBuffers.take(interfaceName);
  164. delete buffer;
  165. }
  166. emit interfaceRemoved(interfaceName);
  167. LOG_DEBUG() << "Closed TCP connection for" << interfaceName;
  168. }
  169. else if (m_udpSockets.contains(interfaceName))
  170. {
  171. QUdpSocket *socket = m_udpSockets.take(interfaceName);
  172. socket->close();
  173. delete socket;
  174. m_openedInterfaces.remove(interfaceName);
  175. m_connectionConfigs.remove(interfaceName);
  176. // 清理数据缓冲区
  177. if (m_dataBuffers.contains(interfaceName))
  178. {
  179. NetworkDataBuffer *buffer = m_dataBuffers.take(interfaceName);
  180. delete buffer;
  181. }
  182. emit interfaceRemoved(interfaceName);
  183. LOG_DEBUG() << "Closed UDP connection for" << interfaceName;
  184. }
  185. }
  186. bool NetworkManager::isConnectionOpen(const QString &interfaceName)
  187. {
  188. if (m_tcpSockets.contains(interfaceName))
  189. {
  190. return m_tcpSockets[interfaceName]->state() == QAbstractSocket::ConnectedState;
  191. }
  192. else if (m_udpSockets.contains(interfaceName))
  193. {
  194. return m_udpSockets[interfaceName]->state() == QAbstractSocket::BoundState;
  195. }
  196. return false;
  197. }
  198. void NetworkManager::closeAllConnections()
  199. {
  200. // 关闭所有TCP连接
  201. for (QTcpSocket *socket : m_tcpSockets.values())
  202. {
  203. socket->disconnectFromHost();
  204. if (socket->state() != QAbstractSocket::UnconnectedState)
  205. {
  206. socket->waitForDisconnected(3000);
  207. }
  208. delete socket;
  209. }
  210. m_tcpSockets.clear();
  211. // 关闭所有UDP连接
  212. for (QUdpSocket *socket : m_udpSockets.values())
  213. {
  214. socket->close();
  215. delete socket;
  216. }
  217. m_udpSockets.clear();
  218. m_openedInterfaces.clear();
  219. m_connectionConfigs.clear();
  220. // 清理所有数据缓冲区
  221. qDeleteAll(m_dataBuffers);
  222. m_dataBuffers.clear();
  223. LOG_DEBUG() << "All network connections closed";
  224. }
  225. bool NetworkManager::setNetworkConfig(const QString &interfaceName, const NetworkConfig &config)
  226. {
  227. // 保存配置
  228. m_networkConfigs[interfaceName] = config;
  229. #ifdef Q_OS_LINUX
  230. // Linux: 使用 ip 命令配置网络
  231. QProcess process;
  232. // 设置IP地址和子网掩码
  233. // 计算子网掩码的前缀长度
  234. QHostAddress netmaskAddr(config.netmask);
  235. int prefixLength = 0;
  236. quint32 mask = netmaskAddr.toIPv4Address();
  237. while (mask & 0x80000000) {
  238. prefixLength++;
  239. mask <<= 1;
  240. }
  241. QStringList ipArgs;
  242. ipArgs << QStringLiteral("addr") << QStringLiteral("add")
  243. << QStringLiteral("%1/%2").arg(config.ipAddress).arg(prefixLength)
  244. << QStringLiteral("dev") << interfaceName;
  245. // 先删除旧地址(如果存在)
  246. QProcess delProcess;
  247. delProcess.start(QStringLiteral("ip"), QStringList() << QStringLiteral("addr")
  248. << QStringLiteral("flush") << QStringLiteral("dev") << interfaceName);
  249. delProcess.waitForFinished(3000);
  250. // 设置新地址
  251. process.start(QStringLiteral("ip"), ipArgs);
  252. if (!process.waitForFinished(5000))
  253. {
  254. LOG_WARNING() << "Failed to set IP address for" << interfaceName;
  255. return false;
  256. }
  257. if (process.exitCode() != 0)
  258. {
  259. LOG_WARNING() << "Failed to set IP address:" << process.readAllStandardError();
  260. return false;
  261. }
  262. // 设置网关
  263. if (!config.gateway.isEmpty())
  264. {
  265. QProcess routeProcess;
  266. routeProcess.start(QStringLiteral("ip"), QStringList() << QStringLiteral("route")
  267. << QStringLiteral("add") << QStringLiteral("default")
  268. << QStringLiteral("via") << config.gateway
  269. << QStringLiteral("dev") << interfaceName);
  270. routeProcess.waitForFinished(5000);
  271. }
  272. // 设置DNS(需要修改 /etc/resolv.conf,需要root权限)
  273. if (!config.dnsServers.isEmpty())
  274. {
  275. // 这里只是保存配置,实际修改DNS需要root权限
  276. // 可以通过systemd-resolved或其他方式配置
  277. LOG_INFO() << "DNS configuration saved for" << interfaceName
  278. << ":" << config.dnsServers.join(QStringLiteral(", "));
  279. }
  280. #elif defined(Q_OS_WIN)
  281. // Windows: 使用 netsh 命令配置网络
  282. QProcess process;
  283. // 设置IP地址和子网掩码
  284. QStringList args;
  285. args << QStringLiteral("interface") << QStringLiteral("ip") << QStringLiteral("set")
  286. << QStringLiteral("address") << QStringLiteral("name=") + interfaceName
  287. << QStringLiteral("static") << config.ipAddress << config.netmask;
  288. process.start(QStringLiteral("netsh"), args);
  289. if (!process.waitForFinished(5000) || process.exitCode() != 0)
  290. {
  291. LOG_WARNING() << "Failed to set IP address for" << interfaceName;
  292. return false;
  293. }
  294. // 设置网关
  295. if (!config.gateway.isEmpty())
  296. {
  297. QProcess routeProcess;
  298. routeProcess.start(QStringLiteral("netsh"), QStringList() << QStringLiteral("interface")
  299. << QStringLiteral("ip") << QStringLiteral("set")
  300. << QStringLiteral("route") << QStringLiteral("0.0.0.0/0")
  301. << QStringLiteral("interface=") + interfaceName
  302. << QStringLiteral("nexthop=") + config.gateway);
  303. routeProcess.waitForFinished(5000);
  304. }
  305. // 设置DNS
  306. if (!config.dnsServers.isEmpty())
  307. {
  308. QStringList dnsArgs;
  309. dnsArgs << QStringLiteral("interface") << QStringLiteral("ip") << QStringLiteral("set")
  310. << QStringLiteral("dns") << QStringLiteral("name=") + interfaceName
  311. << QStringLiteral("static") << config.dnsServers.first();
  312. QProcess dnsProcess;
  313. dnsProcess.start(QStringLiteral("netsh"), dnsArgs);
  314. dnsProcess.waitForFinished(5000);
  315. }
  316. #endif
  317. LOG_DEBUG() << "Network configuration updated for" << interfaceName;
  318. return true;
  319. }
  320. NetworkManager::NetworkConfig NetworkManager::getNetworkConfig(const QString &interfaceName) const
  321. {
  322. if (m_networkConfigs.contains(interfaceName))
  323. {
  324. return m_networkConfigs[interfaceName];
  325. }
  326. // 如果配置不存在,尝试从系统读取
  327. NetworkConfig config;
  328. QNetworkInterface iface = QNetworkInterface::interfaceFromName(interfaceName);
  329. if (iface.isValid())
  330. {
  331. const QList<QNetworkAddressEntry> entries = iface.addressEntries();
  332. for (const QNetworkAddressEntry &entry : entries)
  333. {
  334. if (entry.ip().protocol() == QAbstractSocket::IPv4Protocol)
  335. {
  336. config.ipAddress = entry.ip().toString();
  337. config.netmask = entry.netmask().toString();
  338. break;
  339. }
  340. }
  341. }
  342. return config;
  343. }
  344. QStringList NetworkManager::getOpenedInterfaces() const
  345. {
  346. return m_openedInterfaces.values();
  347. }
  348. QStringList NetworkManager::getAvailableInterfaces() const
  349. {
  350. QStringList interfaces;
  351. const QList<QNetworkInterface> ifaces = QNetworkInterface::allInterfaces();
  352. for (const QNetworkInterface &iface : ifaces)
  353. {
  354. // 跳过回环接口
  355. if (iface.flags().testFlag(QNetworkInterface::IsLoopBack))
  356. {
  357. continue;
  358. }
  359. interfaces << iface.name();
  360. }
  361. return interfaces;
  362. }
  363. bool NetworkManager::writeData(const QString &interfaceName, const QByteArray &data)
  364. {
  365. if (m_tcpSockets.contains(interfaceName))
  366. {
  367. QTcpSocket *socket = m_tcpSockets[interfaceName];
  368. if (socket->state() == QAbstractSocket::ConnectedState)
  369. {
  370. qint64 bytesWritten = socket->write(data);
  371. if (bytesWritten == data.size())
  372. {
  373. LOG_DEBUG() << "Data written to TCP" << interfaceName << ":" << data.toHex();
  374. return true;
  375. }
  376. else
  377. {
  378. LOG_WARNING() << "Failed to write all data to TCP" << interfaceName
  379. << ". Written:" << bytesWritten << "of" << data.size();
  380. }
  381. }
  382. }
  383. else if (m_udpSockets.contains(interfaceName))
  384. {
  385. QUdpSocket *socket = m_udpSockets[interfaceName];
  386. if (m_connectionConfigs.contains(interfaceName))
  387. {
  388. const ConnectionConfig &config = m_connectionConfigs[interfaceName];
  389. qint64 bytesWritten = socket->writeDatagram(data,
  390. QHostAddress(config.remoteAddress),
  391. config.remotePort);
  392. if (bytesWritten == data.size())
  393. {
  394. LOG_DEBUG() << "Data written to UDP" << interfaceName << ":" << data.toHex();
  395. return true;
  396. }
  397. else
  398. {
  399. LOG_WARNING() << "Failed to write all data to UDP" << interfaceName
  400. << ". Written:" << bytesWritten << "of" << data.size();
  401. }
  402. }
  403. }
  404. return false;
  405. }
  406. void NetworkManager::setBusCore(DeviceBusCore *busCore)
  407. {
  408. m_busCore = busCore;
  409. LOG_INFO() << "Bus core set for NetworkManager";
  410. // 更新线程的busCore
  411. if (m_storageThread)
  412. {
  413. // 需要重新创建线程(因为busCore可能变化)
  414. cleanupThreads();
  415. initThreads();
  416. }
  417. }
  418. DeviceBusCore *NetworkManager::getBusCore() const
  419. {
  420. return m_busCore;
  421. }
  422. void NetworkManager::discoverNetworkInterfaces()
  423. {
  424. // 网络接口发现由 NetworkPortWatcher 处理
  425. // 这里可以做一些额外的处理
  426. const QList<devices::network::NetworkDeviceInfo> interfaces = m_portWatcher->knownInterfaces();
  427. QSet<QString> currentInterfaces;
  428. for (const devices::network::NetworkDeviceInfo &info : interfaces)
  429. {
  430. if (!info.isValid() || !info.isUp)
  431. {
  432. continue;
  433. }
  434. QString interfaceName = info.interfaceName;
  435. currentInterfaces.insert(interfaceName);
  436. // 如果是新发现的接口
  437. if (!m_lastDiscoveredInterfaces.contains(interfaceName))
  438. {
  439. registerDiscoveredInterface(info);
  440. emit interfaceDiscovered(interfaceName, info.description);
  441. LOG_DEBUG() << "New interface discovered:" << interfaceName << "-" << info.description;
  442. }
  443. }
  444. // 检查是否有接口被移除
  445. QSet<QString> removedInterfaces = m_lastDiscoveredInterfaces - currentInterfaces;
  446. for (const QString &interfaceName : removedInterfaces)
  447. {
  448. // 如果接口是打开的,先关闭它
  449. if (m_openedInterfaces.contains(interfaceName))
  450. {
  451. closeNetworkConnection(interfaceName);
  452. }
  453. if (m_busCore)
  454. {
  455. m_busCore->markDeviceOfflineByPort(interfaceName);
  456. }
  457. emit interfaceRemoved(interfaceName);
  458. LOG_DEBUG() << "Interface removed:" << interfaceName;
  459. }
  460. // 更新上次发现的接口列表
  461. m_lastDiscoveredInterfaces = currentInterfaces;
  462. }
  463. void NetworkManager::onTcpReadyRead()
  464. {
  465. QTcpSocket *socket = qobject_cast<QTcpSocket*>(sender());
  466. if (!socket)
  467. {
  468. return;
  469. }
  470. // 找到对应的接口名
  471. QString interfaceName;
  472. for (auto it = m_tcpSockets.begin(); it != m_tcpSockets.end(); ++it)
  473. {
  474. if (it.value() == socket)
  475. {
  476. interfaceName = it.key();
  477. break;
  478. }
  479. }
  480. if (interfaceName.isEmpty())
  481. {
  482. return;
  483. }
  484. QByteArray data = socket->readAll();
  485. if (!data.isEmpty())
  486. {
  487. // 发出数据接收信号(用于UI显示)
  488. LOG_DEBUG() << "Received TCP data from" << interfaceName << ":" << data.toHex();
  489. emit dataReceived(interfaceName, data);
  490. // 将数据添加到缓冲区(用于帧拼凑)
  491. if (m_dataBuffers.contains(interfaceName))
  492. {
  493. m_dataBuffers[interfaceName]->appendData(data);
  494. // 通知解析线程有新数据
  495. if (m_parserThread)
  496. {
  497. m_parserThread->notifyNewData(interfaceName);
  498. }
  499. }
  500. // 异步存储原始数据到数据库
  501. if (m_storageThread)
  502. {
  503. // 获取设备ID,如果设备已注册则使用deviceId,否则使用0
  504. int deviceId = 0;
  505. if (m_busCore)
  506. {
  507. DeviceInfo device = m_busCore->getDeviceInfoByPortname(interfaceName);
  508. deviceId = device.id;
  509. }
  510. m_storageThread->enqueueData(deviceId, interfaceName, data);
  511. }
  512. }
  513. }
  514. void NetworkManager::onUdpReadyRead()
  515. {
  516. QUdpSocket *socket = qobject_cast<QUdpSocket*>(sender());
  517. if (!socket)
  518. {
  519. return;
  520. }
  521. // 找到对应的接口名
  522. QString interfaceName;
  523. for (auto it = m_udpSockets.begin(); it != m_udpSockets.end(); ++it)
  524. {
  525. if (it.value() == socket)
  526. {
  527. interfaceName = it.key();
  528. break;
  529. }
  530. }
  531. if (interfaceName.isEmpty())
  532. {
  533. return;
  534. }
  535. while (socket->hasPendingDatagrams())
  536. {
  537. QByteArray data;
  538. data.resize(socket->pendingDatagramSize());
  539. QHostAddress senderAddress;
  540. quint16 senderPort;
  541. socket->readDatagram(data.data(), data.size(), &senderAddress, &senderPort);
  542. if (!data.isEmpty())
  543. {
  544. // 发出数据接收信号(用于UI显示)
  545. LOG_DEBUG() << "Received UDP data from" << interfaceName
  546. << "from" << senderAddress.toString() << ":" << senderPort
  547. << ":" << data.toHex();
  548. emit dataReceived(interfaceName, data);
  549. // 将数据添加到缓冲区(用于帧拼凑)
  550. if (m_dataBuffers.contains(interfaceName))
  551. {
  552. m_dataBuffers[interfaceName]->appendData(data);
  553. // 通知解析线程有新数据
  554. if (m_parserThread)
  555. {
  556. m_parserThread->notifyNewData(interfaceName);
  557. }
  558. }
  559. // 异步存储原始数据到数据库
  560. if (m_storageThread)
  561. {
  562. // 获取设备ID,如果设备已注册则使用deviceId,否则使用0
  563. int deviceId = 0;
  564. if (m_busCore)
  565. {
  566. DeviceInfo device = m_busCore->getDeviceInfoByPortname(interfaceName);
  567. deviceId = device.id;
  568. }
  569. m_storageThread->enqueueData(deviceId, interfaceName, data);
  570. }
  571. }
  572. }
  573. }
  574. void NetworkManager::onNetworkDeviceArrived(const devices::network::NetworkDeviceInfo &info)
  575. {
  576. if (!info.isValid())
  577. {
  578. return;
  579. }
  580. registerDiscoveredInterface(info);
  581. emit interfaceDiscovered(info.interfaceName, info.description);
  582. }
  583. void NetworkManager::onNetworkDeviceRemoved(const devices::network::NetworkDeviceInfo &info)
  584. {
  585. if (!info.isValid())
  586. {
  587. return;
  588. }
  589. // 如果接口是打开的,先关闭它
  590. if (m_openedInterfaces.contains(info.interfaceName))
  591. {
  592. closeNetworkConnection(info.interfaceName);
  593. }
  594. if (m_busCore)
  595. {
  596. m_busCore->markDeviceOfflineByPort(info.interfaceName);
  597. }
  598. emit interfaceRemoved(info.interfaceName);
  599. }
  600. void NetworkManager::onTcpSocketError(QAbstractSocket::SocketError error)
  601. {
  602. Q_UNUSED(error);
  603. QTcpSocket *socket = qobject_cast<QTcpSocket*>(sender());
  604. if (!socket)
  605. {
  606. return;
  607. }
  608. // 找到对应的接口名
  609. QString interfaceName;
  610. for (auto it = m_tcpSockets.begin(); it != m_tcpSockets.end(); ++it)
  611. {
  612. if (it.value() == socket)
  613. {
  614. interfaceName = it.key();
  615. break;
  616. }
  617. }
  618. if (!interfaceName.isEmpty())
  619. {
  620. LOG_WARNING() << "TCP socket error for" << interfaceName << ":" << socket->errorString();
  621. }
  622. }
  623. void NetworkManager::onTcpConnected()
  624. {
  625. QTcpSocket *socket = qobject_cast<QTcpSocket*>(sender());
  626. if (!socket)
  627. {
  628. return;
  629. }
  630. // 找到对应的接口名
  631. QString interfaceName;
  632. for (auto it = m_tcpSockets.begin(); it != m_tcpSockets.end(); ++it)
  633. {
  634. if (it.value() == socket)
  635. {
  636. interfaceName = it.key();
  637. break;
  638. }
  639. }
  640. if (!interfaceName.isEmpty())
  641. {
  642. LOG_DEBUG() << "TCP connected for" << interfaceName;
  643. }
  644. }
  645. void NetworkManager::onTcpDisconnected()
  646. {
  647. QTcpSocket *socket = qobject_cast<QTcpSocket*>(sender());
  648. if (!socket)
  649. {
  650. return;
  651. }
  652. // 找到对应的接口名
  653. QString interfaceName;
  654. for (auto it = m_tcpSockets.begin(); it != m_tcpSockets.end(); ++it)
  655. {
  656. if (it.value() == socket)
  657. {
  658. interfaceName = it.key();
  659. break;
  660. }
  661. }
  662. if (!interfaceName.isEmpty())
  663. {
  664. LOG_DEBUG() << "TCP disconnected for" << interfaceName;
  665. if (m_openedInterfaces.contains(interfaceName))
  666. {
  667. closeNetworkConnection(interfaceName);
  668. }
  669. }
  670. }
  671. void NetworkManager::onRawDataStored(qint64 rawDataId, int deviceId, const QString &interfaceName, const QByteArray &data)
  672. {
  673. Q_UNUSED(deviceId);
  674. Q_UNUSED(data);
  675. QMutexLocker locker(&m_rawDataIdsMutex);
  676. if (!m_rawDataIds.contains(interfaceName))
  677. {
  678. m_rawDataIds[interfaceName] = QQueue<qint64>();
  679. }
  680. m_rawDataIds[interfaceName].enqueue(rawDataId);
  681. // 限制队列大小,避免内存泄漏(保留最近1000条记录)
  682. while (m_rawDataIds[interfaceName].size() > 1000)
  683. {
  684. m_rawDataIds[interfaceName].dequeue();
  685. }
  686. }
  687. void NetworkManager::initThreads()
  688. {
  689. // 创建存储线程
  690. if (!m_storageThread)
  691. {
  692. m_storageThread = new NetworkStorageThread(m_busCore, this);
  693. // 连接原始数据存储完成信号,记录原始数据 id
  694. connect(m_storageThread, &NetworkStorageThread::rawDataStored,
  695. this, &NetworkManager::onRawDataStored);
  696. m_storageThread->start();
  697. LOG_DEBUG() << "NetworkStorageThread created and started";
  698. }
  699. // 创建解析线程
  700. if (!m_parserThread)
  701. {
  702. m_parserThread = new NetworkParserThread(m_busCore, m_pluginManager, this);
  703. // 设置获取原始数据 id 列表的回调函数
  704. m_parserThread->setRawDataIdsCallback([this](const QString &interfaceName) -> QList<qint64> {
  705. QMutexLocker locker(&m_rawDataIdsMutex);
  706. if (m_rawDataIds.contains(interfaceName))
  707. {
  708. // 返回该接口的所有原始数据 id(清空队列,因为已经用于组成帧)
  709. QList<qint64> ids = m_rawDataIds[interfaceName].toList();
  710. m_rawDataIds[interfaceName].clear();
  711. return ids;
  712. }
  713. return QList<qint64>();
  714. });
  715. // 连接解析线程的信号
  716. connect(m_parserThread, &NetworkParserThread::modbusDataParsed,
  717. this, &NetworkManager::modbusDataParsed);
  718. connect(m_parserThread, &NetworkParserThread::customDataParsed,
  719. this, &NetworkManager::customDataParsed);
  720. m_parserThread->start();
  721. LOG_DEBUG() << "NetworkParserThread created and started";
  722. // 注册已有的缓冲区
  723. for (auto it = m_dataBuffers.begin(); it != m_dataBuffers.end(); ++it)
  724. {
  725. m_parserThread->registerBuffer(it.key(), it.value());
  726. }
  727. }
  728. }
  729. void NetworkManager::cleanupThreads()
  730. {
  731. if (m_storageThread)
  732. {
  733. m_storageThread->stop();
  734. m_storageThread->wait(3000);
  735. delete m_storageThread;
  736. m_storageThread = nullptr;
  737. }
  738. if (m_parserThread)
  739. {
  740. m_parserThread->stop();
  741. m_parserThread->wait(3000);
  742. delete m_parserThread;
  743. m_parserThread = nullptr;
  744. }
  745. }
  746. void NetworkManager::setPluginManager(ProtocolPluginManager *pluginManager)
  747. {
  748. m_pluginManager = pluginManager;
  749. // 更新解析线程的插件管理器
  750. if (m_parserThread)
  751. {
  752. m_parserThread->setPluginManager(pluginManager);
  753. }
  754. }
  755. bool NetworkManager::lockDevice(const QString &deviceId, const QString &taskId)
  756. {
  757. QMutexLocker locker(&m_deviceLocksMutex);
  758. if (deviceId.isEmpty() || taskId.isEmpty()) {
  759. return false;
  760. }
  761. // 检查设备是否已被锁定
  762. if (m_deviceLocks.contains(deviceId)) {
  763. QString lockingTaskId = m_deviceLocks.value(deviceId);
  764. if (lockingTaskId != taskId) {
  765. LOG_WARNING() << "Network device" << deviceId << "is already locked by task" << lockingTaskId;
  766. return false;
  767. }
  768. // 如果是同一个任务,直接返回成功
  769. return true;
  770. }
  771. // 锁定设备
  772. m_deviceLocks.insert(deviceId, taskId);
  773. LOG_DEBUG() << "Network device locked:" << deviceId << "by task:" << taskId;
  774. return true;
  775. }
  776. bool NetworkManager::unlockDevice(const QString &deviceId, const QString &taskId)
  777. {
  778. QMutexLocker locker(&m_deviceLocksMutex);
  779. if (deviceId.isEmpty() || taskId.isEmpty()) {
  780. return false;
  781. }
  782. if (!m_deviceLocks.contains(deviceId)) {
  783. LOG_WARNING() << "Network device" << deviceId << "is not locked";
  784. return false;
  785. }
  786. QString lockingTaskId = m_deviceLocks.value(deviceId);
  787. if (lockingTaskId != taskId) {
  788. LOG_WARNING() << "Network device" << deviceId << "is locked by different task:"
  789. << lockingTaskId << "not" << taskId;
  790. return false;
  791. }
  792. m_deviceLocks.remove(deviceId);
  793. LOG_DEBUG() << "Network device unlocked:" << deviceId << "by task:" << taskId;
  794. return true;
  795. }
  796. bool NetworkManager::isDeviceLocked(const QString &deviceId) const
  797. {
  798. QMutexLocker locker(&m_deviceLocksMutex);
  799. return m_deviceLocks.contains(deviceId);
  800. }
  801. void NetworkManager::registerDiscoveredInterface(const devices::network::NetworkDeviceInfo &info)
  802. {
  803. if (!m_busCore)
  804. {
  805. LOG_DEBUG() << "Bus core is not set; skip registering interface" << info.interfaceName;
  806. return;
  807. }
  808. if (!info.isValid() || !info.isUp)
  809. {
  810. LOG_DEBUG() << "Skip registering invalid or down interface" << info.interfaceName;
  811. return;
  812. }
  813. const QString interfaceName = info.interfaceName;
  814. DeviceInfo existingDevice = m_busCore->getDeviceInfoByPortname(interfaceName);
  815. if (existingDevice.id != 0)
  816. {
  817. // 已经注册的设备,如果描述或属性发生变化,更新一次
  818. QString desiredName = info.description.isEmpty()
  819. ? QStringLiteral("网络设备: %1").arg(interfaceName)
  820. : info.description;
  821. QJsonObject updatedProperties = existingDevice.properties;
  822. auto mergeProperty = [&updatedProperties](const QString &key, const QString &value) {
  823. if (value.isEmpty())
  824. {
  825. return false;
  826. }
  827. if (!updatedProperties.contains(key) || updatedProperties.value(key).toString() != value)
  828. {
  829. updatedProperties.insert(key, value);
  830. return true;
  831. }
  832. return false;
  833. };
  834. bool propertyChanged = false;
  835. propertyChanged |= mergeProperty(QStringLiteral("description"), info.description);
  836. propertyChanged |= mergeProperty(QStringLiteral("hardwareAddress"), info.hardwareAddress);
  837. propertyChanged |= mergeProperty(QStringLiteral("ipv4Address"), info.ipv4Address);
  838. propertyChanged |= mergeProperty(QStringLiteral("ipv4Netmask"), info.ipv4Netmask);
  839. propertyChanged |= mergeProperty(QStringLiteral("ipv4Gateway"), info.ipv4Gateway);
  840. propertyChanged |= mergeProperty(QStringLiteral("ipv6Address"), info.ipv6Address);
  841. // DNS服务器列表
  842. if (!info.dnsServers.isEmpty())
  843. {
  844. QJsonArray dnsArray;
  845. for (const QString &dns : info.dnsServers)
  846. {
  847. dnsArray.append(dns);
  848. }
  849. QString dnsStr = QJsonDocument(dnsArray).toJson(QJsonDocument::Compact);
  850. propertyChanged |= mergeProperty(QStringLiteral("dnsServers"), dnsStr);
  851. }
  852. bool nameChanged = existingDevice.name != desiredName;
  853. const bool needFullUpdate = nameChanged || propertyChanged;
  854. if (needFullUpdate)
  855. {
  856. existingDevice.name = desiredName;
  857. existingDevice.properties = updatedProperties;
  858. existingDevice.status = QStringLiteral("online");
  859. existingDevice.isActive = true;
  860. existingDevice.lastSeen = QDateTime::currentDateTimeUtc();
  861. m_busCore->updateDevice(existingDevice);
  862. LOG_DEBUG() << "Updated existing network device registration for interface" << interfaceName;
  863. }
  864. if (!needFullUpdate)
  865. {
  866. m_busCore->updateDeviceStatus(existingDevice.id, QStringLiteral("online"), true,
  867. QDateTime::currentDateTimeUtc());
  868. }
  869. return;
  870. }
  871. DeviceInfo device;
  872. device.id = generateNextDeviceId();
  873. if (device.id <= 0)
  874. {
  875. LOG_WARNING() << "Failed to allocate device ID for interface" << interfaceName;
  876. return;
  877. }
  878. device.portname = interfaceName;
  879. device.type = QStringLiteral("ethernet");
  880. device.protocol = QStringLiteral("modbus");
  881. device.protocol_detail = QStringLiteral("modbus-tcp");
  882. device.address = 0;
  883. device.status = QStringLiteral("online");
  884. device.isActive = true;
  885. device.lastSeen = QDateTime::currentDateTimeUtc();
  886. if (info.description.isEmpty())
  887. {
  888. device.name = QStringLiteral("网络设备: %1").arg(interfaceName);
  889. }
  890. else if (info.description.contains(interfaceName))
  891. {
  892. device.name = info.description;
  893. }
  894. else
  895. {
  896. device.name = QStringLiteral("%1 (%2)").arg(info.description, interfaceName);
  897. }
  898. QJsonObject properties;
  899. if (!info.description.isEmpty())
  900. {
  901. properties.insert(QStringLiteral("description"), info.description);
  902. }
  903. if (!info.hardwareAddress.isEmpty())
  904. {
  905. properties.insert(QStringLiteral("hardwareAddress"), info.hardwareAddress);
  906. }
  907. if (!info.ipv4Address.isEmpty())
  908. {
  909. properties.insert(QStringLiteral("ipv4Address"), info.ipv4Address);
  910. properties.insert(QStringLiteral("ip"), info.ipv4Address); // 兼容Modbus TCP配置
  911. }
  912. if (!info.ipv4Netmask.isEmpty())
  913. {
  914. properties.insert(QStringLiteral("ipv4Netmask"), info.ipv4Netmask);
  915. }
  916. if (!info.ipv4Gateway.isEmpty())
  917. {
  918. properties.insert(QStringLiteral("ipv4Gateway"), info.ipv4Gateway);
  919. }
  920. if (!info.ipv6Address.isEmpty())
  921. {
  922. properties.insert(QStringLiteral("ipv6Address"), info.ipv6Address);
  923. }
  924. if (!info.dnsServers.isEmpty())
  925. {
  926. QJsonArray dnsArray;
  927. for (const QString &dns : info.dnsServers)
  928. {
  929. dnsArray.append(dns);
  930. }
  931. properties.insert(QStringLiteral("dnsServers"), dnsArray);
  932. }
  933. // 默认Modbus TCP端口
  934. properties.insert(QStringLiteral("port"), 502);
  935. device.properties = properties;
  936. m_busCore->registerDevice(device);
  937. m_busCore->updateDeviceStatus(device.id, QStringLiteral("online"), true,
  938. device.lastSeen);
  939. LOG_DEBUG() << "Registered network device in bus core for interface" << interfaceName << "with id" << device.id;
  940. }
  941. int NetworkManager::generateNextDeviceId() const
  942. {
  943. if (!m_busCore)
  944. {
  945. return -1;
  946. }
  947. // 使用 DeviceBusCore 的 generateNextDeviceId,确保按照分配规则生成
  948. // 网络设备范围:30000-39999
  949. return m_busCore->generateNextDeviceId(QStringLiteral("ethernet"));
  950. }