Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/nginx/nginx.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorIgor Sysoev <igor@sysoev.ru>2008-07-30 16:34:04 +0400
committerIgor Sysoev <igor@sysoev.ru>2008-07-30 16:34:04 +0400
commit385af286421e983f744f7f5d339b8060ccd36302 (patch)
tree81c46d0dad40506cc3a331c6ffaf454da85a0177 /src
parent749449097847cc3bee9e4e3966122a94149b755b (diff)
directio
Diffstat (limited to 'src')
-rw-r--r--src/core/ngx_open_file_cache.c7
-rw-r--r--src/core/ngx_open_file_cache.h1
-rw-r--r--src/core/ngx_output_chain.c25
-rw-r--r--src/core/ngx_palloc.c28
-rw-r--r--src/core/ngx_palloc.h1
-rw-r--r--src/http/modules/ngx_http_flv_module.c1
-rw-r--r--src/http/modules/ngx_http_gzip_static_module.c1
-rw-r--r--src/http/modules/ngx_http_index_module.c1
-rw-r--r--src/http/modules/ngx_http_static_module.c1
-rw-r--r--src/http/modules/perl/nginx.xs1
-rw-r--r--src/http/ngx_http_core_module.c39
-rw-r--r--src/http/ngx_http_core_module.h1
-rw-r--r--src/http/ngx_http_script.c1
-rw-r--r--src/os/unix/ngx_alloc.h4
-rw-r--r--src/os/unix/ngx_files.c19
-rw-r--r--src/os/unix/ngx_files.h18
-rw-r--r--src/os/win32/ngx_files.h6
17 files changed, 143 insertions, 12 deletions
diff --git a/src/core/ngx_open_file_cache.c b/src/core/ngx_open_file_cache.c
index 704d0ab79..f2e8afc51 100644
--- a/src/core/ngx_open_file_cache.c
+++ b/src/core/ngx_open_file_cache.c
@@ -497,6 +497,13 @@ ngx_open_and_stat_file(u_char *name, ngx_open_file_info_t *of, ngx_log_t *log)
} else {
of->fd = fd;
+
+ if (of->directio <= ngx_file_size(&fi)) {
+ if (ngx_directio(fd) == -1) {
+ ngx_log_error(NGX_LOG_ALERT, log, ngx_errno,
+ ngx_directio_n " \"%s\" failed", name);
+ }
+ }
}
done:
diff --git a/src/core/ngx_open_file_cache.h b/src/core/ngx_open_file_cache.h
index 4d8393b5d..1e1a27915 100644
--- a/src/core/ngx_open_file_cache.h
+++ b/src/core/ngx_open_file_cache.h
@@ -17,6 +17,7 @@ typedef struct {
ngx_file_uniq_t uniq;
time_t mtime;
off_t size;
+ off_t directio;
ngx_err_t err;
time_t valid;
diff --git a/src/core/ngx_output_chain.c b/src/core/ngx_output_chain.c
index 423a650d3..c4bd67851 100644
--- a/src/core/ngx_output_chain.c
+++ b/src/core/ngx_output_chain.c
@@ -32,6 +32,7 @@ ngx_output_chain(ngx_output_chain_ctx_t *ctx, ngx_chain_t *in)
size_t size;
ngx_int_t rc, last;
ngx_uint_t recycled;
+ ngx_buf_t *b;
ngx_chain_t *cl, *out, **last_out;
if (ctx->in == NULL && ctx->busy == NULL) {
@@ -161,13 +162,29 @@ ngx_output_chain(ngx_output_chain_ctx_t *ctx, ngx_chain_t *in)
}
}
- ctx->buf = ngx_create_temp_buf(ctx->pool, size);
- if (ctx->buf == NULL) {
+ b = ngx_calloc_buf(ctx->pool);
+ if (b == NULL) {
return NGX_ERROR;
}
- ctx->buf->tag = ctx->tag;
- ctx->buf->recycled = recycled;
+ /*
+ * allocate block aligned to a disk sector size
+ * to enable O_DIRECT
+ */
+
+ b->start = ngx_pmemalign(ctx->pool, size, 512);
+ if (b->start == NULL) {
+ return NGX_ERROR;
+ }
+
+ b->pos = b->start;
+ b->last = b->start;
+ b->end = b->last + size;
+ b->temporary = 1;
+ b->tag = ctx->tag;
+ b->recycled = recycled;
+
+ ctx->buf = b;
ctx->allocated++;
}
}
diff --git a/src/core/ngx_palloc.c b/src/core/ngx_palloc.c
index 5a0ea5121..0cadd4aed 100644
--- a/src/core/ngx_palloc.c
+++ b/src/core/ngx_palloc.c
@@ -195,17 +195,35 @@ ngx_palloc_large(ngx_pool_t *pool, size_t size)
void *p;
ngx_pool_large_t *large;
-#if 0
- p = ngx_memalign(ngx_pagesize, size, pool->log);
+ p = ngx_alloc(size, pool->log);
if (p == NULL) {
return NULL;
}
-#else
- p = ngx_alloc(size, pool->log);
+
+ large = ngx_palloc(pool, sizeof(ngx_pool_large_t));
+ if (large == NULL) {
+ ngx_free(p);
+ return NULL;
+ }
+
+ large->alloc = p;
+ large->next = pool->large;
+ pool->large = large;
+
+ return p;
+}
+
+
+void *
+ngx_pmemalign(ngx_pool_t *pool, size_t size, size_t alignment)
+{
+ void *p;
+ ngx_pool_large_t *large;
+
+ p = ngx_memalign(alignment, size, pool->log);
if (p == NULL) {
return NULL;
}
-#endif
large = ngx_palloc(pool, sizeof(ngx_pool_large_t));
if (large == NULL) {
diff --git a/src/core/ngx_palloc.h b/src/core/ngx_palloc.h
index 34878f5f2..2b3a30cbd 100644
--- a/src/core/ngx_palloc.h
+++ b/src/core/ngx_palloc.h
@@ -77,6 +77,7 @@ void ngx_destroy_pool(ngx_pool_t *pool);
void *ngx_palloc(ngx_pool_t *pool, size_t size);
void *ngx_pnalloc(ngx_pool_t *pool, size_t size);
void *ngx_pcalloc(ngx_pool_t *pool, size_t size);
+void *ngx_pmemalign(ngx_pool_t *pool, size_t size, size_t alignment);
ngx_int_t ngx_pfree(ngx_pool_t *pool, void *p);
diff --git a/src/http/modules/ngx_http_flv_module.c b/src/http/modules/ngx_http_flv_module.c
index bed1b48a6..dceb68abc 100644
--- a/src/http/modules/ngx_http_flv_module.c
+++ b/src/http/modules/ngx_http_flv_module.c
@@ -107,6 +107,7 @@ ngx_http_flv_handler(ngx_http_request_t *r)
ngx_memzero(&of, sizeof(ngx_open_file_info_t));
+ of.directio = clcf->directio;
of.valid = clcf->open_file_cache_valid;
of.min_uses = clcf->open_file_cache_min_uses;
of.errors = clcf->open_file_cache_errors;
diff --git a/src/http/modules/ngx_http_gzip_static_module.c b/src/http/modules/ngx_http_gzip_static_module.c
index 51fe0d56d..bc3a65f11 100644
--- a/src/http/modules/ngx_http_gzip_static_module.c
+++ b/src/http/modules/ngx_http_gzip_static_module.c
@@ -121,6 +121,7 @@ ngx_http_gzip_static_handler(ngx_http_request_t *r)
ngx_memzero(&of, sizeof(ngx_open_file_info_t));
+ of.directio = clcf->directio;
of.valid = clcf->open_file_cache_valid;
of.min_uses = clcf->open_file_cache_min_uses;
of.errors = clcf->open_file_cache_errors;
diff --git a/src/http/modules/ngx_http_index_module.c b/src/http/modules/ngx_http_index_module.c
index bc4cd5009..6d4cf34d3 100644
--- a/src/http/modules/ngx_http_index_module.c
+++ b/src/http/modules/ngx_http_index_module.c
@@ -210,6 +210,7 @@ ngx_http_index_handler(ngx_http_request_t *r)
ngx_memzero(&of, sizeof(ngx_open_file_info_t));
+ of.directio = clcf->directio;
of.valid = clcf->open_file_cache_valid;
of.min_uses = clcf->open_file_cache_min_uses;
of.errors = clcf->open_file_cache_errors;
diff --git a/src/http/modules/ngx_http_static_module.c b/src/http/modules/ngx_http_static_module.c
index ce2f0fc65..8d399fccd 100644
--- a/src/http/modules/ngx_http_static_module.c
+++ b/src/http/modules/ngx_http_static_module.c
@@ -98,6 +98,7 @@ ngx_http_static_handler(ngx_http_request_t *r)
ngx_memzero(&of, sizeof(ngx_open_file_info_t));
+ of.directio = clcf->directio;
of.valid = clcf->open_file_cache_valid;
of.min_uses = clcf->open_file_cache_min_uses;
of.errors = clcf->open_file_cache_errors;
diff --git a/src/http/modules/perl/nginx.xs b/src/http/modules/perl/nginx.xs
index f86b76f3e..6e7ad7760 100644
--- a/src/http/modules/perl/nginx.xs
+++ b/src/http/modules/perl/nginx.xs
@@ -652,6 +652,7 @@ sendfile(r, filename, offset = -1, bytes = 0)
ngx_memzero(&of, sizeof(ngx_open_file_info_t));
+ of.directio = clcf->directio;
of.valid = clcf->open_file_cache_valid;
of.min_uses = clcf->open_file_cache_min_uses;
of.errors = clcf->open_file_cache_errors;
diff --git a/src/http/ngx_http_core_module.c b/src/http/ngx_http_core_module.c
index 0ddfc04d1..468b3e151 100644
--- a/src/http/ngx_http_core_module.c
+++ b/src/http/ngx_http_core_module.c
@@ -54,6 +54,8 @@ static char *ngx_http_core_server_name(ngx_conf_t *cf, ngx_command_t *cmd,
static char *ngx_http_core_root(ngx_conf_t *cf, ngx_command_t *cmd, void *conf);
static char *ngx_http_core_limit_except(ngx_conf_t *cf, ngx_command_t *cmd,
void *conf);
+static char *ngx_http_core_directio(ngx_conf_t *cf, ngx_command_t *cmd,
+ void *conf);
static char *ngx_http_core_error_page(ngx_conf_t *cf, ngx_command_t *cmd,
void *conf);
static char *ngx_http_core_open_file_cache(ngx_conf_t *cf, ngx_command_t *cmd,
@@ -353,6 +355,13 @@ static ngx_command_t ngx_http_core_commands[] = {
offsetof(ngx_http_core_loc_conf_t, sendfile_max_chunk),
NULL },
+ { ngx_string("directio"),
+ NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_HTTP_LOC_CONF|NGX_CONF_TAKE1,
+ ngx_http_core_directio,
+ NGX_HTTP_LOC_CONF_OFFSET,
+ 0,
+ NULL },
+
{ ngx_string("tcp_nopush"),
NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_HTTP_LOC_CONF|NGX_CONF_FLAG,
ngx_conf_set_flag_slot,
@@ -2586,6 +2595,7 @@ ngx_http_core_create_loc_conf(ngx_conf_t *cf)
lcf->client_body_in_file_only = NGX_CONF_UNSET;
lcf->sendfile = NGX_CONF_UNSET;
lcf->sendfile_max_chunk = NGX_CONF_UNSET_SIZE;
+ lcf->directio = NGX_CONF_UNSET;
lcf->tcp_nopush = NGX_CONF_UNSET;
lcf->tcp_nodelay = NGX_CONF_UNSET;
lcf->send_timeout = NGX_CONF_UNSET_MSEC;
@@ -2774,6 +2784,8 @@ ngx_http_core_merge_loc_conf(ngx_conf_t *cf, void *parent, void *child)
ngx_conf_merge_value(conf->sendfile, prev->sendfile, 0);
ngx_conf_merge_size_value(conf->sendfile_max_chunk,
prev->sendfile_max_chunk, 0);
+ ngx_conf_merge_off_value(conf->directio, prev->directio,
+ NGX_MAX_OFF_T_VALUE);
ngx_conf_merge_value(conf->tcp_nopush, prev->tcp_nopush, 0);
ngx_conf_merge_value(conf->tcp_nodelay, prev->tcp_nodelay, 1);
@@ -3340,6 +3352,33 @@ ngx_http_core_limit_except(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
static char *
+ngx_http_core_directio(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
+{
+ ngx_http_core_loc_conf_t *clcf = conf;
+
+ ngx_str_t *value;
+
+ if (clcf->directio != NGX_CONF_UNSET) {
+ return "is duplicate";
+ }
+
+ value = cf->args->elts;
+
+ if (ngx_strcmp(value[1].data, "off") == 0) {
+ clcf->directio = NGX_MAX_OFF_T_VALUE;
+ return NGX_CONF_OK;
+ }
+
+ clcf->directio = ngx_parse_offset(&value[1]);
+ if (clcf->directio == (off_t) NGX_ERROR) {
+ return "invalid value";
+ }
+
+ return NGX_CONF_OK;
+}
+
+
+static char *
ngx_http_core_error_page(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
{
ngx_http_core_loc_conf_t *lcf = conf;
diff --git a/src/http/ngx_http_core_module.h b/src/http/ngx_http_core_module.h
index 85d96b079..57ee748e7 100644
--- a/src/http/ngx_http_core_module.h
+++ b/src/http/ngx_http_core_module.h
@@ -265,6 +265,7 @@ struct ngx_http_core_loc_conf_s {
ngx_str_t default_type;
off_t client_max_body_size; /* client_max_body_size */
+ off_t directio; /* directio */
size_t client_body_buffer_size; /* client_body_buffer_size */
size_t send_lowat; /* send_lowat */
diff --git a/src/http/ngx_http_script.c b/src/http/ngx_http_script.c
index 7a47417e4..0ffa07cc8 100644
--- a/src/http/ngx_http_script.c
+++ b/src/http/ngx_http_script.c
@@ -996,6 +996,7 @@ ngx_http_script_file_code(ngx_http_script_engine_t *e)
ngx_memzero(&of, sizeof(ngx_open_file_info_t));
+ of.directio = clcf->directio;
of.valid = clcf->open_file_cache_valid;
of.min_uses = clcf->open_file_cache_min_uses;
of.errors = clcf->open_file_cache_errors;
diff --git a/src/os/unix/ngx_alloc.h b/src/os/unix/ngx_alloc.h
index 8b7b766b2..c7a31aa54 100644
--- a/src/os/unix/ngx_alloc.h
+++ b/src/os/unix/ngx_alloc.h
@@ -21,8 +21,8 @@ void *ngx_calloc(size_t size, ngx_log_t *log);
/*
* Linux has memalign() or posix_memalign()
* Solaris has memalign()
- * FreeBSD has not memalign() or posix_memalign() but its malloc() alignes
- * allocations bigger than page size at the page boundary.
+ * FreeBSD 7.0 has posix_memalign(), besides, early version's malloc()
+ * aligns allocations bigger than page size at the page boundary
*/
#if (NGX_HAVE_POSIX_MEMALIGN || NGX_HAVE_MEMALIGN)
diff --git a/src/os/unix/ngx_files.c b/src/os/unix/ngx_files.c
index 7ee8cbd84..e2148d843 100644
--- a/src/os/unix/ngx_files.c
+++ b/src/os/unix/ngx_files.c
@@ -351,3 +351,22 @@ ngx_unlock_fd(ngx_fd_t fd)
return 0;
}
+
+
+#if (NGX_HAVE_O_DIRECT)
+
+ngx_int_t
+ngx_directio(ngx_fd_t fd)
+{
+ int flags;
+
+ flags = fcntl(fd, F_GETFL);
+
+ if (flags == -1) {
+ return -1;
+ }
+
+ return fcntl(fd, F_SETFL, flags | O_DIRECT);
+}
+
+#endif
diff --git a/src/os/unix/ngx_files.h b/src/os/unix/ngx_files.h
index 0c080c494..62af63bce 100644
--- a/src/os/unix/ngx_files.h
+++ b/src/os/unix/ngx_files.h
@@ -189,4 +189,22 @@ ngx_err_t ngx_unlock_fd(ngx_fd_t fd);
#define ngx_unlock_fd_n "fcntl(F_SETLK, F_UNLCK)"
+#if (NGX_HAVE_O_DIRECT)
+
+ngx_int_t ngx_directio(ngx_fd_t fd);
+#define ngx_directio_n "fcntl(O_DIRECT)"
+
+#elif (NGX_HAVE_F_NOCACHE)
+
+#define ngx_directio(fd) fcntl(fd, F_NOCACHE, 1)
+#define ngx_directio_n "fcntl(F_NOCACHE)"
+
+#else
+
+#define ngx_directio(fd) 0
+#define ngx_directio_n "ngx_directio_n"
+
+#endif
+
+
#endif /* _NGX_FILES_H_INCLUDED_ */
diff --git a/src/os/win32/ngx_files.h b/src/os/win32/ngx_files.h
index 0c4e14fa3..5973e95b3 100644
--- a/src/os/win32/ngx_files.h
+++ b/src/os/win32/ngx_files.h
@@ -200,7 +200,7 @@ typedef struct {
ngx_int_t ngx_open_glob(ngx_glob_t *gl);
-#define ngx_open_glob_n "FindFirstFile()"
+#define ngx_open_glob_n "FindFirstFile()"
ngx_int_t ngx_read_glob(ngx_glob_t *gl, ngx_str_t *name);
void ngx_close_glob(ngx_glob_t *gl);
@@ -216,4 +216,8 @@ ssize_t ngx_write_chain_to_file(ngx_file_t *file, ngx_chain_t *ce,
off_t offset, ngx_pool_t *pool);
+#define ngx_directio(fd) 0
+#define ngx_directio_n "ngx_directio_n"
+
+
#endif /* _NGX_FILES_H_INCLUDED_ */