aboutsummaryrefslogtreecommitdiff
path: root/src/os/unix/ngx_thread.h
blob: a1404038e0054fe7dc22d8a51250a2422db3c10e (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
#ifndef _NGX_THREAD_H_INCLUDED_
#define _NGX_THREAD_H_INCLUDED_


#include <ngx_config.h>
#include <ngx_core.h>

#if (NGX_THREADS)

#define ngx_thread_volatile  volatile

#if (NGX_USE_RFORK)

#include <sys/ipc.h>
#include <sys/sem.h>
#include <sched.h>

typedef pid_t  ngx_tid_t;

#undef ngx_log_pid
#define ngx_log_pid    ngx_thread_self()
#define ngx_log_tid    0

#define TID_T_FMT      PID_T_FMT


#define NGX_MUTEX_LIGHT      1
#define NGX_MUTEX_CV         2

#define NGX_MUTEX_LOCK_BUSY  0x80000000

typedef volatile struct {
    ngx_atomic_t  lock;
    ngx_log_t    *log;
    int           semid;
} ngx_mutex_t;


typedef struct {
    int           semid;
    ngx_log_t    *log;
} ngx_cond_t;


#define ngx_thread_sigmask(how, set, oset)                         \
            (sigprocmask(how, set, oset) == -1) ? ngx_errno : 0

#define ngx_thread_sigmask_n  "sigprocmask()"


extern char    *ngx_freebsd_kern_usrstack;
extern size_t   ngx_thread_stack_size;

static inline int ngx_gettid()
{
    char  *sp;

    if (ngx_thread_stack_size == 0) {
        return 0;
    }

#if ( __i386__ )

    __asm__ volatile ("mov %%esp, %0" : "=q" (sp));

#elif ( __amd64__ )

    __asm__ volatile ("mov %%rsp, %0" : "=q" (sp));

#else

#error "rfork()ed threads are not supported on this platform"

#endif

    return (ngx_freebsd_kern_usrstack - sp) / ngx_thread_stack_size;
}


#define ngx_thread_main()   (ngx_gettid() == 0)


#else /* use pthreads */

#include <pthread.h>

typedef pthread_t  ngx_tid_t;

#define ngx_gettid()   ((ngx_int_t) pthread_getspecific(0))
#define ngx_log_tid    ngx_thread_self()

#define ngx_thread_sigmask     pthread_sigmask
#define ngx_thread_sigmask_n  "pthread_sigmask()"

#endif


ngx_int_t ngx_init_threads(int n, size_t size, ngx_cycle_t *cycle);
int ngx_create_thread(ngx_tid_t *tid, int (*func)(void *arg), void *arg,
                      ngx_log_t *log);
ngx_tid_t ngx_thread_self();


ngx_mutex_t *ngx_mutex_init(ngx_log_t *log, uint flags);
void ngx_mutex_done(ngx_mutex_t *m);

#define ngx_mutex_trylock(m)  ngx_mutex_dolock(m, 1)
#define ngx_mutex_lock(m)     ngx_mutex_dolock(m, 0)
ngx_int_t ngx_mutex_dolock(ngx_mutex_t *m, ngx_int_t try);
ngx_int_t ngx_mutex_unlock(ngx_mutex_t *m);


ngx_cond_t *ngx_cond_init(ngx_log_t *log);
void ngx_cond_done(ngx_cond_t *cv);
ngx_int_t ngx_cond_wait(ngx_cond_t *cv, ngx_mutex_t *m);
ngx_int_t ngx_cond_signal(ngx_cond_t *cv);


#else /* !NGX_THREADS */

#define ngx_thread_volatile

#define ngx_log_tid  0
#define TID_T_FMT    "%d"

#define ngx_mutex_lock(m)     NGX_OK
#define ngx_mutex_unlock(m)

#define ngx_cond_signal(cv)

#define ngx_thread_main()     1

#endif


#endif /* _NGX_THREAD_H_INCLUDED_ */