Annotation of embedaddon/dnsmasq/src/dnsmasq.c, revision 1.1.1.4

1.1.1.4 ! misho       1: /* dnsmasq is Copyright (c) 2000-2021 Simon Kelley
1.1       misho       2: 
                      3:    This program is free software; you can redistribute it and/or modify
                      4:    it under the terms of the GNU General Public License as published by
                      5:    the Free Software Foundation; version 2 dated June, 1991, or
                      6:    (at your option) version 3 dated 29 June, 2007.
                      7:  
                      8:    This program is distributed in the hope that it will be useful,
                      9:    but WITHOUT ANY WARRANTY; without even the implied warranty of
                     10:    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
                     11:    GNU General Public License for more details.
                     12:      
                     13:    You should have received a copy of the GNU General Public License
                     14:    along with this program.  If not, see <http://www.gnu.org/licenses/>.
                     15: */
                     16: 
                     17: /* Declare static char *compiler_opts  in config.h */
                     18: #define DNSMASQ_COMPILE_OPTS
                     19: 
                     20: #include "dnsmasq.h"
                     21: 
                     22: struct daemon *daemon;
                     23: 
                     24: static volatile pid_t pid = 0;
                     25: static volatile int pipewrite;
                     26: 
1.1.1.3   misho      27: static int set_dns_listeners(time_t now);
                     28: static void check_dns_listeners(time_t now);
1.1       misho      29: static void sig_handler(int sig);
                     30: static void async_event(int pipe, time_t now);
                     31: static void fatal_event(struct event_desc *ev, char *msg);
                     32: static int read_event(int fd, struct event_desc *evp, char **msg);
