Qt - QTcpSocket handle in a new thread

Trying to process a connected client socket in a new thread from the global thread pool:

m_threadPool = QThreadPool::globalInstance(); void TCPListenerThread::onNewConnection() { QTcpSocket *clientSocket = m_tcpServer->nextPendingConnection(); clientSocket->localPort(); m_connectThread = new TCPConnectThread(clientSocket); m_threadPool->start(m_connectThread); } 

Here is TCPConnectThread :

 class TCPConnectThread : public QRunnable { TCPConnectThread::TCPConnectThread(QTcpSocket *_socket) { m_socket = _socket; this->setAutoDelete(false); } void TCPConnectThread::run() { if (! m_socket->waitForConnected(-1) ) qDebug("Failed to connect to client"); else qDebug("Connected to %s:%d %s:%d", m_socket->localAddress(), m_socket->localPort(), m_socket->peerAddress(), m_socket->peerPort()); if (! m_socket->waitForReadyRead(-1)) qDebug("Failed to receive message from client") ; else qDebug("Read from client: %s", QString(m_socket->readAll()).toStdString().c_str()); if (! m_socket->waitForDisconnected(-1)) qDebug("Failed to receive disconnect message from client"); else qDebug("Disconnected from client"); } } 

I get endless errors from them. It seems that handling QTcpSocket cross streams QTcpSocket not practical (see Michael's answer).

Some errors:

 QSocketNotifier: socket notifiers cannot be disabled from another thread ASSERT failure in QCoreApplication::sendEvent: "Cannot send events t objects owned by a different thread. 

Should I handle QTcpSocket in another thread?
What if I want to handle QTcpSocket in another thread?
Or is there a way to create a QTcpSocket from a file descriptor?

+6
c ++ qt
source share
1 answer

I think this page contains your answer:

If you want to treat the incoming connection as a new QTcpSocket object in another thread, you must pass the socketDescriptor to another thread and create a QTcpSocket object there and use its setSocketDescriptor ().

To do this, you need to inherit from QTcpServer and override the incomingConnection virtual method.

Inside this method, create a child thread that will create a new QTcpSocket for the child socket.

For example:

 class MyTcpServer : public QTcpServer { protected: virtual void incomingConnection(int socketDescriptor) { TCPConnectThread* clientThread = new TCPConnectThread(socketDescriptor); // add some more code to keep track of running clientThread instances... m_threadPool->start(clientThread); } }; class TCPConnectThread : public QRunnable { private: int m_socketDescriptor; QScopedPointer<QTcpSocket> m_socket; public: TCPConnectionThread(int socketDescriptor) : m_socketDescriptor(socketDescriptor) { setAutoDelete(false); } protected: void TCPConnectThread::run() { m_socket.reset(new QTcpSocket()); m_socket->setSocketDescriptor(m_socketDescriptor); // use m_socket } }; 

or try using moveToThread() on the socket.

+8
source share

All Articles