]> git.ipfire.org Git - thirdparty/squid.git/commitdiff
Author: Henrik Nordstrom <henrik@henriknordstrom.net>
authorAmos Jeffries <squid3@treenet.co.nz>
Sat, 12 Jun 2010 11:42:52 +0000 (23:42 +1200)
committerAmos Jeffries <squid3@treenet.co.nz>
Sat, 12 Jun 2010 11:42:52 +0000 (23:42 +1200)
Port from 2.7: max_filedescriptor config option

Since Squid no longer really has any hardcoded filedescriptor limitations
it makes sense to have a squid.conf directive allowing the number of
filedescriptors to be tuned runtime. Default if unset is to obey whatever
ulimit settings as before.

 * setMaxFD: figures out what to we can use for Squid_MaxFD

 * setSystemLimits: Configures the system limitations to match our
  expectations which might be lower than what setMaxFD finds if
  the comm loop has additional restrictions

 * Restrict limited select() I/O loop below FD_SETSIZE.

AYJ:
  Henrik informs that loops using fd_set() (select and win32-select) must
  be kept below FD_SETSIZE or they can hang Squid or cause out-of-bounds
  memory errors.

NP: Squid-2 does not appear to limit select() like this. May need fixing too.

doc/release-notes/release-3.1.html
doc/release-notes/release-3.1.sgml
src/cf.data.pre
src/main.cc
src/protos.h
src/structs.h
src/tools.cc

index 720600c0781610a144c52cd4618cb84305f56a8b..c553f07d9a7fd576bc50bab17d7c164d29872498 100644 (file)
@@ -1000,6 +1000,9 @@ Default: ON
 </PRE>
 </P>
 
+<DT><B>max_filedescriptors</B><DD>
+<P>Ported from 2.7.</P>
+
 <DT><B>netdb_filename</B><DD>
 <P>
 <PRE>
@@ -1904,9 +1907,6 @@ Use --without-pthreads to disable, but only if you really have to.</P>
 <P><EM>%oa</EM> tag not yet ported from 2.7</P>
 <P><EM>%sn</EM> tag not yet ported from 2.7</P>
 
-<DT><B>max_filedescriptors</B><DD>
-<P>Not yet ported from 2.7</P>
-
 <DT><B>max_stale</B><DD>
 <P>Not yet ported from 2.7</P>
 
index c772aaa5af2495ac2fda2af49a3e0e7997777b94..5a9a946711162fb64e7c10cdd5823604fcc1942c 100644 (file)
@@ -853,6 +853,9 @@ logformat icap_squid %ts.%03tu %6icap::tr %>a %icap::to/%03icap::Hs %icap::<size
        direct client address in the access log.
        </verb>
 
+       <tag>max_filedescriptors</tag>
+       <p>Ported from 2.7.
+
        <tag>netdb_filename</tag>
        <verb>
        A filename where Squid stores it's netdb state between restarts.
@@ -1691,9 +1694,6 @@ This section gives an account of those changes in three categories:
        <p><em>%oa</em> tag not yet ported from 2.7
        <p><em>%sn</em> tag not yet ported from 2.7
 
-       <tag>max_filedescriptors</tag>
-       <p>Not yet ported from 2.7
-
        <tag>max_stale</tag>
        <p>Not yet ported from 2.7
 
index 3a914cb0b171c5d4f0df95c1b8889a8c4d77b1b5..573cefeeebea7ca5af72172dac721e0e1fb374ae 100644 (file)
@@ -6657,4 +6657,17 @@ DOC_START
        Note: after changing this, Squid service must be restarted.
 DOC_END
 
+NAME: max_filedescriptors max_filedesc
+TYPE: int
+DEFAULT: 0
+LOC: Config.max_filedescriptors
+DOC_START
+       The maximum number of filedescriptors supported.
+
+       The default "0" means Squid inherits the current ulimit setting.
+
+       Note: Changing this requires a restart of Squid. Also
+       not all comm loops supports large values.
+DOC_END
+
 EOF
index 47d6a261f6298384afb03a4e41c06c2eeee64feb..3fe99cce8e6804cfc10753e1d8b17e9c7015b4d7 100644 (file)
@@ -928,7 +928,7 @@ mainInitialize(void)
 #endif
 
     debugs(1, 1, "Process ID " << getpid());
