Unsolved QSocketNotifier: Socket notifiers cannot be enabled or disabled from another thread
-
This post is deleted! -
@mrjj the header of server look like:
#ifndef MYSERVER_H #define MYSERVER_H #include <QObject> #include <QDebug> #include <QTcpServer> #include <QTcpSocket> #include <QString> #include <QFile> #include <QStandardPaths> #include <QThread> #include <QElapsedTimer> #include <pool.h> #include <QDateTime> class MyServer : public QObject { Q_OBJECT public: explicit MyServer(QObject *parent = nullptr); signals: public slots: void newConnection(); void onReadyRead(); private: QTcpServer *server; QList<QTcpSocket*> _sockets; QString a; QString com; QTcpSocket *socket; QList<QTcpSocket*> sl; /*protected: void incomingConnection(qintptr socketDescriptor) override;*/ }; #endif // MYSERVER_H
-
Sorry but please learn C++ first. If you want to override a function from a class you should inherit from this class. So inherit from QTcpServer, override the function and do whatever you want to. This is basic c++ stuff...
-
@Christian-Ehrlicher That's the thing, that I didn't notice. Thanks
-
@Christian-Ehrlicher But I don't know, how to edit it.
-
I have rewritten half of my project to solve the problem:
myserver.h#ifndef MYSERVER_H #define MYSERVER_H #include <QStringList> #include <QTcpServer> #include <QDateTime> class MyServer : public QTcpServer { Q_OBJECT public: MyServer(QObject *parent = nullptr); protected: void incomingConnection(qintptr socketDescriptor) override; private: QStringList fortunes; }; #endif // MYSERVER_H
myserver.cpp
#include "myserver.h" #include "pool.h" Pool p; MyServer::MyServer(QObject *parent) : QTcpServer(parent) { p.start(); } void MyServer::incomingConnection(qintptr socketDescriptor) { QDateTime qdt; p.add(socketDescriptor,qdt.time()); }
pool.h
#ifndef POOL_H #define POOL_H #include<QObject> #include<QThread> #include<QTcpSocket> #include<QDateTime> #include<QElapsedTimer> class Pool : public QThread { Q_OBJECT protected: void run(); private: struct conn{ QTcpSocket *s; QTime qdt; }; QList<conn> x; public: void add(int socketDescriptor, QTime qdt); }; #endif // POOL_H
pool.cpp
#include "pool.h" #include <QElapsedTimer> void Pool::run() { QElapsedTimer qet; qet.start(); while (true) { if(qet.elapsed()>=5000){ foreach (conn y, x) { if(y.s==nullptr){ qDebug()<<"empty"; continue; } y.s->write("test"); y.s->flush(); } qet.restart(); } } } void Pool::add(int socketDescriptor, QTime qdt){ QTcpSocket* s = new QTcpSocket; s->setSocketDescriptor(socketDescriptor); s->write("1\n"); conn c; c.s=s; c.qdt=qdt; x.append(c); }
But I have still the same error:
QSocketNotifier: Socket notifiers cannot be enabled or disabled from another thread
What's wrong?
-
Because your add method is called in the thread of the tcp server.
As I already told you, the socket creation must happen in the run function.
-
@SGaist I have solved it. I am creating a list of descriptors in add() method and then rewriting it like this:
pool.cppvoid Pool::run() { QElapsedTimer qet; qet.start(); while (true) { if(!d.empty()){ qDebug()<<"rewriting"; for (int i = 0; i<d.size();i++) { desc des = d[i]; conn con; QTcpSocket* soc = new QTcpSocket; soc->setSocketDescriptor(des.descriptor); con.s=soc; con.qdt=des.qt; d.removeAt(i); x.append(con); } qDebug()<<"done"; } if(qet.elapsed()>=5000){ foreach (conn y, x) { if(!y.s->isOpen()){ qDebug()<<"empty"; continue; } y.s->write("test"); qDebug()<<"l"; y.s->flush(); } qet.restart(); } } } void Pool::add(int socketDescriptor, QTime qdt){ desc de; de.descriptor=socketDescriptor; de.qt=qdt; d.append(de); }
definitions of structs and lists in pool.h:
struct conn{ QTcpSocket *s; QTime qdt; }; struct desc{ qintptr descriptor; QTime qt; }; QList<conn> x; QList<desc> d;
-
You are missing one important thing: you are accessing a resource from two different threads. You should protect its access accordingly.
-
@SGaist In my last code it is fixed, right? If no, how to protect it correctly?
-
When using a new technology it's always a good idea to start by reading the documentation.
-
@SGaist I have read it, but I didn't catch what should I edit in my code.
-
Did you read the Synchronizing Threads chapter linked in it ?