Prev: a-dialogue-on-concurrency Next: interlude-thread-api
Here we introduce threads, which are like processes, but with shared memory – therefore they need coordination.
The state of a thread is like a process – if one thread has to be context switched, its state is saved to a thread control block.
As well, each process now could have multiple stacks (a thread might take 2KB or so), which could increase fragmentation.
Parallelism – if the work a program does can be chopped into smaller pieces that can make progress independently, a program would run faster with threads.
As well, threading removes most of the penalty of slow operations – while one thread is blocked on an I/O request, another thread can make progress.
#include <stdio.h>
#include <assert.h>
#include <pthread.h>
#include "common.h"
#include "common_threads.h"
void *mythread(void *arg) {
("%s\n", (char *) arg);
printfreturn NULL;
}
int main(int argc, char *argv[]) {
, p2;
pthread_t p1int rc;
("main: begin\n");
printf(&p1, NULL, mythread, "A");
Pthread_create(&p2, NULL, mythread, "B");
Pthread_create// join waits for the threads to finish
(p1, NULL);
Pthread_join(p2, NULL);
Pthread_join("main: end\n");
printfreturn 0;
}
Take this example, creating two threads that print the name of the thread, and then joining them. A or B could print in any order, because either A or B prints first. This is all left to the scheduler’s whims.
When we’re incrementing the counter, something like this assembly is emitted:
mov 0x8049a1c, %eax
add $0x1, %eax
mov %eax, 0x8049a1c
This takes three instructions, instead of the one we’d like, so threads can be interrupted in the process of reading the register and adding, causing data races.
We want mutual exclusion, where only one thread can read and increment the value.
We really want the ability to execute those instructions at once. Some instructions like compare and swap are provided by the hardware and allow for this.
What happens if a thread is put to sleep as its I/O request succeeds? It needs to wake – something we’ll cover in another chapter on Condition Variables.
Prev: a-dialogue-on-concurrency Next: interlude-thread-api