lab5, reader/writer problem
This commit is contained in:
@@ -10,7 +10,7 @@
|
||||
|
||||
class ReaderWriter {
|
||||
public:
|
||||
ReaderWriter(int numReaders, int numWriters, const std::string& filename);
|
||||
ReaderWriter(int numReaders, int numWriters, std::string filename);
|
||||
~ReaderWriter();
|
||||
void run();
|
||||
|
||||
@@ -19,9 +19,10 @@ private:
|
||||
int numWriters;
|
||||
std::string filename;
|
||||
|
||||
sem_t resourceAccess;
|
||||
sem_t readCountAccess;
|
||||
sem_t resourceAccess{};
|
||||
sem_t readCountAccess{};
|
||||
int readCount;
|
||||
int writeCount;
|
||||
|
||||
static void* reader(void* arg);
|
||||
static void* writer(void* arg);
|
||||
|
||||
26
main.cpp
26
main.cpp
@@ -6,6 +6,7 @@
|
||||
#include "buffer.h"
|
||||
#include "producer.h"
|
||||
#include "consumer.h"
|
||||
#include "reader_writer.h"
|
||||
|
||||
[[noreturn]] void runSignalHandler() {
|
||||
setupSignalHandlers();
|
||||
@@ -45,11 +46,24 @@ void runProducerConsumer() {
|
||||
}
|
||||
}
|
||||
|
||||
void runReaderWriter() {
|
||||
int numReaders = 5;
|
||||
int numWriters = 2;
|
||||
std::string filename = "shared_resource.txt";
|
||||
|
||||
std::ofstream file(filename, std::ios::trunc);
|
||||
file.close();
|
||||
|
||||
ReaderWriter rw(numReaders, numWriters, filename);
|
||||
rw.run();
|
||||
}
|
||||
|
||||
int main() {
|
||||
while (true) {
|
||||
std::cout << "=== Main Menu ===\n";
|
||||
std::cout << "1. Run Signal Handler Program\n";
|
||||
std::cout << "2. Run Producer/Consumer Program\n";
|
||||
std::cout << "1. Run Signal Handler\n";
|
||||
std::cout << "2. Run Producer/Consumer\n";
|
||||
std::cout << "3. Run Reader/Writer\n";
|
||||
std::cout << "0. Exit\n";
|
||||
std::cout << "Enter your choice: ";
|
||||
|
||||
@@ -58,13 +72,17 @@ int main() {
|
||||
|
||||
switch (choice) {
|
||||
case 1:
|
||||
std::cout << "Running Signal Handler Program...\n";
|
||||
std::cout << "Running Signal Handler...\n";
|
||||
runSignalHandler();
|
||||
break;
|
||||
case 2:
|
||||
std::cout << "Running Producer/Consumer Program...\n";
|
||||
std::cout << "Running Producer/Consumer...\n";
|
||||
runProducerConsumer();
|
||||
break;
|
||||
case 3:
|
||||
std::cout << "Running Reader-Writer...\n";
|
||||
runReaderWriter();
|
||||
break;
|
||||
case 0:
|
||||
std::cout << "Exiting program. Goodbye!\n";
|
||||
return 0;
|
||||
|
||||
@@ -3,3 +3,100 @@
|
||||
//
|
||||
|
||||
#include "reader_writer.h"
|
||||
|
||||
#include <iostream>
|
||||
#include <sstream>
|
||||
#include <utility>
|
||||
#include <unistd.h>
|
||||
#include <vector>
|
||||
|
||||
ReaderWriter::ReaderWriter(const int numReaders, const int numWriters, std::string filename)
|
||||
: numReaders(numReaders), numWriters(numWriters), filename(std::move(filename)), readCount(0), writeCount(0) {
|
||||
sem_init(&resourceAccess, 0, 1);
|
||||
sem_init(&readCountAccess, 0, 1);
|
||||
}
|
||||
|
||||
ReaderWriter::~ReaderWriter() {
|
||||
sem_destroy(&resourceAccess);
|
||||
sem_destroy(&readCountAccess);
|
||||
}
|
||||
|
||||
void* ReaderWriter::reader(void* arg) {
|
||||
auto* rw = static_cast<ReaderWriter*>(arg);
|
||||
|
||||
for (int i = 0; i < 5; ++i) {
|
||||
sem_wait(&rw->readCountAccess);
|
||||
rw->readCount++;
|
||||
if (rw->readCount == 1) {
|
||||
sem_wait(&rw->resourceAccess);
|
||||
}
|
||||
sem_post(&rw->readCountAccess);
|
||||
|
||||
if (std::ifstream file(rw->filename); file.is_open()) {
|
||||
std::ostringstream output;
|
||||
output << "Reader reading: ";
|
||||
std::string line;
|
||||
while (std::getline(file, line)) {
|
||||
output << line << " ";
|
||||
}
|
||||
output << std::endl;
|
||||
std::cout << output.str();
|
||||
} else {
|
||||
std::cerr << "Reader could not open file\n";
|
||||
}
|
||||
|
||||
sem_wait(&rw->readCountAccess);
|
||||
rw->readCount--;
|
||||
if (rw->readCount == 0) {
|
||||
sem_post(&rw->resourceAccess);
|
||||
}
|
||||
sem_post(&rw->readCountAccess);
|
||||
|
||||
sleep(1);
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void* ReaderWriter::writer(void* arg) {
|
||||
auto* rw = static_cast<ReaderWriter*>(arg);
|
||||
|
||||
for (int i = 0; i < 5; ++i) {
|
||||
sem_wait(&rw->resourceAccess);
|
||||
|
||||
std::ofstream file(rw->filename, std::ios::app);
|
||||
if (file.is_open()) {
|
||||
file << rw->writeCount << "\n";
|
||||
std::cout << "Writer writing: " << rw->writeCount << std::endl;
|
||||
rw->writeCount++;
|
||||
} else {
|
||||
std::cerr << "Writer could not open file\n";
|
||||
}
|
||||
file.close();
|
||||
|
||||
sem_post(&rw->resourceAccess);
|
||||
|
||||
sleep(1);
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void ReaderWriter::run() {
|
||||
std::vector<pthread_t> readerThreads(numReaders);
|
||||
std::vector<pthread_t> writerThreads(numWriters);
|
||||
|
||||
for (int i = 0; i < numReaders; ++i) {
|
||||
pthread_create(&readerThreads[i], nullptr, reader, this);
|
||||
}
|
||||
for (int i = 0; i < numWriters; ++i) {
|
||||
pthread_create(&writerThreads[i], nullptr, writer, this);
|
||||
}
|
||||
|
||||
for (const auto& t : readerThreads) {
|
||||
pthread_join(t, nullptr);
|
||||
}
|
||||
for (const auto& t : writerThreads) {
|
||||
pthread_join(t, nullptr);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user