1.1.1.3   misho      33: static void poll_resolv(int force, int do_reload, time_t now);
1.1       misho      34: 
                     35: int main (int argc, char **argv)
                     36: {
                     37:   int bind_fallback = 0;
                     38:   time_t now;
                     39:   struct sigaction sigact;
                     40:   struct iname *if_tmp;
                     41:   int piperead, pipefd[2], err_pipe[2];
                     42:   struct passwd *ent_pw = NULL;
                     43: #if defined(HAVE_SCRIPT)
                     44:   uid_t script_uid = 0;
                     45:   gid_t script_gid = 0;
                     46: #endif
                     47:   struct group *gp = NULL;
                     48:   long i, max_fd = sysconf(_SC_OPEN_MAX);
                     49:   char *baduser = NULL;
                     50:   int log_err;
1.1.1.4 ! misho      51:   int chown_warn = 0;
1.1       misho      52: #if defined(HAVE_LINUX_NETWORK)
                     53:   cap_user_header_t hdr = NULL;
                     54:   cap_user_data_t data = NULL;
1.1.1.4 ! misho      55:   int need_cap_net_admin = 0;
        !            56:   int need_cap_net_raw = 0;
        !            57:   int need_cap_net_bind_service = 0;
1.1.1.2   misho      58:   char *bound_device = NULL;
                     59:   int did_bind = 0;
1.1.1.4 ! misho      60:   struct server *serv;
        !            61:   char *netlink_warn;
1.1       misho      62: #endif 
1.1.1.2   misho      63: #if defined(HAVE_DHCP) || defined(HAVE_DHCP6)
1.1       misho      64:   struct dhcp_context *context;
1.1.1.2   misho      65:   struct dhcp_relay *relay;
                     66: #endif
1.1.1.3   misho      67: #ifdef HAVE_TFTP
                     68:   int tftp_prefix_missing = 0;
                     69: #endif
1.1       misho      70: 
                     71: #ifdef LOCALEDIR
                     72:   setlocale(LC_ALL, "");
                     73:   bindtextdomain("dnsmasq", LOCALEDIR); 
                     74:   textdomain("dnsmasq");
                     75: #endif
                     76: 
                     77:   sigact.sa_handler = sig_handler;
                     78:   sigact.sa_flags = 0;
                     79:   sigemptyset(&sigact.sa_mask);
                     80:   sigaction(SIGUSR1, &sigact, NULL);
                     81:   sigaction(SIGUSR2, &sigact, NULL);
                     82:   sigaction(SIGHUP, &sigact, NULL);
                     83:   sigaction(SIGTERM, &sigact, NULL);
                     84:   sigaction(SIGALRM, &sigact, NULL);
                     85:   sigaction(SIGCHLD, &sigact, NULL);
1.1.1.4 ! misho      86:   sigaction(SIGINT, &sigact, NULL);
        !            87:   
1.1       misho      88:   /* ignore SIGPIPE */
                     89:   sigact.sa_handler = SIG_IGN;
                     90:   sigaction(SIGPIPE, &sigact, NULL);
                     91: 
                     92:   umask(022); /* known umask, create leases and pid files as 0644 */
1.1.1.4 ! misho      93: 
1.1.1.3   misho      94:   rand_init(); /* Must precede read_opts() */
                     95:   
1.1       misho      96:   read_opts(argc, argv, compile_opts);
1.1.1.2   misho      97:  
1.1.1.4 ! misho      98: #ifdef HAVE_LINUX_NETWORK
        !            99:   daemon->kernel_version = kernel_version();
        !           100: #endif
        !           101: 
1.1       misho     102:   if (daemon->edns_pktsz < PACKETSZ)
                    103:     daemon->edns_pktsz = PACKETSZ;
1.1.1.2   misho     104: 
1.1.1.3   misho     105:   /* Min buffer size: we check after adding each record, so there must be 
                    106:      memory for the largest packet, and the largest record so the
                    107:      min for DNS is PACKETSZ+MAXDNAME+RRFIXEDSZ which is < 1000.
                    108:      This might be increased is EDNS packet size if greater than the minimum. */ 
                    109:   daemon->packet_buff_sz = daemon->edns_pktsz + MAXDNAME + RRFIXEDSZ;
1.1       misho     110:   daemon->packet = safe_malloc(daemon->packet_buff_sz);
1.1.1.2   misho     111:   
1.1       misho     112:   daemon->addrbuff = safe_malloc(ADDRSTRLEN);
1.1.1.3   misho     113:   if (option_bool(OPT_EXTRALOG))
                    114:     daemon->addrbuff2 = safe_malloc(ADDRSTRLEN);
1.1.1.2   misho     115:   
                    116: #ifdef HAVE_DNSSEC
                    117:   if (option_bool(OPT_DNSSEC_VALID))
                    118:     {
1.1.1.3   misho     119:       /* Note that both /000 and '.' are allowed within labels. These get
                    120:         represented in presentation format using NAME_ESCAPE as an escape
                    121:         character when in DNSSEC mode. 
                    122:         In theory, if all the characters in a name were /000 or
                    123:         '.' or NAME_ESCAPE then all would have to be escaped, so the 
                    124:         presentation format would be twice as long as the spec.
                    125: 
                    126:         daemon->namebuff was previously allocated by the option-reading
                    127:         code before we knew if we're in DNSSEC mode, so reallocate here. */
                    128:       free(daemon->namebuff);
                    129:       daemon->namebuff = safe_malloc(MAXDNAME * 2);
                    130:       daemon->keyname = safe_malloc(MAXDNAME * 2);
                    131:       daemon->workspacename = safe_malloc(MAXDNAME * 2);
1.1.1.4 ! misho     132:       /* one char flag per possible RR in answer section (may get extended). */
        !           133:       daemon->rr_status_sz = 64;
        !           134:       daemon->rr_status = safe_malloc(sizeof(*daemon->rr_status) * daemon->rr_status_sz);
1.1.1.2   misho     135:     }
                    136: #endif
1.1       misho     137: 
                    138: #ifdef HAVE_DHCP
                    139:   if (!daemon->lease_file)
                    140:     {
                    141:       if (daemon->dhcp || daemon->dhcp6)
                    142:        daemon->lease_file = LEASEFILE;
                    143:     }
                    144: #endif
                    145:   
1.1.1.4 ! misho     146:   /* Ensure that at least stdin, stdout and stderr (fd 0, 1, 2) exist,
1.1       misho     147:      otherwise file descriptors we create can end up being 0, 1, or 2 
                    148:      and then get accidentally closed later when we make 0, 1, and 2 
                    149:      open to /dev/null. Normally we'll be started with 0, 1 and 2 open, 
                    150:      but it's not guaranteed. By opening /dev/null three times, we 
                    151:      ensure that we're not using those fds for real stuff. */
1.1.1.4 ! misho     152:   for (i = 0; i < 3; i++)
        !           153:     open("/dev/null", O_RDWR); 
        !           154:   
        !           155:   /* Close any file descriptors we inherited apart from std{in|out|err} */
        !           156:   close_fds(max_fd, -1, -1, -1);
        !           157:   
1.1       misho     158: #ifndef HAVE_LINUX_NETWORK
                    159: #  if !(defined(IP_RECVDSTADDR) && defined(IP_RECVIF) && defined(IP_SENDSRCADDR))
                    160:   if (!option_bool(OPT_NOWILD))
                    161:     {
                    162:       bind_fallback = 1;
                    163:       set_option_bool(OPT_NOWILD);
                    164:     }
                    165: #  endif
                    166:   
                    167:   /* -- bind-dynamic not supported on !Linux, fall back to --bind-interfaces */
                    168:   if (option_bool(OPT_CLEVERBIND))
                    169:     {
                    170:       bind_fallback = 1;
                    171:       set_option_bool(OPT_NOWILD);
                    172:       reset_option_bool(OPT_CLEVERBIND);
                    173:     }
                    174: #endif
1.1.1.3   misho     175: 
                    176: #ifndef HAVE_INOTIFY
                    177:   if (daemon->dynamic_dirs)
                    178:     die(_("dhcp-hostsdir, dhcp-optsdir and hostsdir are not supported on this platform"), NULL, EC_BADCONF);
                    179: #endif
1.1       misho     180:   
1.1.1.2   misho     181:   if (option_bool(OPT_DNSSEC_VALID))
                    182:     {
                    183: #ifdef HAVE_DNSSEC
1.1.1.3   misho     184:       struct ds_config *ds;
                    185: 
                    186:       /* Must have at least a root trust anchor, or the DNSSEC code
                    187:         can loop forever. */
                    188:       for (ds = daemon->ds; ds; ds = ds->next)
                    189:        if (ds->name[0] == 0)
                    190:          break;
                    191: 
                    192:       if (!ds)
                    193:        die(_("no root trust anchor provided for DNSSEC"), NULL, EC_BADCONF);
1.1.1.2   misho     194:       
                    195:       if (daemon->cachesize < CACHESIZ)
1.1.1.3   misho     196:        die(_("cannot reduce cache size from default when DNSSEC enabled"), NULL, EC_BADCONF);
1.1.1.2   misho     197: #else 
                    198:       die(_("DNSSEC not available: set HAVE_DNSSEC in src/config.h"), NULL, EC_BADCONF);
                    199: #endif
                    200:     }
                    201: 
1.1       misho     202: #ifndef HAVE_TFTP
                    203:   if (option_bool(OPT_TFTP))
                    204:     die(_("TFTP server not available: set HAVE_TFTP in src/config.h"), NULL, EC_BADCONF);
                    205: #endif
                    206: 
                    207: #ifdef HAVE_CONNTRACK
                    208:   if (option_bool(OPT_CONNTRACK) && (daemon->query_port != 0 || daemon->osport))
1.1.1.3   misho     209:     die (_("cannot use --conntrack AND --query-port"), NULL, EC_BADCONF); 
1.1       misho     210: #else
                    211:   if (option_bool(OPT_CONNTRACK))
1.1.1.3   misho     212:     die(_("conntrack support not available: set HAVE_CONNTRACK in src/config.h"), NULL, EC_BADCONF);
1.1       misho     213: #endif
                    214: 
                    215: #ifdef HAVE_SOLARIS_NETWORK
                    216:   if (daemon->max_logs != 0)
1.1.1.4 ! misho     217:     die(_("asynchronous logging is not available under Solaris"), NULL, EC_BADCONF);
1.1       misho     218: #endif
                    219:   
                    220: #ifdef __ANDROID__
                    221:   if (daemon->max_logs != 0)
1.1.1.4 ! misho     222:     die(_("asynchronous logging is not available under Android"), NULL, EC_BADCONF);
1.1       misho     223: #endif
                    224: 
                    225: #ifndef HAVE_AUTH
1.1.1.4 ! misho     226:   if (daemon->auth_zones)
1.1       misho     227:     die(_("authoritative DNS not available: set HAVE_AUTH in src/config.h"), NULL, EC_BADCONF);
                    228: #endif
                    229: 
1.1.1.3   misho     230: #ifndef HAVE_LOOP
                    231:   if (option_bool(OPT_LOOP_DETECT))
                    232:     die(_("loop detection not available: set HAVE_LOOP in src/config.h"), NULL, EC_BADCONF);
                    233: #endif
                    234: 
1.1.1.4 ! misho     235: #ifndef HAVE_UBUS
        !           236:   if (option_bool(OPT_UBUS))
        !           237:     die(_("Ubus not available: set HAVE_UBUS in src/config.h"), NULL, EC_BADCONF);
        !           238: #endif
        !           239:   
1.1.1.3   misho     240:   if (daemon->max_port < daemon->min_port)
                    241:     die(_("max_port cannot be smaller than min_port"), NULL, EC_BADCONF);
                    242: 
1.1       misho     243:   now = dnsmasq_time();
                    244: 
1.1.1.4 ! misho     245:   if (daemon->auth_zones)
        !           246:     {
        !           247:       if (!daemon->authserver)
        !           248:        die(_("--auth-server required when an auth zone is defined."), NULL, EC_BADCONF);
        !           249: 
        !           250:       /* Create a serial at startup if not configured. */
1.1       misho     251: #ifdef HAVE_BROKEN_RTC
1.1.1.4 ! misho     252:       if (daemon->soa_sn == 0)
        !           253:        die(_("zone serial must be configured in --auth-soa"), NULL, EC_BADCONF);
1.1       misho     254: #else
1.1.1.4 ! misho     255:       if (daemon->soa_sn == 0)
        !           256:        daemon->soa_sn = now;
1.1       misho     257: #endif
1.1.1.4 ! misho     258:     }
1.1       misho     259:   
1.1.1.2   misho     260: #ifdef HAVE_DHCP6
                    261:   if (daemon->dhcp6)
                    262:     {
                    263:       daemon->doing_ra = option_bool(OPT_RA);
1.1       misho     264:       
1.1.1.2   misho     265:       for (context = daemon->dhcp6; context; context = context->next)
1.1       misho     266:        {
1.1.1.2   misho     267:          if (context->flags & CONTEXT_DHCP)
                    268:            daemon->doing_dhcp6 = 1;
                    269:          if (context->flags & CONTEXT_RA)
                    270:            daemon->doing_ra = 1;
                    271: #if !defined(HAVE_LINUX_NETWORK) && !defined(HAVE_BSD_NETWORK)
                    272:          if (context->flags & CONTEXT_TEMPLATE)
                    273:            die (_("dhcp-range constructor not available on this platform"), NULL, EC_BADCONF);
1.1       misho     274: #endif 
                    275:        }
1.1.1.2   misho     276:     }
                    277: #endif
                    278:   
                    279: #ifdef HAVE_DHCP
                    280:   /* Note that order matters here, we must call lease_init before
                    281:      creating any file descriptors which shouldn't be leaked
                    282:      to the lease-script init process. We need to call common_init
1.1.1.3   misho     283:      before lease_init to allocate buffers it uses.
                    284:      The script subsystem relies on DHCP buffers, hence the last two
                    285:      conditions below. */  
                    286:   if (daemon->dhcp || daemon->doing_dhcp6 || daemon->relay4 || 
                    287:       daemon->relay6 || option_bool(OPT_TFTP) || option_bool(OPT_SCRIPT_ARP))
1.1.1.2   misho     288:     {
                    289:       dhcp_common_init();
1.1       misho     290:       if (daemon->dhcp || daemon->doing_dhcp6)
1.1.1.2   misho     291:        lease_init(now);
                    292:     }
                    293:   
                    294:   if (daemon->dhcp || daemon->relay4)
1.1.1.4 ! misho     295:     {
        !           296:       dhcp_init();
        !           297: #   ifdef HAVE_LINUX_NETWORK
        !           298:       if (!option_bool(OPT_NO_PING))
        !           299:        need_cap_net_raw = 1;
        !           300:       need_cap_net_admin = 1;
        !           301: #   endif
        !           302:     }
1.1.1.2   misho     303:   
1.1       misho     304: #  ifdef HAVE_DHCP6
1.1.1.2   misho     305:   if (daemon->doing_ra || daemon->doing_dhcp6 || daemon->relay6)
1.1.1.4 ! misho     306:     {
        !           307:       ra_init(now);
        !           308: #   ifdef HAVE_LINUX_NETWORK
        !           309:       need_cap_net_raw = 1;
        !           310:       need_cap_net_admin = 1;
        !           311: #   endif
        !           312:     }
1.1.1.2   misho     313:   
                    314:   if (daemon->doing_dhcp6 || daemon->relay6)
                    315:     dhcp6_init();
1.1       misho     316: #  endif
                    317: 
                    318: #endif
                    319: 
                    320: #ifdef HAVE_IPSET
                    321:   if (daemon->ipsets)
1.1.1.4 ! misho     322:     {
        !           323:       ipset_init();
        !           324: #  ifdef HAVE_LINUX_NETWORK
        !           325:       need_cap_net_admin = 1;
        !           326: #  endif
        !           327:     }
1.1       misho     328: #endif
                    329: 
1.1.1.2   misho     330: #if  defined(HAVE_LINUX_NETWORK)
1.1.1.4 ! misho     331:   netlink_warn = netlink_init();
1.1.1.2   misho     332: #elif defined(HAVE_BSD_NETWORK)
                    333:   route_init();
1.1       misho     334: #endif
                    335: 
1.1.1.2   misho     336:   if (option_bool(OPT_NOWILD) && option_bool(OPT_CLEVERBIND))
                    337:     die(_("cannot set --bind-interfaces and --bind-dynamic"), NULL, EC_BADCONF);
                    338:   
                    339:   if (!enumerate_interfaces(1) || !enumerate_interfaces(0))
1.1       misho     340:     die(_("failed to find list of interfaces: %s"), NULL, EC_MISC);
                    341:   
                    342:   if (option_bool(OPT_NOWILD) || option_bool(OPT_CLEVERBIND)) 
                    343:     {
                    344:       create_bound_listeners(1);
                    345:       
                    346:       if (!option_bool(OPT_CLEVERBIND))
                    347:        for (if_tmp = daemon->if_names; if_tmp; if_tmp = if_tmp->next)
                    348:          if (if_tmp->name && !if_tmp->used)
                    349:            die(_("unknown interface %s"), if_tmp->name, EC_BADNET);
                    350: 
                    351: #if defined(HAVE_LINUX_NETWORK) && defined(HAVE_DHCP)
                    352:       /* after enumerate_interfaces()  */
1.1.1.2   misho     353:       bound_device = whichdevice();
                    354:       
1.1       misho     355:       if (daemon->dhcp)
                    356:        {
1.1.1.2   misho     357:          if (!daemon->relay4 && bound_device)
                    358:            {
                    359:              bindtodevice(bound_device, daemon->dhcpfd);
                    360:              did_bind = 1;
                    361:            }
                    362:          if (daemon->enable_pxe && bound_device)
                    363:            {
                    364:              bindtodevice(bound_device, daemon->pxefd);
                    365:              did_bind = 1;
                    366:            }
1.1       misho     367:        }
                    368: #endif
                    369: 
                    370: #if defined(HAVE_LINUX_NETWORK) && defined(HAVE_DHCP6)
1.1.1.2   misho     371:       if (daemon->doing_dhcp6 && !daemon->relay6 && bound_device)
                    372:        {
                    373:          bindtodevice(bound_device, daemon->dhcp6fd);
                    374:          did_bind = 1;
                    375:        }
1.1       misho     376: #endif
                    377:     }
                    378:   else 
                    379:     create_wildcard_listeners();
                    380:  
                    381: #ifdef HAVE_DHCP6
                    382:   /* after enumerate_interfaces() */
1.1.1.2   misho     383:   if (daemon->doing_dhcp6 || daemon->relay6 || daemon->doing_ra)
1.1       misho     384:     join_multicast(1);
1.1.1.2   misho     385: 
                    386:   /* After netlink_init() and before create_helper() */
                    387:   lease_make_duid(now);
1.1       misho     388: #endif
                    389:   
                    390:   if (daemon->port != 0)
1.1.1.2   misho     391:     {
                    392:       cache_init();
                    393:       blockdata_init();
1.1.1.4 ! misho     394:       hash_questions_init();
1.1.1.2   misho     395:     }
1.1.1.3   misho     396: 
                    397: #ifdef HAVE_INOTIFY
1.1.1.4 ! misho     398:   if ((daemon->port != 0 || daemon->dhcp || daemon->doing_dhcp6)
        !           399:       && (!option_bool(OPT_NO_RESOLV) || daemon->dynamic_dirs))
1.1.1.3   misho     400:     inotify_dnsmasq_init();
                    401:   else
                    402:     daemon->inotifyfd = -1;
                    403: #endif
1.1.1.4 ! misho     404: 
        !           405:   if (daemon->dump_file)
        !           406: #ifdef HAVE_DUMPFILE
        !           407:     dump_init();
        !           408:   else 
        !           409:     daemon->dumpfd = -1;
        !           410: #else
        !           411:   die(_("Packet dumps not available: set HAVE_DUMP in src/config.h"), NULL, EC_BADCONF);
        !           412: #endif
        !           413:   
1.1       misho     414:   if (option_bool(OPT_DBUS))
                    415: #ifdef HAVE_DBUS
                    416:     {
                    417:       char *err;
                    418:       daemon->dbus = NULL;
                    419:       daemon->watches = NULL;
                    420:       if ((err = dbus_init()))
                    421:        die(_("DBus error: %s"), err, EC_MISC);
                    422:     }
                    423: #else
                    424:   die(_("DBus not available: set HAVE_DBUS in src/config.h"), NULL, EC_BADCONF);
                    425: #endif
1.1.1.3   misho     426: 
1.1.1.4 ! misho     427:   if (option_bool(OPT_UBUS))
        !           428: #ifdef HAVE_UBUS
        !           429:     {
        !           430:       daemon->ubus = NULL;
        !           431:       ubus_init();
        !           432:     }
        !           433: #else
        !           434:   die(_("UBus not available: set HAVE_UBUS in src/config.h"), NULL, EC_BADCONF);
        !           435: #endif
        !           436: 
1.1       misho     437:   if (daemon->port != 0)
                    438:     pre_allocate_sfds();
                    439: 
                    440: #if defined(HAVE_SCRIPT)
                    441:   /* Note getpwnam returns static storage */
                    442:   if ((daemon->dhcp || daemon->dhcp6) && 
                    443:       daemon->scriptuser && 
                    444:       (daemon->lease_change_command || daemon->luascript))
                    445:     {
1.1.1.4 ! misho     446:       struct passwd *scr_pw;
        !           447:       
        !           448:       if ((scr_pw = getpwnam(daemon->scriptuser)))
1.1       misho     449:        {
1.1.1.4 ! misho     450:          script_uid = scr_pw->pw_uid;
        !           451:          script_gid = scr_pw->pw_gid;
1.1       misho     452:         }
                    453:       else
                    454:        baduser = daemon->scriptuser;
                    455:     }
                    456: #endif
                    457:   
                    458:   if (daemon->username && !(ent_pw = getpwnam(daemon->username)))
                    459:     baduser = daemon->username;
                    460:   else if (daemon->groupname && !(gp = getgrnam(daemon->groupname)))
                    461:     baduser = daemon->groupname;
                    462: 
                    463:   if (baduser)
                    464:     die(_("unknown user or group: %s"), baduser, EC_BADCONF);
1.1.1.3   misho     465: 
1.1       misho     466:   /* implement group defaults, "dip" if available, or group associated with uid */
                    467:   if (!daemon->group_set && !gp)
                    468:     {
                    469:       if (!(gp = getgrnam(CHGRP)) && ent_pw)
                    470:        gp = getgrgid(ent_pw->pw_gid);
                    471:       
                    472:       /* for error message */
                    473:       if (gp)
                    474:        daemon->groupname = gp->gr_name; 
                    475:     }
                    476: 
                    477: #if defined(HAVE_LINUX_NETWORK)
1.1.1.4 ! misho     478:   /* We keep CAP_NETADMIN (for ARP-injection) and
        !           479:      CAP_NET_RAW (for icmp) if we're doing dhcp,
        !           480:      if we have yet to bind ports because of DAD, 
        !           481:      or we're doing it dynamically, we need CAP_NET_BIND_SERVICE. */
        !           482:   if ((is_dad_listeners() || option_bool(OPT_CLEVERBIND)) &&
        !           483:       (option_bool(OPT_TFTP) || (daemon->port != 0 && daemon->port <= 1024)))
        !           484:     need_cap_net_bind_service = 1;
        !           485: 
        !           486:   /* usptream servers which bind to an interface call SO_BINDTODEVICE
        !           487:      for each TCP connection, so need CAP_NET_RAW */
        !           488:   for (serv = daemon->servers; serv; serv = serv->next)
        !           489:     if (serv->interface[0] != 0)
        !           490:       need_cap_net_raw = 1;
        !           491: 
        !           492:   /* If we're doing Dbus or UBus, the above can be set dynamically,
        !           493:      (as can ports) so always (potentially) needed. */
        !           494: #ifdef HAVE_DBUS
        !           495:   if (option_bool(OPT_DBUS))
        !           496:     {
        !           497:       need_cap_net_bind_service = 1;
        !           498:       need_cap_net_raw = 1;
        !           499:     }
        !           500: #endif
        !           501: 
        !           502: #ifdef HAVE_UBUS
        !           503:   if (option_bool(OPT_UBUS))
        !           504:     {
        !           505:       need_cap_net_bind_service = 1;
        !           506:       need_cap_net_raw = 1;
        !           507:     }
        !           508: #endif
        !           509:   
1.1       misho     510:   /* determine capability API version here, while we can still
                    511:      call safe_malloc */
1.1.1.4 ! misho     512:   int capsize = 1; /* for header version 1 */
        !           513:   char *fail = NULL;
        !           514:   
        !           515:   hdr = safe_malloc(sizeof(*hdr));
        !           516:   
        !           517:   /* find version supported by kernel */
        !           518:   memset(hdr, 0, sizeof(*hdr));
        !           519:   capget(hdr, NULL);
        !           520:   
        !           521:   if (hdr->version != LINUX_CAPABILITY_VERSION_1)
1.1       misho     522:     {
1.1.1.4 ! misho     523:       /* if unknown version, use largest supported version (3) */
        !           524:       if (hdr->version != LINUX_CAPABILITY_VERSION_2)
        !           525:        hdr->version = LINUX_CAPABILITY_VERSION_3;
        !           526:       capsize = 2;
1.1       misho     527:     }
1.1.1.4 ! misho     528:   
        !           529:   data = safe_malloc(sizeof(*data) * capsize);
        !           530:   capget(hdr, data); /* Get current values, for verification */
        !           531: 
        !           532:   if (need_cap_net_admin && !(data->permitted & (1 << CAP_NET_ADMIN)))
        !           533:     fail = "NET_ADMIN";
        !           534:   else if (need_cap_net_raw && !(data->permitted & (1 << CAP_NET_RAW)))
        !           535:     fail = "NET_RAW";
        !           536:   else if (need_cap_net_bind_service && !(data->permitted & (1 << CAP_NET_BIND_SERVICE)))
        !           537:     fail = "NET_BIND_SERVICE";
        !           538:   
        !           539:   if (fail)
        !           540:     die(_("process is missing required capability %s"), fail, EC_MISC);
        !           541: 
        !           542:   /* Now set bitmaps to set caps after daemonising */
        !           543:   memset(data, 0, sizeof(*data) * capsize);
        !           544:   
        !           545:   if (need_cap_net_admin)
        !           546:     data->effective |= (1 << CAP_NET_ADMIN);
        !           547:   if (need_cap_net_raw)
        !           548:     data->effective |= (1 << CAP_NET_RAW);
        !           549:   if (need_cap_net_bind_service)
        !           550:     data->effective |= (1 << CAP_NET_BIND_SERVICE);
        !           551:   
        !           552:   data->permitted = data->effective;  
1.1       misho     553: #endif
                    554: 
                    555:   /* Use a pipe to carry signals and other events back to the event loop 
                    556:      in a race-free manner and another to carry errors to daemon-invoking process */
                    557:   safe_pipe(pipefd, 1);
                    558:   
                    559:   piperead = pipefd[0];
                    560:   pipewrite = pipefd[1];
                    561:   /* prime the pipe to load stuff first time. */
1.1.1.2   misho     562:   send_event(pipewrite, EVENT_INIT, 0, NULL); 
1.1       misho     563: 
                    564:   err_pipe[1] = -1;
                    565:   
                    566:   if (!option_bool(OPT_DEBUG))   
                    567:     {
                    568:       /* The following code "daemonizes" the process. 
                    569:         See Stevens section 12.4 */
                    570:       
                    571:       if (chdir("/") != 0)
                    572:        die(_("cannot chdir to filesystem root: %s"), NULL, EC_MISC); 
                    573: 
                    574:       if (!option_bool(OPT_NO_FORK))
                    575:        {
                    576:          pid_t pid;
                    577:          
                    578:          /* pipe to carry errors back to original process.
                    579:             When startup is complete we close this and the process terminates. */
                    580:          safe_pipe(err_pipe, 0);
                    581:          
                    582:          if ((pid = fork()) == -1)
                    583:            /* fd == -1 since we've not forked, never returns. */
                    584:            send_event(-1, EVENT_FORK_ERR, errno, NULL);
                    585:           
                    586:          if (pid != 0)
                    587:            {
                    588:              struct event_desc ev;
                    589:              char *msg;
                    590: 
                    591:              /* close our copy of write-end */
1.1.1.4 ! misho     592:              close(err_pipe[1]);
1.1       misho     593:              
                    594:              /* check for errors after the fork */
                    595:              if (read_event(err_pipe[0], &ev, &msg))
                    596:                fatal_event(&ev, msg);
                    597:              
                    598:              _exit(EC_GOOD);
                    599:            } 
                    600:          
1.1.1.4 ! misho     601:          close(err_pipe[0]);
1.1       misho     602: 
                    603:          /* NO calls to die() from here on. */
                    604:          
                    605:          setsid();
                    606:         
                    607:          if ((pid = fork()) == -1)
                    608:            send_event(err_pipe[1], EVENT_FORK_ERR, errno, NULL);
                    609:         
                    610:          if (pid != 0)
                    611:            _exit(0);
                    612:        }
                    613:             
                    614:       /* write pidfile _after_ forking ! */
                    615:       if (daemon->runfile)
                    616:        {
                    617:          int fd, err = 0;
                    618: 
                    619:          sprintf(daemon->namebuff, "%d\n", (int) getpid());
                    620: 
                    621:          /* Explanation: Some installations of dnsmasq (eg Debian/Ubuntu) locate the pid-file
                    622:             in a directory which is writable by the non-privileged user that dnsmasq runs as. This
                    623:             allows the daemon to delete the file as part of its shutdown. This is a security hole to the 
                    624:             extent that an attacker running as the unprivileged  user could replace the pidfile with a 
                    625:             symlink, and have the target of that symlink overwritten as root next time dnsmasq starts. 
                    626: 
1.1.1.4 ! misho     627:             The following code first deletes any existing file, and then opens it with the O_EXCL flag,
1.1       misho     628:             ensuring that the open() fails should there be any existing file (because the unlink() failed, 
                    629:             or an attacker exploited the race between unlink() and open()). This ensures that no symlink
                    630:             attack can succeed. 
                    631: 
                    632:             Any compromise of the non-privileged user still theoretically allows the pid-file to be
                    633:             replaced whilst dnsmasq is running. The worst that could allow is that the usual 
                    634:             "shutdown dnsmasq" shell command could be tricked into stopping any other process.
                    635: 
                    636:             Note that if dnsmasq is started as non-root (eg for testing) it silently ignores 
                    637:             failure to write the pid-file.
                    638:          */
                    639: 
                    640:          unlink(daemon->runfile); 
                    641:          
                    642:          if ((fd = open(daemon->runfile, O_WRONLY|O_CREAT|O_TRUNC|O_EXCL, S_IWUSR|S_IRUSR|S_IRGRP|S_IROTH)) == -1)
                    643:            {
                    644:              /* only complain if started as root */
                    645:              if (getuid() == 0)
                    646:                err = 1;
                    647:            }
                    648:          else
                    649:            {
1.1.1.4 ! misho     650:              /* We're still running as root here. Change the ownership of the PID file
        !           651:                 to the user we will be running as. Note that this is not to allow
        !           652:                 us to delete the file, since that depends on the permissions 
        !           653:                 of the directory containing the file. That directory will
        !           654:                 need to by owned by the dnsmasq user, and the ownership of the
        !           655:                 file has to match, to keep systemd >273 happy. */
        !           656:              if (getuid() == 0 && ent_pw && ent_pw->pw_uid != 0 && fchown(fd, ent_pw->pw_uid, ent_pw->pw_gid) == -1)
        !           657:                chown_warn = errno;
        !           658: 
1.1       misho     659:              if (!read_write(fd, (unsigned char *)daemon->namebuff, strlen(daemon->namebuff), 0))
                    660:                err = 1;
1.1.1.4 ! misho     661:              else
1.1.1.3   misho     662:                {
1.1.1.4 ! misho     663:                  if (close(fd) == -1)
1.1.1.3   misho     664:                    err = 1;
                    665:                }
1.1       misho     666:            }
                    667: 
                    668:          if (err)
                    669:            {
                    670:              send_event(err_pipe[1], EVENT_PIDFILE, errno, daemon->runfile);
                    671:              _exit(0);
                    672:            }
                    673:        }
                    674:     }
                    675:   
                    676:    log_err = log_start(ent_pw, err_pipe[1]);
                    677: 
                    678:    if (!option_bool(OPT_DEBUG)) 
                    679:      {       
                    680:        /* open  stdout etc to /dev/null */
                    681:        int nullfd = open("/dev/null", O_RDWR);
1.1.1.3   misho     682:        if (nullfd != -1)
                    683:         {
                    684:           dup2(nullfd, STDOUT_FILENO);
                    685:           dup2(nullfd, STDERR_FILENO);
                    686:           dup2(nullfd, STDIN_FILENO);
                    687:           close(nullfd);
                    688:         }
1.1       misho     689:      }
                    690:    
                    691:    /* if we are to run scripts, we need to fork a helper before dropping root. */
                    692:   daemon->helperfd = -1;
                    693: #ifdef HAVE_SCRIPT 
1.1.1.3   misho     694:   if ((daemon->dhcp || daemon->dhcp6 || option_bool(OPT_TFTP) || option_bool(OPT_SCRIPT_ARP)) && 
                    695:       (daemon->lease_change_command || daemon->luascript))
                    696:       daemon->helperfd = create_helper(pipewrite, err_pipe[1], script_uid, script_gid, max_fd);
1.1       misho     697: #endif
                    698: 
                    699:   if (!option_bool(OPT_DEBUG) && getuid() == 0)   
                    700:     {
                    701:       int bad_capabilities = 0;
                    702:       gid_t dummy;
                    703:       
1.1.1.4 ! misho     704:       /* remove all supplementary groups */
1.1       misho     705:       if (gp && 
                    706:          (setgroups(0, &dummy) == -1 ||
                    707:           setgid(gp->gr_gid) == -1))
                    708:        {
                    709:          send_event(err_pipe[1], EVENT_GROUP_ERR, errno, daemon->groupname);
                    710:          _exit(0);
                    711:        }
                    712:   
                    713:       if (ent_pw && ent_pw->pw_uid != 0)
                    714:        {     
                    715: #if defined(HAVE_LINUX_NETWORK)          
1.1.1.4 ! misho     716:          /* Need to be able to drop root. */
        !           717:          data->effective |= (1 << CAP_SETUID);
        !           718:          data->permitted |= (1 << CAP_SETUID);
1.1       misho     719:          /* Tell kernel to not clear capabilities when dropping root */
                    720:          if (capset(hdr, data) == -1 || prctl(PR_SET_KEEPCAPS, 1, 0, 0, 0) == -1)
                    721:            bad_capabilities = errno;
                    722:                          
                    723: #elif defined(HAVE_SOLARIS_NETWORK)
                    724:          /* http://developers.sun.com/solaris/articles/program_privileges.html */
                    725:          priv_set_t *priv_set;
                    726:          
                    727:          if (!(priv_set = priv_str_to_set("basic", ",", NULL)) ||
                    728:              priv_addset(priv_set, PRIV_NET_ICMPACCESS) == -1 ||
                    729:              priv_addset(priv_set, PRIV_SYS_NET_CONFIG) == -1)
                    730:            bad_capabilities = errno;
                    731: 
                    732:          if (priv_set && bad_capabilities == 0)
                    733:            {
                    734:              priv_inverse(priv_set);
                    735:          
                    736:              if (setppriv(PRIV_OFF, PRIV_LIMIT, priv_set) == -1)
                    737:                bad_capabilities = errno;
                    738:            }
                    739: 
                    740:          if (priv_set)
                    741:            priv_freeset(priv_set);
                    742: 
                    743: #endif    
                    744: 
                    745:          if (bad_capabilities != 0)
                    746:            {
                    747:              send_event(err_pipe[1], EVENT_CAP_ERR, bad_capabilities, NULL);
                    748:              _exit(0);
                    749:            }
                    750:          
                    751:          /* finally drop root */
                    752:          if (setuid(ent_pw->pw_uid) == -1)
                    753:            {
                    754:              send_event(err_pipe[1], EVENT_USER_ERR, errno, daemon->username);
                    755:              _exit(0);
                    756:            }     
                    757: 
                    758: #ifdef HAVE_LINUX_NETWORK
1.1.1.4 ! misho     759:          data->effective &= ~(1 << CAP_SETUID);
        !           760:          data->permitted &= ~(1 << CAP_SETUID);
1.1       misho     761:          
1.1.1.4 ! misho     762:          /* lose the setuid capability */
1.1       misho     763:          if (capset(hdr, data) == -1)
                    764:            {
                    765:              send_event(err_pipe[1], EVENT_CAP_ERR, errno, NULL);
                    766:              _exit(0);
                    767:            }
                    768: #endif
                    769:          
                    770:        }
                    771:     }
                    772:   
                    773: #ifdef HAVE_LINUX_NETWORK
1.1.1.3   misho     774:   free(hdr);
                    775:   free(data);
1.1       misho     776:   if (option_bool(OPT_DEBUG)) 
                    777:     prctl(PR_SET_DUMPABLE, 1, 0, 0, 0);
                    778: #endif
                    779: 
                    780: #ifdef HAVE_TFTP
1.1.1.3   misho     781:   if (option_bool(OPT_TFTP))
1.1       misho     782:     {
                    783:       DIR *dir;
                    784:       struct tftp_prefix *p;
                    785:       
                    786:       if (daemon->tftp_prefix)
                    787:        {
                    788:          if (!((dir = opendir(daemon->tftp_prefix))))
                    789:            {
1.1.1.3   misho     790:              tftp_prefix_missing = 1;
                    791:              if (!option_bool(OPT_TFTP_NO_FAIL))
                    792:                {
                    793:                  send_event(err_pipe[1], EVENT_TFTP_ERR, errno, daemon->tftp_prefix);
                    794:                  _exit(0);
                    795:                }
1.1       misho     796:            }
1.1.1.3   misho     797:          else
                    798:            closedir(dir);
1.1       misho     799:        }
                    800: 
                    801:       for (p = daemon->if_prefix; p; p = p->next)
                    802:        {
1.1.1.3   misho     803:          p->missing = 0;
1.1       misho     804:          if (!((dir = opendir(p->prefix))))
1.1.1.3   misho     805:            {
                    806:              p->missing = 1;
                    807:              if (!option_bool(OPT_TFTP_NO_FAIL))
                    808:                {
                    809:                  send_event(err_pipe[1], EVENT_TFTP_ERR, errno, p->prefix);
                    810:                  _exit(0);
                    811:                }
                    812:            }
                    813:          else
                    814:            closedir(dir);
1.1       misho     815:        }
                    816:     }
                    817: #endif
                    818: 
                    819:   if (daemon->port == 0)
                    820:     my_syslog(LOG_INFO, _("started, version %s DNS disabled"), VERSION);
1.1.1.4 ! misho     821:   else 
        !           822:     {
        !           823:       if (daemon->cachesize != 0)
        !           824:        {
        !           825:          my_syslog(LOG_INFO, _("started, version %s cachesize %d"), VERSION, daemon->cachesize);
        !           826:          if (daemon->cachesize > 10000)
        !           827:            my_syslog(LOG_WARNING, _("cache size greater than 10000 may cause performance issues, and is unlikely to be useful."));
        !           828:        }
        !           829:       else
        !           830:        my_syslog(LOG_INFO, _("started, version %s cache disabled"), VERSION);
        !           831: 
        !           832:       if (option_bool(OPT_LOCAL_SERVICE))
        !           833:        my_syslog(LOG_INFO, _("DNS service limited to local subnets"));
        !           834:     }
1.1       misho     835:   
                    836:   my_syslog(LOG_INFO, _("compile time options: %s"), compile_opts);
1.1.1.4 ! misho     837: 
        !           838:   if (chown_warn != 0)
        !           839:     my_syslog(LOG_WARNING, "chown of PID file %s failed: %s", daemon->runfile, strerror(chown_warn));
1.1       misho     840:   
                    841: #ifdef HAVE_DBUS
                    842:   if (option_bool(OPT_DBUS))
                    843:     {
                    844:       if (daemon->dbus)
                    845:        my_syslog(LOG_INFO, _("DBus support enabled: connected to system bus"));
                    846:       else
                    847:        my_syslog(LOG_INFO, _("DBus support enabled: bus connection pending"));
                    848:     }
                    849: #endif
                    850: 
1.1.1.4 ! misho     851: #ifdef HAVE_UBUS
        !           852:   if (option_bool(OPT_UBUS))
        !           853:     {
        !           854:       if (daemon->ubus)
        !           855:         my_syslog(LOG_INFO, _("UBus support enabled: connected to system bus"));
        !           856:       else
        !           857:         my_syslog(LOG_INFO, _("UBus support enabled: bus connection pending"));
        !           858:     }
        !           859: #endif
        !           860: 
1.1.1.2   misho     861: #ifdef HAVE_DNSSEC
                    862:   if (option_bool(OPT_DNSSEC_VALID))
                    863:     {
1.1.1.3   misho     864:       int rc;
1.1.1.4 ! misho     865:       struct ds_config *ds;
        !           866:       
1.1.1.3   misho     867:       /* Delay creating the timestamp file until here, after we've changed user, so that
                    868:         it has the correct owner to allow updating the mtime later. 
                    869:         This means we have to report fatal errors via the pipe. */
                    870:       if ((rc = setup_timestamp()) == -1)
                    871:        {
                    872:          send_event(err_pipe[1], EVENT_TIME_ERR, errno, daemon->timestamp_file);
                    873:          _exit(0);
                    874:        }
                    875:       
1.1.1.4 ! misho     876:       if (option_bool(OPT_DNSSEC_IGN_NS))
        !           877:        my_syslog(LOG_INFO, _("DNSSEC validation enabled but all unsigned answers are trusted"));
        !           878:       else
        !           879:        my_syslog(LOG_INFO, _("DNSSEC validation enabled"));
1.1.1.3   misho     880:       
1.1.1.4 ! misho     881:       daemon->dnssec_no_time_check = option_bool(OPT_DNSSEC_TIME);
        !           882:       if (option_bool(OPT_DNSSEC_TIME) && !daemon->back_to_the_future)
        !           883:        my_syslog(LOG_INFO, _("DNSSEC signature timestamps not checked until receipt of SIGINT"));
1.1.1.3   misho     884:       
                    885:       if (rc == 1)
                    886:        my_syslog(LOG_INFO, _("DNSSEC signature timestamps not checked until system time valid"));
1.1.1.4 ! misho     887: 
        !           888:       for (ds = daemon->ds; ds; ds = ds->next)
        !           889:        my_syslog(LOG_INFO, _("configured with trust anchor for %s keytag %u"),
        !           890:                  ds->name[0] == 0 ? "<root>" : ds->name, ds->keytag);
1.1.1.2   misho     891:     }
                    892: #endif
                    893: 
1.1       misho     894:   if (log_err != 0)
                    895:     my_syslog(LOG_WARNING, _("warning: failed to change owner of %s: %s"), 
                    896:              daemon->log_file, strerror(log_err));
1.1.1.2   misho     897:   
1.1       misho     898:   if (bind_fallback)
                    899:     my_syslog(LOG_WARNING, _("setting --bind-interfaces option because of OS limitations"));
1.1.1.2   misho     900: 
                    901:   if (option_bool(OPT_NOWILD))
                    902:     warn_bound_listeners();
1.1.1.4 ! misho     903:   else if (!option_bool(OPT_CLEVERBIND))
        !           904:     warn_wild_labels();
1.1.1.2   misho     905: 
                    906:   warn_int_names();
1.1       misho     907:   
                    908:   if (!option_bool(OPT_NOWILD)) 
                    909:     for (if_tmp = daemon->if_names; if_tmp; if_tmp = if_tmp->next)
                    910:       if (if_tmp->name && !if_tmp->used)
                    911:        my_syslog(LOG_WARNING, _("warning: interface %s does not currently exist"), if_tmp->name);
                    912:    
                    913:   if (daemon->port != 0 && option_bool(OPT_NO_RESOLV))
                    914:     {
                    915:       if (daemon->resolv_files && !daemon->resolv_files->is_default)
                    916:        my_syslog(LOG_WARNING, _("warning: ignoring resolv-file flag because no-resolv is set"));
                    917:       daemon->resolv_files = NULL;
                    918:       if (!daemon->servers)
                    919:        my_syslog(LOG_WARNING, _("warning: no upstream servers configured"));
                    920:     } 
                    921: 
                    922:   if (daemon->max_logs != 0)
                    923:     my_syslog(LOG_INFO, _("asynchronous logging enabled, queue limit is %d messages"), daemon->max_logs);
                    924:   
                    925: 
                    926: #ifdef HAVE_DHCP
                    927:   for (context = daemon->dhcp; context; context = context->next)
                    928:     log_context(AF_INET, context);
                    929: 
1.1.1.2   misho     930:   for (relay = daemon->relay4; relay; relay = relay->next)
                    931:     log_relay(AF_INET, relay);
                    932: 
1.1       misho     933: #  ifdef HAVE_DHCP6
                    934:   for (context = daemon->dhcp6; context; context = context->next)
                    935:     log_context(AF_INET6, context);
                    936: 
1.1.1.2   misho     937:   for (relay = daemon->relay6; relay; relay = relay->next)
                    938:     log_relay(AF_INET6, relay);
                    939:   
1.1       misho     940:   if (daemon->doing_dhcp6 || daemon->doing_ra)
                    941:     dhcp_construct_contexts(now);
                    942:   
                    943:   if (option_bool(OPT_RA))
                    944:     my_syslog(MS_DHCP | LOG_INFO, _("IPv6 router advertisement enabled"));
                    945: #  endif
                    946: 
1.1.1.2   misho     947: #  ifdef HAVE_LINUX_NETWORK
                    948:   if (did_bind)
                    949:     my_syslog(MS_DHCP | LOG_INFO, _("DHCP, sockets bound exclusively to interface %s"), bound_device);
1.1.1.4 ! misho     950: 
        !           951:   if (netlink_warn)
        !           952:     my_syslog(LOG_WARNING, netlink_warn);
1.1.1.2   misho     953: #  endif
                    954: 
1.1.1.4 ! misho     955:   /* after dhcp_construct_contexts */
1.1       misho     956:   if (daemon->dhcp || daemon->doing_dhcp6)
                    957:     lease_find_interfaces(now);
                    958: #endif
                    959: 
                    960: #ifdef HAVE_TFTP
1.1.1.3   misho     961:   if (option_bool(OPT_TFTP))
1.1       misho     962:     {
1.1.1.3   misho     963:       struct tftp_prefix *p;
1.1       misho     964: 
1.1.1.4 ! misho     965:       my_syslog(MS_TFTP | LOG_INFO, "TFTP %s%s %s %s", 
1.1       misho     966:                daemon->tftp_prefix ? _("root is ") : _("enabled"),
1.1.1.4 ! misho     967:                daemon->tftp_prefix ? daemon->tftp_prefix : "",
        !           968:                option_bool(OPT_TFTP_SECURE) ? _("secure mode") : "",
        !           969:                option_bool(OPT_SINGLE_PORT) ? _("single port mode") : "");
1.1.1.3   misho     970: 
                    971:       if (tftp_prefix_missing)
                    972:        my_syslog(MS_TFTP | LOG_WARNING, _("warning: %s inaccessible"), daemon->tftp_prefix);
                    973: 
                    974:       for (p = daemon->if_prefix; p; p = p->next)
                    975:        if (p->missing)
                    976:           my_syslog(MS_TFTP | LOG_WARNING, _("warning: TFTP directory %s inaccessible"), p->prefix);
                    977: 
1.1       misho     978:       /* This is a guess, it assumes that for small limits, 
                    979:         disjoint files might be served, but for large limits, 
                    980:         a single file will be sent to may clients (the file only needs
                    981:         one fd). */
                    982: 
                    983:       max_fd -= 30; /* use other than TFTP */
                    984:       
                    985:       if (max_fd < 0)
                    986:        max_fd = 5;
1.1.1.4 ! misho     987:       else if (max_fd < 100 && !option_bool(OPT_SINGLE_PORT))
1.1       misho     988:        max_fd = max_fd/2;
                    989:       else
                    990:        max_fd = max_fd - 20;
                    991:       
                    992:       /* if we have to use a limited range of ports, 
                    993:         that will limit the number of transfers */
                    994:       if (daemon->start_tftp_port != 0 &&
                    995:          daemon->end_tftp_port - daemon->start_tftp_port + 1 < max_fd)
                    996:        max_fd = daemon->end_tftp_port - daemon->start_tftp_port + 1;
                    997: 
                    998:       if (daemon->tftp_max > max_fd)
                    999:        {
                   1000:          daemon->tftp_max = max_fd;
                   1001:          my_syslog(MS_TFTP | LOG_WARNING, 
                   1002:                    _("restricting maximum simultaneous TFTP transfers to %d"), 
                   1003:                    daemon->tftp_max);
                   1004:        }
                   1005:     }
                   1006: #endif
                   1007: 
                   1008:   /* finished start-up - release original process */
                   1009:   if (err_pipe[1] != -1)
1.1.1.4 ! misho    1010:     close(err_pipe[1]);
1.1       misho    1011:   
                   1012:   if (daemon->port != 0)
                   1013:     check_servers();
                   1014:   
                   1015:   pid = getpid();
1.1.1.4 ! misho    1016: 
        !          1017:   daemon->pipe_to_parent = -1;
        !          1018:   for (i = 0; i < MAX_PROCS; i++)
        !          1019:     daemon->tcp_pipes[i] = -1;
1.1       misho    1020:   
1.1.1.3   misho    1021: #ifdef HAVE_INOTIFY
                   1022:   /* Using inotify, have to select a resolv file at startup */
                   1023:   poll_resolv(1, 0, now);
                   1024: #endif
                   1025:   
1.1       misho    1026:   while (1)
                   1027:     {
1.1.1.3   misho    1028:       int t, timeout = -1;
                   1029:       
                   1030:       poll_reset();
1.1       misho    1031:       
                   1032:       /* if we are out of resources, find how long we have to wait
                   1033:         for some to come free, we'll loop around then and restart
                   1034:         listening for queries */
1.1.1.3   misho    1035:       if ((t = set_dns_listeners(now)) != 0)
                   1036:        timeout = t * 1000;
1.1       misho    1037: 
                   1038:       /* Whilst polling for the dbus, or doing a tftp transfer, wake every quarter second */
                   1039:       if (daemon->tftp_trans ||
                   1040:          (option_bool(OPT_DBUS) && !daemon->dbus))
1.1.1.3   misho    1041:        timeout = 250;
                   1042: 
1.1       misho    1043:       /* Wake every second whilst waiting for DAD to complete */
                   1044:       else if (is_dad_listeners())
1.1.1.3   misho    1045:        timeout = 1000;
1.1       misho    1046: 
                   1047: #ifdef HAVE_DBUS
1.1.1.3   misho    1048:       set_dbus_listeners();
1.1.1.4 ! misho    1049: #endif
        !          1050: 
        !          1051: #ifdef HAVE_UBUS
        !          1052:       if (option_bool(OPT_UBUS))
        !          1053:         set_ubus_listeners();
        !          1054: #endif
        !          1055:          
1.1       misho    1056: #ifdef HAVE_DHCP
1.1.1.2   misho    1057:       if (daemon->dhcp || daemon->relay4)
1.1       misho    1058:        {
1.1.1.3   misho    1059:          poll_listen(daemon->dhcpfd, POLLIN);
1.1       misho    1060:          if (daemon->pxefd != -1)
1.1.1.3   misho    1061:            poll_listen(daemon->pxefd, POLLIN);
1.1       misho    1062:        }
                   1063: #endif
                   1064: 
                   1065: #ifdef HAVE_DHCP6
1.1.1.2   misho    1066:       if (daemon->doing_dhcp6 || daemon->relay6)
1.1.1.3   misho    1067:        poll_listen(daemon->dhcp6fd, POLLIN);
                   1068:        
1.1       misho    1069:       if (daemon->doing_ra)
1.1.1.3   misho    1070:        poll_listen(daemon->icmp6fd, POLLIN); 
                   1071: #endif
                   1072:     
                   1073: #ifdef HAVE_INOTIFY
                   1074:       if (daemon->inotifyfd != -1)
                   1075:        poll_listen(daemon->inotifyfd, POLLIN);
1.1       misho    1076: #endif
                   1077: 
1.1.1.2   misho    1078: #if defined(HAVE_LINUX_NETWORK)
1.1.1.3   misho    1079:       poll_listen(daemon->netlinkfd, POLLIN);
1.1.1.2   misho    1080: #elif defined(HAVE_BSD_NETWORK)
1.1.1.3   misho    1081:       poll_listen(daemon->routefd, POLLIN);
1.1       misho    1082: #endif
1.1.1.3   misho    1083:       
                   1084:       poll_listen(piperead, POLLIN);
1.1.1.2   misho    1085: 
1.1.1.3   misho    1086: #ifdef HAVE_SCRIPT
                   1087: #    ifdef HAVE_DHCP
                   1088:       while (helper_buf_empty() && do_script_run(now)); 
                   1089: #    endif
1.1       misho    1090: 
1.1.1.3   misho    1091:       /* Refresh cache */
                   1092:       if (option_bool(OPT_SCRIPT_ARP))
                   1093:        find_mac(NULL, NULL, 0, now);
                   1094:       while (helper_buf_empty() && do_arp_script_run());
1.1       misho    1095: 
                   1096: #    ifdef HAVE_TFTP
                   1097:       while (helper_buf_empty() && do_tftp_script_run());
                   1098: #    endif
                   1099: 
                   1100:       if (!helper_buf_empty())
1.1.1.3   misho    1101:        poll_listen(daemon->helperfd, POLLOUT);
                   1102: #else
1.1       misho    1103:       /* need this for other side-effects */
1.1.1.3   misho    1104: #    ifdef HAVE_DHCP
1.1       misho    1105:       while (do_script_run(now));
1.1.1.3   misho    1106: #    endif
                   1107: 
                   1108:       while (do_arp_script_run());
1.1       misho    1109: 
                   1110: #    ifdef HAVE_TFTP 
                   1111:       while (do_tftp_script_run());
                   1112: #    endif
                   1113: 
                   1114: #endif
1.1.1.3   misho    1115: 
1.1       misho    1116:    
1.1.1.4 ! misho    1117:       /* must do this just before do_poll(), when we know no
1.1       misho    1118:         more calls to my_syslog() can occur */
1.1.1.3   misho    1119:       set_log_writer();
                   1120:       
                   1121:       if (do_poll(timeout) < 0)
                   1122:        continue;
1.1       misho    1123:       
                   1124:       now = dnsmasq_time();
                   1125: 
1.1.1.3   misho    1126:       check_log_writer(0);
1.1.1.2   misho    1127: 
                   1128:       /* prime. */
                   1129:       enumerate_interfaces(1);
                   1130: 
1.1       misho    1131:       /* Check the interfaces to see if any have exited DAD state
                   1132:         and if so, bind the address. */
                   1133:       if (is_dad_listeners())
                   1134:        {
1.1.1.2   misho    1135:          enumerate_interfaces(0);
1.1       misho    1136:          /* NB, is_dad_listeners() == 1 --> we're binding interfaces */
                   1137:          create_bound_listeners(0);
1.1.1.2   misho    1138:          warn_bound_listeners();
1.1       misho    1139:        }
                   1140: 
1.1.1.2   misho    1141: #if defined(HAVE_LINUX_NETWORK)
1.1.1.3   misho    1142:       if (poll_check(daemon->netlinkfd, POLLIN))
                   1143:        netlink_multicast();
1.1.1.2   misho    1144: #elif defined(HAVE_BSD_NETWORK)
1.1.1.3   misho    1145:       if (poll_check(daemon->routefd, POLLIN))
                   1146:        route_sock();
1.1       misho    1147: #endif
                   1148: 
1.1.1.3   misho    1149: #ifdef HAVE_INOTIFY
                   1150:       if  (daemon->inotifyfd != -1 && poll_check(daemon->inotifyfd, POLLIN) && inotify_check(now))
                   1151:        {
                   1152:          if (daemon->port != 0 && !option_bool(OPT_NO_POLL))
                   1153:            poll_resolv(1, 1, now);
                   1154:        }         
                   1155: #else
1.1       misho    1156:       /* Check for changes to resolv files once per second max. */
                   1157:       /* Don't go silent for long periods if the clock goes backwards. */
                   1158:       if (daemon->last_resolv == 0 || 
                   1159:          difftime(now, daemon->last_resolv) > 1.0 || 
                   1160:          difftime(now, daemon->last_resolv) < -1.0)
                   1161:        {
                   1162:          /* poll_resolv doesn't need to reload first time through, since 
                   1163:             that's queued anyway. */
                   1164: 
                   1165:          poll_resolv(0, daemon->last_resolv != 0, now);          
                   1166:          daemon->last_resolv = now;
                   1167:        }
1.1.1.3   misho    1168: #endif
                   1169: 
                   1170:       if (poll_check(piperead, POLLIN))
1.1       misho    1171:        async_event(piperead, now);
                   1172:       
                   1173: #ifdef HAVE_DBUS
                   1174:       /* if we didn't create a DBus connection, retry now. */ 
                   1175:      if (option_bool(OPT_DBUS) && !daemon->dbus)
                   1176:        {
                   1177:          char *err;
                   1178:          if ((err = dbus_init()))
                   1179:            my_syslog(LOG_WARNING, _("DBus error: %s"), err);
                   1180:          if (daemon->dbus)
                   1181:            my_syslog(LOG_INFO, _("connected to system DBus"));
                   1182:        }
1.1.1.3   misho    1183:       check_dbus_listeners();
1.1       misho    1184: #endif
1.1.1.4 ! misho    1185: 
        !          1186: #ifdef HAVE_UBUS
        !          1187:       if (option_bool(OPT_UBUS))
        !          1188:         {
        !          1189:           /* if we didn't create a UBus connection, retry now. */
        !          1190:           if (!daemon->ubus)
        !          1191:             {
        !          1192:               ubus_init();
        !          1193:             }
        !          1194: 
        !          1195:           check_ubus_listeners();
        !          1196:         }
        !          1197: #endif
        !          1198: 
1.1.1.3   misho    1199:       check_dns_listeners(now);
1.1       misho    1200: 
                   1201: #ifdef HAVE_TFTP
1.1.1.3   misho    1202:       check_tftp_listeners(now);
1.1       misho    1203: #endif      
                   1204: 
                   1205: #ifdef HAVE_DHCP
1.1.1.2   misho    1206:       if (daemon->dhcp || daemon->relay4)
1.1       misho    1207:        {
1.1.1.3   misho    1208:          if (poll_check(daemon->dhcpfd, POLLIN))
1.1       misho    1209:            dhcp_packet(now, 0);
1.1.1.3   misho    1210:          if (daemon->pxefd != -1 && poll_check(daemon->pxefd, POLLIN))
1.1       misho    1211:            dhcp_packet(now, 1);
                   1212:        }
                   1213: 
                   1214: #ifdef HAVE_DHCP6
1.1.1.3   misho    1215:       if ((daemon->doing_dhcp6 || daemon->relay6) && poll_check(daemon->dhcp6fd, POLLIN))
1.1       misho    1216:        dhcp6_packet(now);
                   1217: 
1.1.1.3   misho    1218:       if (daemon->doing_ra && poll_check(daemon->icmp6fd, POLLIN))
1.1       misho    1219:        icmp6_packet(now);
                   1220: #endif
                   1221: 
                   1222: #  ifdef HAVE_SCRIPT
1.1.1.3   misho    1223:       if (daemon->helperfd != -1 && poll_check(daemon->helperfd, POLLOUT))
1.1       misho    1224:        helper_write();
                   1225: #  endif
                   1226: #endif
                   1227: 
                   1228:     }
                   1229: }
                   1230: 
                   1231: static void sig_handler(int sig)
                   1232: {
                   1233:   if (pid == 0)
                   1234:     {
                   1235:       /* ignore anything other than TERM during startup
                   1236:         and in helper proc. (helper ignore TERM too) */
1.1.1.4 ! misho    1237:       if (sig == SIGTERM || sig == SIGINT)
1.1       misho    1238:        exit(EC_MISC);
                   1239:     }
                   1240:   else if (pid != getpid())
                   1241:     {
                   1242:       /* alarm is used to kill TCP children after a fixed time. */
                   1243:       if (sig == SIGALRM)
                   1244:        _exit(0);
                   1245:     }
                   1246:   else
                   1247:     {
                   1248:       /* master process */
                   1249:       int event, errsave = errno;
                   1250:       
                   1251:       if (sig == SIGHUP)
                   1252:        event = EVENT_RELOAD;
                   1253:       else if (sig == SIGCHLD)
                   1254:        event = EVENT_CHILD;
                   1255:       else if (sig == SIGALRM)
                   1256:        event = EVENT_ALARM;
                   1257:       else if (sig == SIGTERM)
                   1258:        event = EVENT_TERM;
                   1259:       else if (sig == SIGUSR1)
                   1260:        event = EVENT_DUMP;
                   1261:       else if (sig == SIGUSR2)
                   1262:        event = EVENT_REOPEN;
1.1.1.4 ! misho    1263:       else if (sig == SIGINT)
        !          1264:        {
        !          1265:          /* Handle SIGINT normally in debug mode, so
        !          1266:             ctrl-c continues to operate. */
        !          1267:          if (option_bool(OPT_DEBUG))
        !          1268:            exit(EC_MISC);
        !          1269:          else
        !          1270:            event = EVENT_TIME;
        !          1271:        }
1.1       misho    1272:       else
                   1273:        return;
                   1274: 
                   1275:       send_event(pipewrite, event, 0, NULL); 
                   1276:       errno = errsave;
                   1277:     }
                   1278: }
                   1279: 
                   1280: /* now == 0 -> queue immediate callback */
                   1281: void send_alarm(time_t event, time_t now)
                   1282: {
                   1283:   if (now == 0 || event != 0)
                   1284:     {
                   1285:       /* alarm(0) or alarm(-ve) doesn't do what we want.... */
                   1286:       if ((now == 0 || difftime(event, now) <= 0.0))
                   1287:        send_event(pipewrite, EVENT_ALARM, 0, NULL);
                   1288:       else 
                   1289:        alarm((unsigned)difftime(event, now)); 
                   1290:     }
                   1291: }
                   1292: 
