comparison src/http/modules/ngx_http_upstream_zone_module.c @ 7078:1eb753aa8e5e

Upstream zone: store peers->name and its data in shared memory. The shared objects should generally be allocated from shared memory. While peers->name and the data it points to allocated from cf->pool happened to work on UNIX, it broke on Windows. On UNIX this worked only because the shared memory zone for upstreams is re-created for every new configuration. But on Windows, a worker process does not inherit the address space of the master process, so the peers->name pointed to data allocated from cf->pool by the master process, and was invalid.
author Ruslan Ermilov <ru@nginx.com>
date Tue, 01 Aug 2017 19:12:10 +0300
parents 341e4303d25b
children ac120e797d28
comparison
equal deleted inserted replaced
7077:2a288909abc6 7078:1eb753aa8e5e
183 183
184 static ngx_http_upstream_rr_peers_t * 184 static ngx_http_upstream_rr_peers_t *
185 ngx_http_upstream_zone_copy_peers(ngx_slab_pool_t *shpool, 185 ngx_http_upstream_zone_copy_peers(ngx_slab_pool_t *shpool,
186 ngx_http_upstream_srv_conf_t *uscf) 186 ngx_http_upstream_srv_conf_t *uscf)
187 { 187 {
188 ngx_str_t *name;
188 ngx_http_upstream_rr_peer_t *peer, **peerp; 189 ngx_http_upstream_rr_peer_t *peer, **peerp;
189 ngx_http_upstream_rr_peers_t *peers, *backup; 190 ngx_http_upstream_rr_peers_t *peers, *backup;
190 191
191 peers = ngx_slab_alloc(shpool, sizeof(ngx_http_upstream_rr_peers_t)); 192 peers = ngx_slab_alloc(shpool, sizeof(ngx_http_upstream_rr_peers_t));
192 if (peers == NULL) { 193 if (peers == NULL) {
193 return NULL; 194 return NULL;
194 } 195 }
195 196
196 ngx_memcpy(peers, uscf->peer.data, sizeof(ngx_http_upstream_rr_peers_t)); 197 ngx_memcpy(peers, uscf->peer.data, sizeof(ngx_http_upstream_rr_peers_t));
198
199 name = ngx_slab_alloc(shpool, sizeof(ngx_str_t));
200 if (name == NULL) {
201 return NULL;
202 }
203
204 name->data = ngx_slab_alloc(shpool, peers->name->len);
205 if (name->data == NULL) {
206 return NULL;
207 }
208
209 ngx_memcpy(name->data, peers->name->data, peers->name->len);
210 name->len = peers->name->len;
211
212 peers->name = name;
197 213
198 peers->shpool = shpool; 214 peers->shpool = shpool;
199 215
200 for (peerp = &peers->peer; *peerp; peerp = &peer->next) { 216 for (peerp = &peers->peer; *peerp; peerp = &peer->next) {
201 /* pool is unlocked */ 217 /* pool is unlocked */
219 return NULL; 235 return NULL;
220 } 236 }
221 237
222 ngx_memcpy(backup, peers->next, sizeof(ngx_http_upstream_rr_peers_t)); 238 ngx_memcpy(backup, peers->next, sizeof(ngx_http_upstream_rr_peers_t));
223 239
240 backup->name = name;
241
224 backup->shpool = shpool; 242 backup->shpool = shpool;
225 243
226 for (peerp = &backup->peer; *peerp; peerp = &peer->next) { 244 for (peerp = &backup->peer; *peerp; peerp = &peer->next) {
227 /* pool is unlocked */ 245 /* pool is unlocked */
228 peer = ngx_slab_calloc_locked(shpool, 246 peer = ngx_slab_calloc_locked(shpool,