doc: Documented htpipe.
[ashd.git] / src / plaintcp.c
index 321be41..56fc81c 100644 (file)
@@ -65,7 +65,7 @@ int listensock4(int port)
        close(fd);
        return(-1);
     }
-    if(listen(fd, 16) < 0) {
+    if(listen(fd, 128) < 0) {
        close(fd);
        return(-1);
     }
@@ -90,7 +90,7 @@ int listensock6(int port)
        close(fd);
        return(-1);
     }
-    if(listen(fd, 16) < 0) {
+    if(listen(fd, 128) < 0) {
        close(fd);
        return(-1);
     }
@@ -150,42 +150,57 @@ void servetcp(struct muth *muth, va_list args)
     vavar(int, fd);
     vavar(struct sockaddr_storage, name);
     vavar(struct tcpport *, stcp);
-    FILE *in;
+    struct bufio *in;
     struct conn conn;
     struct tcpconn tcp;
     
     memset(&conn, 0, sizeof(conn));
     memset(&tcp, 0, sizeof(tcp));
-    in = mtstdopen(fd, 1, 60, "r+");
+    in = mtbioopen(fd, 1, 60, "r+", NULL);
     conn.pdata = &tcp;
     conn.initreq = initreq;
     tcp.fd = fd;
     tcp.name = name;
     tcp.port = stcp;
-    serve(in, &conn);
+    serve(in, fd, &conn);
 }
 
 static void listenloop(struct muth *muth, va_list args)
 {
     vavar(struct tcpport *, tcp);
-    int ns;
+    int i, ns, n;
     struct sockaddr_storage name;
     socklen_t namelen;
     
+    fcntl(tcp->fd, F_SETFL, fcntl(tcp->fd, F_GETFL) | O_NONBLOCK);
     while(1) {
        namelen = sizeof(name);
-       block(tcp->fd, EV_READ, 0);
-       ns = accept(tcp->fd, (struct sockaddr *)&name, &namelen);
-       if(ns < 0) {
-           flog(LOG_ERR, "accept: %s", strerror(errno));
+       if(block(tcp->fd, EV_READ, 0) == 0)
            goto out;
+       n = 0;
+       while(1) {
+           ns = accept(tcp->fd, (struct sockaddr *)&name, &namelen);
+           if(ns < 0) {
+               if(errno == EAGAIN)
+                   break;
+               if(errno == ECONNABORTED)
+                   continue;
+               flog(LOG_ERR, "accept: %s", strerror(errno));
+               goto out;
+           }
+           mustart(servetcp, ns, name, tcp);
+           if(++n >= 100)
+               break;
        }
-       mustart(servetcp, ns, name, tcp);
     }
     
 out:
     close(tcp->fd);
     free(tcp);
+    for(i = 0; i < listeners.d; i++) {
+       if(listeners.b[i] == muth)
+           bufdel(listeners, i);
+    }
 }
 
 void handleplain(int argc, char **argp, char **argv)
@@ -215,7 +230,7 @@ void handleplain(int argc, char **argp, char **argv)
     omalloc(tcp);
     tcp->fd = fd;
     tcp->sport = port;
-    mustart(listenloop, tcp);
+    bufadd(listeners, mustart(listenloop, tcp));
     if((fd = listensock4(port)) < 0) {
        if(errno != EADDRINUSE) {
            flog(LOG_ERR, "could not listen on IPv4 (port %i): %s", port, strerror(errno));
@@ -225,6 +240,6 @@ void handleplain(int argc, char **argp, char **argv)
        omalloc(tcp);
        tcp->fd = fd;
        tcp->sport = port;
-       mustart(listenloop, tcp);
+       bufadd(listeners, mustart(listenloop, tcp));
     }
 }