1.1.1.3   misho    1293: void queue_event(int event)
                   1294: {
                   1295:   send_event(pipewrite, event, 0, NULL);
                   1296: }
                   1297: 
1.1       misho    1298: void send_event(int fd, int event, int data, char *msg)
                   1299: {
                   1300:   struct event_desc ev;
                   1301:   struct iovec iov[2];
                   1302: 
                   1303:   ev.event = event;
                   1304:   ev.data = data;
                   1305:   ev.msg_sz = msg ? strlen(msg) : 0;
                   1306:   
                   1307:   iov[0].iov_base = &ev;
                   1308:   iov[0].iov_len = sizeof(ev);
                   1309:   iov[1].iov_base = msg;
                   1310:   iov[1].iov_len = ev.msg_sz;
                   1311:   
                   1312:   /* error pipe, debug mode. */
                   1313:   if (fd == -1)
                   1314:     fatal_event(&ev, msg);
                   1315:   else
                   1316:     /* pipe is non-blocking and struct event_desc is smaller than
                   1317:        PIPE_BUF, so this either fails or writes everything */
                   1318:     while (writev(fd, iov, msg ? 2 : 1) == -1 && errno == EINTR);
                   1319: }
                   1320: 
                   1321: /* NOTE: the memory used to return msg is leaked: use msgs in events only
                   1322:    to describe fatal errors. */
                   1323: static int read_event(int fd, struct event_desc *evp, char **msg)
                   1324: {
                   1325:   char *buf;
                   1326: 
                   1327:   if (!read_write(fd, (unsigned char *)evp, sizeof(struct event_desc), 1))
                   1328:     return 0;
                   1329:   
                   1330:   *msg = NULL;
                   1331:   
                   1332:   if (evp->msg_sz != 0 && 
                   1333:       (buf = malloc(evp->msg_sz + 1)) &&
                   1334:       read_write(fd, (unsigned char *)buf, evp->msg_sz, 1))
                   1335:     {
                   1336:       buf[evp->msg_sz] = 0;
                   1337:       *msg = buf;
                   1338:     }
                   1339: 
                   1340:   return 1;
                   1341: }
                   1342:     
                   1343: static void fatal_event(struct event_desc *ev, char *msg)
                   1344: {
                   1345:   errno = ev->data;
                   1346:   
                   1347:   switch (ev->event)
                   1348:     {
                   1349:     case EVENT_DIE:
                   1350:       exit(0);
                   1351: 
                   1352:     case EVENT_FORK_ERR:
                   1353:       die(_("cannot fork into background: %s"), NULL, EC_MISC);
1.1.1.4 ! misho    1354: 
        !          1355:       /* fall through */
1.1       misho    1356:     case EVENT_PIPE_ERR:
                   1357:       die(_("failed to create helper: %s"), NULL, EC_MISC);
1.1.1.4 ! misho    1358: 
        !          1359:       /* fall through */
1.1       misho    1360:     case EVENT_CAP_ERR:
                   1361:       die(_("setting capabilities failed: %s"), NULL, EC_MISC);
                   1362: 
1.1.1.4 ! misho    1363:       /* fall through */
1.1       misho    1364:     case EVENT_USER_ERR:
                   1365:       die(_("failed to change user-id to %s: %s"), msg, EC_MISC);
                   1366: 
1.1.1.4 ! misho    1367:       /* fall through */
1.1       misho    1368:     case EVENT_GROUP_ERR:
                   1369:       die(_("failed to change group-id to %s: %s"), msg, EC_MISC);
1.1.1.4 ! misho    1370: 
        !          1371:       /* fall through */
1.1       misho    1372:     case EVENT_PIDFILE:
                   1373:       die(_("failed to open pidfile %s: %s"), msg, EC_FILE);
                   1374: 
1.1.1.4 ! misho    1375:       /* fall through */
1.1       misho    1376:     case EVENT_LOG_ERR:
                   1377:       die(_("cannot open log %s: %s"), msg, EC_FILE);
1.1.1.4 ! misho    1378: 
        !          1379:       /* fall through */
1.1       misho    1380:     case EVENT_LUA_ERR:
                   1381:       die(_("failed to load Lua script: %s"), msg, EC_MISC);
                   1382: 
1.1.1.4 ! misho    1383:       /* fall through */
1.1       misho    1384:     case EVENT_TFTP_ERR:
                   1385:       die(_("TFTP directory %s inaccessible: %s"), msg, EC_FILE);
1.1.1.4 ! misho    1386: 
        !          1387:       /* fall through */
1.1.1.3   misho    1388:     case EVENT_TIME_ERR:
                   1389:       die(_("cannot create timestamp file %s: %s" ), msg, EC_BADCONF);
1.1       misho    1390:     }
                   1391: }      
                   1392:       
                   1393: static void async_event(int pipe, time_t now)
                   1394: {
                   1395:   pid_t p;
                   1396:   struct event_desc ev;
1.1.1.2   misho    1397:   int i, check = 0;
1.1       misho    1398:   char *msg;
                   1399:   
                   1400:   /* NOTE: the memory used to return msg is leaked: use msgs in events only
                   1401:      to describe fatal errors. */
                   1402:   
                   1403:   if (read_event(pipe, &ev, &msg))
                   1404:     switch (ev.event)
                   1405:       {
                   1406:       case EVENT_RELOAD:
1.1.1.4 ! misho    1407:        daemon->soa_sn++; /* Bump zone serial, as it may have changed. */
        !          1408:        
1.1.1.2   misho    1409:        /* fall through */
                   1410:        
                   1411:       case EVENT_INIT:
1.1       misho    1412:        clear_cache_and_reload(now);
1.1.1.2   misho    1413:        
                   1414:        if (daemon->port != 0)
1.1       misho    1415:          {
1.1.1.2   misho    1416:            if (daemon->resolv_files && option_bool(OPT_NO_POLL))
                   1417:              {
                   1418:                reload_servers(daemon->resolv_files->name);
                   1419:                check = 1;
                   1420:              }
                   1421: 
                   1422:            if (daemon->servers_file)
                   1423:              {
                   1424:                read_servers_file();
                   1425:                check = 1;
                   1426:              }
                   1427: 
                   1428:            if (check)
                   1429:              check_servers();
1.1       misho    1430:          }
1.1.1.2   misho    1431: 
1.1       misho    1432: #ifdef HAVE_DHCP
                   1433:        rerun_scripts();
                   1434: #endif
                   1435:        break;
                   1436:        
                   1437:       case EVENT_DUMP:
                   1438:        if (daemon->port != 0)
                   1439:          dump_cache(now);
                   1440:        break;
                   1441:        
                   1442:       case EVENT_ALARM:
                   1443: #ifdef HAVE_DHCP
                   1444:        if (daemon->dhcp || daemon->doing_dhcp6)
                   1445:          {
                   1446:            lease_prune(NULL, now);
                   1447:            lease_update_file(now);
                   1448:          }
                   1449: #ifdef HAVE_DHCP6
                   1450:        else if (daemon->doing_ra)
                   1451:          /* Not doing DHCP, so no lease system, manage alarms for ra only */
                   1452:            send_alarm(periodic_ra(now), now);
                   1453: #endif
                   1454: #endif
                   1455:        break;
                   1456:                
                   1457:       case EVENT_CHILD:
                   1458:        /* See Stevens 5.10 */
                   1459:        while ((p = waitpid(-1, NULL, WNOHANG)) != 0)
                   1460:          if (p == -1)
                   1461:            {
                   1462:              if (errno != EINTR)
                   1463:                break;
                   1464:            }      
                   1465:          else 
                   1466:            for (i = 0 ; i < MAX_PROCS; i++)
                   1467:              if (daemon->tcp_pids[i] == p)
                   1468:                daemon->tcp_pids[i] = 0;
                   1469:        break;
                   1470:        
1.1.1.4 ! misho    1471: #if defined(HAVE_SCRIPT)       
1.1       misho    1472:       case EVENT_KILLED:
                   1473:        my_syslog(LOG_WARNING, _("script process killed by signal %d"), ev.data);
                   1474:        break;
                   1475: 
                   1476:       case EVENT_EXITED:
                   1477:        my_syslog(LOG_WARNING, _("script process exited with status %d"), ev.data);
                   1478:        break;
                   1479: 
                   1480:       case EVENT_EXEC_ERR:
                   1481:        my_syslog(LOG_ERR, _("failed to execute %s: %s"), 
                   1482:                  daemon->lease_change_command, strerror(ev.data));
                   1483:        break;
                   1484: 
1.1.1.4 ! misho    1485:       case EVENT_SCRIPT_LOG:
        !          1486:        my_syslog(MS_SCRIPT | LOG_DEBUG, "%s", msg ? msg : "");
        !          1487:         free(msg);
        !          1488:        msg = NULL;
        !          1489:        break;
        !          1490: 
1.1       misho    1491:        /* necessary for fatal errors in helper */
                   1492:       case EVENT_USER_ERR:
                   1493:       case EVENT_DIE:
                   1494:       case EVENT_LUA_ERR:
                   1495:        fatal_event(&ev, msg);
                   1496:        break;
1.1.1.4 ! misho    1497: #endif
1.1       misho    1498: 
                   1499:       case EVENT_REOPEN:
                   1500:        /* Note: this may leave TCP-handling processes with the old file still open.
                   1501:           Since any such process will die in CHILD_LIFETIME or probably much sooner,
                   1502:           we leave them logging to the old file. */
                   1503:        if (daemon->log_file != NULL)
                   1504:          log_reopen(daemon->log_file);
                   1505:        break;
1.1.1.3   misho    1506: 
                   1507:       case EVENT_NEWADDR:
                   1508:        newaddress(now);
                   1509:        break;
                   1510: 
                   1511:       case EVENT_NEWROUTE:
                   1512:        resend_query();
                   1513:        /* Force re-reading resolv file right now, for luck. */
                   1514:        poll_resolv(0, 1, now);
                   1515:        break;
                   1516: 
1.1.1.4 ! misho    1517:       case EVENT_TIME:
        !          1518: #ifdef HAVE_DNSSEC
        !          1519:        if (daemon->dnssec_no_time_check && option_bool(OPT_DNSSEC_VALID) && option_bool(OPT_DNSSEC_TIME))
        !          1520:          {
        !          1521:            my_syslog(LOG_INFO, _("now checking DNSSEC signature timestamps"));
        !          1522:            daemon->dnssec_no_time_check = 0;
        !          1523:            clear_cache_and_reload(now);
        !          1524:          }
        !          1525: #endif
        !          1526:        break;
        !          1527:        
1.1       misho    1528:       case EVENT_TERM:
                   1529:        /* Knock all our children on the head. */
                   1530:        for (i = 0; i < MAX_PROCS; i++)
                   1531:          if (daemon->tcp_pids[i] != 0)
                   1532:            kill(daemon->tcp_pids[i], SIGALRM);
                   1533:        
1.1.1.3   misho    1534: #if defined(HAVE_SCRIPT) && defined(HAVE_DHCP)
1.1       misho    1535:        /* handle pending lease transitions */
                   1536:        if (daemon->helperfd != -1)
                   1537:          {
                   1538:            /* block in writes until all done */
                   1539:            if ((i = fcntl(daemon->helperfd, F_GETFL)) != -1)
                   1540:              fcntl(daemon->helperfd, F_SETFL, i & ~O_NONBLOCK); 
                   1541:            do {
                   1542:              helper_write();
                   1543:            } while (!helper_buf_empty() || do_script_run(now));
1.1.1.4 ! misho    1544:            close(daemon->helperfd);
1.1       misho    1545:          }
                   1546: #endif
                   1547:        
                   1548:        if (daemon->lease_stream)
                   1549:          fclose(daemon->lease_stream);
                   1550: 
1.1.1.3   misho    1551: #ifdef HAVE_DNSSEC
                   1552:        /* update timestamp file on TERM if time is considered valid */
                   1553:        if (daemon->back_to_the_future)
                   1554:          {
1.1.1.4 ! misho    1555:             if (utimes(daemon->timestamp_file, NULL) == -1)
1.1.1.3   misho    1556:                my_syslog(LOG_ERR, _("failed to update mtime on %s: %s"), daemon->timestamp_file, strerror(errno));
                   1557:          }
                   1558: #endif
                   1559: 
1.1       misho    1560:        if (daemon->runfile)
                   1561:          unlink(daemon->runfile);
1.1.1.4 ! misho    1562: 
        !          1563: #ifdef HAVE_DUMPFILE
        !          1564:        if (daemon->dumpfd != -1)
        !          1565:          close(daemon->dumpfd);
        !          1566: #endif
1.1       misho    1567:        
                   1568:        my_syslog(LOG_INFO, _("exiting on receipt of SIGTERM"));
                   1569:        flush_log();
                   1570:        exit(EC_GOOD);
                   1571:       }
                   1572: }
                   1573: 
