Consider the following GUI:
when the user press the button the value is incremented to 6.
However on another computer another user is running the same GUI.
The two GUIs have to stay in sync. If one of the users press the button the value should be updated for both GUIs.
The remote GUI, the client, communicate with the local server via a simple protocol. The communication takes the form of a cmd sent from the client and a response sent from the server. There are two commands:
1. cmd:"GET_VALUE", response: "5"
2. cmd: "INCREMENT", response: "OK"
Unfortunately the client has to poll GET_VALUE to be notified, but the protocol albeit flawed can not be changed.
How can I implement this in Qt, C ?
So far I have come up with the following classes (rough outline):
class Model {
public:
std::atomic<int> m_value;
};
class Widget : public QWidget {
public slots:
void incrementClickedLocally(); // must update Model::m_value somehow
void valueChangedFromModel(int value); // will update the QLineEdit
};
// Reads synchronously from TCP/IP using WinSocket and works on the Model
class RemoteHandler : public QThread {
private:
void run override();
};
I would like to use signals/slots to communicate across the threads.
However it seems that the RemoteHandler
can not use signal/slots to get the Model::m_value
since slots can not have return types?
Further it would be convenient to emit a valueChanged
signal from Model to notify Widget. However in order to do that Model must be a QObject.
It seems that when Model becomes a QObject there are many potential thread problems I have to look out for?
As it is Model
is threadsafe. I can therefore request Model::m_value
directly from the non main thread in RemoteHandler
while the Widget may be accessing the same variable simultaneously from the main thread.
CodePudding user response:
It cannot work with those commands.
The logic is well-known from the design of multi-core CPU's. You need Compare-and-Swap (CAS), Load-Link/Store Conditional (LL/SC) or something equally powerful. With the weak protocol you have, it can be proven that the race conditions are unsolvable.