[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[leafnode-list] [PATCH] Random initial delay for fetchnews



Hi.

François Pétillon, in charge of the biggest French news server
news.proxad.net, asked me to wait for a random delay before connecting
to his new server. As many people, I used

  */5 * * * * /usr/sbin/fetchnews

in a crontab entry, and as many others do that and as we are almost
all synchronized using NTP, we were slammering the NNTP server exactly
on square times.

I've added a "-i seconds" option to fetchnews, which waits for up-to
"seconds" seconds before trying to connect to upstream servers. Now,
my crontab entry reads:

  */5 * * * * /usr/sbin/fetchnews -i 60

which adds a random initial delay between 0 and 60 seconds.

The patch is against leafnode 2.0.0_alpha20060321, the one found in
Gentoo, but is so small that it will probably apply to later versions
without difficulty.

Patch attached. The corresponding ChangeLog entry is:

2006-07-20  Samuel Tardieu  <sam@xxxxxxxxxxx>

  * Add -i option to fetchnews to allow for an initial delay before
    connecting to upstream servers. This prevents multiple leafnode
    clients from slamming a server on square hours for example by
    randomly differing their connections. Feature suggested by
    François Pétillon.

  Sam

diff -r 4ee8f321561f fetchnews.8.in
--- a/fetchnews.8.in	Thu Jul 20 09:54:20 2006 +0200
+++ b/fetchnews.8.in	Thu Jul 20 10:28:06 2006 +0200
@@ -13,7 +13,7 @@ fetchnews \- fetch news via NNTP
 .SH SYNOPSIS
 .B fetchnews -V
 .br
-.B fetchnews [GLOBAL OPTIONS] [-BfHnPR]
+.B fetchnews [GLOBAL OPTIONS] [-BfHnPR] [-i seconds]
 .B [-M message-id] [...] [-x number] [-S server[:port]]
 .B [-N {newsgroup|group.pattern}] [...] [-t #]
 
@@ -40,6 +40,12 @@ Get article bodies from groups that are 
 Get article bodies from groups that are in "delaybody" mode. Done by
 default unless one of -H -M -R -P is used. See the configuration
 section of leafnode(8) for "delaybody".
+.TP
+.I -i seconds
+Wait for a random number of seconds before actually connecting to the
+upstream news servers. This can be used in a crontab to avoid contacting
+news servers at the same time as everyone else (on exact hours for
+example).
 .TP
 .I -f
 Force rereading of whole active file from all upstream servers. This is
diff -r 4ee8f321561f fetchnews.c
--- a/fetchnews.c	Thu Jul 20 09:54:20 2006 +0200
+++ b/fetchnews.c	Thu Jul 20 10:24:14 2006 +0200
@@ -16,6 +16,7 @@
 #include "groupselect.h"
 #include "fetchnews.h"
 #include "mysetvbuf.h"
+#include "arc4random.h"
 
 #include <sys/types.h>
 #include <ctype.h>
@@ -53,6 +54,7 @@ static time_t now;
 /* Variables set by command-line options which are specific for fetchnews */
 static unsigned long extraarticles = 0;		/* go back in upstream high mark and try refetching */
 static unsigned int throttling = 0;		/* pause between streaming operations */
+static unsigned int randomdelay = 0;            /* initial random delay in seconds */
 						/* the higher the value, the less bandwidth is used */
 static int noexpire = 0;	/* if 1, don't automatically unsubscribe newsgroups */
 
@@ -152,6 +154,7 @@ usage(void)
 	    "    -B             - get article bodies in delaybody groups\n");
     fprintf(stderr,
 	    "    -f             - force reload of groupinfo file\n"
+	    "    -i seconds     - sleep for an initial delay\n"
 	    "    -H             - get article headers in delaybody groups\n"
 	    "    -n             - switch off automatic unsubscription of groups\n");
     fprintf(stderr,
@@ -190,7 +193,7 @@ process_options(int argc, char *argv[], 
     /* state information */
     int action_method_seen = 0;	/* BHPR */
 
-    while ((option = getopt(argc, argv, GLOBALOPTS "BfHM:N:nPRS:t:x:")) != -1) {
+    while ((option = getopt(argc, argv, GLOBALOPTS "Bfi:HM:N:nPRS:t:x:")) != -1) {
 	if (parseopt(argv[0], option, optarg, conffile))
 	    continue;
 
@@ -200,6 +203,13 @@ process_options(int argc, char *argv[], 
 	    if (*p || p == optarg) {
 		usage();
 		return -1;
+	    }
+	    break;
+	case 'i':
+	    randomdelay = strtoul(optarg, &p, 10);
+	    if (*p || p == optarg) {
+	      usage();
+	      return -1;
 	    }
 	    break;
 	case 'x':
@@ -2138,6 +2148,8 @@ main(int argc, char **argv)
     }
 
     /* FIXME! Race condition here if no lockfile */
+    if (randomdelay)
+        sleep(arc4random()%randomdelay);
     rereadactive();
     feedincoming();
     if (forceactive) {
-- 
_______________________________________________
leafnode-list mailing list
leafnode-list@xxxxxxxxxxxxxxxxxxxxxxxxxxxx
https://www.dt.e-technik.uni-dortmund.de/mailman/listinfo/leafnode-list
http://leafnode.sourceforge.net/