1.1.1.3   misho    1574: static void poll_resolv(int force, int do_reload, time_t now)
1.1       misho    1575: {
                   1576:   struct resolvc *res, *latest;
                   1577:   struct stat statbuf;
                   1578:   time_t last_change = 0;
                   1579:   /* There may be more than one possible file. 
                   1580:      Go through and find the one which changed _last_.
                   1581:      Warn of any which can't be read. */
                   1582: 
                   1583:   if (daemon->port == 0 || option_bool(OPT_NO_POLL))
                   1584:     return;
                   1585:   
                   1586:   for (latest = NULL, res = daemon->resolv_files; res; res = res->next)
                   1587:     if (stat(res->name, &statbuf) == -1)
                   1588:       {
                   1589:        if (force)
                   1590:          {
                   1591:            res->mtime = 0; 
                   1592:            continue;
                   1593:          }
                   1594: 
                   1595:        if (!res->logged)
                   1596:          my_syslog(LOG_WARNING, _("failed to access %s: %s"), res->name, strerror(errno));
                   1597:        res->logged = 1;
                   1598:        
                   1599:        if (res->mtime != 0)
                   1600:          { 
                   1601:            /* existing file evaporated, force selection of the latest
                   1602:               file even if its mtime hasn't changed since we last looked */
                   1603:            poll_resolv(1, do_reload, now);
                   1604:            return;
                   1605:          }
                   1606:       }
                   1607:     else
                   1608:       {
                   1609:        res->logged = 0;
                   1610:        if (force || (statbuf.st_mtime != res->mtime))
                   1611:           {
                   1612:             res->mtime = statbuf.st_mtime;
                   1613:            if (difftime(statbuf.st_mtime, last_change) > 0.0)
                   1614:              {
                   1615:                last_change = statbuf.st_mtime;
                   1616:                latest = res;
                   1617:              }
                   1618:          }
                   1619:       }
                   1620:   
                   1621:   if (latest)
                   1622:     {
                   1623:       static int warned = 0;
                   1624:       if (reload_servers(latest->name))
                   1625:        {
                   1626:          my_syslog(LOG_INFO, _("reading %s"), latest->name);
                   1627:          warned = 0;
                   1628:          check_servers();
                   1629:          if (option_bool(OPT_RELOAD) && do_reload)
                   1630:            clear_cache_and_reload(now);
                   1631:        }
                   1632:       else 
                   1633:        {
                   1634:          latest->mtime = 0;
                   1635:          if (!warned)
                   1636:            {
                   1637:              my_syslog(LOG_WARNING, _("no servers found in %s, will retry"), latest->name);
                   1638:              warned = 1;
                   1639:            }
                   1640:        }
                   1641:     }
                   1642: }       
                   1643: 
                   1644: void clear_cache_and_reload(time_t now)
                   1645: {
1.1.1.2   misho    1646:   (void)now;
                   1647: 
1.1       misho    1648:   if (daemon->port != 0)
                   1649:     cache_reload();
                   1650:   
                   1651: #ifdef HAVE_DHCP
                   1652:   if (daemon->dhcp || daemon->doing_dhcp6)
                   1653:     {
                   1654:       if (option_bool(OPT_ETHERS))
                   1655:        dhcp_read_ethers();
                   1656:       reread_dhcp();
                   1657:       dhcp_update_configs(daemon->dhcp_conf);
                   1658:       lease_update_from_configs(); 
                   1659:       lease_update_file(now); 
                   1660:       lease_update_dns(1);
                   1661:     }
                   1662: #ifdef HAVE_DHCP6
                   1663:   else if (daemon->doing_ra)
                   1664:     /* Not doing DHCP, so no lease system, manage 
                   1665:        alarms for ra only */
                   1666:     send_alarm(periodic_ra(now), now);
                   1667: #endif
                   1668: #endif
                   1669: }
                   1670: 
