Instead of believing SOMAXCONN from the system header files (which is
authorTom Lane <[email protected]>
Wed, 11 Jul 2001 19:03:07 +0000 (19:03 +0000)
committerTom Lane <[email protected]>
Wed, 11 Jul 2001 19:03:07 +0000 (19:03 +0000)
a lie on many Unixen), invoke listen() with MIN(MaxBackends*2, 10000).
The clamp value 10000 is configurable in config.h.in, if that proves
to be necessary --- hopefully it won't.

src/backend/libpq/pqcomm.c
src/include/config.h.in

index e3250862363cd7e41a5a6d69d49299a91bce36e4..81c57a4e8d75dc864256686203be67c6a1fb0d79 100644 (file)
@@ -29,7 +29,7 @@
  * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
  * Portions Copyright (c) 1994, Regents of the University of California
  *
- * $Id: pqcomm.c,v 1.117 2001/03/22 03:59:30 momjian Exp $
+ * $Id: pqcomm.c,v 1.118 2001/07/11 19:03:07 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
 #include "miscadmin.h"
 
 
-#ifndef SOMAXCONN
-#define SOMAXCONN 5                /* from Linux listen(2) man page */
-#endif
-
-
 static void pq_close(void);
 
 
@@ -185,6 +180,7 @@ StreamServerPort(int family, char *hostName, unsigned short portNumber,
    SockAddr    saddr;
    int         fd,
                err;
+   int         maxconn;
    size_t      len = 0;
    int         one = 1;
 
@@ -350,7 +346,25 @@ StreamServerPort(int family, char *hostName, unsigned short portNumber,
    }
 #endif  /* HAVE_UNIX_SOCKETS */
 
-   listen(fd, SOMAXCONN);
+   /*
+    * Select appropriate accept-queue length limit.  PG_SOMAXCONN is
+    * only intended to provide a clamp on the request on platforms where
+    * an overly large request provokes a kernel error (are there any?).
+    */
+   maxconn = MaxBackends * 2;
+   if (maxconn > PG_SOMAXCONN)
+       maxconn = PG_SOMAXCONN;
+
+   err = listen(fd, maxconn);
+   if (err < 0)
+   {
+       snprintf(PQerrormsg, PQERRORMSG_LENGTH,
+                "FATAL: StreamServerPort: listen() failed: %s\n",
+                strerror(errno));
+       fputs(PQerrormsg, stderr);
+       pqdebug("%s", PQerrormsg);
+       return STATUS_ERROR;
+   }
 
    *fdP = fd;
 
index fde5a1385ba5e0b44b60690a33a9a73239c13c81..941cfe8a0663501ca1f14e8db608c1fc09c7e556 100644 (file)
@@ -8,7 +8,7 @@
  * or in config.h afterwards.  Of course, if you edit config.h, then your
  * changes will be overwritten the next time you run configure.
  *
- * $Id: config.h.in,v 1.166 2001/06/11 22:12:48 momjian Exp $
+ * $Id: config.h.in,v 1.167 2001/07/11 19:03:07 tgl Exp $
  */
 
 #ifndef CONFIG_H
  */
 #define DEFAULT_MAX_EXPR_DEPTH 10000
 
+/*
+ * PG_SOMAXCONN: maximum accept-queue length limit passed to listen(2).
+ * You'd think we should use SOMAXCONN from <sys/socket.h>, but on many
+ * systems that symbol is much smaller than the kernel's actual limit.
+ * In any case, this symbol need be twiddled only if you have a kernel
+ * that refuses large limit values, rather than silently reducing the
+ * value to what it can handle (which is what most if not all Unixen do).
+ */
+#define PG_SOMAXCONN   10000
+
 /*
  * You can try changing this if you have a machine with bytes of another
  * size, but no guarantee...