annotate src/os/unix/ngx_shmem.c @ 3440:88741ec7731a stable-0.7

merge r3294, r3305: Fix a bug introduced in r2032: After a child process has read a terminate message from a channel, the process tries to read the channel again. The kernel (at least FreeBSD) may preempt the process and sends a SIGIO signal to a master process. The master process sends a new terminate message, the kernel switches again to the the child process, and the child process reads the messages instead of an EAGAIN error. And this may repeat over and over. Being that the child process can not exit the cycle and test the termination flag set by the message handler. The fix disallow the master process to send a new terminate message on SIGIO signal reception. It may send the message only on SIGALARM signal.
author Igor Sysoev <igor@sysoev.ru>
date Mon, 01 Feb 2010 15:49:36 +0000
parents 715d24327080
children d620f497c50f
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
441
da8c5707af39 nginx-0.1.0-2004-09-28-12:34:51 import; set copyright and remove unused files
Igor Sysoev <igor@sysoev.ru>
parents: 358
diff changeset
1
da8c5707af39 nginx-0.1.0-2004-09-28-12:34:51 import; set copyright and remove unused files
Igor Sysoev <igor@sysoev.ru>
parents: 358
diff changeset
2 /*
444
42d11f017717 nginx-0.1.0-2004-09-29-20:00:49 import; remove years from copyright
Igor Sysoev <igor@sysoev.ru>
parents: 441
diff changeset
3 * Copyright (C) Igor Sysoev
441
da8c5707af39 nginx-0.1.0-2004-09-28-12:34:51 import; set copyright and remove unused files
Igor Sysoev <igor@sysoev.ru>
parents: 358
diff changeset
4 */
da8c5707af39 nginx-0.1.0-2004-09-28-12:34:51 import; set copyright and remove unused files
Igor Sysoev <igor@sysoev.ru>
parents: 358
diff changeset
5
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
6
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
7 #include <ngx_config.h>
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
8 #include <ngx_core.h>
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
9
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
10
469
2ff194b74f1e nginx-0.1.9-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 467
diff changeset
11 #if (NGX_HAVE_MAP_ANON)
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
12
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
13 ngx_int_t
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
14 ngx_shm_alloc(ngx_shm_t *shm)
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
15 {
639
715d24327080 nginx-0.3.41-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 605
diff changeset
16 shm->addr = (u_char *) mmap(NULL, shm->size,
715d24327080 nginx-0.3.41-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 605
diff changeset
17 PROT_READ|PROT_WRITE,
715d24327080 nginx-0.3.41-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 605
diff changeset
18 MAP_ANON|MAP_SHARED, -1, 0);
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
19
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
20 if (shm->addr == MAP_FAILED) {
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
21 ngx_log_error(NGX_LOG_ALERT, shm->log, ngx_errno,
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
22 "mmap(MAP_ANON|MAP_SHARED, %uz) failed", shm->size);
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
23 return NGX_ERROR;
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
24 }
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
25
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
26 return NGX_OK;
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
27 }
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
28
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
29
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
30 void
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
31 ngx_shm_free(ngx_shm_t *shm)
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
32 {
639
715d24327080 nginx-0.3.41-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 605
diff changeset
33 if (munmap((void *) shm->addr, shm->size) == -1) {
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
34 ngx_log_error(NGX_LOG_ALERT, shm->log, ngx_errno,
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
35 "munmap(%p, %uz) failed", shm->addr, shm->size);
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
36 }
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
37 }
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
38
469
2ff194b74f1e nginx-0.1.9-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 467
diff changeset
39 #elif (NGX_HAVE_MAP_DEVZERO)
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
40
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
41 ngx_int_t
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
42 ngx_shm_alloc(ngx_shm_t *shm)
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
43 {
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
44 ngx_fd_t fd;
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
45
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
46 fd = open("/dev/zero", O_RDWR);
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
47
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
48 if (fd == -1) {
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
49 ngx_log_error(NGX_LOG_ALERT, shm->log, ngx_errno,
467
bbd6b0b4a2b1 nginx-0.1.8-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 461
diff changeset
50 "open(\"/dev/zero\") failed");
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
51 return NGX_ERROR;
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
52 }
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
53
639
715d24327080 nginx-0.3.41-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 605
diff changeset
54 shm->addr = (u_char *) mmap(NULL, shm->size, PROT_READ|PROT_WRITE,
715d24327080 nginx-0.3.41-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 605
diff changeset
55 MAP_SHARED, fd, 0);
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
56
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
57 if (shm->addr == MAP_FAILED) {
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
58 ngx_log_error(NGX_LOG_ALERT, shm->log, ngx_errno,
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
59 "mmap(/dev/zero, MAP_SHARED, %uz) failed", shm->size);
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
60 }
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
61
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
62 if (close(fd) == -1) {
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
63 ngx_log_error(NGX_LOG_ALERT, shm->log, ngx_errno,
467
bbd6b0b4a2b1 nginx-0.1.8-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 461
diff changeset
64 "close(\"/dev/zero\") failed");
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
65 }
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
66
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
67 return (shm->addr == MAP_FAILED) ? NGX_ERROR : NGX_OK;
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
68 }
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
69
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
70
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
71 void
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
72 ngx_shm_free(ngx_shm_t *shm)
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
73 {
639
715d24327080 nginx-0.3.41-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 605
diff changeset
74 if (munmap((void *) shm->addr, shm->size) == -1) {
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
75 ngx_log_error(NGX_LOG_ALERT, shm->log, ngx_errno,
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
76 "munmap(%p, %uz) failed", shm->addr, shm->size);
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
77 }
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
78 }
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
79
469
2ff194b74f1e nginx-0.1.9-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 467
diff changeset
80 #elif (NGX_HAVE_SYSVSHM)
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
81
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
82 #include <sys/ipc.h>
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
83 #include <sys/shm.h>
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
84
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
85
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
86 ngx_int_t
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
87 ngx_shm_alloc(ngx_shm_t *shm)
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
88 {
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
89 int id;
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
90
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
91 id = shmget(IPC_PRIVATE, shm->size, (SHM_R|SHM_W|IPC_CREAT));
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
92
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
93 if (id == -1) {
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
94 ngx_log_error(NGX_LOG_ALERT, shm->log, ngx_errno,
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
95 "shmget(%uz) failed", shm->size);
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
96 return NGX_ERROR;
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
97 }
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
98
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
99 ngx_log_debug1(NGX_LOG_DEBUG_CORE, shm->log, 0, "shmget id: %d", id);
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
100
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
101 shm->addr = shmat(id, NULL, 0);
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
102
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
103 if (shm->addr == (void *) -1) {
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
104 ngx_log_error(NGX_LOG_ALERT, shm->log, ngx_errno, "shmat() failed");
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
105 }
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
106
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
107 if (shmctl(id, IPC_RMID, NULL) == -1) {
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
108 ngx_log_error(NGX_LOG_ALERT, shm->log, ngx_errno,
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
109 "shmctl(IPC_RMID) failed");
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
110 }
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
111
605
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
112 return (shm->addr == (void *) -1) ? NGX_ERROR : NGX_OK;
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
113 }
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
114
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
115
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
116 void
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
117 ngx_shm_free(ngx_shm_t *shm)
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
118 {
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
119 if (shmdt(shm->addr) == -1) {
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
120 ngx_log_error(NGX_LOG_ALERT, shm->log, ngx_errno,
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
121 "shmdt(%p) failed", shm->addr);
5dac8c7fb71b nginx-0.3.24-RELEASE import
Igor Sysoev <igor@sysoev.ru>
parents: 469
diff changeset
122 }
358
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
123 }
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
124
0a03c921c81d nginx-0.0.7-2004-06-17-21:18:53 import
Igor Sysoev <igor@sysoev.ru>
parents:
diff changeset
125 #endif