-
+    setSystemLimits();
     debugs(1, 1, "With " << Squid_MaxFD << " file descriptors available");
 
 #ifdef _SQUID_MSWIN_
index 4a4a2c5886bc2f513792c07cc69ea86ebe7a713d..acb13ceff1c1ffe2248d085be1fcd18d931928ee 100644 (file)
@@ -571,6 +571,7 @@ SQUIDCEXTERN void no_suid(void);
 SQUIDCEXTERN void writePidFile(void);
 SQUIDCEXTERN void setSocketShutdownLifetimes(int);
 SQUIDCEXTERN void setMaxFD(void);
+SQUIDCEXTERN void setSystemLimits(void);
 SQUIDCEXTERN void squid_signal(int sig, SIGHDLR *, int flags);
 SQUIDCEXTERN pid_t readPidFile(void);
 SQUIDCEXTERN void keepCapabilities(void);
index a2ce6fb67eeaa494a6a491c602215c42b47c46d8..0f88b8b76c765ac6db89b27b3d18ff64abaede13 100644 (file)
@@ -618,6 +618,7 @@ struct SquidConfig {
 
     char *accept_filter;
     int umask;
+    int max_filedescriptors;
 
 #if USE_LOADABLE_MODULES
     wordlist *loadable_module_names;
index 63ee61072c979b2cd30d3bf9d3723bd1b4980c59..d9e4dbff0aaa961a8132e318f508dd47b9f9d490 100644 (file)
@@ -869,69 +869,82 @@ readPidFile(void)
     return pid;
 }
 
+/* A little piece of glue for odd systems */
+#ifndef RLIMIT_NOFILE
+#ifdef RLIMIT_OFILE
+#define RLIMIT_NOFILE RLIMIT_OFILE
+#endif
+#endif
 
