#include <iostream>
using namespace std;
#include "Thread.h"
int main ( ) {
Thread reader( READER );
Thread writer( WRITER );
reader.start( );
writer.start( );
reader.join( );
writer.join( );
return 0;
}
#ifndef __THREAD_H
#define __THREAD_H
#include <iostream>
#include <string>
#include <thread>
#include <mutex>
#include <string>
using namespace std;
enum ThreadType {
READER,
WRITER
};
class Thread {
private:
string name;
thread *pThread;
ThreadType threadType;
static mutex commonLock;
static int count;
bool stopped;
void run( );
public:
Thread ( ThreadType typeOfThread );
~Thread( );
void start( );
void stop( );
void join( );
void detach ( );
int getCount( );
int updateCount( );
};
#endif
#include "Thread.h"
mutex Thread::commonLock;
int Thread::count = 0;
Thread::Thread( ThreadType typeOfThread ) {
pThread = NULL;
stopped = false;
threadType = typeOfThread;
(threadType == READER) ? name = "READER" : name = "WRITER";
}
Thread::~Thread() {
delete pThread;
pThread = NULL;
}
int Thread::getCount( ) {
cout << name << " is waiting for lock in getCount() method ..." <<endl;
lock_guard<mutex> locker(commonLock);
cout << name << " has acquired lock in getCount() method ..." <<endl;
return count;
}
int Thread::updateCount( ) {
// int value = getCount(); // deadlock 해결
cout << name << " is waiting for lock in updateCount() method ..." <<endl;
lock_guard<mutex> locker(commonLock);
int value = getCount(); // deadlock
cout << name << " has acquired lock in updateCount() method ..." <<endl;
count = ++value;
return count;
}
void Thread::run( ) {
while ( 1 ) {
switch ( threadType ) {
case READER:
cout << name<< " => value of count from getCount() method is "
<<getCount() << endl;
this_thread::sleep_for ( 1ms );
break;
case WRITER:
cout << name << " => value of count from updateCount() method is "
<<updateCount() << endl;
this_thread::sleep_for ( 1ms );
break;
}
}
}
void Thread::start( ) {
pThread = new thread ( &Thread::run, this );
}
void Thread::stop( ) {
stopped = true;
}
void Thread::join( ) {
pThread->join();
}
void Thread::detach( ) {
pThread->detach( );
}
# release mode build
$ g++-7 Thread.cpp main.cpp -o deadlock -std=c++17 -lpthread
# debug mode build
$ g++ Thread.cpp main.cpp -o deadlock -std=c++17 -lpthread -g
$ valgrind --tool=helgrind ./deadlock