threading object function c++ - c++

i'm having trouble with some threads in my program
I'm new in this thread material
I'm trying to start 2 threads on 2 different object function and it seems that they are not working at the same time (t1 works and t2 dont)..
edit:
the function of t1 works but t2 doesnt work. i checked t2 and t1, on their own they work, but together its like t1 prevents t2 from working
here is the main:
MessagesSender MSM=MessagesSender();
MSM.Push_user("ronik");
MSM.Push_user("ligal");
thread t1(&MessagesSender::DataRead,&MSM);
thread t2(&MessagesSender::DataSend, &MSM);
t1.join();
t2.join();
return 0;
here are is the function of t1:
void MessagesSender::DataRead()
{
ifstream file_read;
ofstream file_delete;
string line;
while (true)
{
file_read.open("data.txt"); // opens the file
mtx.lock(); // locks the use of THOR
while (getline(file_read, line)) // reads to THOR
{
cout << "im reading now" << endl;
this->THOR.push(line);
}
mtx.unlock(); // unlock the use of THOR
file_read.close(); // closes the file for reading
file_delete.open("data.txt", ios::out | ios::trunc);/// opens the file and deletes the content/data
file_delete.close(); // closes the file
cout << "im sleeping now" << endl;
print_THOR();
this_thread::sleep_for(chrono::seconds(30)); // makes the thread sleep for 1 minute
}
}
here is the function of t2:
void MessagesSender::DataSend()
{
ofstream file_send;
file_send.open("output.txt");
set<string>::iterator SEI;
while (true)
{
mtx.lock();
while (!THOR.empty()) // while that prints all the THOR lines
{
for (SEI = ConUsers.begin(); SEI != ConUsers.end(); SEI++) /// to print the users
{
if (THOR.empty())
{
break;
}
string p2(THOR.front());
cout << "im sending now" << endl;
file_send << *SEI << ": " << p2 << endl;
}
}
mtx.unlock();
THOR.push("im empty");
print_THOR();
this_thread::sleep_for(chrono::seconds(30));
}
file_send.close();
}

I believe this may be an issue of buffered streams. You are using the std::cout and calling std::endl. This causes the thread to pause until the data has been written to the console (slow). I've done this before and had the same problem. t2 is getting hung up on the buffered stream, waiting for it to be cleared while t1 has used it. Try replacing your std::endl with regular '\n' then just do a std::cout << std::flush; at the end of your program.

Related

File closes automatically

I am encountering a problem when I am trying to write to sysfs node.
In the below code I am trying to wite to a trace_marker file. In the ftrace log, the first write is successful. But after that the write fails.
The file descriptor seemingly closes.
I do not want to open file every time before writing as writes are too frequent.
class Logger {
int mFileFd;
void logFromAnotherThread(std::string s) {
std::unique_lock<std::mutex> ul(mLogMu);
...
int count = write(mFileFd, s.c_str(), s.length());
if (count > 0)
std::cout << "Wrote n bytes: " << count << std::endl;
else
std::cout << "Errornum: " << strerror(errno) << std::endl;
...
}
Logger() {
mFileFd = open(SYSFS_NODE_WRITE, O_WRONLY);
....
}
}
First write is succesful.
I get output as-
Errornum: Bad file descriptor
My expectation is file open should be once, file descrtiptor should remain open for entire duration, and close on exit.
Edit 1:
Thank you for the suggestions on object getting destroyed. But I ensure that object is not getting destroyed.
For debugging, I had removed class/structure. Logging is now in simple C++ function calls. The file descriptor is a global variable, initialized once in main.
It does not works.
My confusion was is it something to do with the way write operations are performed on sysfs node.
Or can this be because of the number of writes are high (about 2-3 logs in 10us).
I am doing this like below, but this has an overhead of two added system calls.
#define TRACE_MARKER_FILE "/sys/kernel/debug/tracing/trace_marker"
void logdata(pid_t tid, std::string mystring) {
if(useLogger) {
std::stringstream ss;
if (funcname.length() > 0)
ss << LOGTAG << mystring;
int tempfd = open(TRACE_MARKER_FILE, O_WRONLY);
int count = write(tempfd, ss.str().c_str(), ss.str().length());
if (count == 0) {
std::cout << "Errornum: " << strerror(errno) <<std::endl;
}
close(tempfd);
}
}
I would suggest using std::ofstream which allows for proper RAII, in other words it will open the file in your constructor, then will automatically close the file in your destructor
class Logger {
std::ofstream mFile;
void logFromAnotherThread(std::string s) {
std::unique_lock<std::mutex> ul(mLogMu);
...
mFile << s;
...
}
Logger() : mFile(SYSFS_NODE_WRITE, O_WRONLY) {
....
}
}

