nginx-0.0.1-2003-06-02-19:24:30 import
diff --git a/src/os/unix/ngx_files.h b/src/os/unix/ngx_files.h
index 37d136a..e2af722 100644
--- a/src/os/unix/ngx_files.h
+++ b/src/os/unix/ngx_files.h
@@ -15,20 +15,29 @@
 
 
 
-#define ngx_open_file            open
+#define ngx_open_file(name, access, create)                                 \
+                                 open(name, access|create, 0644)
 #define ngx_open_file_n          "open()"
 
+#define NGX_FILE_RDONLY          O_RDONLY
+#define NGX_FILE_RDWR            O_RDWR
+#define NGX_FILE_CREATE_OR_OPEN  O_CREAT
+#define NGX_FILE_OPEN            0
+#define NGX_FILE_APPEND          O_APPEND
+
+
 #define ngx_close_file           close
 #define ngx_close_file_n         "close()"
 
+
 #define ngx_open_tempfile(name, persistent)                                 \
                                  open(name, O_CREAT|O_EXCL|O_RDWR, 0600)
 #define ngx_open_tempfile_n      "open()"
 
+
 ssize_t ngx_read_file(ngx_file_t *file, char *buf, size_t size, off_t offset);
 #define ngx_read_file_n          "read()"
 
-#define NGX_FILE_RDONLY          O_RDONLY
 
 ssize_t ngx_write_file(ngx_file_t *file, char *buf, size_t size, off_t offset);
 
diff --git a/src/os/unix/ngx_freebsd_init.c b/src/os/unix/ngx_freebsd_init.c
index cacc457..e01f9b61 100644
--- a/src/os/unix/ngx_freebsd_init.c
+++ b/src/os/unix/ngx_freebsd_init.c
@@ -9,6 +9,7 @@
 int ngx_freebsd_hw_ncpu;
 int ngx_freebsd_net_inet_tcp_sendspace;
 int ngx_freebsd_sendfile_nbytes_bug;
+int ngx_freebsd_tcp_nopush_flush;
 
 /* FreeBSD 5.0 */
 int ngx_freebsd_kern_ipc_zero_copy_send;
@@ -39,6 +40,8 @@
      &ngx_freebsd_net_inet_tcp_sendspace,
      sizeof(int)},
 
+     /* FreeBSD 5.0 */
+
     {"kern.ipc.zero_copy.send",
      &ngx_freebsd_kern_ipc_zero_copy_send,
      sizeof(int)},
@@ -49,7 +52,7 @@
 
 int ngx_os_init(ngx_log_t *log)
 {
-    int        i;
+    int        i, version;
     size_t     size;
     ngx_err_t  err;
 
@@ -81,9 +84,11 @@
         return NGX_ERROR;
     }
 
+    version = ngx_freebsd_kern_osreldate;
+
     ngx_log_error(NGX_LOG_INFO, log, 0,
                   "kern.osreldate: %d, built on %d",
-                  ngx_freebsd_kern_osreldate, __FreeBSD_version);
+                  version, __FreeBSD_version);
 
 
 #if (HAVE_FREEBSD_SENDFILE)
@@ -91,12 +96,12 @@
     /* The determination of the sendfile() nbytes bug is complex enough.
        There're two sendfile() syscalls: a new 393 has no bug while
        an old 336 has the bug in some versions and has not in others.
-       libc_r wrapper also emulates the bug in some versions.
+       Besides libc_r wrapper also emulates the bug in some versions.
        There's no way to say exactly if a given FreeBSD version has bug.
-       Here is the algorithm that work at least for RELEASEs
+       Here is the algorithm that works at least for RELEASEs
        and for syscalls only (not libc_r wrapper). */
 
-    /* detect was the new sendfile() version available at the compile time
+    /* detect the new sendfile() version available at the compile time
        to allow an old binary to run correctly on an updated FreeBSD system. */
 
 #if (__FreeBSD__ == 4 && __FreeBSD_version >= 460102) \
@@ -115,6 +120,11 @@
 #endif /* HAVE_FREEBSD_SENDFILE */
 
 
+    if ((version < 500000 && version >= 440003) || version >= 500017) {
+        ngx_freebsd_tcp_nopush_flush = 1;
+    }
+
+
     for (i = 0; sysctls[i].name; i++) {
         *sysctls[i].value = 0;
         size = sysctls[i].size;
diff --git a/src/os/unix/ngx_freebsd_init.h b/src/os/unix/ngx_freebsd_init.h
index cc450f9..967951d 100644
--- a/src/os/unix/ngx_freebsd_init.h
+++ b/src/os/unix/ngx_freebsd_init.h
@@ -20,6 +20,8 @@
 extern int ngx_freebsd_hw_ncpu;
 extern int ngx_freebsd_net_inet_tcp_sendspace;
 extern int ngx_freebsd_sendfile_nbytes_bug;
+extern int ngx_freebsd_tcp_nopush_flush;
+extern int ngx_freebsd_kern_ipc_zero_copy_send;
 
 
 #endif /* _NGX_FREEBSD_INIT_H_INCLUDED_ */
diff --git a/src/os/unix/ngx_freebsd_sendfile_chain.c b/src/os/unix/ngx_freebsd_sendfile_chain.c
index bdb7250..cd21ed9 100644
--- a/src/os/unix/ngx_freebsd_sendfile_chain.c
+++ b/src/os/unix/ngx_freebsd_sendfile_chain.c
@@ -13,9 +13,9 @@
    and the first part of the file in one packet but also sends 4K pages
    in the full packets.
 
-   The turning TCP_NOPUSH off flushes any pending data at least in FreeBSD 4.2,
-   although there's special fix in src/sys/netinet/tcp_usrreq.c just before
-   FreeBSD 4.5.
+   Until FreeBSD 4.5 the turning TCP_NOPUSH off does not not flush
+   the pending data that less than MSS and the data sent with 5 second delay.
+   So we use TCP_NOPUSH on FreeBSD 4.5+ only.
 */
 
 
@@ -105,14 +105,15 @@
 
         if (file) {
 
-            if (tcp_nopush == 0) {
+            if (!c->tcp_nopush && ngx_freebsd_tcp_nopush_flush) {
+                c->tcp_nopush = 1;
                 tcp_nopush = 1;
                 if (setsockopt(c->fd, IPPROTO_TCP, TCP_NOPUSH,
                                (const void *) &tcp_nopush,
                                sizeof(int)) == -1)
                 {
                     ngx_log_error(NGX_LOG_CRIT, c->log, ngx_errno,
-                                  "setsockopt(TCP_NO_PUSH) failed");
+                                  "setsockopt(TCP_NOPUSH) failed");
                     return NGX_CHAIN_ERROR;
                 }
             }
@@ -221,14 +222,18 @@
 
     } while ((tail && tail == ce) || eintr);
 
-    if (tcp_nopush == 1) {
+    /* STUB: should be in app code, no need to clear TCP_NOPUSH
+             if the conneciton close()d or shutdown()ed */
+
+    if (c->tcp_nopush) {
+        c->tcp_nopush = 0;
         tcp_nopush = 0;
         if (setsockopt(c->fd, IPPROTO_TCP, TCP_NOPUSH,
                        (const void *) &tcp_nopush,
                        sizeof(int)) == -1)
         {
             ngx_log_error(NGX_LOG_CRIT, c->log, ngx_errno,
-                          "setsockopt(!TCP_NO_PUSH) failed");
+                          "setsockopt(!TCP_NOPUSH) failed");
             return NGX_CHAIN_ERROR;
         }
     }