+/** Figure out the number of supported filedescriptors */
 void
 setMaxFD(void)
 {
-#if HAVE_SETRLIMIT
-    /* try to use as many file descriptors as possible */
-    /* System V uses RLIMIT_NOFILE and BSD uses RLIMIT_OFILE */
-
+#if HAVE_SETRLIMIT && defined(RLIMIT_NOFILE)
     struct rlimit rl;
-#if defined(RLIMIT_NOFILE)
-
     if (getrlimit(RLIMIT_NOFILE, &rl) < 0) {
-        debugs(50, 0, "setrlimit: RLIMIT_NOFILE: " << xstrerror());
-    } else {
-        rl.rlim_cur = Squid_MaxFD;
-
+        debugs(50, DBG_CRITICAL, "setrlimit: RLIMIT_NOFILE: " << xstrerror());
+    } else if (Config.max_filedescriptors > 0) {
+#if USE_SELECT || USE_SELECT_WIN32
+        /* select() breaks if this gets set too big */
+        if (Config.max_filedescriptors > FD_SETSIZE)
+            rl.rlim_cur = FD_SETSIZE;
+        else
+#endif
+            rl.rlim_cur = Config.max_filedescriptors;
         if (rl.rlim_cur > rl.rlim_max)
-            Squid_MaxFD = rl.rlim_cur = rl.rlim_max;
-
-        if (setrlimit(RLIMIT_NOFILE, &rl) < 0) {
-            snprintf(tmp_error_buf, ERROR_BUF_SZ,
-                     "setrlimit: RLIMIT_NOFILE: %s", xstrerror());
-            fatal_dump(tmp_error_buf);
+            rl.rlim_max = rl.rlim_cur;
+        if (setrlimit(RLIMIT_NOFILE, &rl)) {
+            debugs(50, DBG_CRITICAL, "setrlimit: RLIMIT_NOFILE: " << xstrerror());
+            getrlimit(RLIMIT_NOFILE, &rl);
+            rl.rlim_cur = rl.rlim_max;
+            if (setrlimit(RLIMIT_NOFILE, &rl)) {
+                debugs(50, DBG_CRITICAL, "setrlimit: RLIMIT_NOFILE: " << xstrerror());
+            }
         }
     }
-
-#elif defined(RLIMIT_OFILE)
-    if (getrlimit(RLIMIT_OFILE, &rl) < 0) {
-        debugs(50, 0, "setrlimit: RLIMIT_NOFILE: " << xstrerror());
+    if (getrlimit(RLIMIT_NOFILE, &rl) < 0) {
+         debugs(50, DBG_CRITICAL, "setrlimit: RLIMIT_NOFILE: " << xstrerror());
     } else {
-        rl.rlim_cur = Squid_MaxFD;
+        Squid_MaxFD = rl.rlim_cur;
+    }
 
-        if (rl.rlim_cur > rl.rlim_max)
-            Squid_MaxFD = rl.rlim_cur = rl.rlim_max;
+#endif /* HAVE_SETRLIMIT */
+}
 
-        if (setrlimit(RLIMIT_OFILE, &rl) < 0) {
-            snprintf(tmp_error_buf, ERROR_BUF_SZ,
-                     "setrlimit: RLIMIT_OFILE: %s", xstrerror());
+void
+setSystemLimits(void)
+{
+#if HAVE_SETRLIMIT && defined(RLIMIT_NOFILE) && !defined(_SQUID_CYGWIN_)
+    /* limit system filedescriptors to our own limit */
+    struct rlimit rl;
+    if (getrlimit(RLIMIT_NOFILE, &rl) < 0) {
+        debugs(50, DBG_CRITICAL, "setrlimit: RLIMIT_NOFILE: " << xstrerror());
+    } else {
+        rl.rlim_cur = Squid_MaxFD;
+        if (setrlimit(RLIMIT_NOFILE, &rl) < 0) {
+            snprintf(tmp_error_buf, ERROR_BUF_SZ, "setrlimit: RLIMIT_NOFILE: %s", xstrerror());
             fatal_dump(tmp_error_buf);
         }
     }
-
-#endif
-#else /* HAVE_SETRLIMIT */
-    debugs(21, 1, "setMaxFD: Cannot increase: setrlimit() not supported on this system");
-
 #endif /* HAVE_SETRLIMIT */
 
 #if HAVE_SETRLIMIT && defined(RLIMIT_DATA)
-
     if (getrlimit(RLIMIT_DATA, &rl) < 0) {
-        debugs(50, 0, "getrlimit: RLIMIT_DATA: " << xstrerror());
+        debugs(50, DBG_CRITICAL, "getrlimit: RLIMIT_DATA: " << xstrerror());
     } else if (rl.rlim_max > rl.rlim_cur) {
         rl.rlim_cur = rl.rlim_max;     /* set it to the max */
 
         if (setrlimit(RLIMIT_DATA, &rl) < 0) {
-            snprintf(tmp_error_buf, ERROR_BUF_SZ,
-                     "setrlimit: RLIMIT_DATA: %s", xstrerror());
+            snprintf(tmp_error_buf, ERROR_BUF_SZ, "setrlimit: RLIMIT_DATA: %s", xstrerror());
             fatal_dump(tmp_error_buf);
         }
     }
-
 #endif /* RLIMIT_DATA */
+    if (Config.max_filedescriptors > Squid_MaxFD) {
+        debugs(50, DBG_IMPORTANT, "NOTICE: Could not increase the number of filedescriptors");
+    }
+
 #if HAVE_SETRLIMIT && defined(RLIMIT_VMEM)
     if (getrlimit(RLIMIT_VMEM, &rl) < 0) {
         debugs(50, 0, "getrlimit: RLIMIT_VMEM: " << xstrerror());
@@ -939,12 +952,10 @@ setMaxFD(void)
         rl.rlim_cur = rl.rlim_max;     /* set it to the max */
 
         if (setrlimit(RLIMIT_VMEM, &rl) < 0) {
-            snprintf(tmp_error_buf, ERROR_BUF_SZ,
-                     "setrlimit: RLIMIT_VMEM: %s", xstrerror());
+            snprintf(tmp_error_buf, ERROR_BUF_SZ, "setrlimit: RLIMIT_VMEM: %s", xstrerror());
             fatal_dump(tmp_error_buf);
         }
     }
-
 #endif /* RLIMIT_VMEM */
 }