How to use mutex in loops properly in c++?

I'm new for threads and mutex and ı trying to learn them. I write some code that generally create a queue that enqueue all of the numbers from the file ( this file has nearly 20.000 lines and lots of information) since this file contains a lots of information for procees ı need to have multithreads, at the beginning user create the number of threads, then ı stuck at the part that in a while loop ı wanted see which threads enter the loop for dequing the id from queue, but apparently just the first created thread enters and dequeue all of them, ı used mutex for ensure that while a thread enters the loop make it process (dequeue a number) then unlock this mutex in order to other threads can enter but apprently ı did a mistake . Here is the code `
void printer( DynIntQueue & myQueue) // takes the Dynamic Queue
{
//int count = 0;
queMutex.lock(); // lock it before any threads come it
while(!myQueue.isEmpty()) // check this condition
{
int num;
cout << "Thread " << this_thread::get_id << " is working" << endl; // this is for printing out which threads enter this loop
myQueue.dequeue(num); // deqeueu this number from queue
queMutex.unlock(); // unlock this in order to next thread might enter
queMutex.lock(); // when this thread enters lock it in order to other threads to wait
}
queMutex.unlock(); // if myQueue is empty since it is firsly locked, unlock this
}`
My output is like this: Thread 005C1659 is working Thread 005C1659 is working Thread 005C1659 is working Thread 005C1659 is working Thread 005C1659 is working Thread 005C1659 is working Thread 005C1659 is working Thread 005C1659 is working Thread 005C1659 is working Thread 005C1659 is working
This goes on until the myQueue is empty with the same thread. What can ı do ensure that other threads might enter this loop?
Edited: Here is the main part `
int main()
{
DynIntQueue firstQueue;
ifstream input;
string line;
int numofthreads;
input.open("data.tsv");
getline(input, line); // for first empty
int id, houseAge, avgRooms, avgBedRooms, latitue, longitute, medianPrice;
cout << "Please enter the number of threads you want " << endl;
cin >> numofthreads;
vector <thread> Threads(numofthreads);
while (!input.eof())
{
getline(input, line);
istringstream divider(line);
divider >> id >> houseAge >> avgRooms >> avgBedRooms >> latitue >> longitute >> medianPrice;
firstQueue.enqueue(id);
}
for (int i = 0; i < numofthreads; i++)
{
Threads[i] = thread(&printer, ref(firstQueue));
}
for (int i = 0; i < numofthreads; i++)
{
Threads[i].join();
}
return 0;
}
Note: std::this_thread::get_id() is a function, so you should be calling it. I assume this is just a copy/paste error.
If I add some work between opening and closing the queue, i clearly see two threads using the queue.
I don't think you have any issue with the code shown.
#include <iostream>
#include <thread>
#include <mutex>
#include <queue>
struct DynIntQueue {
bool isEmpty() const { return q_.empty(); }
void dequeue(int &elem) { elem = q_.front(); q_.pop(); }
std::queue<int> q_{{10, 20, 4, 8, 92}};
};
std::mutex queMutex;
void printer( DynIntQueue & myQueue) {
queMutex.lock();
while(!myQueue.isEmpty()) {
int num;
std::cout << "Thread " << std::this_thread::get_id() << " is working" << std::endl;
myQueue.dequeue(num);
queMutex.unlock();
std::cout << "working outside the lock" << std::endl;
std::cout << "working outside the lock" << std::endl;
std::cout << "working outside the lock" << std::endl;
std::cout << "working outside the lock" << std::endl;
std::cout << "working outside the lock" << std::endl;
queMutex.lock();
}
queMutex.unlock();
}
int main() {
std::cout << "Hello World!\n";
DynIntQueue q;
std::thread t1([&q]() { printer(q); });
std::thread t2([&q]() { printer(q); });
t1.join();
t2.join();
}
$ clang++-7 -pthread -std=c++17 -o main main.c
$ ./main
Hello World!
Thread 139686844172032 is working
working outside the lock
working outside the lock
working outside the lock
working outside the lock
working outside the lock
Thread 139686835779328 is working
working outside the lock
working outside the lock
working outside the lock
working outside the lock
working outside the lock
Thread 139686844172032 is working
working outside the lock
working outside the lock
working outside the lock
working outside the lock
working outside the lock
Thread 139686835779328 is working
working outside the lock
working outside the lock
working outside the lock
working outside the lock
working outside the lock
Thread 139686844172032 is working
working outside the lock
working outside the lock
working outside the lock
working outside the lock
working outside the lock

