Segmentation error while creating stream

I am trying to implement a class that creates a thread, increments a value and sends it to another thread, whose number is defined as (value * value)% number of threads

#include <iostream>
#include <pthread.h>
#include <unistd.h>
#include <cstdlib>
#include <vector>

pthread_mutex_t m = PTHREAD_MUTEX_INITIALIZER;
pthread_cond_t cv = PTHREAD_COND_INITIALIZER;
volatile int counter = 0;
volatile int maxval = 0;
volatile int next = 0;

extern "C" void *func(void *p);

class Worker {
private:
    pthread_t thread = 0;
    int nth = 0;
    int nproc = 0;
public:
    Worker () {};
    Worker(int _nproc, int _nth) {
        nth = _nth;
        nproc = _nproc;
    };
    void start() {
        pthread_create(&thread, NULL, func, NULL); // Line 27

    };
    void wait() {
        while (nth != next) {
            pthread_cond_wait(&cv, &m);
        }
    };
    void notify() {
        pthread_cond_broadcast(&cv);
    };
    void run() {
        while (counter != maxval) {
            pthread_mutex_lock(&m);
            Worker::wait();
            if (counter != maxval) {
                printf("%d %d\n", nth, counter);
                ++counter;
            }
            next = (counter * counter) % nproc;
            Worker::notify();
            pthread_mutex_unlock(&m);
        }
    };
    void join() {
        pthread_join(thread, NULL);
    }
};

extern "C" void *func(void *p) {
    Worker *w = reinterpret_cast<Worker*>(p);
    w->run();
    return NULL;
}

int main(int argc, char *argv[]) {
    int nthreads = atoi(argv[1]);
    maxval = atoi(argv[2]);
    std::vector<Worker> workers;
    for (int i = 0; i != nthreads; ++i) {
        workers.push_back(Worker(nthreads, i));
    }
    for (int i = 0; i != workers.size(); ++i) {
        workers[i].start();
    }
    for (int i = 0; i != workers.size(); ++i) {
        workers[i].join();
    }
    return 0;
}

It is not possible to verify the correctness of the algorithm since I get a segmentation error when I call pthread_create (line 27)

Here is what gdb said:

#0  0x0000000000400f5a in Worker::wait (this=0x0) at ht19-4.cpp:30
#1  0x0000000000400fd5 in Worker::run (this=0x0) at ht19-4.cpp:40
#2  0x0000000000400d26 in func (p=0x0) at ht19-4.cpp:57
#3  0x00007ffff76296aa in start_thread (arg=0x7ffff6f4f700)
    at pthread_create.c:333
#4  0x00007ffff735eeed in clone ()
    at ../sysdeps/unix/sysv/linux/x86_64/clone.S:109

Can someone explain what exactly is happening in this function, please? How to implement this correctly?

Many thanks.

+4
source share
2 answers

func NULL, 4- pthread_create - , .

func, NULL, :

extern "C" void *func(void *p) {
    if (NULL == p)
        return NULL;
    Worker *w = reinterpret_cast<Worker*>(p);
    w->run();
    return NULL;
}

, +1 gdb, :

( , ), , func run Worker, NULL. (p=0x0) (this=0x0):

#2  0x0000000000400d26 in func (p=0x0) at ht19-4.cpp:57
#1  0x0000000000400fd5 in Worker::run (this=0x0) at ht19-4.cpp:40

Worker::run , counter, maxval m, Worker::wait()

#0  0x0000000000400f5a in Worker::wait (this=0x0) at ht19-4.cpp:30

Worker::wait() nth, null Worker, , , segfault.

+2

, NULL .

pthread_create(&thread, NULL, func, NULL);

, func() NULL. func() p NULL, , . .

+2

Source: https://habr.com/ru/post/1620790/


All Articles