diff src/http/modules/ngx_http_index_module.c @ 332:3a91bfeffaba NGINX_0_6_10

nginx 0.6.10 *) Feature: the "open_file_cache", "open_file_cache_retest", and "open_file_cache_errors" directives. *) Bugfix: socket leak; bug appeared in 0.6.7. *) Bugfix: a charset set by the "charset" directive was not appended to the "Content-Type" header set by $r->send_http_header(). *) Bugfix: a segmentation fault might occur in worker process if /dev/poll method was used.
author Igor Sysoev <http://sysoev.ru>
date Mon, 03 Sep 2007 00:00:00 +0400
parents c5c2b2883984
children eae74a780a84
line wrap: on
line diff
--- a/src/http/modules/ngx_http_index_module.c
+++ b/src/http/modules/ngx_http_index_module.c
@@ -38,7 +38,7 @@ typedef struct {
 
 
 static ngx_int_t ngx_http_index_test_dir(ngx_http_request_t *r,
-    ngx_http_index_ctx_t *ctx);
+    ngx_http_core_loc_conf_t *clcf, ngx_http_index_ctx_t *ctx);
 static ngx_int_t ngx_http_index_error(ngx_http_request_t *r,
     ngx_http_index_ctx_t *ctx, ngx_err_t err);
 
@@ -59,17 +59,6 @@ static ngx_command_t  ngx_http_index_com
       0,
       NULL },
 
-#if (NGX_HTTP_CACHE)
-
-    { ngx_string("index_cache"),
-      NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_HTTP_LOC_CONF|NGX_CONF_TAKE3,
-      ngx_http_set_cache_slot,
-      NGX_HTTP_LOC_CONF_OFFSET,
-      offsetof(ngx_http_index_loc_conf_t, index_cache),
-      NULL },
-
-#endif
-
       ngx_null_command
 };
 
