changeset 253:b6793bc5034b

nginx-0.0.2-2004-02-09-10:46:43 import
author Igor Sysoev <igor@sysoev.ru>
date Mon, 09 Feb 2004 07:46:43 +0000
parents 84b1c672ec5a
children 98c77ca0f354
files auto/configure auto/fmt/xfmt auto/func auto/headers auto/inc auto/lib/md5/conf auto/lib/zlib/conf auto/options auto/os/freebsd auto/os/linux auto/os/solaris auto/summary auto/unix src/core/nginx.c src/core/ngx_config.h src/core/ngx_connection.c src/core/ngx_connection.h src/event/modules/ngx_epoll_module.c src/event/modules/ngx_poll_module.c src/event/ngx_event.c src/event/ngx_event_accept.c src/http/modules/ngx_http_static_handler.c src/http/ngx_http.c src/http/ngx_http_core_module.c src/http/ngx_http_request.c src/os/unix/ngx_freebsd_init.c src/os/unix/ngx_freebsd_sendfile_chain.c src/os/unix/ngx_linux_config.h src/os/unix/ngx_linux_sendfile_chain.c src/os/unix/ngx_recv.c src/os/unix/ngx_recv.h src/os/unix/ngx_socket.c
diffstat 32 files changed, 302 insertions(+), 246 deletions(-) [+]
line wrap: on
line diff
--- a/auto/configure
+++ b/auto/configure
@@ -3,8 +3,13 @@
 . auto/init
 . auto/sources
 
+test $OBJ || mkdir $OBJ
 echo > $NGX_AUTO_CONFIG_H
 
+if [ "$PLATFORM" != win32 ]; then
+    . auto/headers
+fi
+
 . auto/os/conf
 . auto/modules
 
--- a/auto/fmt/xfmt
+++ b/auto/fmt/xfmt
@@ -1,6 +1,8 @@
 
-echo "#ifndef $ngx_fmt_name"                 >> $NGX_AUTO_CONFIG_H
-echo "#define $ngx_fmt_name  \"$ngx_fmt\"" | sed -e 's/d"$/x"/' \
-                                             >> $NGX_AUTO_CONFIG_H
-echo "#endif"                                >> $NGX_AUTO_CONFIG_H
-echo                                         >> $NGX_AUTO_CONFIG_H
+cat << END | sed -e 's/d"$/x"/' >> $NGX_AUTO_CONFIG_H
+
+#ifndef $ngx_fmt_name
+#define $ngx_fmt_name  "$ngx_fmt"
+#endif
+
+END
--- a/auto/func
+++ b/auto/func
@@ -24,15 +24,7 @@ eval "$CC $CC_TEST_FLAGS -o $NGX_AUTOTES
 
 if [ -x $NGX_AUTOTEST ]; then
     echo " found"
-
-    cat << END >> $NGX_AUTO_CONFIG_H
-
-#ifndef HAVE_$func
-#define HAVE_$func  1
-#endif
-
-END
-
+    have=HAVE_$func . auto/have
     ngx_found=yes
 
 else
new file mode 100644
--- /dev/null
+++ b/auto/headers
@@ -0,0 +1,3 @@
+
+ngx_inc="unistd.h"; . auto/inc
+ngx_inc="inttypes.h"; . auto/inc
--- a/auto/inc
+++ b/auto/inc
@@ -21,15 +21,7 @@ eval "${CC} -o $NGX_AUTOTEST $NGX_AUTOTE
 
 if [ -x $NGX_AUTOTEST ]; then
     echo " found"
-
-    cat << END >> $NGX_AUTO_CONFIG_H
-
-#ifndef HAVE_$inc
-#define HAVE_$inc  1
-#endif
-
-END
-
+    have=HAVE_$inc . auto/have
     eval "NGX_$inc='#include <$ngx_inc>'"
     ngx_found=yes
 
--- a/auto/lib/md5/conf
+++ b/auto/lib/md5/conf
@@ -1,5 +1,5 @@
 
-if [ $MD5 != NO ]; then
+if [ $MD5 != NONE ]; then
 
     if grep MD5_Init $MD5/md5.h >/dev/null; then
         # OpenSSL md5
@@ -25,6 +25,8 @@ else
 ngx_lib_inc="#include <sys/types.h>
 #include <md5.h>"
 
+    MD5=NO
+
         # Solaris 8/9
         ngx_lib="rsaref md5"
         ngx_lib_test="MD5_CTX md5; MD5Init(&md5)"
--- a/auto/lib/zlib/conf
+++ b/auto/lib/zlib/conf
@@ -1,5 +1,5 @@
 
-if [ $ZLIB != NO ]; then
+if [ $ZLIB != NONE ]; then
     CORE_INCS="$CORE_INCS -I $ZLIB"
 
     if [ "$PLATFORM" = "win32" ]; then
@@ -23,6 +23,8 @@ else
     if [ $ngx_found = yes ]; then
         CORE_LIBS="$CORE_LIBS $ngx_libs"
         ZLIB=YES
+    else
+        ZLIB=NO
     fi
 
 fi
--- a/auto/options
+++ b/auto/options
@@ -22,12 +22,10 @@ HTTP_PROXY=YES
 PCRE=NO
 
 USE_MD5=NO
-MD5=NO
-MD5_LIB=NO
+MD5=NONE
 
 USE_ZLIB=NO
-ZLIB=NO
-ZLIB_LIB=NO
+ZLIB=NONE
 
 
 for option
--- a/auto/os/freebsd
+++ b/auto/os/freebsd
@@ -1,11 +1,8 @@
-
 
 CORE_INCS="$UNIX_INCS"
 CORE_DEPS="$UNIX_DEPS $FREEBSD_DEPS"
 CORE_SRCS="$UNIX_SRCS $FREEBSD_SRCS"
 
-MD5_LIB="-lmd"
-ZLIB_LIB="-lz"
 
 version=`grep "#define __FreeBSD_version" /usr/include/osreldate.h \
          | sed -e 's/^.* \(.*\)$/\1/'`
--- a/auto/os/linux
+++ b/auto/os/linux
@@ -4,7 +4,6 @@ CORE_DEPS="$UNIX_DEPS $LINUX_DEPS"
 CORE_SRCS="$UNIX_SRCS $LINUX_SRCS"
 EVENT_MODULES="$EVENT_MODULES"
 