1.1.1.3   misho    1671: static int set_dns_listeners(time_t now)
1.1       misho    1672: {
                   1673:   struct serverfd *serverfdp;
                   1674:   struct listener *listener;
                   1675:   int wait = 0, i;
                   1676:   
                   1677: #ifdef HAVE_TFTP
                   1678:   int  tftp = 0;
                   1679:   struct tftp_transfer *transfer;
1.1.1.4 ! misho    1680:   if (!option_bool(OPT_SINGLE_PORT))
        !          1681:     for (transfer = daemon->tftp_trans; transfer; transfer = transfer->next)
        !          1682:       {
        !          1683:        tftp++;
        !          1684:        poll_listen(transfer->sockfd, POLLIN);
        !          1685:       }
1.1       misho    1686: #endif
                   1687:   
                   1688:   /* will we be able to get memory? */
                   1689:   if (daemon->port != 0)
1.1.1.4 ! misho    1690:     get_new_frec(now, &wait, NULL);
1.1       misho    1691:   
                   1692:   for (serverfdp = daemon->sfds; serverfdp; serverfdp = serverfdp->next)
1.1.1.3   misho    1693:     poll_listen(serverfdp->fd, POLLIN);
                   1694:     
1.1       misho    1695:   if (daemon->port != 0 && !daemon->osport)
                   1696:     for (i = 0; i < RANDOM_SOCKS; i++)
                   1697:       if (daemon->randomsocks[i].refcount != 0)
1.1.1.3   misho    1698:        poll_listen(daemon->randomsocks[i].fd, POLLIN);
                   1699:          
1.1       misho    1700:   for (listener = daemon->listeners; listener; listener = listener->next)
                   1701:     {
                   1702:       /* only listen for queries if we have resources */
                   1703:       if (listener->fd != -1 && wait == 0)
1.1.1.3   misho    1704:        poll_listen(listener->fd, POLLIN);
                   1705:        
1.1       misho    1706:       /* death of a child goes through the select loop, so
                   1707:         we don't need to explicitly arrange to wake up here */
                   1708:       if  (listener->tcpfd != -1)
                   1709:        for (i = 0; i < MAX_PROCS; i++)
1.1.1.4 ! misho    1710:          if (daemon->tcp_pids[i] == 0 && daemon->tcp_pipes[i] == -1)
1.1       misho    1711:            {
1.1.1.3   misho    1712:              poll_listen(listener->tcpfd, POLLIN);
1.1       misho    1713:              break;
                   1714:            }
                   1715: 
                   1716: #ifdef HAVE_TFTP
1.1.1.4 ! misho    1717:       /* tftp == 0 in single-port mode. */
1.1       misho    1718:       if (tftp <= daemon->tftp_max && listener->tftpfd != -1)
1.1.1.3   misho    1719:        poll_listen(listener->tftpfd, POLLIN);
1.1       misho    1720: #endif
                   1721: 
                   1722:     }
                   1723:   
1.1.1.4 ! misho    1724:   if (!option_bool(OPT_DEBUG))
        !          1725:     for (i = 0; i < MAX_PROCS; i++)
        !          1726:       if (daemon->tcp_pipes[i] != -1)
        !          1727:        poll_listen(daemon->tcp_pipes[i], POLLIN);
        !          1728:   
1.1       misho    1729:   return wait;
                   1730: }
                   1731: 
