]> jfr.im git - irc/rqf/shadowircd.git/blobdiff - src/ircd.c
More TS6 special cases simplified.
[irc/rqf/shadowircd.git] / src / ircd.c
index bf13e0d3f5f617b6e896afa92481ae8b452377e0..907e6970b898c952f380de2d5c869e9c51d20c64 100644 (file)
 #include "client.h"
 #include "common.h"
 #include "hash.h"
-#include "irc_string.h"
+#include "match.h"
 #include "ircd_signal.h"
-#include "sprintf_irc.h"
-#include "s_gline.h"
 #include "msg.h"               /* msgtab */
 #include "hostmask.h"
 #include "numeric.h"
 #include "serno.h"
 #include "sslproc.h"
 
-/* /quote set variables */\r
+/* /quote set variables */
 struct SetOptions GlobalSetOptions;
-\r
-/* configuration set from ircd.conf */\r
-struct config_file_entry ConfigFileEntry;\r
-/* server info set from ircd.conf */\r
-struct server_info ServerInfo;\r
-/* admin info set from ircd.conf */\r
+
+/* configuration set from ircd.conf */
+struct config_file_entry ConfigFileEntry;
+/* server info set from ircd.conf */
+struct server_info ServerInfo;
+/* admin info set from ircd.conf */
 struct admin_info AdminInfo;
 
-struct Counter Count;\r
+struct Counter Count;
 struct ServerStatistics ServerStats;
 
 int maxconnections;
 struct timeval SystemTime;
-struct Client me;              /* That's me */\r
+struct Client me;              /* That's me */
 struct LocalUser meLocalUser;  /* That's also part of me */
 
-rb_dlink_list lclient_list = { NULL, NULL, 0 };\r
-rb_dlink_list global_client_list = { NULL, NULL, 0 };\r
-rb_dlink_list global_channel_list = { NULL, NULL, 0 };\r
-\r
-rb_dlink_list unknown_list;        /* unknown clients ON this server only */\r
-rb_dlink_list serv_list;           /* local servers to this server ONLY */\r
-rb_dlink_list global_serv_list;    /* global servers on the network */\r
-rb_dlink_list local_oper_list;     /* our opers, duplicated in lclient_list */\r
+rb_dlink_list lclient_list = { NULL, NULL, 0 };
+rb_dlink_list global_client_list = { NULL, NULL, 0 };
+rb_dlink_list global_channel_list = { NULL, NULL, 0 };
+
+rb_dlink_list unknown_list;        /* unknown clients ON this server only */
+rb_dlink_list serv_list;           /* local servers to this server ONLY */
+rb_dlink_list global_serv_list;    /* global servers on the network */
+rb_dlink_list local_oper_list;     /* our opers, duplicated in lclient_list */
 rb_dlink_list oper_list;           /* network opers */
 
-time_t startup_time;\r
-\r
-int default_server_capabs = CAP_MASK;\r
-\r
-int splitmode;\r
-int splitchecking;\r
-int split_users;\r
-int split_servers;\r
-int eob_count;\r
-\r
-unsigned long initialVMTop = 0;  /* top of virtual memory at init */\r
-const char *logFileName = LPATH;\r
+time_t startup_time;
+
+int default_server_capabs = CAP_MASK;
+
+int splitmode;
+int splitchecking;
+int split_users;
+int split_servers;
+int eob_count;
+
+unsigned long initialVMTop = 0;  /* top of virtual memory at init */
+const char *logFileName = LPATH;
 const char *pidFileName = PPATH;
 
 char **myargv;
-int dorehash = 0;\r
-int dorehashbans = 0;\r
-int doremotd = 0;\r
-int kline_queued = 0;\r
-int server_state_foreground = 0;\r
-int opers_see_all_users = 0;\r
-int ssl_ok = 0;\r
-int zlib_ok = 1;\r
-\r
-int testing_conf = 0;\r
-\r
-struct config_channel_entry ConfigChannel;\r
-rb_bh *channel_heap;\r
-rb_bh *ban_heap;\r
-rb_bh *topic_heap;\r
-rb_bh *member_heap;\r
-\r
-rb_bh *client_heap = NULL;\r
-rb_bh *lclient_heap = NULL;\r
-rb_bh *pclient_heap = NULL;\r
-\r
-char current_uid[IDLEN];\r
-\r
-/* patricia */\r
-rb_bh *prefix_heap;\r
-rb_bh *node_heap;\r
-rb_bh *patricia_heap;\r
-\r
-rb_bh *linebuf_heap;\r
-\r
+int dorehash = 0;
+int dorehashbans = 0;
+int doremotd = 0;
+int kline_queued = 0;
+int server_state_foreground = 0;
+int opers_see_all_users = 0;
+int ssl_ok = 0;
+int zlib_ok = 1;
+
+int testing_conf = 0;
+
+struct config_channel_entry ConfigChannel;
+rb_bh *channel_heap;
+rb_bh *ban_heap;
+rb_bh *topic_heap;
+rb_bh *member_heap;
+
+rb_bh *client_heap = NULL;
+rb_bh *lclient_heap = NULL;
+rb_bh *pclient_heap = NULL;
+
+char current_uid[IDLEN];
+
+/* patricia */
+rb_bh *prefix_heap;
+rb_bh *node_heap;
+rb_bh *patricia_heap;
+
+rb_bh *linebuf_heap;
+
 rb_bh *dnode_heap;
 