-ZLIB_LIB="-lz"
 
 CC_TEST_FLAGS="-D_GNU_SOURCE -D_FILE_OFFSET_BITS=64 -D_LARGEFILE_SOURCE"
 
@@ -13,7 +12,7 @@ CC_TEST_FLAGS="-D_GNU_SOURCE -D_FILE_OFF
 
 ngx_func="epoll";
 ngx_func_inc="#include <sys/epoll.h>"
-ngx_func_test="int fd = 1; int n;
+ngx_func_test="int efd = 0, fd = 1, n;
                struct epoll_event ee;
                ee.events = EPOLLIN|EPOLLOUT|EPOLLET;
                ee.data.ptr = NULL;
@@ -21,7 +20,7 @@ ngx_func_test="int fd = 1; int n;
 . auto/func
 
 if [ $ngx_found = yes ]; then
-    CFLAGS="$CFLAGS -D HAVE_EPOLL=1"
+    have=HAVE_EPOLL . auto/have
     CORE_SRCS="$CORE_SRCS $EPOLL_SRCS"
     EVENT_MODULES="$EVENT_MODULES $EPOLL_MODULE"
     EVENT_FOUND=YES
@@ -39,7 +38,6 @@ ngx_func_test="int s = 0, fd = 1;
 . auto/func
 
 if [ $ngx_found = yes ]; then
-    CFLAGS="$CFLAGS -D HAVE_SENDFILE=1"
     CORE_SRCS="$CORE_SRCS $LINUX_SENDFILE_SRCS"
 fi
 
@@ -49,6 +47,14 @@ fi
 CC_TEST_FLAGS="-D_GNU_SOURCE -D_FILE_OFFSET_BITS=64 -D_LARGEFILE_SOURCE"
 ngx_func="sendfile64()"; . auto/func
 
+
+# prctl(PR_SET_DUMPABLE)
+
+ngx_func="prctl()";
+ngx_func_inc="#include <sys/prctl.h>"
+ngx_func_test="prctl(PR_SET_DUMPABLE, 1, 0, 0, 0)"
+. auto/func
+
 if [ $ngx_found = yes ]; then
-    CFLAGS="$CFLAGS -D HAVE_SENDFILE64=1"
+    have=HAVE_PR_SET_DUMPABLE . auto/have
 fi
--- a/auto/os/solaris
+++ b/auto/os/solaris
@@ -4,17 +4,16 @@ CORE_DEPS="$UNIX_DEPS $SOLARIS_DEPS"
 CORE_SRCS="$UNIX_SRCS $SOLARIS_SRCS "
 EVENT_MODULES="$EVENT_MODULES"
 
-MD5_LIB="-lmd5"
-ZLIB_LIB="-lz"
 CORE_LIBS="$CORE_LIBS -lsocket -lnsl"
 
+
 CC_TEST_FLAGS="-D_FILE_OFFSET_BITS=64"
 
 
 ngx_inc="sys/devpoll.h"; . auto/inc
 
 if [ $ngx_found = yes ]; then
-    CFLAGS="$CFLAGS -D HAVE_DEVPOLL=1"
+    have=HAVE_DEVPOLL . auto/have
     CORE_SRCS="$CORE_SRCS $DEVPOLL_SRCS"
     EVENT_MODULES="$EVENT_MODULES $DEVPOLL_MODULE"
     EVENT_FOUND=YES
@@ -25,13 +24,13 @@ ngx_func="sendfilev()";
 ngx_func_inc="#include <sys/sendfile.h>"
 ngx_func_libs="-lsendfile"
 ngx_func_test="int fd = 1; sendfilevec_t vec[1];
-               size_t sent = 1; ssize_t n;
+               size_t sent; ssize_t n;
                n = sendfilev(fd, vec, 1, &sent)"
 . auto/func
 
 
 if [ $ngx_found = yes ]; then
-    CFLAGS="$CFLAGS -D HAVE_SENDFILE=1"
+    have=HAVE_SENDFILE . auto/have
     CORE_SRCS="$CORE_SRCS $SOLARIS_SENDFILEV_SRCS"
     CORE_LIBS="$CORE_LIBS -lsendfile"
 fi
--- a/auto/summary
+++ b/auto/summary
@@ -3,21 +3,24 @@ echo
 echo "Configuration summary"
 
 case $PCRE in
-    YES) echo " + using system PCRE library" ;;
-    NO)  echo " + PCRE library is not found" ;;
-    *)   echo " + using PCRE library: $PCRE" ;;
+    YES)   echo " + using system PCRE library" ;;
+    NONE)  echo " + PCRE library is not used" ;;
+    NO)    echo " + PCRE library is not found" ;;
+    *)     echo " + using PCRE library: $PCRE" ;;
 esac
 
 case $MD5 in
-    YES) echo " + using system md5 library" ;;
-    NO)  echo " + md5 library is not found" ;;
-    *)   echo " + using md5 library: $MD5" ;;
+    YES)   echo " + using system md5 library" ;;
+    NONE)  echo " + md5 library is not used" ;;
+    NO)    echo " + md5 library is not found" ;;
+    *)     echo " + using md5 library: $MD5" ;;
 esac
 
 case $ZLIB in
-    YES) echo " + using system zlib library" ;;
-    NO)  echo " + zlib library is not found" ;;
-    *)   echo " + using zlib library: $ZLIB" ;;
+    YES)   echo " + using system zlib library" ;;
+    NONE)  echo " + zlib library is not used" ;;
+    NO)    echo " + zlib library is not found" ;;
+    *)     echo " + using zlib library: $ZLIB" ;;
 esac
 
 echo
--- a/auto/unix
+++ b/auto/unix
@@ -16,12 +16,7 @@ ngx_formats="%lld %qd"; . auto/fmt/fmt
 ngx_type="void *"; . auto/types/sizeof; ngx_ptr_bytes=$ngx_bytes
 
 
-# headers
-
-ngx_inc="unistd.h"; . auto/inc
-ngx_inc="inttypes.h"; . auto/inc
-
-#POSIX types
+# POSIX types
 
 NGX_AUTO_CONFIG="#include \"../$NGX_AUTO_CONFIG_H\""
 
