Browse Source

r18226@catbus: nickm | 2008-02-19 18:01:01 -0500
Brown-paper-bag time. We were failing to count all the sockets from accept().


svn:r13595

Nick Mathewson 17 years ago
parent
commit
9479dd3768
4 changed files with 45 additions and 18 deletions
  1. 5 0
      ChangeLog
  2. 38 17
      src/common/compat.c
  3. 1 0
      src/common/compat.h
  4. 1 1
      src/or/connection.c

+ 5 - 0
ChangeLog

@@ -12,6 +12,11 @@ Changes in version 0.2.0.20-?? - 2008-02-??
       would stop building circuits and start refusing connections after
       24 hours, since we falsely believed that Tor was dormant. Reported
       by nwf; bugfix on 0.1.2.x.
+    - When counting the number of open sockets, count not only the number
+      of sockets we have received from the socket() call, but also the
+      number we've gotten from accept().  This bug made us fail to count
+      all sockets that we were using for incoming connections.  Bugfix on
+      0.2.0.x
 
   o Minor features (performance):
     - Tune parameters for cell pool allocation to minimize amount of

+ 38 - 17
src/common/compat.c

@@ -546,6 +546,29 @@ tor_close_socket(int s)
   return r;
 }
 
+#ifdef DEBUG_SOCKET_COUNTING
+static INLINE void
+mark_socket_open(int s)
+{
+  if (s > max_socket) {
+    if (max_socket == -1) {
+      open_sockets = bitarray_init_zero(s+128);
+      max_socket = s+128;
+    } else {
+      open_sockets = bitarray_expand(open_sockets, max_socket, s+128);
+      max_socket = s+128;
+    }
+  }
+  if (bitarray_is_set(open_sockets, s)) {
+    log_warn(LD_BUG, "I thought that %d was already open, but socket() just "
+             "gave it to me!", s);
+  }
+  bitarray_set(open_sockets, s);
+}
+#else
+#define mark_socket_open(s) STMT_NIL
+#endif
+
 /** As socket(), but counts the number of open sockets. */
 int
 tor_open_socket(int domain, int type, int protocol)
@@ -553,22 +576,19 @@ tor_open_socket(int domain, int type, int protocol)
   int s = socket(domain, type, protocol);
   if (s >= 0) {
     ++n_sockets_open;
-#ifdef DEBUG_SOCKET_COUNTING
-    if (s > max_socket) {
-      if (max_socket == -1) {
-        open_sockets = bitarray_init_zero(s+128);
-        max_socket = s+128;
-      } else {
-        open_sockets = bitarray_expand(open_sockets, max_socket, s+128);
-        max_socket = s+128;
-      }
-    }
-    if (bitarray_is_set(open_sockets, s)) {
-      log_warn(LD_BUG, "I thought that %d was already open, but socket() just "
-               "gave it to me!", s);
-    }
-    bitarray_set(open_sockets, s);
-#endif
+    mark_socket_open(s);
+  }
+  return s;
+}
+
+/** As socket(), but counts the number of open sockets. */
+int
+tor_accept_socket(int sockfd, struct sockaddr *addr, socklen_t *len)
+{
+  int s = accept(sockfd, addr, len);
+  if (s >= 0) {
+    ++n_sockets_open;
+    mark_socket_open(s);
   }
   return s;
 }
@@ -676,7 +696,8 @@ tor_socketpair(int family, int type, int protocol, int fd[2])
       goto tidy_up_and_fail;
 
     size = sizeof(listen_addr);
-    acceptor = accept(listener, (struct sockaddr *) &listen_addr, &size);
+    acceptor = tor_accept_socket(listener,
+                                 (struct sockaddr *) &listen_addr, &size);
     if (acceptor < 0)
       goto tidy_up_and_fail;
     if (size != sizeof(listen_addr))

+ 1 - 0
src/common/compat.h

@@ -257,6 +257,7 @@ int touch_file(const char *fname);
 
 int tor_close_socket(int s);
 int tor_open_socket(int domain, int type, int protocol);
+int tor_accept_socket(int sockfd, struct sockaddr *addr, socklen_t *len);
 int get_n_open_sockets(void);
 
 #ifdef USE_BSOCKETS

+ 1 - 1
src/or/connection.c

@@ -929,7 +929,7 @@ connection_handle_listener_read(connection_t *conn, int new_type)
   tor_assert((size_t)remotelen >= sizeof(struct sockaddr_in));
   memset(addrbuf, 0, sizeof(addrbuf));
 
-  news = accept(conn->s,(struct sockaddr *)&addrbuf,&remotelen);
+  news = tor_accept_socket(conn->s,(struct sockaddr *)&addrbuf,&remotelen);
   if (news < 0) { /* accept() error */
     int e = tor_socket_errno(conn->s);
     if (ERRNO_IS_ACCEPT_EAGAIN(e)) {