c++ allow background thread to finish before exiting application

c++ win 32 application . VS 2013
I am making use of a 3rd party library.
I want to call 3rd party library's function in a background thread.
I then also want to eventually turn it off.
I suspect I dont give third party enough time to properly shut itself down before I exist the application.
How do I ensure the detached task I started on a separate thread is done before I exit the main().
//this class interfaces with the third part and runs on a separate thread
class ThirdParty
{
void Start(std::string filename)
{
MyApplication application;
FIX::SessionSettings settings(filename);
FIX::FileStoreFactory storeFactory(settings);
FIX::ScreenLogFactory logFactory(settings);
FIX::SocketAcceptor acceptor(application, storeFactory, settings, logFactory);
acceptor.start(); //this third party internally starts new threads and does stuff thats transparent to consumer like myself.
while (m_runEngine)
{}
//this shutsdown a few things and cant execute instantaneously
//This does not finish execution and main() already ends.
acceptor.stop();
}
void Stop()
{
m_runEngine = false;
}
private:
bool m_runEngine{ true };
}
Here is my main() in a win32 application
int _tmain(int argc, _TCHAR* argv[])
{
std::wstring arg = argv[1];
std::string filename = std::string(arg.begin(), arg.end());
ThirdParty myprocess;
std::thread t(&ThirdParty::Start, &myprocess, filename);
t.detach();
while (true)
{
std::string value;
std::cin >> value;
if (value == "quit")
break;
}
myprocess.Stop(); //This line will execute really fast and application will exit without allowing acceptor.stop() to properly finish execution
//How can I ensure acceptor.stop() has finished execution before I move on to the next line and finish the application
return 0;
}
Do not make you thread detached, so that you can wait for it to end using thread::join():
//t.detach() do not detach thread
...
myprocess.Stop();
t.join(); // wait for t to end
I think the following example illustrates the interesting aspects of thread join.
void pause_thread(int n, std::string lbl)
{
std::this_thread::sleep_for (std::chrono::seconds(n));
std::cout << lbl << " pause of " << n << " seconds ended" << std::endl;
}
int t403(void) // in context of thread main
{
std::cout << "Spawning 3 threads...\n" << std::flush;
std::thread t1 (pause_thread, 3, "t1");
std::thread t2 (pause_thread, 2, "t2");
std::thread t3 (pause_thread, 1, "t3");
std::cout << "Done spawning threads, "
"Note that the threads finish out-of-order. \n"
"Now 'main' thread waits for spawned threads to join:\n" << std::flush;
t1.join(); std::cout << "join t1 " << std::flush;
t2.join(); std::cout << "join t2 " << std::flush;
t3.join(); std::cout << "join t3 " << std::flush;
std::cout << "completed join \n"
"note: \n - join sequence is in-order, but finish sequence is out-of-order\n"
" - inference: the threads waited in join main. "<< std::endl;
return(0);
}
Note that the threads are spawned in order: t1, t2, t3.
Note that the threads end in a different order.
But the join is still in the launch order, because that is what main waits for.
Using 'std::flush()' presents the timeline that has been chosen slow enough for human vision.

