Reputation: 16502
I have a class that encapsulates all the business logic related to using Asio to read and write to a generic stream socket. I'd like to add a flag so my users know if they can retrieve data from a getter or whether we're still waiting for the backend.
How is this normally done? Set a flag to busy after the write and do the read in the background in a separate thread? The flag would be something similar to PQisBusy
Upvotes: 1
Views: 91
Reputation: 1086
Don't know if you are looking for an asynchronous solution such as using a callback or a polling method. From the question it seems you are looking for a polling method since you want a flag that users can check to see if the data is fully ready. In that case just define a variable and function in your class, .h file:
#include <atomic>
#include <thread>
class MySocket
{
public:
~MySocket();
bool IsReady();
void StartDataGather();
private:
void GatherDataThread();
static std::atomic<bool> _isReady;
std::thread _thread;
}
In your .cpp file:
#include "MySocket.h"
static std::atomic<bool> MySocket::_isReady(false); // Default flag to false.
MySocket::~MySocket()
{
// Make sure to kill the thread if this class is destroyed.
if (_thread.joinable())
_thread.join();
}
bool MySocket::IsReady() { return _isReady; }
void MySocket::StartDataGather()
{
_isReady = false; // Reset flag.
// If your gather thread is running then stop it or wait for it
// to finish before starting it again.
if(_thread.joinable())
_thread.join();
// Start the background thread to gather data.
_thread = std::thread(GatherDataThread());
}
void MySocket::GatherDataThread()
{
// This is your thread that gathers data.
// Once all of the data is gathered, do the following:
_isReady = true;
}
To use this method from outside of your client class do the following:
MySocket mySock;
mySock.StartDataGather();
while(!mySock.IsReady())
{
// Do some other code here until data is ready.
// Once the MySocket::GatherDataThread() finishes it will
// set _isReady = true which will cause mySock.IsReady() to
// return true.
}
You now have a flag that others can check and it is thread safe because of the std::atomic<>
template. The following uses C++ 11 or newer -std=c++11
.
Upvotes: 2
Reputation: 4473
if by user, you mean user of a library, I would recommend wrapping the result of the asynchronous method in an std::future
or similar thread synchronization mechanism. You could use the wait_for
method to fail and notify that the process is still ongoing, then try again.
Upvotes: 0