我已经用
std::thread
定义了一个基类。 对于子类,我执行了一些成员变量的初始化,然后使用
m_thread.reset(new std::thread(&MyClass::ThreadMain, this));
启动线程,其中m_thread是MyClass的成员。 该类的目的是从串口中读取数据并向父类报告。 在创建线程之前,父类的posix消息队列句柄在初始化时被传递给MyClass。 在运行过程中,我得到了异常,而且我看到在线程开始前被初始化的成员变量似乎在GDB中使用观察器不再有效。
看起来好像串行端口上的第一条信息被接收并通过验证,以便进入
SendToParent
的调用。 在这个调用中,我似乎失去了堆栈。 我试着运行cppcheck,看看我是否有任何内存泄漏或缓冲区溢出,结果没有发现。
void MyClass::ThreadMain(void)
ssize_t bytesRead = 0;
UINT8 buffer[256];
UINT8 message[256];
BOOL partialMessage = FALSE;
UINT8 messageIndex = 0;
UINT8 payloadLength = 0;
// read data from the UART
while(1)
// the UART is setup to pend until data is available
bytesRead = read(m_radioFileDescriptor, buffer, sizeof(buffer));
if (FAIL == bytesRead)
LOG_SYSTEM_INFO("UART Read interrupted by a system call");
else if (bytesRead > 0)
// build the message
for(ssize_t i = 0 ; i < bytesRead ; i++)
if (FALSE == partialMessage)
// have we found the start of the message?
if(START_BYTE == buffer[i])
// start of new message
messageIndex = 0;
message[messageIndex] = buffer[i];
partialMessage = TRUE;
messageIndex++;
// keep building the message until the expected length is reached
if(LENGTH_POSITION == messageIndex)
// capture the expected message length
message[messageIndex] = buffer[i];
messageIndex++;
payloadLength = buffer[i];
message[messageIndex] = buffer[i];
messageIndex++;
// check for expected length and end byte
if((messageIndex == payloadLength) && (END_BYTE == buffer[i]))
// this should be a valid message but need to confirm by checking for a valid checksum
UINT8 messageChecksum = message[messageIndex - CHKSUM_POS_FROM_END];
UINT8 calculatedChecksum = RadioProtocol::Instance().GenerateRadioChecksum(message, (payloadLength - CHKSUM_POS_FROM_END));
if (messageChecksum == calculatedChecksum)
SendToParent(message, payloadLength);
LOG_SYSTEM_ERROR("Checksum FAILURE");
// reset for the next message
partialMessage = FALSE;
messageIndex = 0;
else if((messageIndex == payloadLength) && (END_BYTE != buffer[i]))
// malformed message - throw out and look for start of next message
LOG_SYSTEM_ERROR("Bytes read exceeded expected message length");
partialMessage = FALSE;
messageIndex = 0;
} // end for loop of bytes read on the port
LOG_SYSTEM_INFO("Read returned 0 bytes which is unexpected");
void MyClass::SendToParent(UINT8* pMsg, UINT8 size)
if ((pMsg != NULL) && (m_parentQueueHandle > 0))
// message is valid - pass up for processing
MsgQueueMessage msgToSend;
msgToSend.m_msgHeader = UART_MESSASGE;
bzero(msgToSend.m_msgData, sizeof(msgToSend.m_msgData));
for (UINT8 i = 0; i < size; i++)
msgToSend.m_msgData[i] = pMsg[i];
if (FAIL == msgsnd(m_parentQueueHandle, &msgToSend, sizeof(msgToSend), IPC_NOWAIT))
LOG_SYSTEM_ERROR("FAILED to send message on queue");