无法发送TRDP MD与PD消息:QT集成TRDP库排障求助
TRDP通信发送无数据包排查(QT集成场景)
我正在开发基于TRDP的通信功能,已在QT项目中集成验证过可用的TRDP库。通过初始化Trdp类对象,调用sendPDMessage或sendMDMessage方法发送消息,但接收端未收到任何数据包,Wireshark也捕获不到TRDP数据包,需要协助排查问题。
相关代码
#include "trdp.h" Trdp::Trdp ( QObject * parent ) : QObject ( parent ) { ip[0] = 127; ip[1] = 0; ip[2] = 0; ip[3] = 1; comId = PD_COMID; this->pubHandle = NULL; mdConfiguration = { NULL, NULL, {3, 64, 2}, TRDP_FLAGS_NONE, 1000000u, 1000000u, 1000000u, 1000000u, 17225u, 0, 5u, }; pdConfiguration = { NULL, NULL, TRDP_PD_DEFAULT_SEND_PARAM, TRDP_FLAGS_NONE, 1000000u, TRDP_TO_SET_TO_ZERO, 0u, }; dynamicConfig = { NULL, RESERVED_MEMORY, { 0 } }; processConfig = { "Me", "", "", TRDP_PROCESS_DEFAULT_CYCLE_TIME, 0, TRDP_OPTION_NONE }; ownIP = vos_dottedIP("127.0.0.1"); dstIP = vos_dottedIP("127.0.0.1"); rv = 0; if ( tlc_init ( &this->dbgOut, NULL, &dynamicConfig ) != TRDP_NO_ERR ) { qDebug ( ) << "Init error!"; } if ( tlc_openSession ( &appHandle, ownIP, 0, NULL, &pdConfiguration, &mdConfiguration, &processConfig ) != TRDP_NO_ERR ) { qDebug ( ) << "Init error! 2"; } memset ( trdpBuffer, 0, sizeof ( trdpBuffer ) ); } void Trdp::dbgOut ( void *pRefCon, TRDP_LOG_T category, const CHAR8 *pTime, const CHAR8 *pFile, UINT16 LineNumber, const CHAR8 *pMsgStr) { } // Add this method to initialize a publisher for PD messages void Trdp::initPDPublisher() { TRDP_PUB_T pubHandle = NULL; TRDP_ERR_T err = tlp_publish( this->appHandle, // Application session handle &pubHandle, // Publisher handle to be initialized NULL, // User reference NULL, // Callback function for receiving data (not needed for publishing) 0, // Service ID (0 for default) comId, // Communication ID 0, // etbTopoCnt (0 for default) 0, // etbConfigCnt (0 for default) ownIP, // Source IP address dstIP, // Destination IP address 1000000u, // Interval 0u, // Packet time-to-live TRDP_FLAGS_NONE, // Flags NULL, // Marshalling function NULL, // Data pointer (NULL for initialization) 0 // Data size (0 for initialization) ); if (err != TRDP_NO_ERR) { qDebug() << "Error initializing PD publisher: " << err; } else { this->pubHandle = pubHandle; // Store the initialized pubHandle for later use qDebug() << "PD Publisher initialized successfully."; } } TRDP_ERR_T Trdp::sendPDMessage(const void *pData, UINT32 dataSize) { qDebug() << "Sending PD message" << reinterpret_cast<const UINT8 *>(pData) << "with size" << dataSize; const UINT8* data = reinterpret_cast<const UINT8 *>(pData); // Ensure pubHandle is initialized; call initPDPublisher() before this if not already done if (this->pubHandle == NULL) { qDebug() << "Publisher not initialized. Initializing now."; initPDPublisher(); if (this->pubHandle == NULL) { qDebug() << "Failed to initialize publisher. Cannot send PD message."; return TRDP_INIT_ERR; } } TRDP_ERR_T err = tlp_put( this->appHandle, // Use class member appHandle this->pubHandle, // Use the initialized publisher handle data, // Data to send dataSize // Size of the data to send ); if (err != TRDP_NO_ERR) { qDebug() << "Error sending PD message: " << err; } return err; } // Method for sending MD messages TRDP_ERR_T Trdp::sendMDMessage(const void *pData, UINT32 dataSize) { qDebug() << "Sending MD message" << reinterpret_cast<const UINT8 *>(pData) << "with size" << dataSize; const UINT8* data = reinterpret_cast<const UINT8 *>(pData); TRDP_ERR_T err = tlm_request( this->appHandle, // Application session handle NULL, // Message handle (NULL for auto) NULL, // User reference NULL, // Callback function (NULL for no callback) 1, // Service ID (1 for default) PD_COMID + 1, // ComId (0 for default) 0, // etbTopoCnt (0 for default) 0, // etbConfigCnt (0 for default) vos_dottedIP("127.0.0.1"), // Destination IP address TRDP_FLAGS_DEFAULT, // Flags 0, // Priority (0 for default) 1000000u, // Timeout (in microseconds) NULL, // Marshalling function data, // Data pointer dataSize, // Data size NULL, // Response timeout (NULL for no response) NULL // Response callback (NULL for no callback) ); if (err != TRDP_NO_ERR) { qDebug() << "Error sending MD message: " << err; } else { qDebug() << "MD message sent successfully."; } return err; }
排查要点
- 必须执行TRDP核心循环:TRDP库依赖
tlc_processCycle函数处理发送队列、网络IO等核心逻辑,当前代码未调用该函数,导致数据包无法从缓冲区发送到网络。需在QT事件循环中通过QTimer定时调用tlc_processCycle(appHandle),建议调用周期与processConfig中的cycleTime保持一致(默认1ms)。 - PD消息发送间隔配置:
tlp_publish中设置的Interval为1000000u(1秒),tlp_put后TRDP会按此间隔发送数据包。若需立即发送,需将Interval设为0。 - MD消息参数有效性检查:
tlm_request中直接调用vos_dottedIP("127.0.0.1"),需确认返回值有效,建议复用类中已初始化的dstIP变量,避免重复调用可能导致的内存或参数错误。 - 启用TRDP内部日志:自定义的
dbgOut函数为空实现,无法获取库内部的错误信息。需添加日志输出,例如:void Trdp::dbgOut ( void *pRefCon, TRDP_LOG_T category, const CHAR8 *pTime, const CHAR8 *pFile, UINT16 LineNumber, const CHAR8 *pMsgStr) { qDebug() << "[TRDP Log]" << pTime << pFile << LineNumber << pMsgStr; } - 网络环境验证:确认本地防火墙未拦截UDP端口17225;Wireshark过滤规则需正确,可使用
udp.port == 17225或trdp过滤TRDP数据包。 - Session初始化有效性校验:当前
tlc_openSession失败后仍继续执行后续逻辑,需确保appHandle初始化成功后再进行发布和发送操作,避免使用无效句柄。
内容的提问来源于stack exchange,提问作者Evgeni Atanasov
相关产品推荐
相关产品推荐

