Hi!

Recently libradius(3) got long-awaited 'dead_time' option
that allows to skip 'dead' radius servers for 'dead_time' timeout
while dealing with multiple servers.

I'd like to ask for small improvement of the code.
Presently it will fail without a try if all servers marked 'dead'.

Instead, in that case it shoud ignore 'dead' state of servers and
make at try as if all of them were marked 'alive'. That would greatly
increase recovery time after great network disasters.

Also, I'd like to be able to see notification of such disasters in system logs
(as an option). Something like this (compile-tested only):

--- radlib.c.orig       2012-12-20 18:13:25.000000000 +0700
+++ radlib.c    2012-12-20 18:54:43.000000000 +0700
@@ -55,6 +55,9 @@
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
+#ifdef LIBRADIUS_USE_SYSLOG
+#include <syslog.h>
+#endif
 #include <unistd.h>
 
 #include "radlib_private.h"
@@ -686,9 +689,35 @@
        if (h->servers[h->srv].num_tries >= h->servers[h->srv].max_tries) {
                /* Set next probe time for this server */
                if (h->servers[h->srv].dead_time) {
+                       int alldead = 1;
+                       int i;
+#ifdef LIBRADIUS_USE_SYSLOG
+                       char host[13]; /* AF_INET in dot notation */
+                       syslog(LOG_INFO,
+                           "RADIUS server %s:%u is not responding and is being 
marked dead.",
+                           inet_ntop(AF_INET, 
&(h->servers[h->srv].addr.sin_addr),
+                               host, sizeof(host)),
+                           (int)ntohs(h->servers[h->srv].addr.sin_port));
+#endif
                        h->servers[h->srv].is_dead = 1;
                        h->servers[h->srv].next_probe = now +
                            h->servers[h->srv].dead_time;
+                       for (i = 0; i < h->num_servers; i++) {
+                           if (!h->servers[i].is_dead) {
+                               alldead = 0;
+                               break;
+                           }
+                       }
+                       if (alldead) {
+#ifdef LIBRADIUS_USE_SYSLOG
+                           syslog(LOG_NOTICE, "ALL RADIUS servers are dead.");
+#endif
+                           /* don't be idle */
+                           for (i = 0; i < h->num_servers; i++) {
+                               h->servers[i].is_dead = 0;
+                               h->servers[i].num_tries = 0;
+                           }
+                       }
                }
                do {
                        h->srv++;
@@ -698,6 +727,14 @@
                                break;
                        if (h->servers[h->srv].dead_time &&
                            h->servers[h->srv].next_probe <= now) {
+#ifdef LIBRADIUS_USE_SYSLOG
+                               char host[13]; /* AF_INET in dot notation */
+                               syslog(LOG_INFO,
+                                   "RADIUS server %s:%u is being marked 
alive.",
+                                   inet_ntop(AF_INET, 
&(h->servers[h->srv].addr.sin_addr),
+                                       host, sizeof(host)),
+                                   
(int)ntohs(h->servers[h->srv].addr.sin_port));
+#endif
                                h->servers[h->srv].is_dead = 0;
                                h->servers[h->srv].num_tries = 0;
                                break;
_______________________________________________
freebsd-net@freebsd.org mailing list
http://lists.freebsd.org/mailman/listinfo/freebsd-net
To unsubscribe, send any mail to "freebsd-net-unsubscr...@freebsd.org"

Reply via email to