@@ -43,6 +38,15 @@ ngx_types="int"; . auto/types/typedef
 . auto/types/uintptr_t
 
 
+ngx_func="sin_len"
+ngx_func_inc="#include <sys/types.h>
+#include <sys/socket.h>
+#include <netinet/in.h>"
+
+ngx_func_test="struct sockaddr_in sa; sa.sin_len = 5"
+. auto/func
+
+
 # printf() formats
 
 CC_WARN=$CC_STRONG
@@ -70,19 +74,15 @@ eval ngx_formats=\${ngx_${ngx_bytes}_fmt
 
 ngx_func="pread()"
 ngx_func_inc=
-ngx_func_test="
-char    buf[1];
-ssize_t n;
-n = pread(0, buf, 1, 0)"
+ngx_func_test="char buf[1]; ssize_t n;
+               n = pread(0, buf, 1, 0)"
 . auto/func
 
 
 ngx_func="pwrite()"
 ngx_func_inc=
-ngx_func_test="
-char    buf[1];
-ssize_t n;
-n = pwrite(1, buf, 1, 0)"
+ngx_func_test="char buf[1]; ssize_t n;
+               n = pwrite(1, buf, 1, 0)"
 . auto/func
 
 
@@ -94,7 +94,7 @@ n = pwrite(1, buf, 1, 0)"
 
 ngx_func="strerror_r()"
 ngx_func_inc="#include <string.h>"
-ngx_func_test="char buf[20]; strerror_r(1, buf, 20)"
+ngx_func_test="char buf[20]; int n; n = strerror_r(1, buf, 20)"
 . auto/func
 
 
--- a/src/core/nginx.c
+++ b/src/core/nginx.c
@@ -377,8 +377,11 @@ static void ngx_master_process_cycle(ngx
                                      ngx_log_error(NGX_LOG_ALERT, cycle->log, 0,
                                                    "can not respawn %s",
                                                    ngx_processes[i].name);
+                                     continue;
                                  }
 
+                                 live = 1;
+
                                  continue;
                             }
 
