improve ngx_slab_alloc() error logging
diff --git a/src/core/ngx_slab.c b/src/core/ngx_slab.c
index afa2b40..cca8374 100644
--- a/src/core/ngx_slab.c
+++ b/src/core/ngx_slab.c
@@ -63,6 +63,8 @@
     ngx_uint_t pages);
 static void ngx_slab_free_pages(ngx_slab_pool_t *pool, ngx_slab_page_t *page,
     ngx_uint_t pages);
+static void ngx_slab_error(ngx_slab_pool_t *pool, ngx_uint_t level,
+    char *text);
 
 
 static ngx_uint_t  ngx_slab_max_size;
@@ -129,6 +131,9 @@
         pages -= m;
         pool->pages->slab = pages;
     }
+
+    pool->log_ctx = &pool->zero;
+    pool->zero = '\0';
 }
 
 
@@ -415,8 +420,7 @@
     ngx_log_debug1(NGX_LOG_DEBUG_ALLOC, ngx_cycle->log, 0, "slab free: %p", p);
 
     if ((u_char *) p < pool->start || (u_char *) p > pool->end) {
-        ngx_log_error(NGX_LOG_ALERT, ngx_cycle->log, 0,
-                      "ngx_slab_free(): outside of pool");
+        ngx_slab_error(pool, NGX_LOG_ALERT, "ngx_slab_free(): outside of pool");
         goto fail;
     }
 
@@ -564,14 +568,14 @@
         }
 
         if (slab == NGX_SLAB_PAGE_FREE) {
-            ngx_log_error(NGX_LOG_ALERT, ngx_cycle->log, 0,
-                          "ngx_slab_free(): page is already free");
+            ngx_slab_error(pool, NGX_LOG_ALERT,
+                           "ngx_slab_free(): page is already free");
             goto fail;
         }
 
         if (slab == NGX_SLAB_PAGE_BUSY) {
-            ngx_log_error(NGX_LOG_ALERT, ngx_cycle->log, 0,
-                          "ngx_slab_free(): pointer to wrong page");
+            ngx_slab_error(pool, NGX_LOG_ALERT,
+                           "ngx_slab_free(): pointer to wrong page");
             goto fail;
         }
 
@@ -597,15 +601,15 @@
 
 wrong_chunk:
 
-    ngx_log_error(NGX_LOG_ALERT, ngx_cycle->log, 0,
-                      "ngx_slab_free(): pointer to wrong chunk");
+    ngx_slab_error(pool, NGX_LOG_ALERT,
+                   "ngx_slab_free(): pointer to wrong chunk");
 
     goto fail;
 
 chunk_already_free:
 
-    ngx_log_error(NGX_LOG_ALERT, ngx_cycle->log, 0,
-                      "ngx_slab_free(): chunk is already free");
+    ngx_slab_error(pool, NGX_LOG_ALERT,
+                   "ngx_slab_free(): chunk is already free");
 
 fail:
 
@@ -656,8 +660,7 @@
         }
     }
 
-    ngx_log_error(NGX_LOG_ALERT, ngx_cycle->log, NGX_ENOMEM,
-                  "ngx_slab_alloc(): failed");
+    ngx_slab_error(pool, NGX_LOG_CRIT, "ngx_slab_alloc() failed: no memory");
 
     return NULL;
 }
@@ -688,3 +691,10 @@
 
     pool->free.next = page;
 }
+
+
+static void
+ngx_slab_error(ngx_slab_pool_t *pool, ngx_uint_t level, char *text)
+{
+    ngx_log_error(level, ngx_cycle->log, 0, "%s%s", text, pool->log_ctx);
+}
diff --git a/src/core/ngx_slab.h b/src/core/ngx_slab.h
index 5bdacaf..348da81 100644
--- a/src/core/ngx_slab.h
+++ b/src/core/ngx_slab.h
@@ -34,6 +34,9 @@
     u_char           *end;
 
     ngx_shmtx_t       mutex;
+
+    u_char           *log_ctx;
+    u_char            zero;
 } ngx_slab_pool_t;
 
 
