Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/external/bsd/dhcpcd/dist/src Sync
details: https://anonhg.NetBSD.org/src/rev/d24be638e752
branches: trunk
changeset: 845667:d24be638e752
user: roy <roy%NetBSD.org@localhost>
date: Fri Oct 11 11:03:59 2019 +0000
description:
Sync
diffstat:
external/bsd/dhcpcd/dist/src/bpf.c | 81 +--------
external/bsd/dhcpcd/dist/src/dhcp.c | 243 ++++++++++++++++-------------
external/bsd/dhcpcd/dist/src/dhcp6.c | 76 +++-----
external/bsd/dhcpcd/dist/src/dhcpcd.8.in | 11 +-
external/bsd/dhcpcd/dist/src/dhcpcd.c | 7 +-
external/bsd/dhcpcd/dist/src/if-bsd.c | 63 +++++++
external/bsd/dhcpcd/dist/src/if-options.c | 17 +-
7 files changed, 264 insertions(+), 234 deletions(-)
diffs (truncated from 945 to 300 lines):
diff -r 7ea10d50a9d5 -r d24be638e752 external/bsd/dhcpcd/dist/src/bpf.c
--- a/external/bsd/dhcpcd/dist/src/bpf.c Fri Oct 11 11:00:49 2019 +0000
+++ b/external/bsd/dhcpcd/dist/src/bpf.c Fri Oct 11 11:03:59 2019 +0000
@@ -410,13 +410,7 @@
#endif
#ifdef ARP
-
static const struct bpf_insn bpf_arp_ether [] = {
- /* Ensure packet is at least correct size. */
- BPF_STMT(BPF_LD + BPF_W + BPF_LEN, 0),
- BPF_JUMP(BPF_JMP + BPF_JGE + BPF_K, sizeof(struct ether_arp), 1, 0),
- BPF_STMT(BPF_RET + BPF_K, 0),
-
/* Check this is an ARP packet. */
BPF_STMT(BPF_LD + BPF_H + BPF_ABS,
offsetof(struct ether_header, ether_type)),
@@ -552,17 +546,8 @@
}
#endif
-#define BPF_M_FHLEN 0
-#define BPF_M_IPHLEN 1
-#define BPF_M_IPLEN 2
-#define BPF_M_UDP 3
-#define BPF_M_UDPLEN 4
-
#ifdef ARPHRD_NONE
static const struct bpf_insn bpf_bootp_none[] = {
- /* Set the frame header length to zero. */
- BPF_STMT(BPF_LD + BPF_IMM, 0),
- BPF_STMT(BPF_ST, BPF_M_FHLEN),
};
#define BPF_BOOTP_NONE_LEN __arraycount(bpf_bootp_none)
#endif
@@ -574,13 +559,14 @@
BPF_JUMP(BPF_JMP + BPF_JEQ + BPF_K, ETHERTYPE_IP, 1, 0),
BPF_STMT(BPF_RET + BPF_K, 0),
- /* Load frame header length into X. */
- BPF_STMT(BPF_LDX + BPF_W + BPF_IMM, sizeof(struct ether_header)),
- /* Copy frame header length to memory */
- BPF_STMT(BPF_STX, BPF_M_FHLEN),
+ /* Advance to the IP header. */
+ BPF_STMT(BPF_LDX + BPF_K, sizeof(struct ether_header)),
};
#define BPF_BOOTP_ETHER_LEN __arraycount(bpf_bootp_ether)
+#define BOOTP_MIN_SIZE sizeof(struct ip) + sizeof(struct udphdr) + \
+ sizeof(struct bootp)
+
static const struct bpf_insn bpf_bootp_filter[] = {
/* Make sure it's an IPv4 packet. */
BPF_STMT(BPF_LD + BPF_B + BPF_IND, 0),
@@ -588,15 +574,6 @@
BPF_JUMP(BPF_JMP + BPF_JEQ + BPF_K, 0x40, 1, 0),
BPF_STMT(BPF_RET + BPF_K, 0),
- /* Ensure IP header length is big enough and
- * store the IP header length in memory. */
- BPF_STMT(BPF_LD + BPF_B + BPF_IND, 0),
- BPF_STMT(BPF_ALU + BPF_AND + BPF_K, 0x0f),
- BPF_STMT(BPF_ALU + BPF_MUL + BPF_K, 4),
- BPF_JUMP(BPF_JMP + BPF_JGE + BPF_K, sizeof(struct ip), 1, 0),
- BPF_STMT(BPF_RET + BPF_K, 0),
- BPF_STMT(BPF_ST, BPF_M_IPHLEN),
-
/* Make sure it's a UDP packet. */
BPF_STMT(BPF_LD + BPF_B + BPF_IND, offsetof(struct ip, ip_p)),
BPF_JUMP(BPF_JMP + BPF_JEQ + BPF_K, IPPROTO_UDP, 1, 0),
@@ -607,49 +584,17 @@
BPF_JUMP(BPF_JMP + BPF_JSET + BPF_K, 0x1fff, 0, 1),
BPF_STMT(BPF_RET + BPF_K, 0),
- /* Store IP length. */
- BPF_STMT(BPF_LD + BPF_H + BPF_IND, offsetof(struct ip, ip_len)),
- BPF_STMT(BPF_ST, BPF_M_IPLEN),
-
/* Advance to the UDP header. */
- BPF_STMT(BPF_LD + BPF_MEM, BPF_M_IPHLEN),
+ BPF_STMT(BPF_LD + BPF_B + BPF_IND, 0),
+ BPF_STMT(BPF_ALU + BPF_AND + BPF_K, 0x0f),
+ BPF_STMT(BPF_ALU + BPF_MUL + BPF_K, 4),
BPF_STMT(BPF_ALU + BPF_ADD + BPF_X, 0),
BPF_STMT(BPF_MISC + BPF_TAX, 0),
- /* Store UDP location */
- BPF_STMT(BPF_STX, BPF_M_UDP),
-
/* Make sure it's from and to the right port. */
BPF_STMT(BPF_LD + BPF_W + BPF_IND, 0),
BPF_JUMP(BPF_JMP + BPF_JEQ + BPF_K, (BOOTPS << 16) + BOOTPC, 1, 0),
BPF_STMT(BPF_RET + BPF_K, 0),
-
- /* Store UDP length. */
- BPF_STMT(BPF_LD + BPF_H + BPF_IND, offsetof(struct udphdr, uh_ulen)),
- BPF_STMT(BPF_ST, BPF_M_UDPLEN),
-
- /* Ensure that UDP length + IP header length == IP length */
- /* Copy IP header length to X. */
- BPF_STMT(BPF_LDX + BPF_MEM, BPF_M_IPHLEN),
- /* Add UDP length (A) to IP header length (X). */
- BPF_STMT(BPF_ALU + BPF_ADD + BPF_X, 0),
- /* Store result in X. */
- BPF_STMT(BPF_MISC + BPF_TAX, 0),
- /* Copy IP length to A. */
- BPF_STMT(BPF_LD + BPF_MEM, BPF_M_IPLEN),
- /* Ensure X == A. */
- BPF_JUMP(BPF_JMP + BPF_JEQ + BPF_X, 0, 1, 0),
- BPF_STMT(BPF_RET + BPF_K, 0),
-
- /* Advance to the BOOTP packet. */
- BPF_STMT(BPF_LD + BPF_MEM, BPF_M_UDP),
- BPF_STMT(BPF_ALU + BPF_ADD + BPF_K, sizeof(struct udphdr)),
- BPF_STMT(BPF_MISC + BPF_TAX, 0),
-
- /* Make sure it's BOOTREPLY. */
- BPF_STMT(BPF_LD + BPF_B + BPF_IND, offsetof(struct bootp, op)),
- BPF_JUMP(BPF_JMP + BPF_JEQ + BPF_K, BOOTREPLY, 1, 0),
- BPF_STMT(BPF_RET + BPF_K, 0),
};
#define BPF_BOOTP_FILTER_LEN __arraycount(bpf_bootp_filter)
@@ -729,14 +674,8 @@
}
#endif
- /* All passed, return the packet - frame length + ip length */
- BPF_SET_STMT(bp, BPF_LD + BPF_MEM, BPF_M_FHLEN);
- bp++;
- BPF_SET_STMT(bp, BPF_LDX + BPF_MEM, BPF_M_IPLEN);
- bp++;
- BPF_SET_STMT(bp, BPF_ALU + BPF_ADD + BPF_X, 0);
- bp++;
- BPF_SET_STMT(bp, BPF_RET + BPF_A, 0);
+ /* All passed, return the packet. */
+ BPF_SET_STMT(bp, BPF_RET + BPF_K, BPF_WHOLEPACKET);
bp++;
return bpf_attach(fd, bpf, (unsigned int)(bp - bpf));
diff -r 7ea10d50a9d5 -r d24be638e752 external/bsd/dhcpcd/dist/src/dhcp.c
--- a/external/bsd/dhcpcd/dist/src/dhcp.c Fri Oct 11 11:00:49 2019 +0000
+++ b/external/bsd/dhcpcd/dist/src/dhcp.c Fri Oct 11 11:03:59 2019 +0000
@@ -988,7 +988,8 @@
#ifdef AUTH
if ((ifo->auth.options & DHCPCD_AUTH_SENDREQUIRE) !=
- DHCPCD_AUTH_SENDREQUIRE)
+ DHCPCD_AUTH_SENDREQUIRE &&
+ !has_option_mask(ifo->nomask, DHO_FORCERENEW_NONCE))
{
/* We support HMAC-MD5 */
AREA_CHECK(1);
@@ -1032,10 +1033,7 @@
i < ifp->ctx->dhcp_opts_len;
i++, opt++)
{
- if (!(opt->type & OT_REQUEST ||
- has_option_mask(ifo->requestmask, opt->option)))
- continue;
- if (opt->type & OT_NOREQ)
+ if (!DHC_REQOPT(opt, ifo->requestmask, ifo->nomask))
continue;
if (type == DHCP_INFORM &&
(opt->option == DHO_RENEWALTIME ||
@@ -1054,10 +1052,7 @@
break;
if (lp < p)
continue;
- if (!(opt->type & OT_REQUEST ||
- has_option_mask(ifo->requestmask, opt->option)))
- continue;
- if (opt->type & OT_NOREQ)
+ if (!DHC_REQOPT(opt, ifo->requestmask, ifo->nomask))
continue;
if (type == DHCP_INFORM &&
(opt->option == DHO_RENEWALTIME ||
@@ -1738,15 +1733,32 @@
if (r == -1)
goto fail;
len = (size_t)r;
- from.s_addr = bootp->ciaddr;
- if (from.s_addr != INADDR_ANY)
+
+ if (ipv4_iffindaddr(ifp, &state->lease.addr, NULL) != NULL)
+ from.s_addr = state->lease.addr.s_addr;
+ else
+ from.s_addr = INADDR_ANY;
+ if (from.s_addr != INADDR_ANY &&
+ state->lease.server.s_addr != INADDR_ANY)
to.s_addr = state->lease.server.s_addr;
else
- to.s_addr = INADDR_ANY;
-
- /* If unicasting, try and avoid sending by BPF so we don't
- * use a L2 broadcast. */
- if (to.s_addr != INADDR_ANY && to.s_addr != INADDR_BROADCAST) {
+ to.s_addr = INADDR_BROADCAST;
+
+ /*
+ * If not listening on the unspecified address we can
+ * only receive broadcast messages via BPF.
+ * Sockets bound to an address cannot receive broadcast messages
+ * even if they are setup to send them.
+ * Broadcasting from UDP is only an optimisation for rebinding
+ * and on BSD, at least, is reliant on the subnet route being
+ * correctly configured to recieve the unicast reply.
+ * As such, we always broadcast and receive the reply to it via BPF.
+ * This also guarantees we have a DHCP server attached to the
+ * interface we want to configure because we can't dictate the
+ * interface via IP_PKTINFO unlike for IPv6.
+ */
+ if (to.s_addr != INADDR_BROADCAST)
+ {
if (dhcp_sendudp(ifp, &to, bootp, len) != -1)
goto out;
logerr("%s: dhcp_sendudp", ifp->name);
@@ -2001,30 +2013,44 @@
}
-static void
+static bool
dhcp_addr_duplicated(struct interface *ifp, struct in_addr *ia)
{
struct dhcp_state *state = D_STATE(ifp);
+ unsigned long long opts = ifp->options->options;
+ struct dhcpcd_ctx *ctx = ifp->ctx;
+ bool deleted = false;
#ifdef IN_IFF_DUPLICATED
struct ipv4_addr *iap;
#endif
if ((state->offer == NULL || state->offer->yiaddr != ia->s_addr) &&
!IN_ARE_ADDR_EQUAL(ia, &state->lease.addr))
- return;
+ return deleted;
/* RFC 2131 3.1.5, Client-server interaction */
logerrx("%s: DAD detected %s", ifp->name, inet_ntoa(*ia));
unlink(state->leasefile);
- if (!(ifp->options->options & DHCPCD_STATIC) && !state->lease.frominfo)
+ if (!(opts & DHCPCD_STATIC) && !state->lease.frominfo)
dhcp_decline(ifp);
#ifdef IN_IFF_DUPLICATED
- if ((iap = ipv4_iffindaddr(ifp, ia, NULL)) != NULL)
+ if ((iap = ipv4_iffindaddr(ifp, ia, NULL)) != NULL) {
ipv4_deladdr(iap, 0);
+ deleted = true;
+ }
#endif
- eloop_timeout_delete(ifp->ctx->eloop, NULL, ifp);
+ eloop_timeout_delete(ctx->eloop, NULL, ifp);
+ if (opts & (DHCPCD_STATIC | DHCPCD_INFORM)) {
+ state->reason = "EXPIRE";
+ script_runreason(ifp, state->reason);
+#define NOT_ONLY_SELF (DHCPCD_MASTER | DHCPCD_IPV6RS | DHCPCD_DHCP6)
+ if (!(ctx->options & NOT_ONLY_SELF))
+ eloop_exit(ifp->ctx->eloop, EXIT_FAILURE);
+ return deleted;
+ }
eloop_timeout_add_sec(ifp->ctx->eloop,
DHCP_RAND_MAX, dhcp_discover, ifp);
+ return deleted;
}
#endif
@@ -2362,7 +2388,9 @@
/* Add the address now, let the kernel handle DAD. */
ipv4_addaddr(ifp, &l.addr, &l.mask, &l.brd,
l.leasetime, l.rebindtime);
- } else
+ } else if (ia->addr_flags & IN_IFF_DUPLICATED)
+ dhcp_addr_duplicated(ifp, &ia->addr);
+ else
loginfox("%s: waiting for DAD on %s",
ifp->name, inet_ntoa(addr));
return 0;
@@ -2841,14 +2869,18 @@
#define LOGDHCP(l, m) \
log_dhcp((l), (m), ifp, bootp, bootp_len, from, 1)
+#define IS_STATE_ACTIVE(s) ((s)-state != DHS_NONE && \
+ (s)->state != DHS_INIT && (s)->state != DHS_BOUND)
+
if (bootp->op != BOOTREPLY) {
- logdebugx("%s: op (%d) is not BOOTREPLY",
- ifp->name, bootp->op);
+ if (IS_STATE_ACTIVE(state))
+ logdebugx("%s: op (%d) is not BOOTREPLY",
+ ifp->name, bootp->op);
return;
}
if (state->xid != ntohl(bootp->xid)) {
- if (state->state != DHS_BOUND && state->state != DHS_NONE)
+ if (IS_STATE_ACTIVE(state))
logdebugx("%s: wrong xid 0x%x (expecting 0x%x) from %s",
ifp->name, ntohl(bootp->xid), state->xid,
inet_ntoa(*from));
Home |
Main Index |
Thread Index |
Old Index