Pthreads and concurrency

I have the following code:

#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>

#define LOOPS 10000

void *run(void *arg)
{
    int id = strtol(arg,NULL,0);
    int i;
    for(i=0; i<LOOPS; i++)
    {
        printf("In %d.\n",id);
    }
}

int main()
{
    pthread_t p1,p2;
    void *res;

    pthread_create(&p1,NULL,run,"1");
    pthread_create(&p2,NULL,run,"2");
    pthread_join(p1,&res);
    pthread_join(p2,&res);
    return 0;
}

      

When I run this, either the "IN 1" line is displayed 10,000 times in a row and the "IN 2" is displayed 10,000 times in a row, or vice versa. Shouldn't the lines be interleaved and displayed sequentially as they are here?

+3


source to share


3 answers


The order in which the threads are interleaved by the scheduler is not deterministic (... well, that's just from a scheduler / kernel perspective). You don't have to make assumptions about the order.



In this situation, you experience that either one of the threads is allowed to complete all of its work before the scheduler -> unloads it, and allows the other thread to start.

+8


source


Schedulers start processes in time slots. The time interval is large enough to be effective, but short enough to create the illusion of simultaneous execution.

In a multi-core CPUS, threads implemented at the OS kernel level will actually execute in parallel.

Also, the output is sometimes buffered because it takes the same processing power to get one big write to make a small write. Buffering is disabled on most systems when the output goes to an interactive terminal device, but now the details of your environment start to matter.



For the output to be interleaved, it must be unbuffered and run in a scheduler that is either multi-core or unusually fine-grained and willing to do expensive context switches just because you created an output string. If multi-core, the execution paths through the library and the kernel would have to match on three cores. This will probably never happen.

After all, you create one at a time, and each will always be ready to launch before the other.

+2


source


The other two answers are correct, but I would like to add this:

The two outputs alternate. They simply do not alternate one or two lines, but rather thousands of lines. When a time slice is given to each thread, it has time to output thousands of lines. Since you are only printing 10k lines on each thread, you have time to finish before another starts.

Try replacing the loop with an for

infinite loop and see what happens.

+2


source







All Articles