Code won't advance past wait function for conditional variable

So, I've been trying to get a better understand of how condition variables work and I've written the following code that tries to implement reading and writing from the same text file:
#include <iostream>
#include <fstream>
#include <cstdlib>
#include <condition_variable>
#include <mutex>
#include <thread>
using namespace std;
mutex mtx;
condition_variable conditionVariable;
ifstream readFile;
ofstream writeFile;
bool doneReading=false;
bool doneWriting=false;
void readFromFile()
{
string line;
readFile.open("./testFile.txt");
if(readFile.is_open())
{
cout << "Successfully opened file!" << "\n";
}
else
{
cout << "Failed to open file..." << "\n";
}
cout << "The file contents are:" << "\n";
while(getline(readFile,line))
{
unique_lock<mutex> lock(mtx);
conditionVariable.wait(lock, [] () {return doneWriting;});
cout << line << "\n";
doneReading=true;
lock.unlock();
conditionVariable.notify_one();
}
readFile.close();
}
void writeToFile()
{
string input;
writeFile.open("./testFile.txt");
cout << "Enter something you want to write to the text file:" << "\n";
cin >> input;
cout << "Going to write " << input << " to the file" << "\n";
if(writeFile.is_open())
{
cout << "Successfully opened file!" << "\n";
unique_lock<mutex> lock2(mtx);
/////////PROGRAM WON'T ADVANCE PAST THIS LINE/////////////
conditionVariable.wait(lock2, [] () {return doneReading;});
cout << "After calling the wait function for the condition variable" << "\n";
writeFile << input;
doneWriting=true;
lock2.unlock();
conditionVariable.notify_one();
writeFile.close();
}
else
{
cout << "Failed to open file..." << "\n";
}
}
int main()
{
int i;
for(i=0;i<10;i++)
{
thread t1(readFromFile);
thread t2(writeToFile);
t1.join();
t2.join();
}
}
And, I modeled my use of boolean variables after the following example from
cppreference.com (scroll down to the bottom to see the example code). However, it has something do the predicate I am passing to the wait function, and I'm not quite sure what is wrong with it. If someone could give some insight, that would be brilliant. Thanks!
Initial state is:
bool doneReading=false;
bool doneWriting=false;
The first thing readFromFile does to these variables is sit and wait for doneWriting to become true
conditionVariable.wait(lock, [] () {return doneWriting;});
The first thing writeFromFile does to these variables is sit and wait for doneReading to become true
conditionVariable.wait(lock2, [] () {return doneReading;});
Neither condition will become true.
Note that the cppreference example does something very different: one thread begins by executing cv.wait(lk, []{return ready;}); while the other begins by executing ready=true;

How can I execute two threads asynchronously using boost?

I have the book "beyond the C++ standard library" and there are no examples of multithreading using boost. Would somebody be kind enough to show me a simple example where two threads are executed using boost- lets say asynchronously?
This is my minimal Boost threading example.
#include <boost/thread.hpp>
#include <iostream>
using namespace std;
void ThreadFunction()
{
int counter = 0;
for(;;)
{
cout << "thread iteration " << ++counter << " Press Enter to stop" << endl;
try
{
// Sleep and check for interrupt.
// To check for interrupt without sleep,
// use boost::this_thread::interruption_point()
// which also throws boost::thread_interrupted
boost::this_thread::sleep(boost::posix_time::milliseconds(500));
}
catch(boost::thread_interrupted&)
{
cout << "Thread is stopped" << endl;
return;
}
}
}
int main()
{
// Start thread
boost::thread t(&ThreadFunction);
// Wait for Enter
char ch;
cin.get(ch);
// Ask thread to stop
t.interrupt();
// Join - wait when thread actually exits
t.join();
cout << "main: thread ended" << endl;
return 0;
}