Nmap Development mailing list archives

[PATCH] Redo max_sd() for (hopefully) better results


From: Kris Katterjohn <katterjohn () gmail com>
Date: Sat, 13 Jan 2007 18:26:48 -0600

The attached patch (/nmap-exp/kris SVN r4351) redoes max_sd() (tcpip.cc)
so that we can try to get more out of it. The documentation (comments)
in the patch and the SVN log below should explain it all.

------------------------------------------------------------------------
r4351 | kris | 2007-01-13 18:19:04 -0600 (Sat, 13 Jan 2007) | 1 line

This basically redoes max_sd() (tcpip.cc). If we're root, we attempt to
set the limit to RLIM_INFINITY or (if that fails) POSIX _SC_OPEN_MAX (if
available). If that fails or we weren't root to begin with, we just set
rlim_cur=rlim_max. It's still "experimental" (because I kinda tossed it
together), but I don't have any problems with it. Hopefully I can get
some feedback from people with other OS's on nmap-dev.
------------------------------------------------------------------------

I'd really appreciate any feedback on it.

Thanks,
Kris Katterjohn
Index: tcpip.cc
===================================================================
--- tcpip.cc    (revision 4350)
+++ tcpip.cc    (revision 4351)
@@ -3051,39 +3051,87 @@
 }
 
 /* Maximize the open file descriptor limit for this process go up to the
-   max allowed  */
+ * max allowed. If we're root, we try setting rlim_cur and rlim_max to
+ * RLIM_INFINITY to try to "remove" the limit. Some OS's have a problem
+ * with that, so if that fails we try to set them to the POSIX _SC_OPEN_MAX
+ * (if available and bigger than rlim_max but smaller than RLIM_INFINITY).
+ * If that fails too we resort to rlim_cur=rlim_max. If we're not root we
+ * just do rlim_cur=rlim_max.
+ */
 int max_sd() {
 #ifndef WIN32
-  struct rlimit r;
+  struct rlimit r, sr;
+  int ret = -1;
   static int maxfds = -1;
+#ifdef _SC_OPEN_MAX
+  static long openmax = sysconf(_SC_OPEN_MAX);
+#else
+  static long openmax;
+#endif
 
   if (maxfds > 0)
     return maxfds;
 
-#if(defined(RLIMIT_NOFILE))
+  /* if sysconf() failed for some reason */
+  if (openmax == -1)
+    openmax = 0;
+
+#ifdef RLIMIT_NOFILE
+  if (o.isr00t) {
+    sr.rlim_cur = sr.rlim_max = RLIM_INFINITY;
+    ret = setrlimit(RLIMIT_NOFILE, &sr);
+  }
+
+  if (ret && !getrlimit(RLIMIT_NOFILE, &r)) {
+    if (o.isr00t && ((rlim_t) openmax > r.rlim_max) && ((rlim_t) openmax < RLIM_INFINITY)) {
+      sr.rlim_cur = sr.rlim_max = openmax;
+
+      ret = setrlimit(RLIMIT_NOFILE, &sr);
+    }
+
+    if (ret) {
+      r.rlim_cur = r.rlim_max;
+
+      if (setrlimit(RLIMIT_NOFILE, &r))
+        if (o.debugging)
+          perror("setrlimit RLIMIT_NOFILE failed");
+    }
+  }
+
   if (!getrlimit(RLIMIT_NOFILE, &r)) {
-    r.rlim_cur = r.rlim_max;
-    if (setrlimit(RLIMIT_NOFILE, &r))
-      if (o.debugging) perror("setrlimit RLIMIT_NOFILE failed");
-    if (!getrlimit(RLIMIT_NOFILE, &r)) {
-      maxfds = r.rlim_cur;
-      return maxfds;
-    } else return 0;
+    maxfds = r.rlim_cur;
+    return maxfds;
   }
-#endif
-#if(defined(RLIMIT_OFILE) && !defined(RLIMIT_NOFILE))
-  if (!getrlimit(RLIMIT_OFILE, &r)) {
-    r.rlim_cur = r.rlim_max;
-    if (setrlimit(RLIMIT_OFILE, &r))
-      if (o.debugging) perror("setrlimit RLIMIT_OFILE failed");
-    if (!getrlimit(RLIMIT_OFILE, &r)) {
-      maxfds = r.rlim_cur;
-      return maxfds;
+#elif defined RLIMIT_OFILE
+  if (o.isr00t) {
+    sr.rlim_cur = sr.rlim_max = RLIM_INFINITY;
+    ret = setrlimit(RLIMIT_OFILE, &sr);
+  }
+
+  if (ret && !getrlimit(RLIMIT_OFILE, &r)) {
+    if (o.isr00t && ((rlim_t) openmax > r.rlim_max) && ((rlim_t) openmax < RLIM_INFINITY)) {
+      sr.rlim_cur = sr.rlim_max = openmax;
+
+      ret = setrlimit(RLIMIT_OFILE, &sr);
     }
-    else return 0;
+
+    if (ret) {
+      r.rlim_cur = r.rlim_max;
+
+      if (setrlimit(RLIMIT_OFILE, &r))
+        if (o.debugging)
+          perror("setrlimit RLIMIT_OFILE failed");
+    }
   }
+
+  if (!getrlimit(RLIMIT_OFILE, &r)) {
+    maxfds = r.rlim_cur;
+    return maxfds;
+  }
 #endif
 #endif /* WIN32 */
+
+  /* something went wrong */
   return 0;
 }
 

_______________________________________________
Sent through the nmap-dev mailing list
http://cgi.insecure.org/mailman/listinfo/nmap-dev
Archived at http://SecLists.Org

Current thread: