Commit | Line | Data |
0f15f207 |
1 | Some old globals (e.g. stack_sp, op) and some old per-interpreter |
2 | variables (e.g. tmps_stack, cxstack) move into struct thread. |
3 | All fields of struct thread (apart from a few only applicable to |
4 | FAKE_THREADS) are of the form Tfoo. For example, stack_sp becomes |
5 | the field Tstack_sp of struct thread. For those fields which moved |
6 | from original perl, thread.h does |
7 | #define foo (thr->Tfoo) |
8 | This means that all functions in perl which need to use one of these |
9 | fields need an (automatic) variable thr which points at the current |
10 | thread's struct thread. For pp_foo functions, it is passed around as |
11 | an argument, for other functions they do |
12 | dTHR; |
13 | which declares and initialises thr from thread-specific data |
14 | via pthread_getspecific. If a function fails to compile with an |
15 | error about "no such variable thr", it probably just needs a dTHR |
16 | at the top. |
17 | |
18 | For FAKE_THREADS, thr is a global variable and perl schedules threads |
19 | by altering thr in between appropriate ops. The next and prev fields |
20 | of struct thread keep all fake threads on a doubly linked list and |
21 | the next_run and prev_run fields keep all runnable threads on a |
22 | doubly linked list. Mutexes are stubs for FAKE_THREADS. Condition |
23 | variables are implemented as a list of waiting threads. |
24 | |
25 | |
26 | Mutexes and condition variables |
27 | |
28 | The API is via macros MUTEX_{INIT,LOCK,UNLOCK,DESTROY} and |
29 | COND_{INIT,WAIT,SIGNAL,BROADCAST,DESTROY}. For POSIX threads, |
30 | perl mutexes and condition variables correspond to POSIX ones. |
31 | For FAKE_THREADS, mutexes are stubs and condition variables are |
32 | implmented as lists of waiting threads. For FAKE_THREADS, a thread |
33 | waits on a condition variable by removing itself from the runnable |
34 | list, calling SCHEDULE to change thr to the next appropriate |
35 | runnable thread and returning op (i.e. the new threads next op). |
36 | This means that fake threads can only block while in PP code. |
37 | A PP function which contains a COND_WAIT must be prepared to |
38 | handle such restarts and can use the field "private" of struct |
39 | thread to record its state. For fake threads, COND_SIGNAL and |
40 | COND_BROADCAST work by putting back all the threads on the |
41 | condition variables list into the run queue. Note that a mutex |
42 | must *not* be held while returning from a PP function. |
43 | |
44 | Perl locks are a condpair_t structure (a triple of a mutex, a |
45 | condtion variable and an owner thread field) attached by 'm' |
46 | magic to any SV. pp_lock locks such an object by waiting on the |
47 | condition variable until the owner field is zero and then setting |
48 | the owner field to its own thread pointer. The lock is recursive |
49 | so if the owner field already matches the current thread then |
50 | pp_lock returns straight away. If the owner field has to be filled |
51 | in then unlock_condpair is queued as an end-of-block destructor and |
52 | that function zeroes out the owner field, releasing the lock. |