Use usleep() instead of sleep(), MinGW complained.
[tinc] / src / net.c
index 6700a29..8762db3 100644 (file)
--- a/src/net.c
+++ b/src/net.c
@@ -3,6 +3,7 @@
     Copyright (C) 1998-2005 Ivo Timmermans,
                   2000-2011 Guus Sliepen <guus@tinc-vpn.org>
                   2006      Scott Lamb <slamb@slamb.org>
+                 2011      Loïc Grenié <loic.grenie@gmail.com>
 
     This program is free software; you can redistribute it and/or modify
     it under the terms of the GNU General Public License as published by
@@ -49,6 +50,7 @@ bool graph_dump = false;
 time_t now = 0;
 int contradicting_add_edge = 0;
 int contradicting_del_edge = 0;
+static int sleeptime = 10;
 
 /* Purge edges and subnets of unreachable nodes. Use carefully. */
 
@@ -463,18 +465,25 @@ int main_loop(void) {
                                keyexpires = now + keylifetime;
                        }
 
-                       if(contradicting_del_edge > 10 && contradicting_add_edge > 10) {
-                               logger(LOG_WARNING, "Possible node with same Name as us!");
-
-                               if(rand() % 3 == 0) {
-                                       logger(LOG_ERR, "Shutting down, check configuration of all nodes for duplicate Names!");
-                                       running = false;
-                                       break;
-                               }
-
-                               contradicting_add_edge = 0;
-                               contradicting_del_edge = 0;
+                       /* Detect ADD_EDGE/DEL_EDGE storms that are caused when
+                        * two tinc daemons with the same name are on the VPN.
+                        * If so, sleep a while. If this happens multiple times
+                        * in a row, sleep longer. */
+
+                       if(contradicting_del_edge > 100 && contradicting_add_edge > 100) {
+                               logger(LOG_WARNING, "Possible node with same Name as us! Sleeping %d seconds.", sleeptime);
+                               usleep(sleeptime * 1000000LL);
+                               sleeptime *= 2;
+                               if(sleeptime < 0)
+                                       sleeptime = 3600;
+                       } else {
+                               sleeptime /= 2;
+                               if(sleeptime < 10)
+                                       sleeptime = 10;
                        }
+
+                       contradicting_add_edge = 0;
+                       contradicting_del_edge = 0;
                }
 
                if(sigalrm) {
@@ -500,6 +509,8 @@ int main_loop(void) {
                        struct stat s;
                        
                        sighup = false;
+
+                       reopenlogger();
                        
                        /* Reread our own configuration file */