# HG changeset patch # User Igor Sysoev # Date 1280332174 0 # Node ID ce6ba077c2702a4d86c464a35bdbd1471c743438 # Parent 5f63b6ab4d4b5baeb5732d322bc3fae1cd198c7c several changes in cache cleanup handling: *) now ngx_http_file_cache_cleanup() uses ngx_http_file_cache_free() *) ngx_http_file_cache_free() interface has been changed to accept r->cache ngx_http_file_cache_cleanup() must use r->cache, but not r, because there can be several r->cache's during request processing, r->cache may be NULL at request finalising, etc. *) test if updating request does not complete correctly diff --git a/src/http/ngx_http_cache.h b/src/http/ngx_http_cache.h --- a/src/http/ngx_http_cache.h +++ b/src/http/ngx_http_cache.h @@ -78,6 +78,7 @@ struct ngx_http_cache_s { ngx_http_file_cache_node_t *node; unsigned updated:1; + unsigned updating:1; unsigned exists:1; unsigned temp_file:1; }; @@ -129,7 +130,7 @@ ngx_int_t ngx_http_file_cache_open(ngx_h void ngx_http_file_cache_set_header(ngx_http_request_t *r, u_char *buf); void ngx_http_file_cache_update(ngx_http_request_t *r, ngx_temp_file_t *tf); ngx_int_t ngx_http_cache_send(ngx_http_request_t *); -void ngx_http_file_cache_free(ngx_http_request_t *r, ngx_temp_file_t *tf); +void ngx_http_file_cache_free(ngx_http_cache_t *c, ngx_temp_file_t *tf); time_t ngx_http_file_cache_valid(ngx_array_t *cache_valid, ngx_uint_t status); char *ngx_http_file_cache_set_slot(ngx_conf_t *cf, ngx_command_t *cmd, diff --git a/src/http/ngx_http_file_cache.c b/src/http/ngx_http_file_cache.c --- a/src/http/ngx_http_file_cache.c +++ b/src/http/ngx_http_file_cache.c @@ -430,6 +430,7 @@ ngx_http_file_cache_read(ngx_http_reques } else { c->node->updating = 1; + c->updating = 1; rc = NGX_HTTP_CACHE_STALE; } @@ -793,6 +794,7 @@ ngx_http_file_cache_update(ngx_http_requ "http file cache update"); c->updated = 1; + c->updating = 0; cache = c->file_cache; @@ -902,30 +904,28 @@ ngx_http_cache_send(ngx_http_request_t * void -ngx_http_file_cache_free(ngx_http_request_t *r, ngx_temp_file_t *tf) +ngx_http_file_cache_free(ngx_http_cache_t *c, ngx_temp_file_t *tf) { - ngx_http_cache_t *c; ngx_http_file_cache_t *cache; ngx_http_file_cache_node_t *fcn; - c = r->cache; - if (c->updated) { return; } - c->updated = 1; - cache = c->file_cache; - ngx_log_debug0(NGX_LOG_DEBUG_HTTP, r->connection->log, 0, + ngx_log_debug0(NGX_LOG_DEBUG_HTTP, c->file.log, 0, "http file cache free"); ngx_shmtx_lock(&cache->shpool->mutex); fcn = c->node; fcn->count--; - fcn->updating = 0; + + if (c->updating) { + fcn->updating = 0; + } if (c->error) { fcn->valid_sec = c->valid_sec; @@ -941,14 +941,17 @@ ngx_http_file_cache_free(ngx_http_reques ngx_shmtx_unlock(&cache->shpool->mutex); + c->updated = 1; + c->updating = 0; + if (c->temp_file) { if (tf && tf->file.fd != NGX_INVALID_FILE) { - ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0, + ngx_log_debug1(NGX_LOG_DEBUG_HTTP, c->file.log, 0, "http file cache incomplete: \"%s\"", tf->file.name.data); if (ngx_delete_file(tf->file.name.data) == NGX_FILE_ERROR) { - ngx_log_error(NGX_LOG_CRIT, r->connection->log, ngx_errno, + ngx_log_error(NGX_LOG_CRIT, c->file.log, ngx_errno, ngx_delete_file_n " \"%s\" failed", tf->file.name.data); } @@ -962,28 +965,19 @@ ngx_http_file_cache_cleanup(void *data) { ngx_http_cache_t *c = data; - ngx_http_file_cache_t *cache; - if (c->updated) { return; } - c->updated = 1; - ngx_log_debug0(NGX_LOG_DEBUG_HTTP, c->file.log, 0, "http file cache cleanup"); - if (c->error) { - return; + if (c->updating) { + ngx_log_error(NGX_LOG_ALERT, c->file.log, 0, + "stalled cache updating, error:%ui", c->error); } - cache = c->file_cache; - - ngx_shmtx_lock(&cache->shpool->mutex); - - c->node->count--; - - ngx_shmtx_unlock(&cache->shpool->mutex); + ngx_http_file_cache_free(c, NULL); } diff --git a/src/http/ngx_http_upstream.c b/src/http/ngx_http_upstream.c --- a/src/http/ngx_http_upstream.c +++ b/src/http/ngx_http_upstream.c @@ -1735,7 +1735,7 @@ ngx_http_upstream_intercept_errors(ngx_h r->cache->error = status; } - ngx_http_file_cache_free(r, u->pipe->temp_file); + ngx_http_file_cache_free(r->cache, u->pipe->temp_file); } #endif ngx_http_upstream_finalize_request(r, u, status); @@ -2189,7 +2189,7 @@ ngx_http_upstream_send_response(ngx_http "http cacheable: %d", u->cacheable); if (u->cacheable == 0 && r->cache) { - ngx_http_file_cache_free(r, u->pipe->temp_file); + ngx_http_file_cache_free(r->cache, u->pipe->temp_file); } #endif @@ -2664,7 +2664,7 @@ ngx_http_upstream_process_request(ngx_ht ngx_http_file_cache_update(r, u->pipe->temp_file); } else if (p->upstream_error) { - ngx_http_file_cache_free(r, u->pipe->temp_file); + ngx_http_file_cache_free(r->cache, u->pipe->temp_file); } } @@ -3005,7 +3005,7 @@ ngx_http_upstream_finalize_request(ngx_h } } - ngx_http_file_cache_free(r, u->pipe->temp_file); + ngx_http_file_cache_free(r->cache, u->pipe->temp_file); } #endif