Search code examples
c++pointersvectorpthreadspthread-join

Creating and Joining pthreads using vector<pthread_t>::iterator


Working on a simple project to tally multiple txt files using threads. The only error I'm getting in compilation involves the vector<pthread_t>::iterator being used in the pthread_join loop.

The error is:

error: invalid conversion from long unsigned int* to pthread_t {aka long unsigned int} [-permissive]}
`pthread_join(&*iter, (void**)&returnValue);` <--

Here's the relevant code:

vector<string> voteTallyFiles;
vector<voteTally> intermVoteTallies;
tallyArgs *pThreadArgs;
void *returnValue;
int index = 0;

getFileNames(VOTE_TALLY_DPATH, voteTallyFiles);

vector<pthread_t> threads(voteTallyFiles.size());

for (vector<pthread_t>::iterator iter = threads.begin(); iter != threads.end(); ++iter, index++)
{
    pThreadArgs->fName = voteTallyFiles[index];
    pthread_create(&*iter, NULL, countVotes, pThreadArgs);
}

for (vector<pthread_t>::iterator iter = threads.begin(); iter != threads.end(); ++iter)
{
    pthread_join(&*iter, (void**)&returnValue);
    intermVoteTallies.push_back((voteTally)returnValue)
}

I've read through the documentation for pthread, and pthread_join specifically, and think I've correctly tracked all the pointers/reference/deference but obviously I missed something somewhere.

I tried:

pthread_join(iter, (void**)&returnValue);

and

pthread_join(&iter, (void**)&returnValue);

but get similar errors:

error: cannot convert std::vector<long unsigned int>::iterator {aka __gnu_c} long unsigned int*, std::vector<long unsigned int>} to pthread_t {aka long unsigned int} 
pthread_join(iter, (void**)&returnValue); <--

and

error: invalid conversion from std::vector<long unsigned int>::iterator* {aka __gnu_cxx::__normal_iterator<long unsigned int*, std::vector<long unsigned int> >*} to pthread_t {aka long unsigned int} [-fpermissive]}
pthread_join(&iter, (void**)&returnValue); <--

In both cases it's apparent that I'm trying to do a pointer to non-pointer conversion. pthread_join wants a non-pointer thread_t but an iterator is by definition a pointer, so is de-referencing it not enough? Is explicit casting part of the solution? Nothing I've tried so far has worked.


Solution

  • The first argument of pthread_join() shall be pthread_t.

    Your iterator iter is of type vector<pthread_t>::iterator. This means that *iter will be of type pthread_t

    So you have to dereference it: pthread_join(*iter, (void**)&returnValue);

    Note: &*iter is hence of type pthread_t * and &iter is of type pointer to an iterator.