2 * IRC - Internet Relay Chat, ircd/s_bsd.c
3 * Copyright (C) 1990 Jarkko Oikarinen and
4 * University of Oulu, Computing Center
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 1, or (at your option)
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
23 #include <sys/socket.h>
28 #include <sys/ioctl.h>
31 #include <sys/filio.h>
40 #else /* HAVE_POLL_H */
45 #endif /* HAVE_POLL_H */
56 #include <sys/resource.h>
60 #include <sys/utsname.h>
61 #include <netinet/in.h>
62 #include <arpa/inet.h>
63 #include <arpa/nameser.h>
90 #include "sprintf_irc.h"
91 #include "querycmds.h"
96 #ifndef IN_LOOPBACKNET
97 #define IN_LOOPBACKNET 0x7f
100 aClient *loc_clients[MAXCONNECTIONS];
101 int highest_fd = 0, udpfd = -1, resfd = -1;
102 unsigned int readcalls = 0;
103 static struct sockaddr_in mysk;
104 static void polludp();
106 static struct sockaddr *connect_inet(aConfItem *, aClient *, int *);
107 static int completed_connection(aClient *);
108 static int check_init(aClient *, char *);
109 static void do_dns_async(), set_sock_opts(int, aClient *);
111 static struct sockaddr *connect_unix(aConfItem *, aClient *, int *);
112 static void add_unixconnection(aClient *, int);
113 static char unixpath[256];
115 static char readbuf[8192];
117 static struct pollfd poll_fds[MAXCONNECTIONS + 1];
118 static aClient *poll_cptr[MAXCONNECTIONS + 1];
119 #endif /* USE_POLL */
121 struct sockaddr_in vserv;
123 static int running_in_background;
129 #ifndef NOFLOODCONTROL
130 #define NOFLOODCONTROL
135 * Try and find the correct name to use with getrlimit() for setting the max.
136 * number of files allowed to be open by this process.
139 #define RLIMIT_FD_MAX RLIMIT_FDMAX
142 #define RLIMIT_FD_MAX RLIMIT_NOFILE
144 #ifdef RLIMIT_OPEN_MAX
145 #define RLIMIT_FD_MAX RLIMIT_OPEN_MAX
152 #if !defined(USE_POLL)
153 #if FD_SETSIZE < (MAXCONNECTIONS + 4)
157 * All operating systems work when MAXCONNECTIONS <= 252.
158 * Most operating systems work when MAXCONNECTIONS <= 1020 and FD_SETSIZE is
159 * updated correctly in the system headers (on BSD systems our sys.h has
160 * defined FD_SETSIZE to MAXCONNECTIONS+4 before including the system's headers
161 * but sys/types.h might have abruptly redefined it so the check is still
162 * done), you might already need to recompile your kernel.
163 * For larger FD_SETSIZE your milage may vary (kernel patches may be needed).
164 * The check is _NOT_ done if we will not use FD_SETS at all (USE_POLL)
166 #error "FD_SETSIZE is too small or MAXCONNECTIONS too large."
171 * Cannot use perror() within daemon. stderr is closed in
172 * ircd and cannot be used. And, worse yet, it might have
173 * been reassigned to a normal connection...
179 * This a replacement for perror(). Record error to log and
180 * also send a copy to all *LOCAL* opers online.
182 * text is a *format* string for outputting error. It must
183 * contain only two '%s', the first will be replaced
184 * by the sockhost from the cptr, and the latter will
185 * be taken from sys_errlist[errno].
187 * cptr if not NULL, is the *LOCAL* client associated with
190 void report_error(char *text, aClient *cptr)
192 Reg1 int errtmp = errno; /* debug may change 'errno' */
195 size_t len = sizeof(err);
197 host = (cptr) ? get_client_name(cptr, FALSE) : "";
199 Debug((DEBUG_ERROR, text, host, strerror(errtmp)));
202 * Get the *real* error from the socket (well try to anyway..).
203 * This may only work when SO_DEBUG is enabled but its worth the
206 #if defined(SO_ERROR) && !defined(SOL2)
207 if (cptr && !IsMe(cptr) && cptr->fd >= 0)
208 if (!getsockopt(cptr->fd, SOL_SOCKET, SO_ERROR, (OPT_TYPE *)&err, &len))
212 sendto_ops(text, host, strerror(errtmp));
214 syslog(LOG_WARNING, text, host, strerror(errtmp));
216 if (!running_in_background)
218 fprintf(stderr, text, host, strerror(errtmp));
219 fprintf(stderr, "\n");
228 * Create a socket in the AF_INET domain, bind it to the port given in
229 * 'port' and listen to it. Connections are accepted to this socket
230 * depending on the IP# mask given by 'name'. Returns the fd of the
231 * socket created or -1 on error.
233 int inetport(aClient *cptr, char *name, unsigned short int port)
235 static struct sockaddr_in server;
237 size_t len = sizeof(server);
240 ad[0] = ad[1] = ad[2] = ad[3] = 0;
243 * do it this way because building ip# from separate values for each
244 * byte requires endian knowledge or some nasty messing. Also means
245 * easy conversion of "*" 0.0.0.0 or 134.* to 134.0.0.0 :-)
247 sscanf(name, "%d.%d.%d.%d", &ad[0], &ad[1], &ad[2], &ad[3]);
248 sprintf_irc(ipname, "%d.%d.%d.%d", ad[0], ad[1], ad[2], ad[3]);
252 sprintf(cptr->sockhost, "%-.42s.%u", name, port);
253 strcpy(cptr->name, me.name);
256 * At first, open a new socket
261 cptr->fd = socket(AF_INET, SOCK_STREAM, 0);
263 if (cptr->fd < 0 && errno == EAGAIN)
265 sendto_ops("opening stream socket %s: No more sockets",
266 get_client_name(cptr, TRUE));
272 report_error("opening stream socket %s: %s", cptr);
275 else if (cptr->fd >= MAXCLIENTS)
277 sendto_ops("No more connections allowed (%s)", cptr->name);
283 setsockopt(cptr->fd, SOL_SOCKET, SO_REUSEADDR, (OPT_TYPE *)&opt, sizeof(opt));
286 * Bind a port to listen for new connections if port is non-null,
287 * else assume it is already open and try get something from it.
291 server.sin_family = AF_INET;
293 server.sin_addr.s_addr = INADDR_ANY;
295 if (vserv.sin_addr.s_addr == 0) /* Not already initialised ? */
298 memset(&vserv, 0, sizeof(vserv));
299 vserv.sin_family = AF_INET;
300 hep = gethostbyname(me.name); /* Use name from M: line */
301 if (hep && hep->h_addrtype == AF_INET && hep->h_addr_list[0] &&
302 !hep->h_addr_list[1])
303 memcpy(&vserv.sin_addr, hep->h_addr_list[0], sizeof(struct in_addr));
306 report_error("Error creating virtual host %s: %s", cptr);
310 server.sin_addr = vserv.sin_addr;
313 server.sin_port = htons(port + 10000);
315 server.sin_port = htons(port);
317 if (bind(cptr->fd, (struct sockaddr *)&server, sizeof(server)) == -1)
319 report_error("binding stream socket %s: %s", cptr);
324 if (getsockname(cptr->fd, (struct sockaddr *)&server, &len))
326 report_error("getsockname failed for %s: %s", cptr);
331 if (cptr == &me) /* KLUDGE to get it work... */
336 sprintf_irc(buf, rpl_str(RPL_MYPORTIS), me.name, "*",
337 ntohs(server.sin_port) - 10000);
339 sprintf_irc(buf, rpl_str(RPL_MYPORTIS), me.name, "*",
340 ntohs(server.sin_port));
342 write(1, buf, strlen(buf));
344 if (cptr->fd > highest_fd)
345 highest_fd = cptr->fd;
346 cptr->ip.s_addr = inet_addr(ipname);
348 cptr->port = ntohs(server.sin_port) - 10000;
350 cptr->port = ntohs(server.sin_port);
352 listen(cptr->fd, 128); /* Use listen port backlog of 128 */
353 loc_clients[cptr->fd] = cptr;
362 * Create a socket and bind it to a filename which is comprised of the path
363 * (directory where file is placed) and port (actual filename created).
364 * Set directory permissions as rwxr-xr-x so other users can connect to the
365 * file which is 'forced' to rwxrwxrwx (different OS's have different need of
366 * modes so users can connect to the socket).
368 int unixport(aClient *cptr, char *path, unsigned short int port)
370 struct sockaddr_un un;
373 cptr->fd = socket(AF_UNIX, SOCK_STREAM, 0);
375 if (cptr->fd == -1 && errno == EAGAIN)
377 sendto_ops("error opening unix domain socket %s: No more sockets",
378 get_client_name(cptr, TRUE));
383 report_error("error opening unix domain socket %s: %s", cptr);
386 else if (cptr->fd >= MAXCLIENTS)
388 sendto_ops("No more connections allowed (%s)", cptr->name);
394 un.sun_family = AF_UNIX;
398 if (chmod(path, 0755) == -1)
400 sendto_ops("error 'chmod 0755 %s': %s", path, strerror(errno));
402 syslog(LOG_WARNING, "error 'chmod 0755 %s': %s", path, strerror(errno));
409 sprintf_irc(unixpath, "%s/%u", path, port);
411 strncpy(un.sun_path, unixpath, sizeof(un.sun_path) - 1);
412 un.sun_path[sizeof(un.sun_path) - 1] = 0;
413 strcpy(cptr->name, me.name);
415 get_sockhost(cptr, unixpath);
417 if (bind(cptr->fd, (struct sockaddr *)&un, strlen(unixpath) + 2) == -1)
419 report_error("error binding unix socket %s: %s", cptr);
423 if (cptr->fd > highest_fd)
424 highest_fd = cptr->fd;
426 chmod(unixpath, 0777);
427 cptr->flags |= FLAGS_UNIX;
429 loc_clients[cptr->fd] = cptr;
438 * Create a new client which is essentially the stub like 'me' to be used
439 * for a socket that is passive (listen'ing for connections to be accepted).
441 int add_listener(aConfItem *aconf)
445 cptr = make_client(NULL, STAT_ME);
446 cptr->flags = FLAGS_LISTEN;
449 strncpy(cptr->name, aconf->host, sizeof(cptr->name) - 1);
450 cptr->name[sizeof(cptr->name) - 1] = 0;
452 if (*aconf->host == '/')
454 if (unixport(cptr, aconf->host, aconf->port))
459 if (inetport(cptr, aconf->host, aconf->port))
464 cptr->confs = make_link();
465 cptr->confs->next = NULL;
466 cptr->confs->value.aconf = aconf;
467 set_non_blocking(cptr->fd, cptr);
477 * Close and free all clients which are marked as having their socket open
478 * and in a state where they can accept connections. Unix sockets have
479 * the path to the socket unlinked for cleanliness.
481 void close_listeners(void)
485 Reg3 aConfItem *aconf;
488 * close all 'extra' listening ports we have and unlink the file
489 * name if it was a unix socket.
491 for (i = highest_fd; i >= 0; i--)
493 if (!(cptr = loc_clients[i]))
495 if (!IsMe(cptr) || cptr == &me || !IsListening(cptr))
497 aconf = cptr->confs->value.aconf;
499 if (IsIllegal(aconf) && aconf->clients == 0)
502 if (IsUnixSocket(cptr))
504 sprintf_irc(unixpath, "%s/%u", aconf->host, aconf->port);
508 close_connection(cptr);
519 #if defined(HAVE_SETRLIMIT) && defined(RLIMIT_FD_MAX)
522 if (!getrlimit(RLIMIT_FD_MAX, &limit))
525 if (limit.rlim_cur < MAXCONNECTIONS)
527 if (limit.rlim_max < MAXCONNECTIONS)
530 fprintf(stderr, "ircd fd table too big\n");
531 fprintf(stderr, "Hard Limit: " LIMIT_FMT " IRC max: %d\n",
537 (int)MAXCONNECTIONS);
538 fprintf(stderr, "Fix MAXCONNECTIONS\n");
542 limit.rlim_cur = limit.rlim_max; /* make soft limit the max */
543 if (setrlimit(RLIMIT_FD_MAX, &limit) == -1)
545 fprintf(stderr, "error setting max fd's to " LIMIT_FMT "\n",
551 #endif /* defined(HAVE_SETRLIMIT) && defined(RLIMIT_FD_MAX) */
555 static char logbuf[BUFSIZ];
557 setvbuf(stderr, _IOLBF, logbuf, sizeof(logbuf));
559 setvbuf(stderr, logbuf, _IOLBF, sizeof(logbuf));
564 for (fd = 3; fd < MAXCONNECTIONS; fd++)
567 loc_clients[fd] = NULL;
569 loc_clients[1] = NULL;
572 if (bootopt & BOOT_TTY) /* debugging is going to a tty */
574 if (!(bootopt & BOOT_DEBUG))
577 if (((bootopt & BOOT_CONSOLE) || isatty(0)) &&
578 !(bootopt & (BOOT_INETD | BOOT_OPER)))
582 running_in_background = 1;
584 if ((fd = open("/dev/tty", O_RDWR)) >= 0)
586 ioctl(fd, TIOCNOTTY, (char *)NULL);
590 #if defined(HPUX) || defined(SOL2) || defined(_SEQUENT_) || \
591 defined(_POSIX_SOURCE) || defined(SVR4)
596 close(0); /* fd 0 opened by inetd */
597 loc_clients[0] = NULL;
600 resfd = init_resolver();
605 void write_pidfile(void)
610 if ((fd = open(PPATH, O_CREAT | O_WRONLY, 0600)) >= 0)
612 memset(buff, 0, sizeof(buff));
613 sprintf(buff, "%5d\n", (int)getpid());
614 if (write(fd, buff, strlen(buff)) == -1)
615 Debug((DEBUG_NOTICE, "Error writing to pid file %s", PPATH));
621 Debug((DEBUG_NOTICE, "Error opening pid file \"%s\": %s",
622 PPATH, strerror(errno)));
628 * Initialize the various name strings used to store hostnames. This is set
629 * from either the server's sockhost (if client fd is a tty or localhost)
630 * or from the ip# converted into a string. 0 = success, -1 = fail.
632 static int check_init(aClient *cptr, char *sockn)
634 struct sockaddr_in sk;
635 size_t len = sizeof(struct sockaddr_in);
639 if (IsUnixSocket(cptr))
641 strncpy(sockn, cptr->acpt->sockhost, HOSTLEN);
642 get_sockhost(cptr, sockn);
647 /* If descriptor is a tty, special checking... */
648 if (isatty(cptr->fd))
650 strncpy(sockn, me.sockhost, HOSTLEN);
651 memset(&sk, 0, sizeof(struct sockaddr_in));
653 else if (getpeername(cptr->fd, (struct sockaddr *)&sk, &len) == -1)
655 report_error("connect failure: %s %s", cptr);
658 strcpy(sockn, inetntoa(sk.sin_addr));
659 if (inet_netof(sk.sin_addr) == IN_LOOPBACKNET)
662 strncpy(sockn, me.sockhost, HOSTLEN);
664 memcpy(&cptr->ip, &sk.sin_addr, sizeof(struct in_addr));
666 cptr->port = ntohs(sk.sin_port) - 10000;
668 cptr->port = ntohs(sk.sin_port);
675 * Ordinary client access check. Look for conf lines which have the same
676 * status as the flags passed.
678 enum AuthorizationCheckResult check_client(aClient *cptr)
680 static char sockname[HOSTLEN + 1];
681 Reg2 struct hostent *hp = NULL;
683 enum AuthorizationCheckResult acr;
686 Debug((DEBUG_DNS, "ch_cl: check access for %s[%s]",
687 cptr->name, inetntoa(cptr->ip)));
689 if (check_init(cptr, sockname))
690 return ACR_BAD_SOCKET;
692 if (!IsUnixSocket(cptr))
695 * Verify that the host to ip mapping is correct both ways and that
696 * the ip#(s) for the socket is listed for the host.
700 for (i = 0; hp->h_addr_list[i]; i++)
701 if (!memcmp(hp->h_addr_list[i], &cptr->ip, sizeof(struct in_addr)))
703 if (!hp->h_addr_list[i])
705 sendto_op_mask(SNO_IPMISMATCH, "IP# Mismatch: %s != %s[%08x]",
706 inetntoa(cptr->ip), hp->h_name, *((unsigned int *)hp->h_addr));
711 if ((acr = attach_Iline(cptr, hp, sockname)))
713 Debug((DEBUG_DNS, "ch_cl: access denied: %s[%s]", cptr->name, sockname));
717 Debug((DEBUG_DNS, "ch_cl: access ok: %s[%s]", cptr->name, sockname));
719 if (inet_netof(cptr->ip) == IN_LOOPBACKNET || IsUnixSocket(cptr) ||
720 inet_netof(cptr->ip) == inet_netof(mysk.sin_addr))
723 cptr->flags |= FLAGS_LOCAL;
728 #define CFLAG CONF_CONNECT_SERVER
729 #define NFLAG CONF_NOCONNECT_SERVER
734 * Check access for a server given its name (passed in cptr struct).
735 * Must check for all C/N lines which have a name which matches the
736 * name given and a host which matches. A host alias which is the
737 * same as the server name is also acceptable in the host field of a
745 int check_server(aClient *cptr)
747 Reg1 const char *name;
748 Reg2 aConfItem *c_conf = NULL, *n_conf = NULL;
749 struct hostent *hp = NULL;
751 char abuff[HOSTLEN + USERLEN + 2];
752 char sockname[HOSTLEN + 1], fullname[HOSTLEN + 1];
756 Debug((DEBUG_DNS, "sv_cl: check access for %s[%s]", name, cptr->sockhost));
758 if (IsUnknown(cptr) && !attach_confs(cptr, name, CFLAG | NFLAG))
760 Debug((DEBUG_DNS, "No C/N lines for %s", name));
765 * We initiated this connection so the client should have a C and N
766 * line already attached after passing through the connec_server()
769 if (IsConnecting(cptr) || IsHandshake(cptr))
771 c_conf = find_conf(lp, name, CFLAG);
772 n_conf = find_conf(lp, name, NFLAG);
773 if (!c_conf || !n_conf)
775 sendto_ops("Connecting Error: %s[%s]", name, cptr->sockhost);
776 det_confs_butmask(cptr, 0);
781 if (IsUnixSocket(cptr))
784 c_conf = find_conf(lp, name, CFLAG);
786 n_conf = find_conf(lp, name, NFLAG);
791 * If the servername is a hostname, either an alias (CNAME) or
792 * real name, then check with it as the host. Use gethostbyname()
793 * to check for servername as hostname.
795 if (!IsUnixSocket(cptr) && !cptr->hostp)
797 Reg1 aConfItem *aconf;
799 aconf = count_cnlines(lp);
806 * Do a lookup for the CONF line *only* and not
807 * the server connection else we get stuck in a
808 * nasty state since it takes a SERVER message to
809 * get us here and we cant interrupt that very well.
812 lin.value.aconf = aconf;
813 lin.flags = ASYNC_CONF;
815 if ((s = strchr(aconf->host, '@')))
819 Debug((DEBUG_DNS, "sv_ci:cache lookup (%s)", s));
820 hp = gethost_byname(s, &lin);
827 if (check_init(cptr, sockname))
833 for (i = 0; hp->h_addr_list[i]; i++)
834 if (!memcmp(hp->h_addr_list[i], &cptr->ip, sizeof(struct in_addr)))
836 if (!hp->h_addr_list[i])
838 sendto_op_mask(SNO_IPMISMATCH, "IP# Mismatch: %s != %s[%08x]",
839 inetntoa(cptr->ip), hp->h_name, *((unsigned int *)hp->h_addr));
843 else if (cptr->hostp)
846 goto check_serverback;
851 * If we are missing a C or N line from above, search for
852 * it under all known hostnames we have for this ip#.
854 for (i = 0, name = hp->h_name; name; name = hp->h_aliases[i++])
856 strncpy(fullname, name, sizeof(fullname) - 1);
857 fullname[sizeof(fullname) - 1] = 0;
858 add_local_domain(fullname, HOSTLEN - strlen(fullname));
859 Debug((DEBUG_DNS, "sv_cl: gethostbyaddr: %s->%s", sockname, fullname));
860 sprintf_irc(abuff, "%s@%s", cptr->username, fullname);
862 c_conf = find_conf_host(lp, abuff, CFLAG);
864 n_conf = find_conf_host(lp, abuff, NFLAG);
865 if (c_conf && n_conf)
867 get_sockhost(cptr, fullname);
874 * Check for C and N lines with the hostname portion the ip number
875 * of the host the server runs on. This also checks the case where
876 * there is a server connecting from 'localhost'.
878 if (IsUnknown(cptr) && (!c_conf || !n_conf))
880 sprintf_irc(abuff, "%s@%s", cptr->username, sockname);
882 c_conf = find_conf_host(lp, abuff, CFLAG);
884 n_conf = find_conf_host(lp, abuff, NFLAG);
887 * Attach by IP# only if all other checks have failed.
888 * It is quite possible to get here with the strange things that can
889 * happen when using DNS in the way the irc server does. -avalon
894 c_conf = find_conf_ip(lp, (char *)&cptr->ip, cptr->username, CFLAG);
896 n_conf = find_conf_ip(lp, (char *)&cptr->ip, cptr->username, NFLAG);
899 for (i = 0; hp->h_addr_list[i]; i++)
902 c_conf = find_conf_ip(lp, hp->h_addr_list[i], cptr->username, CFLAG);
904 n_conf = find_conf_ip(lp, hp->h_addr_list[i], cptr->username, NFLAG);
907 * detach all conf lines that got attached by attach_confs()
909 det_confs_butmask(cptr, 0);
911 * if no C or no N lines, then deny access
913 if (!c_conf || !n_conf)
915 get_sockhost(cptr, sockname);
916 Debug((DEBUG_DNS, "sv_cl: access denied: %s[%s@%s] c %p n %p",
917 name, cptr->username, cptr->sockhost, c_conf, n_conf));
921 * attach the C and N lines to the client structure for later use.
923 attach_conf(cptr, n_conf);
924 attach_conf(cptr, c_conf);
925 attach_confs(cptr, name, CONF_HUB | CONF_LEAF | CONF_UWORLD);
927 if ((c_conf->ipnum.s_addr == INADDR_NONE) && !IsUnixSocket(cptr))
928 memcpy(&c_conf->ipnum, &cptr->ip, sizeof(struct in_addr));
929 if (!IsUnixSocket(cptr))
930 get_sockhost(cptr, c_conf->host);
932 Debug((DEBUG_DNS, "sv_cl: access ok: %s[%s]", name, cptr->sockhost));
939 * completed_connection
941 * Complete non-blocking connect()-sequence. Check access and
942 * terminate connection, if trouble detected.
944 * Return TRUE, if successfully completed
945 * FALSE, if failed and ClientExit
947 static int completed_connection(aClient *cptr)
954 aconf = find_conf(cptr->confs, cptr->name, CONF_CONNECT_SERVER);
957 sendto_ops("Lost C-Line for %s", get_client_name(cptr, FALSE));
960 if (!BadPtr(aconf->passwd))
961 sendto_one(cptr, "PASS :%s", aconf->passwd);
963 aconf = find_conf(cptr->confs, cptr->name, CONF_NOCONNECT_SERVER);
966 sendto_ops("Lost N-Line for %s", get_client_name(cptr, FALSE));
970 /* Create a unique timestamp */
972 for (i = highest_fd; i >= 0; i--)
974 if (!(acptr = loc_clients[i]) || (!IsServer(acptr) && !IsHandshake(acptr)))
976 if (acptr->serv->timestamp >= newts)
977 newts = acptr->serv->timestamp + 1;
979 cptr->serv->timestamp = newts;
981 /* Make us timeout after twice the timeout for DNS look ups */
982 cptr->lasttime = now;
983 cptr->flags |= FLAGS_PINGSENT;
984 sendto_one(cptr, "SERVER %s 1 " TIME_T_FMT " " TIME_T_FMT " J%s %s%s :%s",
985 my_name_for_link(me.name, aconf), me.serv->timestamp,
986 newts, MAJOR_PROTOCOL, NumServCap(&me), me.info);
990 return (IsDead(cptr)) ? -1 : 0;
996 * Close the physical connection. This function must make
997 * MyConnect(cptr) == FALSE, and set cptr->from == NULL.
999 void close_connection(aClient *cptr)
1001 Reg1 aConfItem *aconf;
1003 int empty = cptr->fd;
1008 ircstp->is_sbs += cptr->sendB;
1009 ircstp->is_sbr += cptr->receiveB;
1010 ircstp->is_sks += cptr->sendK;
1011 ircstp->is_skr += cptr->receiveK;
1012 ircstp->is_sti += now - cptr->firsttime;
1013 if (ircstp->is_sbs > 1023)
1015 ircstp->is_sks += (ircstp->is_sbs >> 10);
1016 ircstp->is_sbs &= 0x3ff;
1018 if (ircstp->is_sbr > 1023)
1020 ircstp->is_skr += (ircstp->is_sbr >> 10);
1021 ircstp->is_sbr &= 0x3ff;
1024 else if (IsUser(cptr))
1027 ircstp->is_cbs += cptr->sendB;
1028 ircstp->is_cbr += cptr->receiveB;
1029 ircstp->is_cks += cptr->sendK;
1030 ircstp->is_ckr += cptr->receiveK;
1031 ircstp->is_cti += now - cptr->firsttime;
1032 if (ircstp->is_cbs > 1023)
1034 ircstp->is_cks += (ircstp->is_cbs >> 10);
1035 ircstp->is_cbs &= 0x3ff;
1037 if (ircstp->is_cbr > 1023)
1039 ircstp->is_ckr += (ircstp->is_cbr >> 10);
1040 ircstp->is_cbr &= 0x3ff;
1047 * Remove outstanding DNS queries.
1049 del_queries((char *)cptr);
1051 * If the connection has been up for a long amount of time, schedule
1052 * a 'quick' reconnect, else reset the next-connect cycle.
1055 if ((aconf = find_conf_exact(cptr->name, cptr->username,
1056 cptr->sockhost, CONF_CONNECT_SERVER)))
1059 * Reschedule a faster reconnect, if this was a automaticly
1060 * connected configuration entry. (Note that if we have had
1061 * a rehash in between, the status has been changed to
1062 * CONF_ILLEGAL). But only do this if it was a "good" link.
1065 aconf->hold += (aconf->hold - cptr->since > HANGONGOODLINK) ?
1066 HANGONRETRYDELAY : ConfConFreq(aconf);
1067 if (nextconnect > aconf->hold)
1068 nextconnect = aconf->hold;
1071 if (cptr->authfd >= 0)
1072 close(cptr->authfd);
1076 flush_connections(cptr->fd);
1077 loc_clients[cptr->fd] = NULL;
1082 DBufClear(&cptr->sendQ);
1083 DBufClear(&cptr->recvQ);
1084 memset(cptr->passwd, 0, sizeof(cptr->passwd));
1085 set_snomask(cptr, 0, SNO_SET);
1087 * Clean up extra sockets from P-lines which have been discarded.
1089 if (cptr->acpt != &me && cptr->acpt != cptr)
1091 aconf = cptr->acpt->confs->value.aconf;
1092 if (aconf->clients > 0)
1094 if (!aconf->clients && IsIllegal(aconf))
1095 close_connection(cptr->acpt);
1098 for (; highest_fd > 0; highest_fd--)
1099 if (loc_clients[highest_fd])
1102 det_confs_butmask(cptr, 0);
1105 * fd remap to keep loc_clients[i] filled at the bottom.
1108 if ((j = highest_fd) > (i = empty) && !IsLog(loc_clients[j]))
1110 if (IsListening(loc_clients[j]))
1112 if (dup2(j, i) == -1)
1114 loc_clients[i] = loc_clients[j];
1115 loc_clients[i]->fd = i;
1116 loc_clients[j] = NULL;
1118 while (!loc_clients[highest_fd])
1128 static void set_sock_opts(int fd, aClient *cptr)
1133 if (setsockopt(fd, SOL_SOCKET, SO_REUSEADDR,
1134 (OPT_TYPE *)&opt, sizeof(opt)) < 0)
1135 report_error("setsockopt(SO_REUSEADDR) %s: %s", cptr);
1137 #ifdef SO_USELOOPBACK
1139 if (setsockopt(fd, SOL_SOCKET, SO_USELOOPBACK,
1140 (OPT_TYPE *)&opt, sizeof(opt)) < 0)
1141 report_error("setsockopt(SO_USELOOPBACK) %s: %s", cptr);
1145 if (setsockopt(fd, SOL_SOCKET, SO_RCVBUF, (OPT_TYPE *)&opt, sizeof(opt)) < 0)
1146 report_error("setsockopt(SO_RCVBUF) %s: %s", cptr);
1151 * Seems that Sequent freezes up if the receving buffer is a different size
1152 * to the sending buffer (maybe a tcp window problem too).
1158 if (setsockopt(fd, SOL_SOCKET, SO_SNDBUF, (OPT_TYPE *)&opt, sizeof(opt)) < 0)
1159 report_error("setsockopt(SO_SNDBUF) %s: %s", cptr);
1161 #if defined(IP_OPTIONS) && defined(IPPROTO_IP)
1163 char *s = readbuf, *t = readbuf + sizeof(readbuf) / 2;
1165 opt = sizeof(readbuf) / 8;
1166 if (getsockopt(fd, IPPROTO_IP, IP_OPTIONS, (OPT_TYPE *)t, &opt) < 0)
1167 report_error("getsockopt(IP_OPTIONS) %s: %s", cptr);
1168 else if (opt > 0 && opt != sizeof(readbuf) / 8)
1170 for (*readbuf = '\0'; opt > 0; opt--, s += 3)
1171 sprintf(s, "%02x:", *t++);
1173 sendto_ops("Connection %s using IP opts: (%s)",
1174 get_client_name(cptr, TRUE), readbuf);
1176 if (setsockopt(fd, IPPROTO_IP, IP_OPTIONS, (OPT_TYPE *)NULL, 0) < 0)
1177 report_error("setsockopt(IP_OPTIONS) %s: %s", cptr);
1182 int get_sockerr(aClient *cptr)
1184 int errtmp = errno, err = 0;
1185 size_t len = sizeof(err);
1186 #if defined(SO_ERROR) && !defined(SOL2)
1188 if (!getsockopt(cptr->fd, SOL_SOCKET, SO_ERROR, (OPT_TYPE *)&err, &len))
1198 * Set the client connection into non-blocking mode. If your
1199 * system doesn't support this, you can make this a dummy
1200 * function (and get all the old problems that plagued the
1201 * blocking version of IRC--not a problem if you are a
1202 * lightly loaded node...)
1204 void set_non_blocking(int fd, aClient *cptr)
1212 * NOTE: consult ALL your relevant manual pages *BEFORE* changing
1213 * these ioctl's. There are quite a few variations on them,
1214 * as can be seen by the PCS one. They are *NOT* all the same.
1215 * Heed this well. - Avalon.
1224 /* This portion of code might also apply to NeXT. -LynX */
1227 if (ioctl(fd, FIONBIO, &res) < 0)
1228 report_error("ioctl(fd,FIONBIO) failed for %s: %s", cptr);
1230 if ((res = fcntl(fd, F_GETFL, 0)) == -1)
1231 report_error("fcntl(fd, F_GETFL) failed for %s: %s", cptr);
1232 else if (fcntl(fd, F_SETFL, res | nonb) == -1)
1233 report_error("fcntl(fd, F_SETL, nonb) failed for %s: %s", cptr);
1238 extern unsigned short server_port;
1241 * Creates a client which has just connected to us on the given fd.
1242 * The sockhost field is initialized with the ip# of the host.
1243 * The client is added to the linked list of clients but isnt added to any
1244 * hash tables yet since it doesn't have a name.
1246 aClient *add_connection(aClient *cptr, int fd, int type)
1250 aConfItem *aconf = NULL;
1253 (cptr->port == server_port) ? STAT_UNKNOWN_SERVER : STAT_UNKNOWN_USER);
1256 aconf = cptr->confs->value.aconf;
1258 * Removed preliminary access check. Full check is performed in
1259 * m_server and m_user instead. Also connection time out help to
1260 * get rid of unwanted connections.
1262 if (type == ADCON_TTY) /* If descriptor is a tty,
1263 special checking... */
1264 get_sockhost(acptr, cptr->sockhost);
1268 struct sockaddr_in addr;
1269 size_t len = sizeof(struct sockaddr_in);
1271 if (getpeername(fd, (struct sockaddr *)&addr, &len) == -1)
1273 report_error("Failed in connecting to %s: %s", cptr);
1281 /* Don't want to add "Failed in connecting to" here.. */
1282 if (aconf && IsIllegal(aconf))
1283 goto add_con_refuse;
1285 * Copy ascii address to 'sockhost' just in case. Then we
1286 * have something valid to put into error messages...
1288 get_sockhost(acptr, inetntoa(addr.sin_addr));
1289 memcpy(&acptr->ip, &addr.sin_addr, sizeof(struct in_addr));
1291 acptr->port = ntohs(addr.sin_port) - 10000;
1293 acptr->port = ntohs(addr.sin_port);
1297 * Check that this socket (client) is allowed to accept
1298 * connections from this IP#.
1300 for (s = (char *)&cptr->ip, t = (char *)&acptr->ip, len = 4;
1301 len > 0; len--, s++, t++)
1310 goto add_con_refuse;
1312 lin.flags = ASYNC_CLIENT;
1313 lin.value.cptr = acptr;
1315 if (!strcmp("127.0.0.1", inetntoa(addr.sin_addr)))
1317 static struct hostent lhe = { "localhost", NULL, 0, 0, NULL };
1318 acptr->hostp = &lhe;
1319 if (!DoingAuth(acptr))
1325 Debug((DEBUG_DNS, "lookup %s", inetntoa(addr.sin_addr)));
1326 acptr->hostp = gethost_byaddr(&acptr->ip, &lin);
1338 if (fd > highest_fd)
1340 loc_clients[fd] = acptr;
1342 Count_newunknown(nrof);
1343 add_client_to_list(acptr);
1344 set_non_blocking(acptr->fd, acptr);
1345 set_sock_opts(acptr->fd, acptr);
1348 * Add this local client to the IPcheck registry.
1349 * If it is a connection to a user port and if the site has been throttled,
1352 if (IPcheck_local_connect(acptr) == -1 && IsUserPort(acptr))
1355 exit_client(cptr, acptr, &me,
1356 "Your host is trying to (re)connect too fast -- throttled");
1365 static void add_unixconnection(aClient *cptr, int fd)
1368 aConfItem *aconf = NULL;
1370 acptr = make_client(NULL, STAT_UNKNOWN);
1373 * Copy ascii address to 'sockhost' just in case. Then we
1374 * have something valid to put into error messages...
1376 get_sockhost(acptr, me.sockhost);
1378 aconf = cptr->confs->value.aconf;
1381 if (IsIllegal(aconf))
1393 if (fd > highest_fd)
1395 loc_clients[fd] = acptr;
1398 memcpy(&acptr->ip, &me.ip, sizeof(struct in_addr));
1400 Count_newunknown(nrof);
1401 add_client_to_list(acptr);
1402 set_non_blocking(acptr->fd, acptr);
1403 set_sock_opts(acptr->fd, acptr);
1410 * select/poll convert macro's by Run.
1412 * The names are chosen to reflect what they means when NOT using poll().
1415 typedef fd_set *fd_setp_t;
1416 #define RFD_ISSET(fd, rfd, index) FD_ISSET((fd), (rfd))
1417 #define WFD_ISSET(fd, wfd, index) FD_ISSET((fd), (wfd))
1418 #define RFD_SET(fd, rfd, index, cptr) FD_SET((fd), (rfd))
1419 #define WFD_SET(fd, wfd, index, cptr) FD_SET((fd), (wfd))
1420 #define RWFD_SET(fd, wfd, index) FD_SET((fd), (wfd))
1421 #define RFD_CLR_OUT(fd, rfd, index) FD_CLR((fd), (rfd))
1422 #define WFD_CLR_OUT(fd, wfd, index) FD_CLR((fd), (wfd))
1423 #define LOC_FD(index) (index)
1424 #define LOC_CLIENTS(index) loc_clients[index]
1425 #define HIGHEST_INDEX highest_fd
1426 #else /* USE_POLL */
1427 typedef unsigned int fd_setp_t; /* Actually, an index to poll_fds[] */
1429 #define POLLREADFLAGS (POLLIN|POLLMSG)
1431 # if defined(POLLMSG) && defined(POLLIN) && defined(POLLRDNORM)
1432 # define POLLREADFLAGS (POLLMSG|POLLIN|POLLRDNORM)
1434 # if defined(POLLIN) && defined(POLLRDNORM)
1435 # define POLLREADFLAGS (POLLIN|POLLRDNORM)
1437 # if defined(POLLIN)
1438 # define POLLREADFLAGS POLLIN
1440 # if defined(POLLRDNORM)
1441 # define POLLREADFLAGS POLLRDNORM
1447 #if defined(POLLOUT) && defined(POLLWRNORM)
1448 #define POLLWRITEFLAGS (POLLOUT|POLLWRNORM)
1450 # if defined(POLLOUT)
1451 # define POLLWRITEFLAGS POLLOUT
1453 # if defined(POLLWRNORM)
1454 # define POLLWRITEFLAGS POLLWRNORM
1459 #define POLLERRORS (POLLHUP|POLLERR)
1461 #define POLLERRORS POLLERR
1463 #define RFD_ISSET(fd, rfd, index) \
1464 ((poll_fds[index].revents & POLLREADFLAGS) || \
1465 ((poll_fds[index].events & POLLREADFLAGS) && \
1466 (poll_fds[index].revents & POLLERRORS)))
1467 #define WFD_ISSET(fd, wfd, index) \
1468 ((poll_fds[index].revents & POLLWRITEFLAGS) || \
1469 ((poll_fds[index].events & POLLWRITEFLAGS) && \
1470 (poll_fds[index].revents & POLLERRORS)))
1471 #define RFD_SET(fdes, rfd, index, cptr) \
1473 poll_fds[index].fd = fdes; \
1474 poll_cptr[index] = cptr; \
1475 poll_fds[index].events = POLLREADFLAGS; \
1478 #define WFD_SET(fdes, wfd, index, cptr) \
1480 poll_fds[index].fd = fdes; \
1481 poll_cptr[index] = cptr; \
1483 poll_fds[index].events |= POLLWRITEFLAGS; \
1486 poll_fds[index].events = POLLWRITEFLAGS; \
1490 /* This identical to WFD_SET() when used after a call to RFD_SET(): */
1491 #define RWFD_SET(fd, wfd, index) poll_fds[index].events |= POLLWRITEFLAGS
1492 /* [RW]FD_CLR_OUT() clears revents, not events */
1493 #define RFD_CLR_OUT(fd, rfd, index) poll_fds[index].revents &= ~POLLREADFLAGS
1494 #define WFD_CLR_OUT(fd, wfd, index) poll_fds[index].revents &= ~POLLWRITEFLAGS
1495 #define LOC_FD(index) (poll_fds[index].fd)
1496 #define LOC_CLIENTS(index) (poll_cptr[index])
1497 #define HIGHEST_INDEX (currfd_index - 1)
1498 #endif /* USE_POLL */
1503 * Read a 'packet' of data from a connection and process it. Read in 8k
1504 * chunks to give a better performance rating (for server connections).
1505 * Do some tricky stuff for client connections to make sure they don't do
1506 * any flooding >:-) -avalon
1508 static int read_packet(aClient *cptr, fd_setp_t rfd)
1514 if (RFD_ISSET(cptr->fd, rfd, rfd) &&
1515 !(IsUser(cptr) && DBufLength(&cptr->recvQ) > 6090))
1518 length = recv(cptr->fd, readbuf, sizeof(readbuf), 0);
1520 cptr->lasttime = now;
1521 if (cptr->lasttime > cptr->since)
1522 cptr->since = cptr->lasttime;
1523 cptr->flags &= ~(FLAGS_PINGSENT | FLAGS_NONL);
1525 * If not ready, fake it so it isnt closed
1527 if (length == -1 && ((errno == EWOULDBLOCK) || (errno == EAGAIN)))
1534 * For server connections, we process as many as we can without
1535 * worrying about the time of day or anything :)
1537 if (IsServer(cptr) || IsConnecting(cptr) || IsHandshake(cptr))
1540 if ((done = dopacket(cptr, readbuf, length)))
1546 * Before we even think of parsing what we just read, stick
1547 * it on the end of the receive queue and do it when its
1548 * turn comes around.
1550 if (!dbuf_put(&cptr->recvQ, readbuf, length))
1551 return exit_client(cptr, cptr, &me, "dbuf_put fail");
1553 #ifndef NOFLOODCONTROL
1554 if (IsUser(cptr) && DBufLength(&cptr->recvQ) > CLIENT_FLOOD)
1555 return exit_client(cptr, cptr, &me, "Excess Flood");
1558 while (DBufLength(&cptr->recvQ) && !NoNewLine(cptr)
1559 #ifndef NOFLOODCONTROL
1560 && (IsTrusted(cptr) || cptr->since - now < 10)
1565 * If it has become registered as a Server
1566 * then skip the per-message parsing below.
1571 * XXX - this blindly deletes data if no cr/lf is received at
1572 * the end of a lot of messages and the data stored in the
1573 * dbuf is greater than sizeof(readbuf)
1575 dolen = dbuf_get(&cptr->recvQ, readbuf, sizeof(readbuf));
1578 if ((done = dopacket(cptr, readbuf, dolen)))
1582 dolen = dbuf_getmsg(&cptr->recvQ, cptr->buffer, BUFSIZE);
1584 * Devious looking...whats it do ? well..if a client
1585 * sends a *long* message without any CR or LF, then
1586 * dbuf_getmsg fails and we pull it out using this
1587 * loop which just gets the next 512 bytes and then
1588 * deletes the rest of the buffer contents.
1593 if (DBufLength(&cptr->recvQ) < 510)
1595 cptr->flags |= FLAGS_NONL;
1598 DBufClear(&cptr->recvQ);
1601 else if (CPTR_KILLED == client_dopacket(cptr, dolen))
1609 * Check all connections for new connections and input data that is to be
1610 * processed. Also check for connections with data queued and whether we can
1613 * Don't ever use ZERO for `delay', unless you mean to poll and then
1614 * you have to have sleep/wait somewhere else in the code.--msa
1616 int read_message(time_t delay)
1620 struct timeval wait;
1622 struct timeval nowt;
1625 time_t delay2 = delay;
1626 unsigned long usec = 0;
1627 int res, length, fd, i;
1628 int auth = 0, ping = 0;
1630 fd_set read_set, write_set;
1631 #else /* USE_POLL */
1632 unsigned int currfd_index = 0;
1633 unsigned int udpfdindex = 0;
1634 unsigned int resfdindex = 0;
1635 unsigned long timeout;
1637 #endif /* USE_POLL */
1640 gettimeofday(&nowt, NULL);
1648 FD_ZERO(&write_set);
1649 #endif /* not USE_POLL */
1650 for (i = highest_fd; i >= 0; i--)
1654 #endif /* USE_POLL */
1655 if (!(cptr = loc_clients[i]))
1659 if (DoingAuth(cptr))
1662 Debug((DEBUG_NOTICE, "auth on %p %d", cptr, i));
1663 RFD_SET(cptr->authfd, &read_set, currfd_index, cptr);
1664 if (cptr->flags & FLAGS_WRAUTH)
1665 RWFD_SET(cptr->authfd, &write_set, currfd_index);
1670 Debug((DEBUG_NOTICE, "open ping on %p %d", cptr, i));
1671 if (!cptr->firsttime || now <= cptr->firsttime)
1673 RFD_SET(i, &read_set, currfd_index, cptr);
1675 if (DoPing(cptr) && now > cptr->lasttime)
1676 RWFD_SET(i, &write_set, currfd_index);
1680 del_queries((char *)cptr);
1686 #endif /* USE_POLL */
1689 if (DoingDNS(cptr) || DoingAuth(cptr))
1694 #endif /* USE_POLL */
1697 if (IsMe(cptr) && IsListening(cptr))
1698 RFD_SET(i, &read_set, currfd_index, cptr);
1699 else if (!IsMe(cptr))
1701 if (DBufLength(&cptr->recvQ) && delay2 > 2)
1703 if (DBufLength(&cptr->recvQ) < 4088)
1704 RFD_SET(i, &read_set, currfd_index, cptr);
1705 if (DBufLength(&cptr->sendQ) || IsConnecting(cptr) ||
1706 (cptr->listing && DBufLength(&cptr->sendQ) < 2048))
1708 WFD_SET(i, &write_set, currfd_index, cptr);
1711 if (!(cptr->flags & FLAGS_BLOCKED))
1712 WFD_SET(i, &write_set, currfd_index, cptr);
1714 delay2 = 0, usec = 500000;
1716 if (now - cptr->lw.tv_sec && nowt.tv_usec - cptr->lw.tv_usec < 0)
1721 if (us - cptr->lw.tv_usec > 500000)
1722 cptr->flags &= ~FLAGS_BLOCKED;
1728 #endif /* USE_POLL */
1733 RFD_SET(udpfd, &read_set, currfd_index, NULL);
1735 udpfdindex = currfd_index;
1737 #endif /* USE_POLL */
1741 RFD_SET(resfd, &read_set, currfd_index, NULL);
1743 resfdindex = currfd_index;
1745 #endif /* USE_POLL */
1748 wait.tv_sec = MIN(delay2, delay);
1749 wait.tv_usec = usec;
1752 nfds = select(FD_SETSIZE, (int *)&read_set, (int *)&write_set, 0, &wait);
1754 nfds = select(FD_SETSIZE, &read_set, &write_set, 0, &wait);
1756 #else /* USE_POLL */
1757 timeout = (wait.tv_sec * 1000) + (wait.tv_usec / 1000);
1758 nfds = poll(poll_fds, currfd_index, timeout);
1759 #endif /* USE_POLL */
1761 if (nfds == -1 && errno == EINTR)
1765 report_error("select %s: %s", &me);
1768 restart("too many select errors");
1773 if (udpfd >= 0 && RFD_ISSET(udpfd, &read_set, udpfdindex))
1777 RFD_CLR_OUT(udpfd, &read_set, udpfdindex);
1780 * Check fd sets for the ping fd's (if set and valid!) first
1781 * because these can not be processed using the normal loops below.
1782 * And we want them to be as fast as possible.
1785 for (i = HIGHEST_INDEX; (ping > 0) && (i >= 0); i--)
1787 if (!(cptr = LOC_CLIENTS(i)))
1792 if ((nfds > 0) && RFD_ISSET(cptr->fd, &read_set, i))
1795 RFD_CLR_OUT(cptr->fd, &read_set, i);
1796 read_ping(cptr); /* This can RunFree(cptr) ! */
1798 else if ((nfds > 0) && WFD_ISSET(cptr->fd, &write_set, i))
1801 cptr->lasttime = now;
1802 WFD_CLR_OUT(cptr->fd, &write_set, i);
1803 send_ping(cptr); /* This can RunFree(cptr) ! */
1806 if (resfd >= 0 && RFD_ISSET(resfd, &read_set, resfdindex))
1810 RFD_CLR_OUT(resfd, &read_set, resfdindex);
1813 * Check fd sets for the auth fd's (if set and valid!) first
1814 * because these can not be processed using the normal loops below.
1817 for (i = HIGHEST_INDEX; (auth > 0) && (i >= 0); i--)
1819 if (!(cptr = LOC_CLIENTS(i)))
1821 if (cptr->authfd < 0)
1824 if ((nfds > 0) && WFD_ISSET(cptr->authfd, &write_set, i))
1827 send_authports(cptr);
1829 else if ((nfds > 0) && RFD_ISSET(cptr->authfd, &read_set, i))
1832 read_authports(cptr);
1835 for (i = HIGHEST_INDEX; i >= 0; i--)
1836 if ((cptr = LOC_CLIENTS(i)) && RFD_ISSET(i, &read_set, i) &&
1839 RFD_CLR_OUT(i, &read_set, i);
1841 cptr->lasttime = now;
1843 * There may be many reasons for error return, but
1844 * in otherwise correctly working environment the
1845 * probable cause is running out of file descriptors
1846 * (EMFILE, ENFILE or others?). The man pages for
1847 * accept don't seem to list these as possible,
1848 * although it's obvious that it may happen here.
1849 * Thus no specific errors are tested at this
1850 * point, just assume that connections cannot
1851 * be accepted until some old is closed first.
1853 if ((fd = accept(LOC_FD(i), NULL, NULL)) < 0)
1855 if (errno != EWOULDBLOCK)
1856 report_error("accept() failed%s: %s", NULL);
1859 #if defined(USE_SYSLOG) && defined(SYSLOG_CONNECTS)
1860 { /* get an early log of all connections --dl */
1861 static struct sockaddr_in peer;
1864 getpeername(fd, (struct sockaddr *)&peer, &len);
1865 syslog(LOG_DEBUG, "Conn: %s", inetntoa(peer.sin_addr));
1869 if (fd >= MAXCLIENTS)
1871 /* Don't send more messages then one every 10 minutes */
1873 static time_t last_time;
1876 if (last_time < now - (time_t) 600)
1881 last_time = me.since;
1883 ("All connections in use! Had to refuse %d clients in the last "
1884 STIME_T_FMT " minutes", count, (now - last_time) / 60);
1887 sendto_ops("All connections in use. (%s)", get_client_name(cptr,
1892 send(fd, "ERROR :All connections in use\r\n", 32, 0);
1897 * Use of add_connection (which never fails :) meLazy
1900 if (IsUnixSocket(cptr))
1901 add_unixconnection(cptr, fd);
1904 if (!add_connection(cptr, fd, ADCON_SOCKET))
1911 for (i = HIGHEST_INDEX; i >= 0; i--)
1913 if (!(cptr = LOC_CLIENTS(i)) || IsMe(cptr))
1916 if (DoingDNS(cptr) || DoingAuth(cptr) || !(cptr = loc_clients[LOC_FD(i)]))
1918 #endif /* USE_POLL */
1923 if (WFD_ISSET(i, &write_set, i))
1928 * ...room for writing, empty some queue then...
1930 cptr->flags &= ~FLAGS_BLOCKED;
1931 if (IsConnecting(cptr))
1932 write_err = completed_connection(cptr);
1935 if (cptr->listing && DBufLength(&cptr->sendQ) < 2048)
1936 list_next_channels(cptr, 64);
1939 if (IsDead(cptr) || write_err)
1942 if (RFD_ISSET(i, &read_set, i))
1945 RFD_CLR_OUT(i, &read_set, i);
1947 exit_client(cptr, cptr, &me,
1948 IsDead(cptr) ? LastDeadComment(cptr) : strerror(get_sockerr(cptr)));
1952 length = 1; /* for fall through case */
1953 if ((!NoNewLine(cptr) || RFD_ISSET(i, &read_set, i)) && !IsDead(cptr))
1955 length = read_packet(cptr, &read_set);
1956 #else /* USE_POLL */
1957 length = read_packet(cptr, i);
1958 #endif /* USE_POLL */
1960 /* Bullshit, why would we want to flush sockets while using non-blocking?
1961 * This uses > 4% cpu! --Run */
1963 flush_connections(LOC_FD(i));
1965 if ((length != CPTR_KILLED) && IsDead(cptr))
1967 if (!RFD_ISSET(i, &read_set, i) && length > 0)
1975 * ...hmm, with non-blocking sockets we might get
1976 * here from quite valid reasons, although.. why
1977 * would select report "data available" when there
1978 * wasn't... So, this must be an error anyway... --msa
1979 * actually, EOF occurs when read() returns 0 and
1980 * in due course, select() returns that fd as ready
1981 * for reading even though it ends up being an EOF. -avalon
1983 Debug((DEBUG_ERROR, "READ ERROR: fd = %d %d %d", LOC_FD(i), errno, length));
1985 if (length == CPTR_KILLED)
1988 if ((IsServer(cptr) || IsHandshake(cptr)) && errno == 0 && length == 0)
1989 exit_client_msg(cptr, cptr, &me, "Server %s closed the connection (%s)",
1990 get_client_name(cptr, FALSE), cptr->serv->last_error_msg);
1992 exit_client_msg(cptr, cptr, &me, "Read error to %s: %s",
1993 get_client_name(cptr, FALSE), (length < 0) ?
1994 strerror(get_sockerr(cptr)) : "EOF from client");
2002 int connect_server(aConfItem *aconf, aClient *by, struct hostent *hp)
2004 Reg1 struct sockaddr *svp;
2005 Reg2 aClient *cptr, *c2ptr;
2009 Debug((DEBUG_NOTICE, "Connect to %s[%s] @%s",
2010 aconf->name, aconf->host, inetntoa(aconf->ipnum)));
2012 if ((c2ptr = FindClient(aconf->name)))
2014 if (IsServer(c2ptr) || IsMe(c2ptr))
2016 sendto_ops("Server %s already present from %s",
2017 aconf->name, c2ptr->from->name);
2018 if (by && IsUser(by) && !MyUser(by))
2020 #ifndef NO_PROTOCOL9
2021 if (Protocol(by->from) < 10)
2022 sendto_one(by, ":%s NOTICE %s :Server %s already present from %s",
2023 me.name, by->name, aconf->name, c2ptr->from->name);
2026 sendto_one(by, "%s NOTICE %s%s :Server %s already present from %s",
2027 NumServ(&me), NumNick(by), aconf->name, c2ptr->from->name);
2031 else if (IsHandshake(c2ptr) || IsConnecting(c2ptr))
2033 if (by && IsUser(by))
2035 if (MyUser(by) || Protocol(by->from) < 10)
2036 sendto_one(by, ":%s NOTICE %s :Connection to %s already in progress",
2037 me.name, by->name, get_client_name(c2ptr, TRUE));
2040 "%s NOTICE %s%s :Connection to %s already in progress",
2041 NumServ(&me), NumNick(by), get_client_name(c2ptr, TRUE));
2048 * If we dont know the IP# for this host and itis a hostname and
2049 * not a ip# string, then try and find the appropriate host record.
2051 if ((!aconf->ipnum.s_addr)
2053 && ((aconf->host[2]) != '/') /* needed for Unix domain -- dl */
2059 lin.flags = ASYNC_CONNECT;
2060 lin.value.aconf = aconf;
2062 s = strchr(aconf->host, '@');
2063 s++; /* should NEVER be NULL */
2064 if ((aconf->ipnum.s_addr = inet_addr(s)) == INADDR_NONE)
2066 aconf->ipnum.s_addr = INADDR_ANY;
2067 hp = gethost_byname(s, &lin);
2068 Debug((DEBUG_NOTICE, "co_sv: hp %p ac %p na %s ho %s",
2069 hp, aconf, aconf->name, s));
2072 memcpy(&aconf->ipnum, hp->h_addr, sizeof(struct in_addr));
2075 cptr = make_client(NULL, STAT_UNKNOWN);
2078 * Copy these in so we have something for error detection.
2080 strncpy(cptr->name, aconf->name, sizeof(cptr->name) - 1);
2081 cptr->name[sizeof(cptr->name) - 1] = 0;
2082 strncpy(cptr->sockhost, aconf->host, HOSTLEN);
2083 cptr->sockhost[HOSTLEN] = 0;
2086 if (aconf->host[2] == '/') /* (/ starts a 2), Unix domain -- dl */
2087 svp = connect_unix(aconf, cptr, &len);
2089 svp = connect_inet(aconf, cptr, &len);
2091 svp = connect_inet(aconf, cptr, &len);
2099 if (by && IsUser(by) && !MyUser(by))
2101 #ifndef NO_PROTOCOL9
2102 if (Protocol(by->from) < 10)
2103 sendto_one(by, ":%s NOTICE %s :Couldn't connect to %s",
2104 me.name, by->name, get_client_name(cptr, TRUE));
2107 sendto_one(by, "%s NOTICE %s%s :Couldn't connect to %s",
2108 NumServ(&me), NumNick(by), get_client_name(cptr, TRUE));
2114 set_non_blocking(cptr->fd, cptr);
2115 set_sock_opts(cptr->fd, cptr);
2116 signal(SIGALRM, dummy);
2118 if (connect(cptr->fd, svp, len) < 0 && errno != EINPROGRESS)
2120 int err = get_sockerr(cptr);
2121 errtmp = errno; /* other system calls may eat errno */
2123 report_error("Connect to host %s failed: %s", cptr);
2124 if (by && IsUser(by) && !MyUser(by))
2126 #ifndef NO_PROTOCOL9
2127 if (Protocol(by->from) < 10)
2128 sendto_one(by, ":%s NOTICE %s :Connect to host %s failed: %s",
2129 me.name, by->name, get_client_name(cptr, TRUE), strerror(err));
2132 sendto_one(by, "%s NOTICE %s%s :Connect to host %s failed: %s",
2133 NumServ(&me), NumNick(by), get_client_name(cptr, TRUE),
2147 * Attach config entries to client here rather than in
2148 * completed_connection. This to avoid null pointer references
2149 * when name returned by gethostbyaddr matches no C lines
2150 * (could happen in 2.6.1a when host and servername differ).
2151 * No need to check access and do gethostbyaddr calls.
2152 * There must at least be one as we got here C line... meLazy
2154 attach_confs_host(cptr, aconf->host,
2155 CONF_NOCONNECT_SERVER | CONF_CONNECT_SERVER);
2157 if (!find_conf_host(cptr->confs, aconf->host, CONF_NOCONNECT_SERVER) ||
2158 !find_conf_host(cptr->confs, aconf->host, CONF_CONNECT_SERVER))
2160 sendto_ops("Host %s is not enabled for connecting:no C/N-line",
2162 if (by && IsUser(by) && !MyUser(by))
2164 #ifndef NO_PROTOCOL9
2165 if (Protocol(by->from) < 10)
2167 ":%s NOTICE %s :Connect to host %s failed: no C/N-lines",
2168 me.name, by->name, get_client_name(cptr, TRUE));
2172 "%s NOTICE %s%s :Connect to host %s failed: no C/N-lines",
2173 NumServ(&me), NumNick(by), get_client_name(cptr, TRUE));
2175 det_confs_butmask(cptr, 0);
2182 * The socket has been connected or connect is in progress.
2185 if (by && IsUser(by))
2187 sprintf_irc(cptr->serv->by, "%s%s", NumNick(by));
2188 if (cptr->serv->user)
2189 free_user(cptr->serv->user, NULL);
2190 cptr->serv->user = by->user;
2195 *cptr->serv->by = '\0';
2196 if (cptr->serv->user)
2197 free_user(cptr->serv->user, NULL);
2198 cptr->serv->user = NULL;
2200 cptr->serv->up = &me;
2201 if (cptr->fd > highest_fd)
2202 highest_fd = cptr->fd;
2203 loc_clients[cptr->fd] = cptr;
2205 SetConnecting(cptr);
2207 get_sockhost(cptr, aconf->host);
2208 Count_newunknown(nrof);
2209 add_client_to_list(cptr);
2216 static struct sockaddr *connect_inet(aConfItem *aconf, aClient *cptr, int *lenp)
2218 static struct sockaddr_in server;
2219 Reg3 struct hostent *hp;
2222 * Might as well get sockhost from here, the connection is attempted
2223 * with it so if it fails its useless.
2226 cptr->fd = socket(AF_INET, SOCK_STREAM, 0);
2228 if (cptr->fd == -1 && errno == EAGAIN)
2230 sendto_ops("opening stream socket to server %s: No more sockets",
2231 get_client_name(cptr, TRUE));
2236 report_error("opening stream socket to server %s: %s", cptr);
2239 if (cptr->fd >= MAXCLIENTS)
2241 sendto_ops("No more connections allowed (%s)", cptr->name);
2245 memset(&server, 0, sizeof(server));
2246 server.sin_family = AF_INET;
2247 get_sockhost(cptr, aconf->host);
2250 mysk.sin_addr = vserv.sin_addr;
2254 * Bind to a local IP# (with unknown port - let unix decide) so
2255 * we have some chance of knowing the IP# that gets used for a host
2256 * with more than one IP#.
2258 /* No we don't bind it, not all OS's can handle connecting with
2259 * an already bound socket, different ip# might occur anyway
2260 * leading to a freezing select() on this side for some time.
2261 * I had this on my Linux 1.1.88 --Run
2265 * No, we do bind it if we have virtual host support. If we don't
2266 * explicitly bind it, it will default to IN_ADDR_ANY and we lose
2267 * due to the other server not allowing our base IP --smg
2269 if (bind(cptr->fd, (struct sockaddr *)&mysk, sizeof(mysk)) == -1)
2271 report_error("error binding to local port for %s: %s", cptr);
2277 * By this point we should know the IP# of the host listed in the
2278 * conf line, whether as a result of the hostname lookup or the ip#
2279 * being present instead. If we dont know it, then the connect fails.
2281 if (isDigit(*aconf->host) && (aconf->ipnum.s_addr == INADDR_NONE))
2282 aconf->ipnum.s_addr = inet_addr(aconf->host);
2283 if (aconf->ipnum.s_addr == INADDR_NONE)
2288 Debug((DEBUG_FATAL, "%s: unknown host", aconf->host));
2291 memcpy(&aconf->ipnum, hp->h_addr, sizeof(struct in_addr));
2293 memcpy(&server.sin_addr, &aconf->ipnum, sizeof(struct in_addr));
2294 memcpy(&cptr->ip, &aconf->ipnum, sizeof(struct in_addr));
2296 server.sin_port = htons(((aconf->port > 0) ? aconf->port : portnum) + 10000);
2298 server.sin_port = htons(((aconf->port > 0) ? aconf->port : portnum));
2300 *lenp = sizeof(server);
2301 return (struct sockaddr *)&server;
2308 * Build a socket structure for cptr so that it can connet to the unix
2309 * socket defined by the conf structure aconf.
2311 static struct sockaddr *connect_unix(aConfItem *aconf, aClient *cptr, int *lenp)
2313 static struct sockaddr_un sock;
2316 cptr->fd = socket(AF_UNIX, SOCK_STREAM, 0);
2318 if (cptr->fd == -1 && errno == EAGAIN)
2320 sendto_ops("Unix domain connect to host %s failed: No more sockets",
2321 get_client_name(cptr, TRUE));
2326 report_error("Unix domain connect to host %s failed: %s", cptr);
2329 else if (cptr->fd >= MAXCLIENTS)
2331 sendto_ops("No more connections allowed (%s)", cptr->name);
2335 get_sockhost(cptr, aconf->host);
2336 /* +2 needed for working Unix domain -- dl */
2337 strncpy(sock.sun_path, aconf->host + 2, sizeof(sock.sun_path) - 1);
2338 sock.sun_path[sizeof(sock.sun_path) - 1] = 0;
2339 sock.sun_family = AF_UNIX;
2340 *lenp = strlen(sock.sun_path) + 2;
2343 return (struct sockaddr *)&sock;
2349 * Find the real hostname for the host running the server (or one which
2350 * matches the server's name) and its primary IP#. Hostname is stored
2351 * in the client structure passed as a pointer.
2353 void get_my_name(aClient *cptr, char *name, size_t len)
2355 static char tmp[HOSTLEN + 1];
2357 struct utsname utsn;
2360 char *cname = cptr->name;
2364 * Setup local socket structure to use for binding to.
2366 memset(&mysk, 0, sizeof(mysk));
2367 mysk.sin_family = AF_INET;
2370 if (uname(&utsn) == -1)
2372 len2 = strlen(utsn.nodename);
2375 strncpy(name, utsn.nodename, len2);
2376 #else /* HAVE_GETHOSTNAME */
2377 if (gethostname(name, len) == -1)
2382 /* Assume that a name containing '.' is a FQDN */
2383 if (!strchr(name, '.'))
2384 add_local_domain(name, len - strlen(name));
2387 * If hostname gives another name than cname, then check if there is
2388 * a CNAME record for cname pointing to hostname. If so accept
2389 * cname as our name. meLazy
2395 /* I don't have DNS while testing, this delays too much */
2396 (hp = gethostbyname(cname)) ||
2398 (hp = gethostbyname(name)))
2403 for (hname = hp->h_name; hname; hname = hp->h_aliases[i++])
2405 strncpy(tmp, hname, sizeof(tmp) - 1);
2406 add_local_domain(tmp, sizeof(tmp) - 1 - strlen(tmp));
2409 * Copy the matching name over and store the
2410 * 'primary' IP# as 'myip' which is used
2411 * later for making the right one is used
2412 * for connecting to other hosts.
2414 if (!strCasediff(me.name, tmp))
2417 if (strCasediff(me.name, tmp))
2418 strncpy(name, hp->h_name, len);
2420 strncpy(name, tmp, len);
2421 memcpy(&mysk.sin_addr, hp->h_addr, sizeof(struct in_addr));
2422 Debug((DEBUG_DEBUG, "local name is %s", get_client_name(&me, TRUE)));
2428 * Setup a UDP socket and listen for incoming packets
2430 int setup_ping(void)
2432 struct sockaddr_in from;
2435 memset(&from, 0, sizeof(from));
2437 from.sin_addr = vserv.sin_addr;
2439 from.sin_addr.s_addr = htonl(INADDR_ANY);
2442 from.sin_port = htons(atoi(UDP_PORT) + 10000);
2444 from.sin_port = htons(atoi(UDP_PORT));
2446 from.sin_family = AF_INET;
2448 if ((udpfd = socket(AF_INET, SOCK_DGRAM, 0)) == -1)
2450 Debug((DEBUG_ERROR, "socket udp : %s", strerror(errno)));
2453 if (setsockopt(udpfd, SOL_SOCKET, SO_REUSEADDR,
2454 (OPT_TYPE *)&on, sizeof(on)) == -1)
2457 syslog(LOG_ERR, "setsockopt udp fd %d : %m", udpfd);
2459 Debug((DEBUG_ERROR, "setsockopt so_reuseaddr : %s", strerror(errno)));
2465 setsockopt(udpfd, SOL_SOCKET, SO_BROADCAST, (char *)&on, sizeof(on));
2466 if (bind(udpfd, (struct sockaddr *)&from, sizeof(from)) == -1)
2469 syslog(LOG_ERR, "bind udp.%d fd %d : %m", from.sin_port, udpfd);
2471 Debug((DEBUG_ERROR, "bind : %s", strerror(errno)));
2476 if (fcntl(udpfd, F_SETFL, FNDELAY) == -1)
2478 Debug((DEBUG_ERROR, "fcntl fndelay : %s", strerror(errno)));
2487 * max # of pings set to 15/sec.
2489 static void polludp(void)
2492 struct sockaddr_in from;
2494 size_t fromlen = sizeof(from);
2495 static time_t last = 0;
2496 static int cnt = 0, mlen = 0;
2499 * find max length of data area of packet.
2503 mlen = sizeof(readbuf) - strlen(me.name) - strlen(version);
2508 Debug((DEBUG_DEBUG, "udp poll"));
2510 n = recvfrom(udpfd, readbuf, mlen, 0, (struct sockaddr *)&from, &fromlen);
2519 if ((errno == EWOULDBLOCK) || (errno == EAGAIN))
2523 report_error("udp port recvfrom (%s): %s", &me);
2533 * attach my name and version for the reply
2540 sendto(udpfd, readbuf, s - readbuf, 0,
2541 (struct sockaddr *)&from, sizeof(from));
2548 * Called when the fd returned from init_resolver() has been selected for
2551 static void do_dns_async(void)
2558 ln.flags = ASYNC_NONE;
2559 hp = get_res((char *)&ln);
2561 Debug((DEBUG_DNS, "%p = get_res(%d,%p)", hp, ln.flags, ln.value.cptr));
2567 * No reply was processed that was outstanding or had a client
2572 if ((cptr = ln.value.cptr))
2574 del_queries((char *)cptr);
2576 if (!DoingAuth(cptr))
2582 aconf = ln.value.aconf;
2585 memcpy(&aconf->ipnum, hp->h_addr, sizeof(struct in_addr));
2586 connect_server(aconf, NULL, hp);
2589 sendto_ops("Connect to %s failed: host lookup",
2590 (aconf) ? aconf->host : "unknown");
2593 cptr = ln.value.cptr;
2594 del_queries((char *)cptr);
2597 memcpy(&cptr->ip, hp->h_addr, sizeof(struct in_addr));
2598 if (ping_server(cptr) == -1)
2603 sendto_ops("Udp ping to %s failed: host lookup", cptr->sockhost);
2608 aconf = ln.value.aconf;
2610 memcpy(&aconf->ipnum, hp->h_addr, sizeof(struct in_addr));