1.1.1.3   misho    1732: static void check_dns_listeners(time_t now)
1.1       misho    1733: {
                   1734:   struct serverfd *serverfdp;
                   1735:   struct listener *listener;
                   1736:   int i;
1.1.1.4 ! misho    1737:   int pipefd[2];
        !          1738:   
1.1       misho    1739:   for (serverfdp = daemon->sfds; serverfdp; serverfdp = serverfdp->next)
1.1.1.3   misho    1740:     if (poll_check(serverfdp->fd, POLLIN))
1.1       misho    1741:       reply_query(serverfdp->fd, serverfdp->source_addr.sa.sa_family, now);
                   1742:   
                   1743:   if (daemon->port != 0 && !daemon->osport)
                   1744:     for (i = 0; i < RANDOM_SOCKS; i++)
                   1745:       if (daemon->randomsocks[i].refcount != 0 && 
1.1.1.3   misho    1746:          poll_check(daemon->randomsocks[i].fd, POLLIN))
1.1       misho    1747:        reply_query(daemon->randomsocks[i].fd, daemon->randomsocks[i].family, now);
1.1.1.4 ! misho    1748: 
        !          1749:   /* Races. The child process can die before we read all of the data from the
        !          1750:      pipe, or vice versa. Therefore send tcp_pids to zero when we wait() the 
        !          1751:      process, and tcp_pipes to -1 and close the FD when we read the last
        !          1752:      of the data - indicated by cache_recv_insert returning zero.
        !          1753:      The order of these events is indeterminate, and both are needed
        !          1754:      to free the process slot. Once the child process has gone, poll()
        !          1755:      returns POLLHUP, not POLLIN, so have to check for both here. */
        !          1756:   if (!option_bool(OPT_DEBUG))
        !          1757:     for (i = 0; i < MAX_PROCS; i++)
        !          1758:       if (daemon->tcp_pipes[i] != -1 &&
        !          1759:          poll_check(daemon->tcp_pipes[i], POLLIN | POLLHUP) &&
        !          1760:          !cache_recv_insert(now, daemon->tcp_pipes[i]))
        !          1761:        {
        !          1762:          close(daemon->tcp_pipes[i]);
        !          1763:          daemon->tcp_pipes[i] = -1;    
        !          1764:        }
        !          1765:        
1.1       misho    1766:   for (listener = daemon->listeners; listener; listener = listener->next)
                   1767:     {
1.1.1.3   misho    1768:       if (listener->fd != -1 && poll_check(listener->fd, POLLIN))
1.1       misho    1769:        receive_query(listener, now); 
                   1770:       
                   1771: #ifdef HAVE_TFTP     
1.1.1.3   misho    1772:       if (listener->tftpfd != -1 && poll_check(listener->tftpfd, POLLIN))
1.1       misho    1773:        tftp_request(listener, now);
                   1774: #endif
                   1775: 
1.1.1.3   misho    1776:       if (listener->tcpfd != -1 && poll_check(listener->tcpfd, POLLIN))
1.1       misho    1777:        {
                   1778:          int confd, client_ok = 1;
                   1779:          struct irec *iface = NULL;
                   1780:          pid_t p;
                   1781:          union mysockaddr tcp_addr;
                   1782:          socklen_t tcp_len = sizeof(union mysockaddr);
                   1783: 
                   1784:          while ((confd = accept(listener->tcpfd, NULL, NULL)) == -1 && errno == EINTR);
                   1785:          
                   1786:          if (confd == -1)
                   1787:            continue;
1.1.1.2   misho    1788:          
1.1       misho    1789:          if (getsockname(confd, (struct sockaddr *)&tcp_addr, &tcp_len) == -1)
                   1790:            {
1.1.1.4 ! misho    1791:              close(confd);
1.1       misho    1792:              continue;
                   1793:            }
1.1.1.2   misho    1794:          
                   1795:          /* Make sure that the interface list is up-to-date.
                   1796:             
                   1797:             We do this here as we may need the results below, and
                   1798:             the DNS code needs them for --interface-name stuff.
                   1799: 
                   1800:             Multiple calls to enumerate_interfaces() per select loop are
                   1801:             inhibited, so calls to it in the child process (which doesn't select())
                   1802:             have no effect. This avoids two processes reading from the same
                   1803:             netlink fd and screwing the pooch entirely.
                   1804:          */
1.1       misho    1805:  
1.1.1.2   misho    1806:          enumerate_interfaces(0);
                   1807:          
                   1808:          if (option_bool(OPT_NOWILD))
                   1809:            iface = listener->iface; /* May be NULL */
                   1810:          else 
                   1811:            {
                   1812:              int if_index;
                   1813:              char intr_name[IF_NAMESIZE];
                   1814:              
                   1815:              /* if we can find the arrival interface, check it's one that's allowed */
                   1816:              if ((if_index = tcp_interface(confd, tcp_addr.sa.sa_family)) != 0 &&
                   1817:                  indextoname(listener->tcpfd, if_index, intr_name))
                   1818:                {
1.1.1.4 ! misho    1819:                  union all_addr addr;
        !          1820:                  
1.1.1.2   misho    1821:                  if (tcp_addr.sa.sa_family == AF_INET6)
1.1.1.4 ! misho    1822:                    addr.addr6 = tcp_addr.in6.sin6_addr;
        !          1823:                  else
        !          1824:                    addr.addr4 = tcp_addr.in.sin_addr;
1.1.1.2   misho    1825:                  
                   1826:                  for (iface = daemon->interfaces; iface; iface = iface->next)
1.1.1.4 ! misho    1827:                    if (iface->index == if_index &&
        !          1828:                        iface->addr.sa.sa_family == tcp_addr.sa.sa_family)
1.1.1.2   misho    1829:                      break;
                   1830:                  
                   1831:                  if (!iface && !loopback_exception(listener->tcpfd, tcp_addr.sa.sa_family, &addr, intr_name))
                   1832:                    client_ok = 0;
                   1833:                }
                   1834:              
                   1835:              if (option_bool(OPT_CLEVERBIND))
                   1836:                iface = listener->iface; /* May be NULL */
                   1837:              else
                   1838:                {
                   1839:                  /* Check for allowed interfaces when binding the wildcard address:
                   1840:                     we do this by looking for an interface with the same address as 
                   1841:                     the local address of the TCP connection, then looking to see if that's
                   1842:                     an allowed interface. As a side effect, we get the netmask of the
                   1843:                     interface too, for localisation. */
                   1844:                  
                   1845:                  for (iface = daemon->interfaces; iface; iface = iface->next)
                   1846:                    if (sockaddr_isequal(&iface->addr, &tcp_addr))
                   1847:                      break;
                   1848:                  
                   1849:                  if (!iface)
                   1850:                    client_ok = 0;
                   1851:                }
                   1852:            }
                   1853:          
1.1       misho    1854:          if (!client_ok)
                   1855:            {
                   1856:              shutdown(confd, SHUT_RDWR);
1.1.1.4 ! misho    1857:              close(confd);
1.1       misho    1858:            }
1.1.1.4 ! misho    1859:          else if (!option_bool(OPT_DEBUG) && pipe(pipefd) == 0 && (p = fork()) != 0)
1.1       misho    1860:            {
1.1.1.4 ! misho    1861:              close(pipefd[1]); /* parent needs read pipe end. */
        !          1862:              if (p == -1)
        !          1863:                close(pipefd[0]);
        !          1864:              else
1.1       misho    1865:                {
                   1866:                  int i;
1.1.1.4 ! misho    1867: #ifdef HAVE_LINUX_NETWORK
        !          1868:                  /* The child process inherits the netlink socket, 
        !          1869:                     which it never uses, but when the parent (us) 
        !          1870:                     uses it in the future, the answer may go to the 
        !          1871:                     child, resulting in the parent blocking
        !          1872:                     forever awaiting the result. To avoid this
        !          1873:                     the child closes the netlink socket, but there's
        !          1874:                     a nasty race, since the parent may use netlink
        !          1875:                     before the child has done the close.
        !          1876:                     
        !          1877:                     To avoid this, the parent blocks here until a 
        !          1878:                     single byte comes back up the pipe, which
        !          1879:                     is sent by the child after it has closed the
        !          1880:                     netlink socket. */
        !          1881:                  
        !          1882:                  unsigned char a;
        !          1883:                  read_write(pipefd[0], &a, 1, 1);
        !          1884: #endif
        !          1885: 
1.1       misho    1886:                  for (i = 0; i < MAX_PROCS; i++)
1.1.1.4 ! misho    1887:                    if (daemon->tcp_pids[i] == 0 && daemon->tcp_pipes[i] == -1)
1.1       misho    1888:                      {
                   1889:                        daemon->tcp_pids[i] = p;
1.1.1.4 ! misho    1890:                        daemon->tcp_pipes[i] = pipefd[0];
1.1       misho    1891:                        break;
                   1892:                      }
                   1893:                }
1.1.1.4 ! misho    1894:              close(confd);
1.1.1.3   misho    1895: 
                   1896:              /* The child can use up to TCP_MAX_QUERIES ids, so skip that many. */
                   1897:              daemon->log_id += TCP_MAX_QUERIES;
1.1       misho    1898:            }
                   1899:          else
                   1900:            {
                   1901:              unsigned char *buff;
                   1902:              struct server *s; 
                   1903:              int flags;
                   1904:              struct in_addr netmask;
                   1905:              int auth_dns;
1.1.1.4 ! misho    1906:           
1.1       misho    1907:              if (iface)
                   1908:                {
                   1909:                  netmask = iface->netmask;
                   1910:                  auth_dns = iface->dns_auth;
                   1911:                }
                   1912:              else
                   1913:                {
                   1914:                  netmask.s_addr = 0;
                   1915:                  auth_dns = 0;
                   1916:                }
                   1917: 
1.1.1.4 ! misho    1918:              /* Arrange for SIGALRM after CHILD_LIFETIME seconds to
1.1       misho    1919:                 terminate the process. */
                   1920:              if (!option_bool(OPT_DEBUG))
1.1.1.4 ! misho    1921:                {
        !          1922: #ifdef HAVE_LINUX_NETWORK
        !          1923:                  /* See comment above re: netlink socket. */
        !          1924:                  unsigned char a = 0;
        !          1925: 
        !          1926:                  close(daemon->netlinkfd);
        !          1927:                  read_write(pipefd[1], &a, 1, 0);
        !          1928: #endif           
        !          1929:                  alarm(CHILD_LIFETIME);
        !          1930:                  close(pipefd[0]); /* close read end in child. */
        !          1931:                  daemon->pipe_to_parent = pipefd[1];
        !          1932:                }
1.1       misho    1933: 
                   1934:              /* start with no upstream connections. */
                   1935:              for (s = daemon->servers; s; s = s->next)
                   1936:                 s->tcpfd = -1; 
                   1937:              
                   1938:              /* The connected socket inherits non-blocking
                   1939:                 attribute from the listening socket. 
                   1940:                 Reset that here. */
                   1941:              if ((flags = fcntl(confd, F_GETFL, 0)) != -1)
                   1942:                fcntl(confd, F_SETFL, flags & ~O_NONBLOCK);
                   1943:              
                   1944:              buff = tcp_request(confd, now, &tcp_addr, netmask, auth_dns);
                   1945:               
                   1946:              shutdown(confd, SHUT_RDWR);
1.1.1.4 ! misho    1947:              close(confd);
1.1       misho    1948:              
                   1949:              if (buff)
                   1950:                free(buff);
                   1951:              
                   1952:              for (s = daemon->servers; s; s = s->next)
                   1953:                if (s->tcpfd != -1)
                   1954:                  {
                   1955:                    shutdown(s->tcpfd, SHUT_RDWR);
1.1.1.4 ! misho    1956:                    close(s->tcpfd);
1.1       misho    1957:                  }
1.1.1.4 ! misho    1958:              
1.1       misho    1959:              if (!option_bool(OPT_DEBUG))
                   1960:                {
1.1.1.4 ! misho    1961:                  close(daemon->pipe_to_parent);
1.1       misho    1962:                  flush_log();
                   1963:                  _exit(0);
                   1964:                }
                   1965:            }
                   1966:        }
                   1967:     }
                   1968: }
                   1969: 
                   1970: #ifdef HAVE_DHCP
                   1971: int make_icmp_sock(void)
                   1972: {
                   1973:   int fd;
                   1974:   int zeroopt = 0;
                   1975: 
                   1976:   if ((fd = socket (AF_INET, SOCK_RAW, IPPROTO_ICMP)) != -1)
                   1977:     {
                   1978:       if (!fix_fd(fd) ||
                   1979:          setsockopt(fd, SOL_SOCKET, SO_DONTROUTE, &zeroopt, sizeof(zeroopt)) == -1)
                   1980:        {
                   1981:          close(fd);
                   1982:          fd = -1;
                   1983:        }
                   1984:     }
                   1985: 
                   1986:   return fd;
                   1987: }
                   1988: 
                   1989: int icmp_ping(struct in_addr addr)
                   1990: {
                   1991:   /* Try and get an ICMP echo from a machine. */
                   1992: 
1.1.1.4 ! misho    1993:   int fd;
1.1       misho    1994:   struct sockaddr_in saddr;
                   1995:   struct { 
                   1996:     struct ip ip;
                   1997:     struct icmp icmp;
                   1998:   } packet;
                   1999:   unsigned short id = rand16();
1.1.1.4 ! misho    2000:   unsigned int i, j;
1.1       misho    2001:   int gotreply = 0;
                   2002: 
                   2003: #if defined(HAVE_LINUX_NETWORK) || defined (HAVE_SOLARIS_NETWORK)
                   2004:   if ((fd = make_icmp_sock()) == -1)
                   2005:     return 0;
                   2006: #else
                   2007:   int opt = 2000;
                   2008:   fd = daemon->dhcp_icmp_fd;
                   2009:   setsockopt(fd, SOL_SOCKET, SO_RCVBUF, &opt, sizeof(opt));
                   2010: #endif
                   2011: 
                   2012:   saddr.sin_family = AF_INET;
                   2013:   saddr.sin_port = 0;
                   2014:   saddr.sin_addr = addr;
                   2015: #ifdef HAVE_SOCKADDR_SA_LEN
                   2016:   saddr.sin_len = sizeof(struct sockaddr_in);
                   2017: #endif
                   2018:   
                   2019:   memset(&packet.icmp, 0, sizeof(packet.icmp));
                   2020:   packet.icmp.icmp_type = ICMP_ECHO;
                   2021:   packet.icmp.icmp_id = id;
                   2022:   for (j = 0, i = 0; i < sizeof(struct icmp) / 2; i++)
                   2023:     j += ((u16 *)&packet.icmp)[i];
                   2024:   while (j>>16)
                   2025:     j = (j & 0xffff) + (j >> 16);  
                   2026:   packet.icmp.icmp_cksum = (j == 0xffff) ? j : ~j;
                   2027:   
1.1.1.3   misho    2028:   while (retry_send(sendto(fd, (char *)&packet.icmp, sizeof(struct icmp), 0, 
                   2029:                           (struct sockaddr *)&saddr, sizeof(saddr))));
1.1       misho    2030:   
1.1.1.4 ! misho    2031:   gotreply = delay_dhcp(dnsmasq_time(), PING_WAIT, fd, addr.s_addr, id);
        !          2032: 
        !          2033: #if defined(HAVE_LINUX_NETWORK) || defined(HAVE_SOLARIS_NETWORK)
        !          2034:   close(fd);
        !          2035: #else
        !          2036:   opt = 1;
        !          2037:   setsockopt(fd, SOL_SOCKET, SO_RCVBUF, &opt, sizeof(opt));
        !          2038: #endif
        !          2039: 
        !          2040:   return gotreply;
        !          2041: }
        !          2042: 
        !          2043: int delay_dhcp(time_t start, int sec, int fd, uint32_t addr, unsigned short id)
        !          2044: {
        !          2045:   /* Delay processing DHCP packets for "sec" seconds counting from "start".
        !          2046:      If "fd" is not -1 it will stop waiting if an ICMP echo reply is received
        !          2047:      from "addr" with ICMP ID "id" and return 1 */
        !          2048: 
        !          2049:   /* Note that whilst waiting, we check for
        !          2050:      (and service) events on the DNS and TFTP  sockets, (so doing that
        !          2051:      better not use any resources our caller has in use...)
        !          2052:      but we remain deaf to signals or further DHCP packets. */
        !          2053: 
        !          2054:   /* There can be a problem using dnsmasq_time() to end the loop, since
        !          2055:      it's not monotonic, and can go backwards if the system clock is
        !          2056:      tweaked, leading to the code getting stuck in this loop and
        !          2057:      ignoring DHCP requests. To fix this, we check to see if select returned
        !          2058:      as a result of a timeout rather than a socket becoming available. We
        !          2059:      only allow this to happen as many times as it takes to get to the wait time
        !          2060:      in quarter-second chunks. This provides a fallback way to end loop. */
        !          2061: 
        !          2062:   int rc, timeout_count;
        !          2063:   time_t now;
        !          2064: 
        !          2065:   for (now = dnsmasq_time(), timeout_count = 0;
        !          2066:        (difftime(now, start) <= (float)sec) && (timeout_count < sec * 4);)
1.1       misho    2067:     {
1.1.1.3   misho    2068:       poll_reset();
1.1.1.4 ! misho    2069:       if (fd != -1)
        !          2070:         poll_listen(fd, POLLIN);
1.1.1.3   misho    2071:       set_dns_listeners(now);
                   2072:       set_log_writer();
1.1       misho    2073:       
                   2074: #ifdef HAVE_DHCP6
                   2075:       if (daemon->doing_ra)
1.1.1.3   misho    2076:        poll_listen(daemon->icmp6fd, POLLIN); 
1.1       misho    2077: #endif
                   2078:       
1.1.1.3   misho    2079:       rc = do_poll(250);
                   2080:       
                   2081:       if (rc < 0)
                   2082:        continue;
                   2083:       else if (rc == 0)
                   2084:        timeout_count++;
1.1       misho    2085: 
                   2086:       now = dnsmasq_time();
1.1.1.4 ! misho    2087:       
1.1.1.3   misho    2088:       check_log_writer(0);
                   2089:       check_dns_listeners(now);
1.1.1.4 ! misho    2090:       
1.1       misho    2091: #ifdef HAVE_DHCP6
1.1.1.3   misho    2092:       if (daemon->doing_ra && poll_check(daemon->icmp6fd, POLLIN))
1.1       misho    2093:        icmp6_packet(now);
                   2094: #endif
                   2095:       
                   2096: #ifdef HAVE_TFTP
1.1.1.3   misho    2097:       check_tftp_listeners(now);
1.1       misho    2098: #endif
                   2099: 
1.1.1.4 ! misho    2100:       if (fd != -1)
        !          2101:         {
        !          2102:           struct {
        !          2103:             struct ip ip;
        !          2104:             struct icmp icmp;
        !          2105:           } packet;
        !          2106:           struct sockaddr_in faddr;
        !          2107:           socklen_t len = sizeof(faddr);
        !          2108:          
        !          2109:           if (poll_check(fd, POLLIN) &&
        !          2110:              recvfrom(fd, &packet, sizeof(packet), 0, (struct sockaddr *)&faddr, &len) == sizeof(packet) &&
        !          2111:              addr == faddr.sin_addr.s_addr &&
        !          2112:              packet.icmp.icmp_type == ICMP_ECHOREPLY &&
        !          2113:              packet.icmp.icmp_seq == 0 &&
        !          2114:              packet.icmp.icmp_id == id)
        !          2115:            return 1;
1.1       misho    2116:        }
                   2117:     }
                   2118: 
1.1.1.4 ! misho    2119:   return 0;
1.1       misho    2120: }
1.1.1.4 ! misho    2121: #endif /* HAVE_DHCP */

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>