[PATCH 10 of 25] Fix for socket leak with "aio sendfile" and "limit_rate"

Maxim Dounin mdounin at mdounin.ru
Tue Sep 6 15:58:07 UTC 2011


# HG changeset patch
# User Maxim Dounin <mdounin at mdounin.ru>
# Date 1315324497 -14400
# Node ID 8e75ca21ad556974aeee9156a6534ebe4d12146b
# Parent  e8c97615dd5c845ba1dc76681c687be3fe71130d
Fix for socket leak with "aio sendfile" and "limit_rate".

Second aio post happened when timer set by limit_rate expired while we have
aio request in flight, resulting in "second aio post" alert and socket leak.

The patch adds actual protection from aio calls with r->aio already set to
aio sendfile code in ngx_http_copy_filter().  This should fix other cases
as well, e.g. when sending buffered to disk upstream replies while still
talking to upstream.

The ngx_http_writer() is also fixed to handle the above case (though it's
mostly optimization now).

Reported by Oleksandr V. Typlyns'kyi.

diff --git a/src/http/ngx_http_copy_filter_module.c b/src/http/ngx_http_copy_filter_module.c
--- a/src/http/ngx_http_copy_filter_module.c
+++ b/src/http/ngx_http_copy_filter_module.c
@@ -158,6 +158,11 @@ ngx_http_copy_filter(ngx_http_request_t 
             ngx_file_t            *file;
             ngx_http_ephemeral_t  *e;
 
+            if (r->aio) {
+                c->busy_sendfile = NULL;
+                return rc;
+            }
+
             file = c->busy_sendfile->file;
             offset = c->busy_sendfile->file_pos;
 
diff --git a/src/http/ngx_http_request.c b/src/http/ngx_http_request.c
--- a/src/http/ngx_http_request.c
+++ b/src/http/ngx_http_request.c
@@ -2248,17 +2248,17 @@ ngx_http_writer(ngx_http_request_t *r)
             return;
         }
 
-    } else {
-        if (wev->delayed || r->aio) {
-            ngx_log_debug0(NGX_LOG_DEBUG_HTTP, wev->log, 0,
-                           "http writer delayed");
-
-            if (ngx_handle_write_event(wev, clcf->send_lowat) != NGX_OK) {
-                ngx_http_close_request(r, 0);
-            }
-
-            return;
+    }
+
+    if (wev->delayed || r->aio) {
+        ngx_log_debug0(NGX_LOG_DEBUG_HTTP, wev->log, 0,
+                       "http writer delayed");
+
+        if (ngx_handle_write_event(wev, clcf->send_lowat) != NGX_OK) {
+            ngx_http_close_request(r, 0);
         }
+
+        return;
     }
 
     rc = ngx_http_output_filter(r, NULL);



More information about the nginx-devel mailing list