我们创建了一个从QTcpServer派生的Qt HTTP服务器。 每个传入的客户端连接都在一个新的线程中处理,如下所示:
void WebClientThread::run()
{
// Configure the web client socket
m_socket = new QTcpSocket();
connect(m_socket, SIGNAL(disconnected()), this, SLOT(disconnected()));
connect(m_socket, SIGNAL (error(QAbstractSocket::SocketError)), this, SLOT(socketError(QAbstractSocket::SocketError)));
// Create the actual web client = worker
WebClient client(m_socket, m_configuration, m_pEventConnection, m_pThumbnailStreams, m_server, m_macAddress, 0 );
// Thread event loop
exec();
m_pLog->LOG(L_INFO, "Webclient thread finished");
}
//
// Client disconnect
//
void WebClientThread::disconnected()
{
m_socket->deleteLater();
exit(0);
}
此代码有效,但是当我们的设备的NTP连接启动并且系统时间从01/01/1970纪元更正到当前时间时,我们遇到应用程序崩溃。 运行应用程序时也可以重现崩溃,同时从脚本中更改系统时间。
应用程序运行正常 - 即使系统时间如此动态变化:
void WebClientThread::run()
{
// Configure the web client socket
m_socket = new QTcpSocket();
connect(m_socket, SIGNAL(disconnected()), this, SLOT(disconnected()));
connect(m_socket, SIGNAL (error(QAbstractSocket::SocketError)), this, SLOT(socketError(QAbstractSocket::SocketError)));
// Create the actual web client = worker
WebClient client(m_socket, m_configuration, m_pEventConnection, m_pThumbnailStreams, m_server, m_macAddress, 0 );
// Make this thread a loop,
exec();
delete m_socket;
m_pLog->LOG(L_INFO, "Webclient thread finished");
}
//=======================================================================
//
// Client disconnect
//
void WebClientThread::disconnected()
{
exit(0);
}
为什么deleteLater()会在系统时间转移时使应用程序崩溃?
其他信息:
OS =嵌入式Linux 3.0.0。 Qt = 4.8
套接字是我们的Qt Web服务器应用程序和前端服务器= lighttpd之间的连接。当系统时间转移47年并且我们的Web服务器仍处理请求时,lighttpd是否会关闭套接字?
我可以通过向服务器发送请求来重现它,同时并行运行将日期设置为1980年,1990年和2000年的脚本。它每秒更改一次。
答案 0 :(得分:0)
这种Qt线程错误使用的气味。如果你从QThread
方法调用exec()
,我建议你不要继承run()
,因为如果你这样做,那就太容易做错了。
请参阅示例https://wiki.qt.io/QThreads_general_usage以了解如何为 QThread 设置worker QObject ,但要点是,创建{{的子类1}}并将您的代码放在那里。然后将其实例移动到QObject
实例,并连接信号和插槽以使事情发生。
另外,你通常不应该使用线程进行Qt网络,例如QThread
。 Qt是基于事件和异步的,只要您只使用信号和插槽并且永远不会阻塞您的插槽方法,就不需要线程,它们只会使事情复杂化而没有任何好处。只有当你有耗时的计算,或者你的程序真的需要利用多个CPU内核来获得足够好的性能时,才会考虑多线程。