Mercurial > hg > nginx
changeset 3755:76e3a93821b1
fix race condition if during reconfiguration two cache managers try
to delete old inactive entries: one of them removes a entry just locked by
other manager from the queue and the rbtree as long inactive entry,
causes the latter manager to segfault leaving cache mutex locked,
the bug has been introduced in r3727
author | Igor Sysoev <igor@sysoev.ru> |
---|---|
date | Thu, 02 Sep 2010 14:31:47 +0000 |
parents | 5f58badd13ed |
children | 7224d008faaf |
files | src/http/ngx_http_cache.h src/http/ngx_http_file_cache.c |
diffstat | 2 files changed, 10 insertions(+), 1 deletions(-) [+] |
line wrap: on
line diff
--- a/src/http/ngx_http_cache.h Thu Sep 02 14:02:57 2010 +0000 +++ b/src/http/ngx_http_cache.h Thu Sep 02 14:31:47 2010 +0000 @@ -43,7 +43,8 @@ unsigned error:10; unsigned exists:1; unsigned updating:1; - /* 12 unused bits */ + unsigned deleting:1; + /* 11 unused bits */ ngx_file_uniq_t uniq; time_t expire;
--- a/src/http/ngx_http_file_cache.c Thu Sep 02 14:02:57 2010 +0000 +++ b/src/http/ngx_http_file_cache.c Thu Sep 02 14:31:47 2010 +0000 @@ -582,6 +582,7 @@ fcn->uses = 1; fcn->count = 1; fcn->updating = 0; + fcn->deleting = 0; renew: @@ -1102,6 +1103,10 @@ continue; } + if (fcn->deleting) { + continue; + } + p = ngx_hex_dump(key, (u_char *) &fcn->node.key, sizeof(ngx_rbtree_key_t)); len = NGX_HTTP_CACHE_KEY_LEN - sizeof(ngx_rbtree_key_t); @@ -1153,6 +1158,7 @@ *p = '\0'; fcn->count++; + fcn->deleting = 1; ngx_shmtx_unlock(&cache->shpool->mutex); len = path->name.len + 1 + path->len + 2 * NGX_HTTP_CACHE_KEY_LEN; @@ -1168,6 +1174,7 @@ ngx_shmtx_lock(&cache->shpool->mutex); fcn->count--; + fcn->deleting = 0; } if (fcn->count == 0) { @@ -1431,6 +1438,7 @@ fcn->error = 0; fcn->exists = 1; fcn->updating = 0; + fcn->deleting = 0; fcn->uniq = c->uniq; fcn->valid_sec = c->valid_sec; fcn->body_start = c->body_start;