@@ -120,16 +109,13 @@ ngx_http_index_handler(ngx_http_request_
 {
     u_char                       *last;
     size_t                        len;
-    ngx_fd_t                      fd;
     ngx_int_t                     rc;
-    ngx_err_t                     err;
-    ngx_str_t                     uri;
+    ngx_str_t                     path, uri;
     ngx_log_t                    *log;
     ngx_uint_t                    i;
     ngx_http_index_t             *index;
     ngx_http_index_ctx_t         *ctx;
-    ngx_pool_cleanup_t           *cln;
-    ngx_pool_cleanup_file_t      *clnf;
+    ngx_open_file_info_t          of;
     ngx_http_script_code_pt       code;
     ngx_http_script_engine_t      e;
     ngx_http_core_loc_conf_t     *clcf;
@@ -151,13 +137,14 @@ ngx_http_index_handler(ngx_http_request_
 
     log = r->connection->log;
 
+    ilcf = ngx_http_get_module_loc_conf(r, ngx_http_index_module);
+    clcf = ngx_http_get_module_loc_conf(r, ngx_http_core_module);
+
     /*
      * we use context because the handler supports an async file opening,
      * and may be called several times
      */
 
-    ilcf = ngx_http_get_module_loc_conf(r, ngx_http_index_module);
-
     ctx = ngx_http_get_module_ctx(r, ngx_http_index_module);
     if (ctx == NULL) {
 
@@ -214,12 +201,16 @@ ngx_http_index_handler(ngx_http_request_
             ctx->index.data = last;
         }
 
+        path.data = ctx->path.data;
+
         if (index[i].values == NULL) {
 
             /* index[i].name.len includes the terminating '\0' */
 
             ngx_memcpy(ctx->index.data, index[i].name.data, index[i].name.len);
 
+            path.len = (ctx->index.data + index[i].name.len - 1) - path.data;
+
         } else {
             e.ip = index[i].values->elts;
             e.pos = ctx->index.data;
@@ -234,39 +225,46 @@ ngx_http_index_handler(ngx_http_request_
                 return ngx_http_internal_redirect(r, &ctx->index, &r->args);
             }
 
+            path.len = e.pos - path.data;
+
             *e.pos++ = '\0';
         }
 
         ngx_log_debug1(NGX_LOG_DEBUG_HTTP, log, 0,
-                       "open index \"%s\"", ctx->path.data);
+                       "open index \"%V\"", &path);
 
-        cln = ngx_pool_cleanup_add(r->pool, sizeof(ngx_pool_cleanup_file_t));
-        if (cln == NULL) {
-            return NGX_HTTP_INTERNAL_SERVER_ERROR;
-        }
+        of.test_dir = 0;
+        of.retest = clcf->open_file_cache_retest;
+        of.errors = clcf->open_file_cache_errors;
+        of.events = clcf->open_file_cache_events;
 
-        fd = ngx_open_file(ctx->path.data, NGX_FILE_RDONLY, NGX_FILE_OPEN, 0);
+        rc = ngx_open_cached_file(clcf->open_file_cache, &path, &of, r->pool);
 
-        if (fd == (ngx_fd_t) NGX_AGAIN) {
+#if 0
+        if (rc == NGX_AGAIN) {
             ctx->current = i;
             return NGX_AGAIN;
         }
+#endif
 
-        if (fd == NGX_INVALID_FILE) {
-            err = ngx_errno;
+        if (rc == NGX_ERROR) {
 
-            ngx_log_debug1(NGX_LOG_DEBUG_HTTP, log, err,
+            ngx_log_debug1(NGX_LOG_DEBUG_HTTP, log, of.err,
                            ngx_open_file_n " \"%s\" failed", ctx->path.data);
 
-            if (err == NGX_ENOTDIR) {
-                return ngx_http_index_error(r, ctx, err);
+            if (of.err == 0) {
+                return NGX_HTTP_INTERNAL_SERVER_ERROR;
+            }
 
-            } else if (err == NGX_EACCES) {
-                return ngx_http_index_error(r, ctx, err);
+            if (of.err == NGX_ENOTDIR) {
+                return ngx_http_index_error(r, ctx, of.err);
+
+            } else if (of.err == NGX_EACCES) {
+                return ngx_http_index_error(r, ctx, of.err);
             }
 
             if (!ctx->tested) {
-                rc = ngx_http_index_test_dir(r, ctx);
+                rc = ngx_http_index_test_dir(r, clcf, ctx);
 
                 if (rc != NGX_OK) {
                     return rc;
@@ -275,25 +273,16 @@ ngx_http_index_handler(ngx_http_request_
                 ctx->tested = 1;
             }
 
-            if (err == NGX_ENOENT) {
+            if (of.err == NGX_ENOENT) {
                 continue;
             }
 
-            ngx_log_error(NGX_LOG_ERR, log, err,
+            ngx_log_error(NGX_LOG_ERR, log, of.err,
                           ngx_open_file_n " \"%s\" failed", ctx->path.data);
 
             return NGX_HTTP_INTERNAL_SERVER_ERROR;
         }
 
-        cln->handler = ngx_pool_cleanup_file;
-        clnf = cln->data;
-
-        clnf->fd = fd;
-        clnf->name = ctx->path.data;
-        clnf->log = r->pool->log;
-
-        clcf = ngx_http_get_module_loc_conf(r, ngx_http_core_module);
-
         uri.len = r->uri.len + ctx->index.len - 1;
 
         if (!clcf->alias) {
@@ -317,43 +306,53 @@ ngx_http_index_handler(ngx_http_request_
 
 
 static ngx_int_t
-ngx_http_index_test_dir(ngx_http_request_t *r, ngx_http_index_ctx_t *ctx)
+ngx_http_index_test_dir(ngx_http_request_t *r, ngx_http_core_loc_conf_t *clcf,
+    ngx_http_index_ctx_t *ctx)
 {
-    u_char           c;
-    ngx_uint_t       i;
-    ngx_err_t        err;
-    ngx_file_info_t  fi;
+    u_char                c;
+    ngx_str_t             path;
+    ngx_uint_t            i;
+    ngx_open_file_info_t  of;
 
     c = *(ctx->index.data - 1);
     i = (c == '/') ? 1 : 0;
     *(ctx->index.data - i) = '\0';
 
-    ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
-                   "http index check dir: \"%s\"", ctx->path.data);
+    path.len = (ctx->index.data - i) - ctx->path.data;
+    path.data = ctx->path.data;
 
-    if (ngx_file_info(ctx->path.data, &fi) == -1) {
+    ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
+                   "http index check dir: \"%V\"", &path);
 
-        err = ngx_errno;
+    of.test_dir = 1;
+    of.retest = clcf->open_file_cache_retest;
+    of.errors = clcf->open_file_cache_errors;
 
-        if (err == NGX_ENOENT) {
-            *(ctx->index.data - i) = c;
-            return ngx_http_index_error(r, ctx, err);
+    if (ngx_open_cached_file(clcf->open_file_cache, &path, &of, r->pool)
+        != NGX_OK)
+    {
+        if (of.err) {
+
+            if (of.err == NGX_ENOENT) {
+                *(ctx->index.data - i) = c;
+                return ngx_http_index_error(r, ctx, of.err);
+            }
+
+            ngx_log_error(NGX_LOG_CRIT, r->connection->log, of.err,
+                          ngx_open_file_n " \"%s\" failed", path.data);
         }
 
-        ngx_log_error(NGX_LOG_CRIT, r->connection->log, err,
-                      ngx_file_info_n " \"%s\" failed", ctx->path.data);
-
         return NGX_HTTP_INTERNAL_SERVER_ERROR;
     }
 
     *(ctx->index.data - i) = c;
 
-    if (ngx_is_dir(&fi)) {
+    if (of.is_dir) {
         return NGX_OK;
     }
 
     ngx_log_error(NGX_LOG_ALERT, r->connection->log, 0,
-                  "\"%s\" is not a directory", ctx->path.data);
+                  "\"%s\" is not a directory", path.data);
 
     return NGX_HTTP_INTERNAL_SERVER_ERROR;
 }