components/proftpd/patches/004.proftpd-retry.patch
author Tomas Klacko <tomas.klacko@oracle.com>
Wed, 11 Mar 2015 03:50:20 -0700
changeset 3932 1b7dd68f6aa9
parent 1952 components/proftpd/patches/proftpd-retry.patch@edbaa9c65514
permissions -rw-r--r--
20553228 add proftpd dtrace provider from AK to Userland

--- a/src/data.c
+++ b/src/data.c
@@ -337,6 +337,7 @@ static int data_pasv_open(char *reason, off_t size) {
 static int data_active_open(char *reason, off_t size) {
   conn_t *c;
   int bind_port, rev;
+  int retries = 0;
   pr_netaddr_t *bind_addr;
   unsigned char *root_revoke = NULL;
 
@@ -368,7 +369,9 @@ static int data_active_open(char *reason, off_t size) {
     bind_port = INPORT_ANY;
   }
 
-  session.d = pr_inet_create_conn(session.pool, -1, bind_addr, bind_port, TRUE);
+  for (;;) {
+    session.d = pr_inet_create_conn(session.pool, -1, bind_addr, bind_port,
+      TRUE);
 
   /* Default remote address to which to connect for an active transfer,
    * if the client has not specified a different address via PORT/EPRT,
@@ -416,6 +419,15 @@ static int data_active_open(char *reason, off_t size) {
 
   if (pr_inet_connect(session.d->pool, session.d, &session.data_addr,
       session.data_port) == -1) {
+
+    if (session.d->xerrno == EADDRINUSE && retries < 16) {
+      destroy_pool(session.d->pool);
+      pr_signals_handle();
+      /* Wait up to MSL to avoid TIME_WAIT. */
+      sleep(retries++);
+      continue;
+    }
+
     pr_log_debug(DEBUG6,
       "Error connecting to %s#%u for active data transfer: %s",
       pr_netaddr_get_ipstr(&session.data_addr), session.data_port,
@@ -427,6 +439,9 @@ static int data_active_open(char *reason, off_t size) {
     destroy_pool(session.d->pool);
     session.d = NULL;
     return -1;
+  } else
+    break;
+
   }
 
   c = pr_inet_openrw(session.pool, session.d, NULL, PR_NETIO_STRM_DATA,