Module Name: src Committed By: roy Date: Mon Jan 1 11:50:56 UTC 2018
Modified Files: src/external/bsd/dhcpcd/dist/src: bpf.c dhcp.c dhcpcd.c if-options.c Log Message: Sync To generate a diff of this commit: cvs rdiff -u -r1.5 -r1.6 src/external/bsd/dhcpcd/dist/src/bpf.c \ src/external/bsd/dhcpcd/dist/src/if-options.c cvs rdiff -u -r1.6 -r1.7 src/external/bsd/dhcpcd/dist/src/dhcp.c \ src/external/bsd/dhcpcd/dist/src/dhcpcd.c Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/external/bsd/dhcpcd/dist/src/bpf.c diff -u src/external/bsd/dhcpcd/dist/src/bpf.c:1.5 src/external/bsd/dhcpcd/dist/src/bpf.c:1.6 --- src/external/bsd/dhcpcd/dist/src/bpf.c:1.5 Wed Dec 6 10:35:05 2017 +++ src/external/bsd/dhcpcd/dist/src/bpf.c Mon Jan 1 11:50:56 2018 @@ -1,6 +1,6 @@ /* * dhcpcd: BPF arp and bootp filtering - * Copyright (c) 2006-2017 Roy Marples <r...@marples.name> + * Copyright (c) 2006-2018 Roy Marples <r...@marples.name> * All rights reserved * Redistribution and use in source and binary forms, with or without Index: src/external/bsd/dhcpcd/dist/src/if-options.c diff -u src/external/bsd/dhcpcd/dist/src/if-options.c:1.5 src/external/bsd/dhcpcd/dist/src/if-options.c:1.6 --- src/external/bsd/dhcpcd/dist/src/if-options.c:1.5 Tue Sep 19 19:19:21 2017 +++ src/external/bsd/dhcpcd/dist/src/if-options.c Mon Jan 1 11:50:56 2018 @@ -1,6 +1,6 @@ /* * dhcpcd - DHCP client daemon - * Copyright (c) 2006-2017 Roy Marples <r...@marples.name> + * Copyright (c) 2006-2018 Roy Marples <r...@marples.name> * All rights reserved * Redistribution and use in source and binary forms, with or without Index: src/external/bsd/dhcpcd/dist/src/dhcp.c diff -u src/external/bsd/dhcpcd/dist/src/dhcp.c:1.6 src/external/bsd/dhcpcd/dist/src/dhcp.c:1.7 --- src/external/bsd/dhcpcd/dist/src/dhcp.c:1.6 Wed Dec 6 10:35:05 2017 +++ src/external/bsd/dhcpcd/dist/src/dhcp.c Mon Jan 1 11:50:56 2018 @@ -1,6 +1,6 @@ /* * dhcpcd - DHCP client daemon - * Copyright (c) 2006-2017 Roy Marples <r...@marples.name> + * Copyright (c) 2006-2018 Roy Marples <r...@marples.name> * All rights reserved * Redistribution and use in source and binary forms, with or without @@ -777,7 +777,8 @@ make_message(struct bootp **bootpm, cons (type == DHCP_INFORM || type == DHCP_RELEASE || (type == DHCP_REQUEST && state->addr->mask.s_addr == lease->mask.s_addr && - (state->new == NULL || IS_DHCP(state->new))))) + (state->new == NULL || IS_DHCP(state->new)) && + !(state->added & STATE_FAKE)))) bootp->ciaddr = state->addr->addr.s_addr; bootp->op = BOOTREQUEST; @@ -845,6 +846,7 @@ make_message(struct bootp **bootpm, cons if (type == DHCP_DECLINE || (type == DHCP_REQUEST && (state->addr == NULL || + state->added & STATE_FAKE || lease->addr.s_addr != state->addr->addr.s_addr))) { PUT_ADDR(DHO_IPADDRESS, &lease->addr); @@ -1587,10 +1589,6 @@ dhcp_openudp(struct interface *ifp) int s; struct sockaddr_in sin; int n; - struct dhcp_state *state; -#ifdef SO_BINDTODEVICE - struct ifreq ifr; -#endif if ((s = xsocket(PF_INET, SOCK_DGRAM|SOCK_CLOEXEC, IPPROTO_UDP)) == -1) return -1; @@ -1598,20 +1596,12 @@ dhcp_openudp(struct interface *ifp) n = 1; if (setsockopt(s, SOL_SOCKET, SO_REUSEADDR, &n, sizeof(n)) == -1) goto eexit; -#ifdef SO_BINDTODEVICE - if (ifp) { - memset(&ifr, 0, sizeof(ifr)); - strlcpy(ifr.ifr_name, ifp->name, sizeof(ifr.ifr_name)); - if (setsockopt(s, SOL_SOCKET, SO_BINDTODEVICE, &ifr, - sizeof(ifr)) == -1) - goto eexit; - } -#endif memset(&sin, 0, sizeof(sin)); sin.sin_family = AF_INET; sin.sin_port = htons(BOOTPC); if (ifp) { - state = D_STATE(ifp); + struct dhcp_state *state = D_STATE(ifp); + if (state->addr) sin.sin_addr.s_addr = state->addr->addr.s_addr; } @@ -1694,6 +1684,63 @@ dhcp_makeudppacket(size_t *sz, const uin return udpp; } +static ssize_t +dhcp_sendudp(struct interface *ifp, struct in_addr *to, void *data, size_t len) +{ + int s; + struct msghdr msg; + struct sockaddr_in sin; + struct iovec iov[1]; + ssize_t r; +#ifdef IP_PKTINFO + uint8_t cmsg[CMSG_SPACE(sizeof(struct in_pktinfo))]; + struct cmsghdr *cm; + struct in_pktinfo ipi; +#endif + + iov[0].iov_base = data; + iov[0].iov_len = len; + + memset(&sin, 0, sizeof(sin)); + sin.sin_family = AF_INET; + sin.sin_addr = *to; + sin.sin_port = htons(BOOTPS); +#ifdef HAVE_SA_LEN + sin.sin_len = sizeof(sin); +#endif + + memset(&msg, 0, sizeof(msg)); + msg.msg_name = (void *)&sin; + msg.msg_namelen = sizeof(sin); + msg.msg_iov = iov; + msg.msg_iovlen = 1; + +#ifdef IP_PKTINFO + /* Set the outbound interface */ + msg.msg_control = cmsg; + msg.msg_controllen = sizeof(cmsg); + + memset(&ipi, 0, sizeof(ipi)); + ipi.ipi_ifindex = ifp->index; + cm = CMSG_FIRSTHDR(&msg); + if (cm == NULL) { + errno = ESRCH; + return -1; + } + cm->cmsg_level = IPPROTO_IP; + cm->cmsg_type = IP_PKTINFO; + cm->cmsg_len = CMSG_LEN(sizeof(ipi)); + memcpy(CMSG_DATA(cm), &ipi, sizeof(ipi)); +#endif + + s = dhcp_openudp(ifp); + if (s == -1) + return -1; + r = sendmsg(s, &msg, 0); + close(s); + return r; +} + static void send_message(struct interface *ifp, uint8_t type, void (*callback)(void *)) @@ -1738,9 +1785,6 @@ send_message(struct interface *ifp, uint timespec_to_double(&tv)); } - if (dhcp_openbpf(ifp) == -1) - return; - r = make_message(&bootp, ifp, type); if (r == -1) goto fail; @@ -1750,6 +1794,18 @@ send_message(struct interface *ifp, uint to.s_addr = state->lease.server.s_addr; else to.s_addr = INADDR_ANY; + + /* If unicasting, try and void sending by BPF so we don't + * use a L2 broadcast. */ + if (to.s_addr != INADDR_ANY && to.s_addr != INADDR_BROADCAST) { + if (dhcp_sendudp(ifp, &to, bootp, len) != -1) + goto out; + logerr("%s: dhcp_sendudp", ifp->name); + } + + if (dhcp_openbpf(ifp) == -1) + goto out; + udp = dhcp_makeudppacket(&ulen, (uint8_t *)bootp, len, from, to); if (udp == NULL) { logerr("%s: dhcp_makeudppacket", ifp->name); @@ -1780,6 +1836,8 @@ send_message(struct interface *ifp, uint callback = NULL; } } + +out: free(bootp); fail: @@ -1972,7 +2030,7 @@ dhcp_rebind(void *arg) ifp->name, lease->leasetime - lease->rebindtime); state->state = DHS_REBIND; eloop_timeout_delete(ifp->ctx->eloop, send_renew, ifp); - state->lease.server.s_addr = 0; + state->lease.server.s_addr = INADDR_ANY; state->interval = 0; ifp->options->options &= ~(DHCPCD_CSR_WARNED | DHCPCD_ROUTER_HOST_ROUTE_WARNED); @@ -2327,7 +2385,6 @@ dhcp_arp_address(struct interface *ifp) eloop_timeout_delete(ifp->ctx->eloop, NULL, ifp); state = D_STATE(ifp); - state->state = DHS_PROBE; addr.s_addr = state->offer->yiaddr == INADDR_ANY ? state->offer->ciaddr : state->offer->yiaddr; /* If the interface already has the address configured @@ -2340,6 +2397,7 @@ dhcp_arp_address(struct interface *ifp) #ifdef IN_IFF_TENTATIVE if (ia == NULL || ia->addr_flags & IN_IFF_NOTUSEABLE) { + state->state = DHS_PROBE; if (ia == NULL) { struct dhcp_lease l; @@ -2355,6 +2413,7 @@ dhcp_arp_address(struct interface *ifp) if (ifp->options->options & DHCPCD_ARP && ia == NULL) { struct dhcp_lease l; + state->state = DHS_PROBE; get_lease(ifp, &l, state->offer, state->offer_len); loginfox("%s: probing address %s/%d", ifp->name, inet_ntoa(l.addr), inet_ntocidr(l.mask)); @@ -2570,7 +2629,7 @@ dhcp_reboot(struct interface *ifp) #endif dhcp_new_xid(ifp); - state->lease.server.s_addr = 0; + state->lease.server.s_addr = INADDR_ANY; eloop_timeout_delete(ifp->ctx->eloop, NULL, ifp); #ifdef IPV4LL Index: src/external/bsd/dhcpcd/dist/src/dhcpcd.c diff -u src/external/bsd/dhcpcd/dist/src/dhcpcd.c:1.6 src/external/bsd/dhcpcd/dist/src/dhcpcd.c:1.7 --- src/external/bsd/dhcpcd/dist/src/dhcpcd.c:1.6 Wed Dec 6 10:35:05 2017 +++ src/external/bsd/dhcpcd/dist/src/dhcpcd.c Mon Jan 1 11:50:56 2018 @@ -1,6 +1,6 @@ /* * dhcpcd - DHCP client daemon - * Copyright (c) 2006-2017 Roy Marples <r...@marples.name> + * Copyright (c) 2006-2018 Roy Marples <r...@marples.name> * All rights reserved * Redistribution and use in source and binary forms, with or without @@ -25,7 +25,7 @@ * SUCH DAMAGE. */ -const char dhcpcd_copyright[] = "Copyright (c) 2006-2017 Roy Marples"; +const char dhcpcd_copyright[] = "Copyright (c) 2006-2018 Roy Marples"; #include <sys/file.h> #include <sys/socket.h> @@ -438,7 +438,7 @@ configure_interface1(struct interface *i ~(DHCPCD_IPV6RS | DHCPCD_DHCP6 | DHCPCD_WAITIP6); /* We want to disable kernel interface RA as early as possible. */ - if (ifo->options & DHCPCD_IPV6RS && + if (ifp->active == IF_ACTIVE_USER && !(ifp->ctx->options & DHCPCD_DUMPLEASE)) { int ra_global, ra_iface; @@ -975,6 +975,7 @@ int dhcpcd_handleinterface(void *arg, int action, const char *ifname) { struct dhcpcd_ctx *ctx; + struct ifaddrs *ifaddrs; struct if_head *ifs; struct interface *ifp, *iff, *ifn; const char * const argv[] = { ifname }; @@ -998,7 +999,7 @@ dhcpcd_handleinterface(void *arg, int ac } i = -1; - ifs = if_discover(ctx, -1, UNCONST(argv)); + ifs = if_discover(ctx, &ifaddrs, -1, UNCONST(argv)); if (ifs == NULL) { logerr(__func__); return -1; @@ -1043,6 +1044,17 @@ dhcpcd_handleinterface(void *arg, int ac dhcpcd_prestartinterface(iff); } + if_learnaddrs(ctx, ifs, &ifaddrs); + + /* Now we have learned addresses, start the interface */ + TAILQ_FOREACH_SAFE(ifp, ifs, next, ifn) { + if (strcmp(ifp->name, ifname) != 0) + continue; + iff = if_find(ctx->ifaces, ifp->name); + if (action > 0 && iff->active) + dhcpcd_prestartinterface(iff); + } + /* Free our discovered list */ while ((ifp = TAILQ_FIRST(ifs))) { TAILQ_REMOVE(ifs, ifp, next); @@ -1403,6 +1415,7 @@ int main(int argc, char **argv) { struct dhcpcd_ctx ctx; + struct ifaddrs *ifaddrs = NULL; struct if_options *ifo; struct interface *ifp; uint16_t family = 0; @@ -1678,7 +1691,7 @@ printpidfile: if (optind != argc) { /* We need to try and find the interface so we can load * the hardware address to compare automated IAID */ - ctx.ifaces = if_discover(&ctx, + ctx.ifaces = if_discover(&ctx, &ifaddrs, argc - optind, argv + optind); } else { if ((ctx.ifaces = malloc(sizeof(*ctx.ifaces))) != NULL) @@ -1842,7 +1855,7 @@ printpidfile: (DHCPCD_MASTER | DHCPCD_DEV)) dev_start(&ctx); - ctx.ifaces = if_discover(&ctx, ctx.ifc, ctx.ifv); + ctx.ifaces = if_discover(&ctx, &ifaddrs, ctx.ifc, ctx.ifv); if (ctx.ifaces == NULL) { logerr("%s: if_discover", __func__); goto exit_failure; @@ -1878,6 +1891,7 @@ printpidfile: if (ifp->active) dhcpcd_initstate1(ifp, argc, argv, 0); } + if_learnaddrs(&ctx, ctx.ifaces, &ifaddrs); if (ctx.options & DHCPCD_BACKGROUND && dhcpcd_daemonise(&ctx)) goto exit_success; @@ -1948,6 +1962,8 @@ exit_failure: i = EXIT_FAILURE; exit1: + if (ifaddrs != NULL) + freeifaddrs(ifaddrs); if (control_stop(&ctx) == -1) logerr("%s: control_stop", __func__); /* Free memory and close fd's */