diff --git a/src/event/ngx_event_openssl.c b/src/event/ngx_event_openssl.c
index 5fa400d..eb88888 100644
--- a/src/event/ngx_event_openssl.c
+++ b/src/event/ngx_event_openssl.c
@@ -1412,6 +1412,7 @@
 static ngx_int_t
 ngx_ssl_session_cache_init(ngx_shm_zone_t *shm_zone, void *data)
 {
+    size_t                    len;
     ngx_slab_pool_t          *shpool;
     ngx_ssl_session_cache_t  *cache;
 
@@ -1432,6 +1433,16 @@
 
     ngx_queue_init(&cache->expire_queue);
 
+    len = sizeof(" in SSL session shared cache \"\"") + shm_zone->name.len;
+
+    shpool->log_ctx = ngx_slab_alloc(shpool, len);
+    if (shpool->log_ctx == NULL) {
+        return NGX_ERROR;
+    }
+
+    ngx_sprintf(shpool->log_ctx, " in SSL session shared cache \"%V\"%Z",
+                &shm_zone->name);
+
     shm_zone->data = cache;
 
     return NGX_OK;
diff --git a/src/http/modules/ngx_http_limit_req_module.c b/src/http/modules/ngx_http_limit_req_module.c
index dac62ed..36787b0 100644
--- a/src/http/modules/ngx_http_limit_req_module.c
+++ b/src/http/modules/ngx_http_limit_req_module.c
@@ -457,6 +457,7 @@
 {
     ngx_http_limit_req_ctx_t  *octx = data;
 
+    size_t                     len;
     ngx_rbtree_node_t         *sentinel;
     ngx_http_limit_req_ctx_t  *ctx;
 
@@ -500,6 +501,16 @@
 
     ngx_queue_init(ctx->queue);
 
+    len = sizeof(" in limit_req zone \"\"") + shm_zone->name.len;
+
+    ctx->shpool->log_ctx = ngx_slab_alloc(ctx->shpool, len);
+    if (ctx->shpool->log_ctx == NULL) {
+        return NGX_ERROR;
+    }
+
+    ngx_sprintf(ctx->shpool->log_ctx, " in limit_req zone \"%V\"%Z",
+                &shm_zone->name);
+
     return NGX_OK;
 }
 
diff --git a/src/http/modules/ngx_http_limit_zone_module.c b/src/http/modules/ngx_http_limit_zone_module.c
index 3fc4efa..1519e7f 100644
--- a/src/http/modules/ngx_http_limit_zone_module.c
+++ b/src/http/modules/ngx_http_limit_zone_module.c
@@ -321,6 +321,7 @@
 {
     ngx_http_limit_zone_ctx_t  *octx = data;
 
+    size_t                      len;
     ngx_slab_pool_t            *shpool;
     ngx_rbtree_node_t          *sentinel;
     ngx_http_limit_zone_ctx_t  *ctx;
@@ -356,6 +357,15 @@
     ngx_rbtree_init(ctx->rbtree, sentinel,
                     ngx_http_limit_zone_rbtree_insert_value);
 
+    len = sizeof(" in limit_zone \"\"") + shm_zone->name.len;
+
+    shpool->log_ctx = ngx_slab_alloc(shpool, len);
+    if (shpool->log_ctx == NULL) {
+        return NGX_ERROR;
+    }
+
+    ngx_sprintf(shpool->log_ctx, " in limit_zone \"%V\"%Z", &shm_zone->name);
+
     return NGX_OK;
 }
 
diff --git a/src/http/ngx_http_file_cache.c b/src/http/ngx_http_file_cache.c
index efe0da6..da443ce 100644
--- a/src/http/ngx_http_file_cache.c
+++ b/src/http/ngx_http_file_cache.c
@@ -33,6 +33,7 @@
 {
     ngx_http_file_cache_t  *ocache = data;
 
+    size_t                  len;
     ngx_rbtree_node_t      *sentinel;
     ngx_http_file_cache_t  *cache;
 
@@ -79,6 +80,16 @@
 
     ngx_queue_init(cache->queue);
 
+    len = sizeof(" in cache keys zone \"\"") + shm_zone->name.len;
+
+    cache->shpool->log_ctx = ngx_slab_alloc(cache->shpool, len);
+    if (cache->shpool->log_ctx == NULL) {
+        return NGX_ERROR;
+    }
+
+    ngx_sprintf(cache->shpool->log_ctx, " in cache keys zone \"%V\"%Z",
+                &shm_zone->name);
+
     cache->created = ngx_time();
 
     return NGX_OK;