Browse Source

PhySocket NULL check added to handle_write. Fixed after-close handle_write segfault

Joseph Henry 9 years ago
parent
commit
b203d25656
4 changed files with 49 additions and 39 deletions
  1. 17 9
      netcon/Intercept.c
  2. 27 26
      netcon/NetconEthernetTap.cpp
  3. 5 4
      netcon/README.md
  4. BIN
      netcon/libintercept.so.1.0

+ 17 - 9
netcon/Intercept.c

@@ -166,7 +166,7 @@ int get_retval()
       return retval;
     }
   }
-  dwr("unable to read connect: return value\n");
+  dwr("unable to read return value\n");
   return -1;
 }
 
@@ -342,7 +342,7 @@ int getsockopt(GETSOCKOPT_SIG)
 
 int socket(SOCKET_SIG)
 {
-  //dwr("socket()*:\n");
+  dwr("socket()*:\n");
   int err;
 #ifdef CHECKS
   /* Check that type makes sense */
@@ -375,6 +375,11 @@ int socket(SOCKET_SIG)
 
   char cmd[BUF_SZ];
   fdret_sock = !is_initialized ? init_service_connection() : fdret_sock;
+  if(fdret_sock < 0)
+  {
+    dwr("BAD service connection. exiting.\n");
+    exit(-1);
+  }
 
   if(socket_family == AF_LOCAL
     || socket_family == AF_NETLINK
@@ -405,18 +410,21 @@ int socket(SOCKET_SIG)
     memset(cmd, '\0', BUF_SZ);
     cmd[0] = RPC_FD_MAP_COMPLETION;
     memcpy(&cmd[1], &newfd, sizeof(newfd));
-    if(newfd > -1) {
+
+    //if(newfd > -1) {
       send_command(fdret_sock, cmd);
       pthread_mutex_unlock(&lock);
       errno = ERR_OK; // OK
       return newfd;
-    }
+    //}
+    /*
     else { // Try to read retval+errno since we RXed a bad fd
       dwr("Error, service sent bad fd.\n");
       err = get_retval();
       pthread_mutex_unlock(&lock);
       return err;
     }
+    */
   }
   else {
     dwr("Error while receiving new FD.\n");
@@ -434,7 +442,7 @@ int socket(SOCKET_SIG)
    connect() intercept function */
 int connect(CONNECT_SIG)
 {
-  //dwr("connect()*:\n");
+  dwr("connect()*:\n");
   struct sockaddr_in *connaddr;
   connaddr = (struct sockaddr_in *) __addr;
 
@@ -520,7 +528,7 @@ int select(SELECT_SIG)
    bind() intercept function */
 int bind(BIND_SIG)
 {
-  //dwr("bind()*:\n");
+  dwr("bind()*:\n");
 #ifdef CHECKS
   /* Check that this is a valid fd */
   if(fcntl(sockfd, F_GETFD) < 0) {
@@ -582,7 +590,7 @@ int bind(BIND_SIG)
 /* int sockfd, struct sockaddr *addr, socklen_t *addrlen, int flags */
 int accept4(ACCEPT4_SIG)
 {
-  //dwr("accept4()*:\n");
+  dwr("accept4()*:\n");
 #ifdef CHECKS
   if (flags & ~(SOCK_CLOEXEC | SOCK_NONBLOCK)) {
     errno = EINVAL;
@@ -608,7 +616,7 @@ int accept4(ACCEPT4_SIG)
    accept() intercept function */
 int accept(ACCEPT_SIG)
 {
-  //dwr("accept()*:\n");
+  dwr("accept()*:\n");
 #ifdef CHECKS
   /* Check that this is a valid fd */
   if(fcntl(sockfd, F_GETFD) < 0) {
@@ -701,7 +709,7 @@ int accept(ACCEPT_SIG)
    listen() intercept function */
 int listen(LISTEN_SIG)
 {
-  //dwr("listen()*:\n");
+  dwr("listen()*:\n");
   #ifdef CHECKS
   /* Check that this is a valid fd */
   if(fcntl(sockfd, F_GETFD) < 0) {

+ 27 - 26
netcon/NetconEthernetTap.cpp

@@ -276,7 +276,7 @@ void NetconEthernetTap::closeConnection(TcpConnection *conn)
 	close(conn->their_fd);
 	if(conn->dataSock) {
 		close(_phy.getDescriptor(conn->dataSock));
-		_phy.close(conn->dataSock);
+		_phy.close(conn->dataSock,false);
 	}
 	for(int i=0; i<tcp_connections.size(); i++) {
 		if(tcp_connections[i] == conn) {
@@ -918,14 +918,13 @@ void NetconEthernetTap::handle_listen(PhySocket *sock, void **uptr, struct liste
       fprintf(stderr, "handle_listen(): PCB is already in listening state.\n");
       return;
     }
-
 		struct tcp_pcb* listening_pcb;
+
 #ifdef TCP_LISTEN_BACKLOG
 			listening_pcb = lwipstack->tcp_listen_with_backlog(conn->pcb, listen_rpc->backlog);
 #else
 			listening_pcb = lwipstack->tcp_listen(conn->pcb);
 #endif
-		// FIXME: Correct return values from this method, most is handled in intercept lib
 
     if(listening_pcb != NULL) {
       conn->pcb = listening_pcb;
@@ -1146,34 +1145,36 @@ void NetconEthernetTap::handle_write(TcpConnection *conn)
 			return;
 		}
 
-		int read_fd = _phy.getDescriptor(conn->dataSock);
-		if((r = read(read_fd, (&conn->buf)+conn->idx, sndbuf)) > 0) {
-			conn->idx += r;
-			/* Writes data pulled from the client's socket buffer to LWIP. This merely sends the
-			 * data to LWIP to be enqueued and eventually sent to the network. */
-			if(r > 0) {
-				int sz;
-				// NOTE: this assumes that lwipstack->_lock is locked, either
-				// because we are in a callback or have locked it manually.
-				int err = lwipstack->_tcp_write(conn->pcb, &conn->buf, r, TCP_WRITE_FLAG_COPY);
-				//lwipstack->_tcp_output(conn->pcb);
-				if(err != ERR_OK) {
-					fprintf(stderr, "handle_write(): error while writing to PCB, (err = %d)\n", err);
-					return;
+		if(conn->dataSock) {
+			int read_fd = _phy.getDescriptor(conn->dataSock);
+			if((r = read(read_fd, (&conn->buf)+conn->idx, sndbuf)) > 0) {
+				conn->idx += r;
+				/* Writes data pulled from the client's socket buffer to LWIP. This merely sends the
+				 * data to LWIP to be enqueued and eventually sent to the network. */
+				if(r > 0) {
+					int sz;
+					// NOTE: this assumes that lwipstack->_lock is locked, either
+					// because we are in a callback or have locked it manually.
+					int err = lwipstack->_tcp_write(conn->pcb, &conn->buf, r, TCP_WRITE_FLAG_COPY);
+					//lwipstack->_tcp_output(conn->pcb);
+					if(err != ERR_OK) {
+						fprintf(stderr, "handle_write(): error while writing to PCB, (err = %d)\n", err);
+						return;
+					}
+					else {
+						sz = (conn->idx)-r;
+						if(sz) {
+							memmove(&conn->buf, (conn->buf+r), sz);
+						}
+						conn->idx -= r;
+						return;
+					}
 				}
 				else {
-					sz = (conn->idx)-r;
-					if(sz) {
-						memmove(&conn->buf, (conn->buf+r), sz);
-					}
-					conn->idx -= r;
+					fprintf(stderr, "handle_write(): LWIP stack full\n");
 					return;
 				}
 			}
-			else {
-				fprintf(stderr, "handle_write(): LWIP stack full\n");
-				return;
-			}
 		}
 	}
 }

+ 5 - 4
netcon/README.md

@@ -1,11 +1,12 @@
 Network Containers have been tested with the following:
 
-sshd			[ WORKS as of 20151010] Long ~15-20s delay for client during connect
-ssh			[ WORKS as of 20151010]
-curl			[ WORKS as of 20151021]
+sshd			[ WORKS as of 20151022] Long ~15-20s delay for client during connect
+ssh			[ WORKS as of 20151022]
+sftp			[ WORKS as of 20151022]
+curl			[ WORKS as of 20151021] Sometimes "tcp_input: pcb->next != pcb (before cache)" is seen
 apache (debug mode)	[ WORKS as of 2015xxxx]
 apache (prefork MPM)	[ WORKS as of 20151021]
-nginx			[ WORKS as of 2015xxxx]
+nginx			[ WORKS as of 20151022]
 nodejs			[ WORKS as of 20151021]
 java			[ WORKS as of 2015xxxx]
 tomcat			[ WORKS as of 2015xxxx]

BIN
netcon/libintercept.so.1.0