@@ -443,7 +446,7 @@ static void ngx_master_process_cycle(ngx
 
                     if (ngx_reopen) {
                         if (ngx_process == NGX_PROCESS_MASTER) {
-                            if (ccf->worker_reopen > 0) {
+                            if (ccf->worker_reopen != 0) {
                                 signo = ngx_signal_value(NGX_REOPEN_SIGNAL);
                                 ngx_reopen = 0;
 
@@ -461,7 +464,7 @@ static void ngx_master_process_cycle(ngx
                         ngx_log_error(NGX_LOG_INFO, cycle->log, 0,
                                       "reopening logs");
                         ngx_reopen_files(cycle,
-                                       ccf->worker_reopen > 0 ? ccf->user : -1);
+                             ccf->worker_reopen != 0 ? ccf->user : (uid_t) -1);
                     }
                 }
 
@@ -574,6 +577,17 @@ static void ngx_worker_process_cycle(ngx
         }
     }
 
+#if (HAVE_PR_SET_DUMPABLE)
+
+    /* allow coredump after setuid() in Linux 2.4.x */
+
+    if (prctl(PR_SET_DUMPABLE, 1, 0, 0, 0) == -1) {
+        ngx_log_error(NGX_LOG_ALERT, cycle->log, ngx_errno,
+                      "prctl(PR_SET_DUMPABLE) failed");
+    }
+
+#endif
+
     sigemptyset(&set);
 
     if (sigprocmask(SIG_SETMASK, &set, NULL) == -1) {
--- a/src/core/ngx_config.h
+++ b/src/core/ngx_config.h
@@ -2,7 +2,7 @@
 #define _NGX_CONFIG_H_INCLUDED_
 
 
-#if 1
+#if 0
 /* STUB to allocate a big ngx_connections */
 #undef  FD_SETSIZE
 #define FD_SETSIZE  5000
--- a/src/core/ngx_connection.c
+++ b/src/core/ngx_connection.c
@@ -48,11 +48,6 @@ ngx_int_t ngx_set_inherited_sockets(ngx_
             return NGX_ERROR;
         }
 
-/* STUB: autoconf & set sin_len in ls[i].sockaddr in ngx_http.c */
-#if __FreeBSD__
-        addr_in->sin_len = 0;
-#endif
-
         ls[i].family = addr_in->sin_family;
         ls[i].addr_text.len = ngx_sock_ntop(ls[i].family, ls[i].sockaddr,
                                             ls[i].addr_text.data,
@@ -68,11 +63,11 @@ ngx_int_t ngx_set_inherited_sockets(ngx_
 
 ngx_int_t ngx_open_listening_sockets(ngx_cycle_t *cycle)
 {
-    int              tries, failed, reuseaddr, i;
-    ngx_err_t        err;
-    ngx_log_t       *log;
-    ngx_socket_t     s;
-    ngx_listening_t *ls;
+    ngx_int_t         tries, failed, reuseaddr, i;
+    ngx_err_t         err;
+    ngx_log_t        *log;
+    ngx_socket_t      s;
+    ngx_listening_t  *ls;
 
     reuseaddr = 1;
 #if (NGX_SUPPRESS_WARN)
@@ -241,3 +236,39 @@ void ngx_close_listening_sockets(ngx_cyc
         cycle->connections[fd].fd = -1;
     }
 }
+
+
+ngx_int_t ngx_connection_error(ngx_connection_t *c, ngx_err_t err, char *text)
+{
+    ngx_int_t  level;
+
+    if (err == NGX_ECONNRESET
+        && c->read->log_error == NGX_ERROR_IGNORE_ECONNRESET)
+    {
+        return 0;
+    }
+
+    if (err == NGX_ECONNRESET || err == NGX_EPIPE || err == NGX_ENOTCONN) {
+
+        switch (c->read->log_error) {
+
+        case NGX_ERROR_INFO:
+            level = NGX_LOG_INFO;
+            break;
+
+        case NGX_ERROR_ERR:
+            level = NGX_LOG_ERR;
+            break;
+
+        default:
+            level = NGX_LOG_CRIT;
+        }
+
+    } else {
+        level = NGX_LOG_CRIT;
+    }
+
+    ngx_log_error(level, c->log, err, text);
+
+    return NGX_ERROR;
+}
--- a/src/core/ngx_connection.h
+++ b/src/core/ngx_connection.h
@@ -96,6 +96,7 @@ struct ngx_connection_s {
 ngx_int_t ngx_set_inherited_sockets(ngx_cycle_t *cycle);
 ngx_int_t ngx_open_listening_sockets(ngx_cycle_t *cycle);
 void ngx_close_listening_sockets(ngx_cycle_t *cycle);
+ngx_int_t ngx_connection_error(ngx_connection_t *c, ngx_err_t err, char *text);
 
 
 extern ngx_os_io_t  ngx_io;
--- a/src/event/modules/ngx_epoll_module.c
+++ b/src/event/modules/ngx_epoll_module.c
@@ -202,11 +202,11 @@ static int ngx_epoll_add_event(ngx_event
     }
 #endif
 
-    ee.events = event;
+    ee.events = event|EPOLLET;
     ee.data.ptr = (void *) ((uintptr_t) c | c->read->instance);
 
     ngx_log_debug2(NGX_LOG_DEBUG_EVENT, c->log, 0,
-                   "epoll add event: fd:%d ev:%04X", c->fd, ee.events);
+                   "epoll add event: fd:%d ev:%08X", c->fd, ee.events);
 
     if (epoll_ctl(ep, EPOLL_CTL_ADD, c->fd, &ee) == -1) {
         ngx_log_error(NGX_LOG_ALERT, c->log, ngx_errno,
@@ -230,8 +230,8 @@ static int ngx_epoll_del_event(ngx_event
     ee.events = 0;
     ee.data.ptr = NULL;
 
-    ngx_log_debug2(NGX_LOG_DEBUG_EVENT, c->log, 0,
-                   "epoll del event: fd:%d ev:%04X", c->fd, ee.events);
+    ngx_log_debug1(NGX_LOG_DEBUG_EVENT, c->log, 0,
+                   "epoll del event: fd:%d", c->fd);
 
     if (epoll_ctl(ep, EPOLL_CTL_DEL, c->fd, &ee) == -1) {
         ngx_log_error(NGX_LOG_ALERT, c->log, ngx_errno,
@@ -249,11 +249,11 @@ static int ngx_epoll_add_connection(ngx_
 {
     struct epoll_event  ee;
 
-    ee.events = EPOLLIN|EPOLLOUT;
+    ee.events = EPOLLIN|EPOLLOUT|EPOLLET;
     ee.data.ptr = (void *) ((uintptr_t) c | c->read->instance);
 
     ngx_log_debug2(NGX_LOG_DEBUG_EVENT, c->log, 0,
-                   "epoll add connection: fd:%d ev:%04X", c->fd, ee.events);
+                   "epoll add connection: fd:%d ev:%08X", c->fd, ee.events);
 
     if (epoll_ctl(ep, EPOLL_CTL_ADD, c->fd, &ee) == -1) {
         ngx_log_error(NGX_LOG_ALERT, c->log, ngx_errno,
@@ -355,9 +355,9 @@ int ngx_epoll_process_events(ngx_log_t *
         }
 
         if (event_list[i].events & (EPOLLERR|EPOLLHUP)) {
-            ngx_log_error(NGX_LOG_ALERT, log, 0,
-                          "epoll_wait() error on fd:%d ev:%d",
-                          c->fd, event_list[i].events);
+            ngx_log_debug2(NGX_LOG_DEBUG_EVENT, log, 0,
+                           "epoll_wait() error on fd:%d ev:%04X",
+                           c->fd, event_list[i].events);
         }
 
         if (event_list[i].events & ~(EPOLLIN|EPOLLOUT|EPOLLERR|EPOLLHUP)) {
--- a/src/event/modules/ngx_poll_module.c
+++ b/src/event/modules/ngx_poll_module.c
@@ -286,7 +286,8 @@ static int ngx_poll_process_events(ngx_l
     delta = ngx_elapsed_msec;
     ngx_elapsed_msec = tv.tv_sec * 1000 + tv.tv_usec / 1000 - ngx_start_msec;
 
-    ngx_log_debug1(NGX_LOG_DEBUG_EVENT, log, 0, "poll ready %d", ready);
+    ngx_log_debug2(NGX_LOG_DEBUG_EVENT, log, 0,
+                   "poll ready %d of %d", ready, nevents);
 
     if (err) {
         ngx_log_error((err == NGX_EINTR) ? NGX_LOG_INFO : NGX_LOG_ALERT,
--- a/src/event/ngx_event.c
+++ b/src/event/ngx_event.c
@@ -459,6 +459,12 @@ static char *ngx_event_init_conf(ngx_cyc
     ngx_conf_init_value(ecf->use, ngx_devpoll_module.ctx_index);
     ngx_conf_init_ptr_value(ecf->name, ngx_devpoll_module_ctx.name->data);
 
+#elif (HAVE_EPOLL)
+
+    ngx_conf_init_value(ecf->connections, DEFAULT_CONNECTIONS);
+    ngx_conf_init_value(ecf->use, ngx_epoll_module.ctx_index);
+    ngx_conf_init_ptr_value(ecf->name, ngx_epoll_module_ctx.name->data);
+
 #else /* HAVE_SELECT */
 
     ngx_conf_init_value(ecf->connections,
--- a/src/event/ngx_event_accept.c
+++ b/src/event/ngx_event_accept.c
@@ -145,7 +145,7 @@ void ngx_event_accept(ngx_event_t *ev)
             }
 
         } else {
-            if ((ngx_event_flags & NGX_USE_AIO_EVENT) == 0) {
+            if (!(ngx_event_flags & NGX_USE_AIO_EVENT)) {
                 if (ngx_nonblocking(s) == -1) {
                     ngx_log_error(NGX_LOG_ALERT, log, ngx_socket_errno,
                                   ngx_nonblocking_n " failed");
--- a/src/http/modules/ngx_http_static_handler.c
+++ b/src/http/modules/ngx_http_static_handler.c
@@ -87,8 +87,8 @@ static ngx_int_t ngx_http_static_handler
     }
 
     /*
-     * there is a valid cached open file, i.e by index handler,
-     * and it must be already registered in r->cleanup
+     * there is a valid cached open file, i.e by the index handler,
+     * and it should be already registered in r->cleanup
      */
 
     if (r->cache && !r->cache->expired) {
@@ -100,13 +100,14 @@ static ngx_int_t ngx_http_static_handler
     clcf = ngx_http_get_module_loc_conf(r, ngx_http_core_module);
 
     /*
-     * make a file name
-     * 2 bytes is for a trailing '/' in a possible redirect and for '\0'
+     * make a file name, reserve 2 bytes for a trailing '/'
+     * in a possible redirect and for the last '\0'
      */
 
-    ngx_test_null(name.data,
-                  ngx_palloc(r->pool, clcf->doc_root.len + r->uri.len + 2),
-                  NGX_HTTP_INTERNAL_SERVER_ERROR);
+    name.data = ngx_palloc(r->pool, clcf->doc_root.len + r->uri.len + 2);
+    if (name.data == NULL) {
+        return NGX_HTTP_INTERNAL_SERVER_ERROR;
+    }
 
     location.data = ngx_cpymem(name.data, clcf->doc_root.data,
                                clcf->doc_root.len);
--- a/src/http/ngx_http.c
+++ b/src/http/ngx_http.c
@@ -483,6 +483,9 @@ static char *ngx_http_block(ngx_conf_t *
                           ngx_pcalloc(cf->pool, sizeof(struct sockaddr_in)),
                           NGX_CONF_ERROR);
 
+#if (HAVE_SIN_LEN)
+            addr_in->sin_len = sizeof(struct sockaddr_in);
+#endif
             addr_in->sin_family = AF_INET;
             addr_in->sin_addr.s_addr = in_addr[a].addr;
             addr_in->sin_port = htons((u_short) in_port[p].port);
--- a/src/http/ngx_http_core_module.c
+++ b/src/http/ngx_http_core_module.c
@@ -1217,10 +1217,10 @@ static char *ngx_http_core_merge_loc_con
                              prev->default_type, "text/plain");
 
     ngx_conf_merge_msec_value(conf->client_body_timeout,
-                              prev->client_body_timeout, 10000);
+                              prev->client_body_timeout, 60000);
     ngx_conf_merge_value(conf->sendfile, prev->sendfile, 0);
     ngx_conf_merge_value(conf->tcp_nopush, prev->tcp_nopush, 0);
-    ngx_conf_merge_msec_value(conf->send_timeout, prev->send_timeout, 10000);
+    ngx_conf_merge_msec_value(conf->send_timeout, prev->send_timeout, 60000);
     ngx_conf_merge_size_value(conf->send_lowat, prev->send_lowat, 0);
     ngx_conf_merge_size_value(conf->discarded_buffer_size,
                               prev->discarded_buffer_size, 1500);
--- a/src/http/ngx_http_request.c
+++ b/src/http/ngx_http_request.c
@@ -84,6 +84,8 @@ void ngx_http_init_connection(ngx_connec
     rev->event_handler = ngx_http_init_request;
     rev->log_error = NGX_ERROR_INFO;
 
+    /* STUB: epoll */ c->write->event_handler = ngx_http_empty_handler;
+
     if (rev->ready) {
         /* deferred accept, aio, iocp, epoll */
         ngx_http_init_request(rev);
@@ -160,7 +162,7 @@ static void ngx_http_init_request(ngx_ev
     if (in_port->addrs.nelts > 1) {
 
         /*
-         * There're the several addresses on this port and one of them
+         * There are the several addresses on this port and one of them
          * is "*:port" so getsockname() is needed to determine
          * the server address.
          * AcceptEx() already gave this address.
@@ -215,8 +217,8 @@ static void ngx_http_init_request(ngx_ev
     c->log->log_level = clcf->err_log->log_level;
 
     if (c->buffer == NULL) {
-        c->buffer =
-                ngx_create_temp_hunk(c->pool, cscf->client_header_buffer_size);
+        c->buffer = ngx_create_temp_hunk(c->pool,
+                                         cscf->client_header_buffer_size);
         if (c->buffer == NULL) {
             ngx_http_close_connection(c);
             return;
@@ -918,7 +920,7 @@ void ngx_http_finalize_request(ngx_http_
 #if (NGX_KQUEUE)
         ngx_log_debug0(NGX_LOG_DEBUG_HTTP, r->connection->log,
                        r->connection->read->kq_errno,
-                       "kevent reported about closed connection by client");
+                       "kevent() reported about an closed connection");
 #endif
         ngx_http_close_request(r, 0);
         ngx_http_close_connection(r->connection);
--- a/src/os/unix/ngx_freebsd_init.c
+++ b/src/os/unix/ngx_freebsd_init.c
@@ -115,8 +115,8 @@ int ngx_os_init(ngx_log_t *log)
 
     /*
      * The determination of the sendfile() nbytes bug is complex enough.
-     * There are two sendfile() syscalls: a new 393 has no bug while
-     * an old 336 has the bug in some versions and has not in others.
+     * There are two sendfile() syscalls: a new #393 has no bug while
+     * an old #336 has the bug in some versions and has not in others.
      * Besides libc_r wrapper also emulates the bug in some versions.
      * There's no way to say exactly if a given FreeBSD version has the bug.
      * Here is the algorithm that works at least for RELEASEs
--- a/src/os/unix/ngx_freebsd_sendfile_chain.c
+++ b/src/os/unix/ngx_freebsd_sendfile_chain.c
@@ -5,17 +5,20 @@
 
 
 /*
- * FreeBSD's sendfile() often sends 4K pages over ethernet in 3 packets: 2x1460
- * and 1176 or in 6 packets: 5x1460 and 892.  Besides although sendfile()
- * allows to pass the header and the trailer it never sends the header or
- * the trailer with the part of the file in one packet.  So we use TCP_NOPUSH
- * (similar to Linux's TCP_CORK) to postpone the sending - it not only sends
- * the header and the first part of the file in one packet but also sends
- * 4K pages in the full packets.
+ * Although FreeBSD sendfile() allows to pass a header and a trailer
+ * it never sends a header with a part of the file in one packet until
+ * FreeBSD 5.2-STABLE.  Besides over the fast ethernet connection sendfile()
+ * can send the partially filled packets, i.e. the 8 file pages can be sent
+ * as 11 full 1460-bytes packets, then one incomplete 324-bytes packet, and
+ * then again 11 full 1460-bytes packets.
  *
- * Until FreeBSD 4.5 the turning TCP_NOPUSH off does not flush a pending
+ * So we use the TCP_NOPUSH option (similar to Linux's TCP_CORK)
+ * to postpone the sending - it not only sends a header and the first part
+ * of the file in one packet but also sends file pages in the full packets.
+ *
+ * But until FreeBSD 4.5 the turning TCP_NOPUSH off does not flush a pending
  * data that less than MSS so that data can be sent with 5 second delay.
- * We do not use TCP_NOPUSH on FreeBSD prior to 4.5 although it can be used
+ * So we do not use TCP_NOPUSH on FreeBSD prior to 4.5 although it can be used
  * for non-keepalive HTTP connections.
  */
 
@@ -26,7 +29,7 @@ ngx_chain_t *ngx_freebsd_sendfile_chain(
     char            *prev;
     off_t            sent, fprev;
     size_t           hsize, fsize, size;
-    ngx_int_t        eintr, eagain, level;
+    ngx_int_t        eintr, eagain;
     struct iovec    *iov;
     struct sf_hdtr   hdtr;
     ngx_err_t        err;
@@ -45,7 +48,7 @@ ngx_chain_t *ngx_freebsd_sendfile_chain(
 
     if ((ngx_event_flags & NGX_HAVE_KQUEUE_EVENT) && wev->kq_eof) {
         ngx_log_error(NGX_LOG_INFO, c->log, wev->kq_errno,
-                      "kevent() reported about closed connection");
+                      "kevent() reported about an closed connection");
 
         wev->error = 1;
         return NGX_CHAIN_ERROR;
@@ -59,7 +62,6 @@ ngx_chain_t *ngx_freebsd_sendfile_chain(
         hsize = 0;
         eintr = 0;
         eagain = 0;
-        level = NGX_LOG_CRIT;
 
         ngx_init_array(header, c->pool, 10, sizeof(struct iovec),
                        NGX_CHAIN_ERROR);
@@ -152,14 +154,26 @@ ngx_chain_t *ngx_freebsd_sendfile_chain(
         if (file) {
 
             if (ngx_freebsd_use_tcp_nopush && c->tcp_nopush == 0) {
-                c->tcp_nopush = 1;
-
-                ngx_log_debug0(NGX_LOG_DEBUG_EVENT, c->log, 0, "tcp_nopush");
 
                 if (ngx_tcp_nopush(c->fd) == NGX_ERROR) {
-                    ngx_log_error(NGX_LOG_CRIT, c->log, ngx_errno,
-                                  ngx_tcp_nopush_n " failed");
-                    return NGX_CHAIN_ERROR;
+                    err = ngx_errno;
+
+                    /*
+                     * there is a tiny chance to be interrupted, however
+                     * we continue a processing without the TCP_NOPUSH
+                     */
+
+                    if (err != NGX_EINTR) {
+                        wev->error = 1;
+                        ngx_connection_error(c, err,
+                                             ngx_tcp_nopush_n " failed");
+                        return NGX_CHAIN_ERROR;
+                    }
+
+                } else {
+                    c->tcp_nopush = 1;
+                    ngx_log_debug0(NGX_LOG_DEBUG_EVENT, c->log, 0,
+                                   "tcp_nopush");
                 }
             }
 
@@ -185,30 +199,21 @@ ngx_chain_t *ngx_freebsd_sendfile_chain(
             if (rc == -1) {
                 err = ngx_errno;
 
-                if (err == NGX_EINTR) {
-                    eintr = 1;
-
-                } else if (err == NGX_EAGAIN) {
-                    eagain = 1;
+                if (err == NGX_EAGAIN || err == NGX_EINTR) {
+                    if (err == NGX_EINTR) {
+                        eintr = 1;
 
-                } else if (err == NGX_EPIPE || err == NGX_ENOTCONN) {
-                    level = NGX_LOG_INFO;
-                }
+                    } else {
+                        eagain = 1;
+                    }
 
-                if (err == NGX_EAGAIN || err == NGX_EINTR) {
                     ngx_log_debug1(NGX_LOG_DEBUG_EVENT, c->log, err,
                                    "sendfile() sent only " OFF_T_FMT " bytes",
                                    sent);
 
                 } else {
                     wev->error = 1;
-#if 0
-                    ngx_log_error(level, c->log, err,
-                                  "sendfile() failed");
-#else
-                    ngx_log_error(level, c->log, err,
-                                  "sendfile(#%d) failed", c->fd);
-#endif
+                    ngx_connection_error(c, err, "sendfile() failed");
                     return NGX_CHAIN_ERROR;
                 }
             }
@@ -223,20 +228,17 @@ ngx_chain_t *ngx_freebsd_sendfile_chain(
             if (rc == -1) {
                 err = ngx_errno;
 
-                if (err == NGX_EINTR) {
-                    eintr = 1;
+                if (err == NGX_EAGAIN || err == NGX_EINTR) {
+                    if (err == NGX_EINTR) {
+                        eintr = 1;
+                    }
 
-                } else if (err == NGX_EPIPE) {
-                    level = NGX_LOG_INFO;
-                }
-
-                if (err == NGX_EAGAIN || err == NGX_EINTR) {
                     ngx_log_debug0(NGX_LOG_DEBUG_EVENT, c->log, err,
                                    "writev() not ready");
 
                 } else {
                     wev->error = 1;
-                    ngx_log_error(level, c->log, err, "writev() failed");
+                    ngx_connection_error(c, err, "writev() failed");
                     return NGX_CHAIN_ERROR;
                 }
             }
@@ -292,8 +294,9 @@ ngx_chain_t *ngx_freebsd_sendfile_chain(
 
             /*
              * sendfile() can return EAGAIN even if it has sent
-             * a whole file part and successive sendfile() would
-             * return EAGAIN right away and would not send anything
+             * a whole file part but the successive sendfile() call would
+             * return EAGAIN right away and would not send anything.
+             * We use it as a hint.
              */
 
             wev->ready = 0;
--- a/src/os/unix/ngx_linux_config.h
+++ b/src/os/unix/ngx_linux_config.h
@@ -34,8 +34,17 @@
 #include <netdb.h>
 #include <dirent.h>
 
+
+/* Linux has a broken strerror_r() */
+#define HAVE_STRERROR_R  0
+
 #include <ngx_auto_config.h>
 
+
+#if (HAVE_PRCTL)
+#include <sys/prctl.h>
+#endif
+
 #if (HAVE_SENDFILE64)
 #include <sys/sendfile.h>
 #else
@@ -67,7 +76,7 @@ extern ssize_t sendfile(int s, int fd, i
 
 
 #ifndef HAVE_INHERITED_NONBLOCK
-#define HAVE_INHERITED_NONBLOCK  1
+#define HAVE_INHERITED_NONBLOCK  0
 #endif
 
 
--- a/src/os/unix/ngx_linux_sendfile_chain.c
+++ b/src/os/unix/ngx_linux_sendfile_chain.c
@@ -6,8 +6,8 @@
 
 /*
  * On Linux up to 2.4.21 sendfile() (syscall #187) works with 32-bit
- * offsets only and the including <sys/sendfile.h> breaks the compiling if
- * off_t is 64 bit wide.  So we use own sendfile() definition where offset
+ * offsets only and the including <sys/sendfile.h> breaks the compiling
+ * if off_t is 64 bit wide.  So we use own sendfile() definition where offset
  * parameter is int32_t and use sendfile() with the file parts below 2G.
  *
  * Linux 2.4.21 has a new sendfile64() syscall #239.
@@ -80,14 +80,24 @@ ngx_chain_t *ngx_linux_sendfile_chain(ng
             && cl
             && cl->hunk->type & NGX_HUNK_FILE)
         {
-            c->tcp_nopush = 1;
+            if (ngx_tcp_nopush(c->fd) == NGX_ERROR) {
+                err = ngx_errno;
 
-            ngx_log_debug0(NGX_LOG_DEBUG_EVENT, c->log, 0, "tcp_nopush");
+                /*
+                 * there is a tiny chance to be interrupted, however
+                 * we continue a processing without the TCP_CORK
+                 */
 
-            if (ngx_tcp_nopush(c->fd) == NGX_ERROR) {
-                ngx_log_error(NGX_LOG_CRIT, c->log, ngx_errno,
-                              ngx_tcp_nopush_n " failed");
-                return NGX_CHAIN_ERROR;
+                if (err != NGX_EINTR) { 
+                    wev->error = 1;
+                    ngx_connection_error(c, err, ngx_tcp_nopush_n " failed");
+                    return NGX_CHAIN_ERROR;
+                }
+
+            } else {
+                c->tcp_nopush = 1;
+                ngx_log_debug0(NGX_LOG_DEBUG_EVENT, c->log, 0,
+                               "tcp_nopush");
             }
         }
 
@@ -132,51 +142,52 @@ ngx_chain_t *ngx_linux_sendfile_chain(ng
 
             if (rc == -1) {
                 err = ngx_errno;
-                if (err == NGX_EAGAIN) {
-                    ngx_log_error(NGX_LOG_INFO, c->log, err,
-                                  "sendfile() EAGAIN");
 
-                } else if (err == NGX_EINTR) {
-                    eintr = 1;
-                    ngx_log_error(NGX_LOG_INFO, c->log, err,
-                                  "sendfile() EINTR");
+                if (err == NGX_EAGAIN || err == NGX_EINTR) {
+                    if (err == NGX_EINTR) {
+                        eintr = 1;
+                    }
+
+                    ngx_log_debug0(NGX_LOG_DEBUG_EVENT, c->log, err,
+                                   "sendfile() is not ready");
 
                 } else {
-                    ngx_log_error(NGX_LOG_CRIT, c->log, err,
-                                  "sendfile() failed");
+                    wev->error = 1;
+                    ngx_connection_error(c, err, "sendfile() failed");
                     return NGX_CHAIN_ERROR;
                 }
             }
 
             sent = rc > 0 ? rc : 0;
 
-#if (NGX_DEBUG_WRITE_CHAIN)
-            ngx_log_debug(c->log, "sendfile: %d, @" OFF_T_FMT " %d:%d" _
-                          rc _ file->file_pos _ sent _ fsize);
-#endif
+            ngx_log_debug4(NGX_LOG_DEBUG_EVENT, c->log, 0,
+                           "sendfile: %d, @" OFF_T_FMT " %d:%d",
+                           rc, file->file_pos, sent, fsize);
+
         } else {
             rc = writev(c->fd, header.elts, header.nelts);
 
             if (rc == -1) {
                 err = ngx_errno;
-                if (err == NGX_EAGAIN) {
-                    ngx_log_error(NGX_LOG_INFO, c->log, err, "writev() EAGAIN");
 
-                } else if (err == NGX_EINTR) {
-                    eintr = 1;
-                    ngx_log_error(NGX_LOG_INFO, c->log, err, "writev() EINTR");
+                if (err == NGX_EAGAIN || err == NGX_EINTR) {
+                    if (err == NGX_EINTR) {
+                        eintr = 1;
+                    }
+
+                    ngx_log_debug0(NGX_LOG_DEBUG_EVENT, c->log, err,
+                                   "writev() not ready");
 
                 } else {
-                    ngx_log_error(NGX_LOG_CRIT, c->log, err, "writev() failed");
-                    return NGX_CHAIN_ERROR;
+                    wev->error = 1;
+                    ngx_connection_error(c, err, "writev() failed");
+                    return NGX_CHAIN_ERROR; 
                 }
             }
 
             sent = rc > 0 ? rc : 0;
 
-#if (NGX_DEBUG_WRITE_CHAIN)
-            ngx_log_debug(c->log, "writev: %d" _ sent);
-#endif
+            ngx_log_debug1(NGX_LOG_DEBUG_EVENT, c->log, 0, "writev: %d", sent);
         }
 
         c->sent += sent;
--- a/src/os/unix/ngx_recv.c
+++ b/src/os/unix/ngx_recv.c
@@ -4,14 +4,12 @@
 #include <ngx_event.h>
 
 
-static int ngx_unix_recv_error(ngx_event_t *rev, ngx_err_t err);
-
-
 #if (HAVE_KQUEUE)
 
 ssize_t ngx_unix_recv(ngx_connection_t *c, char *buf, size_t size)
 {
     ssize_t       n;
+    ngx_err_t     err;
     ngx_event_t  *rev;
 
     rev = c->read;
@@ -26,11 +24,12 @@ ssize_t ngx_unix_recv(ngx_connection_t *
                 rev->ready = 0;
                 rev->eof = 1;
 
+                ngx_log_error(NGX_LOG_INFO, c->log, rev->kq_errno,
+                              "kevent() reported about an closed connection");
+
                 if (rev->kq_errno) {
                     rev->error = 1;
                     ngx_set_socket_errno(rev->kq_errno);
-                    ngx_log_error(NGX_LOG_INFO, c->log, rev->kq_errno,
-                                  "kevent() reported about closed connection");
 
                     if (rev->kq_errno == NGX_ECONNRESET
                         && rev->log_error == NGX_ERROR_IGNORE_ECONNRESET)
@@ -52,7 +51,8 @@ ssize_t ngx_unix_recv(ngx_connection_t *
     do {
         n = recv(c->fd, buf, size, 0);
 
-        ngx_log_debug2(NGX_LOG_DEBUG_EVENT, c->log, 0,"recv: %d:%d", n, size);
+        ngx_log_debug3(NGX_LOG_DEBUG_EVENT, c->log, 0,
+                       "recv: fd:%d %d of %d", c->fd, n, size);
 
         if (n >= 0) {
             if (ngx_event_flags & NGX_HAVE_KQUEUE_EVENT) {
@@ -87,11 +87,19 @@ ssize_t ngx_unix_recv(ngx_connection_t *
             return n;
         }
 
-        n = ngx_unix_recv_error(rev, ngx_socket_errno);
+        err = ngx_socket_errno;
+
+        if (err == NGX_EAGAIN || err == NGX_EINTR) {
+            ngx_log_debug0(NGX_LOG_DEBUG_EVENT, rev->log, err,
+                           "recv() not ready");
+            n = NGX_AGAIN;
 
-    } while (n == NGX_EINTR);
+        } else {
+            n = ngx_connection_error(c, err, "recv() failed");
+            break;
+        }
 
-    /* NGX_ERROR || NGX_AGAIN */
+    } while (err == NGX_EINTR);
 
     rev->ready = 0;
 
@@ -107,6 +115,7 @@ ssize_t ngx_unix_recv(ngx_connection_t *
 ssize_t ngx_unix_recv(ngx_connection_t *c, char *buf, size_t size)
 {
     ssize_t       n;
+    ngx_err_t     err;
     ngx_event_t  *rev;
 
     rev = c->read;
@@ -114,7 +123,8 @@ ssize_t ngx_unix_recv(ngx_connection_t *
     do {
         n = recv(c->fd, buf, size, 0);
 
-        ngx_log_debug2(NGX_LOG_DEBUG_EVENT, c->log, 0,"recv: %d:%d", n, size);
+        ngx_log_debug3(NGX_LOG_DEBUG_EVENT, c->log, 0,
+                       "recv: fd:%d %d of %d", c->fd, n, size);
 
         if (n >= 0) {
             if ((size_t) n < size) {
@@ -128,11 +138,19 @@ ssize_t ngx_unix_recv(ngx_connection_t *
             return n;
         }
 
-        n = ngx_unix_recv_error(rev, ngx_socket_errno);
+        err = ngx_socket_errno;
+
+        if (err == NGX_EAGAIN || err == NGX_EINTR) {
+            ngx_log_debug0(NGX_LOG_DEBUG_EVENT, rev->log, err,
+                           "recv() not ready");
+            n = NGX_AGAIN;
 
-    } while (n == NGX_EINTR);
+        } else {
+            n = ngx_connection_error(c, err, "recv() failed");
+            break;
+        }
 
-    /* NGX_ERROR || NGX_AGAIN */
+    } while (err == NGX_EINTR);
 
     rev->ready = 0;
 
@@ -144,37 +162,3 @@ ssize_t ngx_unix_recv(ngx_connection_t *
 }
 
 #endif /* NAVE_KQUEUE */
-
-
-static int ngx_unix_recv_error(ngx_event_t *rev, ngx_err_t err)
-{
-    ngx_int_t  level;
-
-    if (err == NGX_EAGAIN || err == NGX_EINTR) {
-        ngx_log_debug0(NGX_LOG_DEBUG_EVENT, rev->log, err, "recv() not ready");
-        return NGX_AGAIN;
-    }
-
-    if (err == NGX_ECONNRESET) {
-
-        switch (rev->log_error) {
-        case NGX_ERROR_IGNORE_ECONNRESET:
-            return 0;
-        case NGX_ERROR_INFO:
-            level = NGX_LOG_INFO;
-            break;
-        case NGX_ERROR_ERR:
-            level = NGX_LOG_ERR;
-            break;
-        default:
-            level = NGX_LOG_CRIT;
-        }
-
-    } else {
-        level = NGX_LOG_CRIT;
-    }
-
-    ngx_log_error(level, rev->log, err, "recv() failed");
-
-    return NGX_ERROR;
-}
deleted file mode 100644
--- a/src/os/unix/ngx_recv.h
+++ /dev/null
@@ -1,12 +0,0 @@
-#ifndef _NGX_RECV_H_INCLUDED_
-#define _NGX_RECV_H_INCLUDED_
-
-
-#if 0
-#include <errno.h>
-
-#define ngx_recv(fd, buf, size, flags)  recv(fd, buf, size, flags)
-#endif
-
-
-#endif /* _NGX_RECV_H_INCLUDED_ */
--- a/src/os/unix/ngx_socket.c
+++ b/src/os/unix/ngx_socket.c
@@ -4,12 +4,13 @@
 
 
 /*
-   ioctl(FIONBIO) set blocking mode with one syscall only while
-   fcntl(F_SETFL, ~O_NONBLOCK) need to know previous state
-   using fcntl(F_GETFL).
-
-   ioctl() and fcntl() are syscalls on FreeBSD, Solaris 7/8 and Linux
-*/
+ * ioctl(FIONBIO) sets a blocking mode with the single syscall
+ * while fcntl(F_SETFL, ~O_NONBLOCK) needs to learn before
+ * a previous state using fcntl(F_GETFL).
+ *
+ * ioctl() and fcntl() are syscalls on at least FreeBSD 2.x, Linux 2.2
+ * and Solaris 7
+ */
 
 
 #if (HAVE_FIONBIO)