+void
+ircd_shutdown(const char *reason)
+{
+       struct Client *target_p;
+       rb_dlink_node *ptr;
+
+       RB_DLINK_FOREACH(ptr, lclient_list.head)
+       {
+               target_p = ptr->data;
+
+               sendto_one(target_p, ":%s NOTICE %s :Server Terminating. %s",
+                       me.name, target_p->name, reason);
+       }
+
+       RB_DLINK_FOREACH(ptr, serv_list.head)
+       {
+               target_p = ptr->data;
+
+               sendto_one(target_p, ":%s ERROR :Terminated by %s",
+                       me.name, reason);
+       }
+
+       ilog(L_MAIN, "Server Terminating. %s", reason);
+       close_logfiles();
+
+       unlink(pidFileName);
+       exit(0);
+}
+
 /*
  * print_startup - print startup information
  */
@@ -186,7 +213,7 @@ ircd_restart_cb(const char *str)
 static void
 ircd_die_cb(const char *str)
 {
-       if(str != NULL)\r
+       if(str != NULL)
        {
                /* Try to get the message out to currently logged in operators. */
                sendto_realops_snomask(SNO_GENERAL, L_NETWIDE, "Server panic! %s", str);
@@ -207,21 +234,21 @@ ircd_die_cb(const char *str)
 static void
 init_sys(void)
 {
-#if defined(RLIMIT_NOFILE) && defined(HAVE_SYS_RESOURCE_H)\r
-       struct rlimit limit;\r
-\r
-       if(!getrlimit(RLIMIT_NOFILE, &limit))\r
-       {\r
-               maxconnections = limit.rlim_cur;\r
-               if(maxconnections <= MAX_BUFFER)\r
-               {\r
-                       fprintf(stderr, "ERROR: Shell FD limits are too low.\n");\r
-                       fprintf(stderr, "ERROR: ircd-ratbox reserves %d FDs, shell limits must be above this\n", MAX_BUFFER);\r
-                       exit(EXIT_FAILURE);\r
-               }\r
-               return;\r
-       }\r
-#endif /* RLIMIT_FD_MAX */\r
+#if defined(RLIMIT_NOFILE) && defined(HAVE_SYS_RESOURCE_H)
+       struct rlimit limit;
+
+       if(!getrlimit(RLIMIT_NOFILE, &limit))
+       {
+               maxconnections = limit.rlim_cur;
+               if(maxconnections <= MAX_BUFFER)
+               {
+                       fprintf(stderr, "ERROR: Shell FD limits are too low.\n");
+                       fprintf(stderr, "ERROR: ircd-ratbox reserves %d FDs, shell limits must be above this\n", MAX_BUFFER);
+                       exit(EXIT_FAILURE);
+               }
+               return;
+       }
+#endif /* RLIMIT_FD_MAX */
        maxconnections = MAXCONNECTIONS;
 }
 
@@ -315,8 +342,7 @@ check_rehash(void *unused)
        {
                sendto_realops_snomask(SNO_GENERAL, L_ALL,
                                     "Got signal SIGUSR1, reloading ircd motd file");
-               free_cachefile(user_motd);
-               user_motd = cache_file(MPATH, "ircd.motd", 0);
+               cache_user_motd();
                doremotd = 0;
        }
 }
@@ -334,9 +360,9 @@ initialize_global_set_options(void)
        memset(&GlobalSetOptions, 0, sizeof(GlobalSetOptions));
        /* memset( &ConfigFileEntry, 0, sizeof(ConfigFileEntry)); */
 
-       GlobalSetOptions.maxclients = ServerInfo.default_max_clients;\r
-\r
-       if(GlobalSetOptions.maxclients > (maxconnections - MAX_BUFFER) || (GlobalSetOptions.maxclients <= 0))\r
+       GlobalSetOptions.maxclients = ServerInfo.default_max_clients;
+
+       if(GlobalSetOptions.maxclients > (maxconnections - MAX_BUFFER) || (GlobalSetOptions.maxclients <= 0))
                GlobalSetOptions.maxclients = maxconnections - MAX_BUFFER;
 
        GlobalSetOptions.autoconn = 1;
@@ -361,10 +387,10 @@ initialize_global_set_options(void)
 
        GlobalSetOptions.ident_timeout = IDENT_TIMEOUT;
 
-       strlcpy(GlobalSetOptions.operstring,
+       rb_strlcpy(GlobalSetOptions.operstring,
                ConfigFileEntry.default_operstring,
                sizeof(GlobalSetOptions.operstring));
-       strlcpy(GlobalSetOptions.adminstring,
+       rb_strlcpy(GlobalSetOptions.adminstring,
                ConfigFileEntry.default_adminstring,
                sizeof(GlobalSetOptions.adminstring));
 
@@ -475,6 +501,47 @@ setup_corefile(void)
 
 struct ev_entry *check_splitmode_ev = NULL;
 
+static int
+seed_with_urandom(void)
+{
+       unsigned int seed;
+       int fd;
+
+       fd = open("/dev/urandom", O_RDONLY);
+       if(fd >= 0)
+       {
+               if(read(fd, &seed, sizeof(seed)) == sizeof(seed))
+               {
+                       close(fd);
+                       srand(seed);
+                       return 1;
+               }
+       }
+       return 0;
+}
+
+static void
+seed_with_clock(void)
+{
+       const struct timeval *tv;       
+       rb_set_time();
+       tv = rb_current_time_tv();
+       srand(tv->tv_sec ^ (tv->tv_usec | (getpid() << 20)));
+}
+
+static void
+seed_random(void *unused)
+{
+       unsigned int seed;
+       if(rb_get_random(&seed, sizeof(seed)) == -1)
+       {
+               if(!seed_with_urandom())
+                       seed_with_clock();
+               return;
+       }
+       srand(seed);
+}
+
 /*
  * main
  *
@@ -539,7 +606,7 @@ main(int argc, char *argv[])
 
        if(printVersion)
        {
-               printf("ircd: version %s\n", ircd_version);
+               printf("ircd: version %s(%s)\n", ircd_version, serno);
                exit(EXIT_SUCCESS);
        }
 
@@ -628,7 +695,7 @@ main(int argc, char *argv[])
                ierror("no server name specified in serverinfo block.");
                return -1;
        }
-       strlcpy(me.name, ServerInfo.name, sizeof(me.name));
+       rb_strlcpy(me.name, ServerInfo.name, sizeof(me.name));
 
        if(ServerInfo.sid[0] == '\0')
        {
@@ -644,18 +711,18 @@ main(int argc, char *argv[])
                ierror("no server description specified in serverinfo block.");
                return -3;
        }
-       strlcpy(me.info, ServerInfo.description, sizeof(me.info));
-
-       if(ServerInfo.ssl_cert != NULL && ServerInfo.ssl_private_key != NULL)\r
-       {\r
-               /* just do the rb_setup_ssl_server to validate the config */\r
-               if(!rb_setup_ssl_server(ServerInfo.ssl_cert, ServerInfo.ssl_private_key, ServerInfo.ssl_dh_params))\r
-               {\r
-                       ilog(L_MAIN, "WARNING: Unable to setup SSL.");\r
-                       ssl_ok = 0;\r
-               }\r
-               else\r
-                       ssl_ok = 1;\r
+       rb_strlcpy(me.info, ServerInfo.description, sizeof(me.info));
+
+       if(ServerInfo.ssl_cert != NULL && ServerInfo.ssl_private_key != NULL)
+       {
+               /* just do the rb_setup_ssl_server to validate the config */
+               if(!rb_setup_ssl_server(ServerInfo.ssl_cert, ServerInfo.ssl_private_key, ServerInfo.ssl_dh_params))
+               {
+                       ilog(L_MAIN, "WARNING: Unable to setup SSL.");
+                       ssl_ok = 0;
+               }
+               else
+                       ssl_ok = 1;
        }
 
        if (testing_conf)
@@ -685,8 +752,6 @@ main(int argc, char *argv[])
 
        ilog(L_MAIN, "Server Ready");
 
-       rb_event_addish("cleanup_glines", cleanup_glines, NULL, CLEANUP_GLINES_TIME);
-
        /* We want try_connections to be called as soon as possible now! -- adrian */
        /* No, 'cause after a restart it would cause all sorts of nick collides */
        /* um.  by waiting even longer, that just means we have even *more*
@@ -694,11 +759,8 @@ main(int argc, char *argv[])
         */
        rb_event_addish("try_connections", try_connections, NULL, STARTUP_CONNECTIONS_TIME);
        rb_event_addonce("try_connections_startup", try_connections, NULL, 0);
-
-       /* Setup the timeout check. I'll shift it later :)  -- adrian */
-       rb_event_addish("rb_checktimeouts", rb_checktimeouts, NULL, 1);
-
        rb_event_add("check_rehash", check_rehash, NULL, 1);
+       rb_event_addish("reseed_srand", seed_random, NULL, 300); /* reseed every 10 minutes */
 
        if(splitmode)
                check_splitmode_ev = rb_event_add("check_splitmode", check_splitmode, NULL, 2);