Sync
This commit is contained in:
parent
9d162be235
commit
1f96c74429
92
external/bsd/dhcpcd/dist/dhcp.c
vendored
92
external/bsd/dhcpcd/dist/dhcp.c
vendored
@ -1,5 +1,5 @@
|
||||
#include <sys/cdefs.h>
|
||||
__RCSID("$NetBSD: dhcp.c,v 1.13 2014/06/14 20:55:37 roy Exp $");
|
||||
__RCSID("$NetBSD: dhcp.c,v 1.14 2014/07/14 11:49:48 roy Exp $");
|
||||
|
||||
/*
|
||||
* dhcpcd - DHCP client daemon
|
||||
@ -128,16 +128,24 @@ static const size_t udp_dhcp_len = sizeof(struct udp_dhcp_packet);
|
||||
static int dhcp_open(struct interface *);
|
||||
|
||||
void
|
||||
dhcp_printoptions(const struct dhcpcd_ctx *ctx)
|
||||
dhcp_printoptions(const struct dhcpcd_ctx *ctx,
|
||||
const struct dhcp_opt *opts, size_t opts_len)
|
||||
{
|
||||
const char * const *p;
|
||||
size_t i;
|
||||
const struct dhcp_opt *opt;
|
||||
size_t i, j;
|
||||
const struct dhcp_opt *opt, *opt2;
|
||||
|
||||
for (p = dhcp_params; *p; p++)
|
||||
printf(" %s\n", *p);
|
||||
|
||||
for (i = 0, opt = ctx->dhcp_opts; i < ctx->dhcp_opts_len; i++, opt++)
|
||||
for (i = 0, opt = ctx->dhcp_opts; i < ctx->dhcp_opts_len; i++, opt++) {
|
||||
for (j = 0, opt2 = opts; j < opts_len; j++, opt2++)
|
||||
if (opt->option == opt2->option)
|
||||
break;
|
||||
if (j == opts_len)
|
||||
printf("%03d %s\n", opt->option, opt->var);
|
||||
}
|
||||
for (i = 0, opt = opts; i < opts_len; i++, opt++)
|
||||
printf("%03d %s\n", opt->option, opt->var);
|
||||
}
|
||||
|
||||
@ -289,7 +297,7 @@ decode_rfc3442(char *out, size_t len, const uint8_t *p, size_t pl)
|
||||
errno = EINVAL;
|
||||
return -1;
|
||||
}
|
||||
ocets = (cidr + 7) / 8;
|
||||
ocets = (cidr + 7) / NBBY;
|
||||
if (!out) {
|
||||
p += 4 + ocets;
|
||||
bytes += ((4 * 4) * 2) + 4;
|
||||
@ -360,7 +368,7 @@ decode_rfc3442_rt(const uint8_t *data, size_t dl)
|
||||
}
|
||||
TAILQ_INSERT_TAIL(routes, rt, next);
|
||||
|
||||
ocets = (cidr + 7) / 8;
|
||||
ocets = (cidr + 7) / NBBY;
|
||||
/* If we have ocets then we have a destination and netmask */
|
||||
if (ocets > 0) {
|
||||
memcpy(&rt->dest.s_addr, p, ocets);
|
||||
@ -946,6 +954,30 @@ make_message(struct dhcp_message **message,
|
||||
goto toobig;
|
||||
*p++ = (uint8_t)opt->option;
|
||||
}
|
||||
for (i = 0, opt = ifo->dhcp_override;
|
||||
i < ifo->dhcp_override_len;
|
||||
i++, opt++)
|
||||
{
|
||||
/* Check if added above */
|
||||
for (lp = n_params + 1; lp < p; lp++)
|
||||
if (*lp == (uint8_t)opt->option)
|
||||
break;
|
||||
if (lp < p)
|
||||
continue;
|
||||
if (!(opt->type & REQUEST ||
|
||||
has_option_mask(ifo->requestmask, opt->option)))
|
||||
continue;
|
||||
if (opt->type & NOREQ)
|
||||
continue;
|
||||
if (type == DHCP_INFORM &&
|
||||
(opt->option == DHO_RENEWALTIME ||
|
||||
opt->option == DHO_REBINDTIME))
|
||||
continue;
|
||||
len = (size_t)((p - m) + 2);
|
||||
if (len > sizeof(*dhcp))
|
||||
goto toobig;
|
||||
*p++ = (uint8_t)opt->option;
|
||||
}
|
||||
*n_params = (uint8_t)(p - n_params - 1);
|
||||
}
|
||||
|
||||
@ -2736,40 +2768,23 @@ dhcp_open(struct interface *ifp)
|
||||
}
|
||||
|
||||
int
|
||||
dhcp_dump(struct dhcpcd_ctx *ctx, const char *ifname)
|
||||
dhcp_dump(struct interface *ifp)
|
||||
{
|
||||
struct interface *ifp;
|
||||
struct dhcp_state *state;
|
||||
|
||||
if (ctx->ifaces == NULL) {
|
||||
ctx->ifaces = malloc(sizeof(*ctx->ifaces));
|
||||
if (ctx->ifaces == NULL)
|
||||
return -1;
|
||||
TAILQ_INIT(ctx->ifaces);
|
||||
}
|
||||
state = NULL;
|
||||
ifp = calloc(1, sizeof(*ifp));
|
||||
if (ifp == NULL)
|
||||
goto eexit;
|
||||
ifp->ctx = ctx;
|
||||
TAILQ_INSERT_HEAD(ctx->ifaces, ifp, next);
|
||||
ifp->if_data[IF_DATA_DHCP] = state = calloc(1, sizeof(*state));
|
||||
if (state == NULL)
|
||||
goto eexit;
|
||||
ifp->options = calloc(1, sizeof(*ifp->options));
|
||||
if (ifp->options == NULL)
|
||||
goto eexit;
|
||||
strlcpy(ifp->name, ifname, sizeof(ifp->name));
|
||||
snprintf(state->leasefile, sizeof(state->leasefile),
|
||||
LEASEFILE, ifp->name);
|
||||
state->new = read_lease(ifp);
|
||||
if (state->new == NULL && errno == ENOENT) {
|
||||
strlcpy(state->leasefile, ifname, sizeof(state->leasefile));
|
||||
strlcpy(state->leasefile, ifp->name, sizeof(state->leasefile));
|
||||
state->new = read_lease(ifp);
|
||||
}
|
||||
if (state->new == NULL) {
|
||||
if (errno == ENOENT)
|
||||
syslog(LOG_ERR, "%s: no lease to dump", ifname);
|
||||
syslog(LOG_ERR, "%s: no lease to dump", ifp->name);
|
||||
return -1;
|
||||
}
|
||||
state->reason = "DUMP";
|
||||
@ -3018,13 +3033,22 @@ dhcp_start(struct interface *ifp)
|
||||
if (!(ifp->options->options & DHCPCD_IPV4))
|
||||
return;
|
||||
|
||||
tv.tv_sec = DHCP_MIN_DELAY;
|
||||
tv.tv_usec = (suseconds_t)arc4random_uniform(
|
||||
(DHCP_MAX_DELAY - DHCP_MIN_DELAY) * 1000000);
|
||||
timernorm(&tv);
|
||||
syslog(LOG_DEBUG,
|
||||
"%s: delaying DHCP for %0.1f seconds",
|
||||
ifp->name, timeval_to_double(&tv));
|
||||
/* No point in delaying a static configuration */
|
||||
if (ifp->options->options & DHCPCD_STATIC &&
|
||||
!(ifp->options->options & DHCPCD_INFORM))
|
||||
{
|
||||
tv.tv_sec = 0;
|
||||
tv.tv_usec = 0;
|
||||
} else {
|
||||
tv.tv_sec = DHCP_MIN_DELAY;
|
||||
tv.tv_usec = (suseconds_t)arc4random_uniform(
|
||||
(DHCP_MAX_DELAY - DHCP_MIN_DELAY) * 1000000);
|
||||
timernorm(&tv);
|
||||
syslog(LOG_DEBUG,
|
||||
"%s: delaying DHCP for %0.1f seconds",
|
||||
ifp->name, timeval_to_double(&tv));
|
||||
}
|
||||
|
||||
eloop_timeout_add_tv(ifp->ctx->eloop, &tv, dhcp_start1, ifp);
|
||||
}
|
||||
|
||||
|
29
external/bsd/dhcpcd/dist/dhcpcd.8.in
vendored
29
external/bsd/dhcpcd/dist/dhcpcd.8.in
vendored
@ -1,4 +1,4 @@
|
||||
.\" $NetBSD: dhcpcd.8.in,v 1.28 2014/06/14 20:55:37 roy Exp $
|
||||
.\" $NetBSD: dhcpcd.8.in,v 1.29 2014/07/14 11:49:48 roy Exp $
|
||||
.\" Copyright (c) 2006-2014 Roy Marples
|
||||
.\" All rights reserved
|
||||
.\"
|
||||
@ -23,7 +23,7 @@
|
||||
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.Dd June 2, 2014
|
||||
.Dd July 7, 2014
|
||||
.Dt DHCPCD 8
|
||||
.Os
|
||||
.Sh NAME
|
||||
@ -76,7 +76,7 @@
|
||||
.Sh DESCRIPTION
|
||||
.Nm
|
||||
is an implementation of the DHCP client specified in
|
||||
.%R RFC 2131 .
|
||||
.Li RFC 2131 .
|
||||
.Nm
|
||||
gets the host information
|
||||
.Po
|
||||
@ -104,17 +104,17 @@ to renew early.
|
||||
.Pp
|
||||
.Nm
|
||||
is also an implementation of the BOOTP client specified in
|
||||
.%R RFC 951 .
|
||||
.Li RFC 951 .
|
||||
.Pp
|
||||
.Nm
|
||||
is also an implementation of the IPv6 Router Solicitor as specified in
|
||||
.%R RFC 4861
|
||||
.Li RFC 4861
|
||||
and
|
||||
.%R RFC 6106 .
|
||||
.Li RFC 6106 .
|
||||
.Pp
|
||||
.Nm
|
||||
is also an implemenation of the DHCPv6 client as specified in
|
||||
.%R RFC 3315 .
|
||||
.Li RFC 3315 .
|
||||
By default,
|
||||
.Nm
|
||||
only starts DHCPv6 when instructed to do so by an IPV6 Router Advertisement.
|
||||
@ -212,7 +212,7 @@ instead of the default
|
||||
.Pa @SCRIPT@ .
|
||||
.It Fl D , Fl Fl duid
|
||||
Generate an
|
||||
.%R RFC 4361
|
||||
.Li RFC 4361
|
||||
compliant clientid.
|
||||
This requires persistent storage and not all DHCP servers work with it so it
|
||||
is not enabled by default.
|
||||
@ -260,7 +260,7 @@ are disable, none, ptr and both.
|
||||
itself never does any DNS updates.
|
||||
.Nm
|
||||
encodes the FQDN hostname as specified in
|
||||
.%R RFC1035 .
|
||||
.Li RFC1035 .
|
||||
.It Fl f , Fl Fl config Ar file
|
||||
Specify a config to load instead of
|
||||
.Pa @SYSCONFDIR@/dhcpcd.conf .
|
||||
@ -553,6 +553,14 @@ Dumps the last lease for the
|
||||
to stdout.
|
||||
.Ar interface
|
||||
could also be a path to a DHCP wire formatted file.
|
||||
Use the
|
||||
.Fl 4
|
||||
or
|
||||
.Fl 6
|
||||
flags to specify an address family.
|
||||
Pass a 2nd
|
||||
.Fl U, Fl Fl dumplease option to dump a secondary lease, such as
|
||||
DHCPv6 Prefix Delegation when not being mixed with another IA type.
|
||||
.It Fl V, Fl Fl variables
|
||||
Display a list of option codes and the associated variable for use in
|
||||
.Xr dhcpcd-run-hooks 8 .
|
||||
@ -672,7 +680,8 @@ RFC\ 951, RFC\ 1534, RFC\ 2104, RFC\ 2131, RFC\ 2132, RFC\ 2563, RFC\ 2855,
|
||||
RFC\ 3004, RFC\ 3118, RFC\ 3203, RFC\ 3315, RFC\ 3361, RFC\ 3633, RFC\ 3396,
|
||||
RFC\ 3397, RFC\ 3442, RFC\ 3495, RFC\ 3925, RFC\ 3927, RFC\ 4039, RFC\ 4075,
|
||||
RFC\ 4242, RFC\ 4361, RFC\ 4390, RFC\ 4702, RFC\ 4074, RFC\ 4861, RFC\ 4833,
|
||||
RFC\ 5227, RFC\ 5942, RFC\ 5969, RFC\ 6106, RFC\ 6334, RFC\ 6704, RFC\ 7217.
|
||||
RFC\ 5227, RFC\ 5942, RFC\ 5969, RFC\ 6106, RFC\ 6334, RFC\ 6603, RFC\ 6704,
|
||||
RFC\ 7217.
|
||||
.Sh AUTHORS
|
||||
.An Roy Marples Aq Mt roy@marples.name
|
||||
.Sh BUGS
|
||||
|
269
external/bsd/dhcpcd/dist/dhcpcd.c
vendored
269
external/bsd/dhcpcd/dist/dhcpcd.c
vendored
@ -1,5 +1,5 @@
|
||||
#include <sys/cdefs.h>
|
||||
__RCSID("$NetBSD: dhcpcd.c,v 1.5 2014/06/14 20:55:37 roy Exp $");
|
||||
__RCSID("$NetBSD: dhcpcd.c,v 1.6 2014/07/14 11:49:48 roy Exp $");
|
||||
|
||||
/*
|
||||
* dhcpcd - DHCP client daemon
|
||||
@ -142,14 +142,14 @@ free_globals(struct dhcpcd_ctx *ctx)
|
||||
struct dhcp_opt *opt;
|
||||
|
||||
if (ctx->ifac) {
|
||||
for (ctx->ifac--; ctx->ifac >= 0; ctx->ifac--)
|
||||
free(ctx->ifav[ctx->ifac]);
|
||||
for (; ctx->ifac > 0; ctx->ifac--)
|
||||
free(ctx->ifav[ctx->ifac - 1]);
|
||||
free(ctx->ifav);
|
||||
ctx->ifav = NULL;
|
||||
}
|
||||
if (ctx->ifdc) {
|
||||
for (ctx->ifdc--; ctx->ifdc >= 0; ctx->ifdc--)
|
||||
free(ctx->ifdv[ctx->ifdc]);
|
||||
for (; ctx->ifdc > 0; ctx->ifdc--)
|
||||
free(ctx->ifdv[ctx->ifdc - 1]);
|
||||
free(ctx->ifdv);
|
||||
ctx->ifdv = NULL;
|
||||
}
|
||||
@ -326,6 +326,9 @@ configure_interface1(struct interface *ifp)
|
||||
{
|
||||
struct if_options *ifo = ifp->options;
|
||||
int ra_global, ra_iface;
|
||||
#ifdef INET6
|
||||
size_t i;
|
||||
#endif
|
||||
|
||||
/* Do any platform specific configuration */
|
||||
if_conf(ifp);
|
||||
@ -342,7 +345,7 @@ configure_interface1(struct interface *ifp)
|
||||
ifo->options &= ~(DHCPCD_ARP | DHCPCD_IPV4LL);
|
||||
if (!(ifp->flags & (IFF_POINTOPOINT | IFF_LOOPBACK | IFF_MULTICAST)))
|
||||
ifo->options &= ~DHCPCD_IPV6RS;
|
||||
if (ifo->options & DHCPCD_LINK && if_carrier(ifp) == LINK_UNKNOWN)
|
||||
if (ifo->options & DHCPCD_LINK && ifp->carrier == LINK_UNKNOWN)
|
||||
ifo->options &= ~DHCPCD_LINK;
|
||||
|
||||
if (ifo->metric != -1)
|
||||
@ -434,17 +437,27 @@ configure_interface1(struct interface *ifp)
|
||||
}
|
||||
|
||||
#ifdef INET6
|
||||
if (ifo->ia == NULL && ifo->options & DHCPCD_IPV6) {
|
||||
ifo->ia = malloc(sizeof(*ifo->ia));
|
||||
if (ifo->ia == NULL)
|
||||
syslog(LOG_ERR, "%s: %m", __func__);
|
||||
else {
|
||||
if (ifo->ia_type == 0)
|
||||
ifo->ia_type = D6_OPTION_IA_NA;
|
||||
memcpy(ifo->ia->iaid, ifo->iaid, sizeof(ifo->iaid));
|
||||
ifo->ia_len = 1;
|
||||
ifo->ia->sla = NULL;
|
||||
ifo->ia->sla_len = 0;
|
||||
if (ifo->options & DHCPCD_IPV6) {
|
||||
if (ifo->ia == NULL) {
|
||||
ifo->ia = malloc(sizeof(*ifo->ia));
|
||||
if (ifo->ia == NULL)
|
||||
syslog(LOG_ERR, "%s: %m", __func__);
|
||||
else {
|
||||
ifo->ia_len = 1;
|
||||
ifo->ia->ia_type = D6_OPTION_IA_NA;
|
||||
memcpy(ifo->ia->iaid, ifo->iaid,
|
||||
sizeof(ifo->iaid));
|
||||
memset(&ifo->ia->addr, 0,
|
||||
sizeof(ifo->ia->addr));
|
||||
ifo->ia->sla = NULL;
|
||||
ifo->ia->sla_len = 0;
|
||||
}
|
||||
} else {
|
||||
for (i = 0; i < ifo->ia_len; i++) {
|
||||
if (!ifo->ia[i].iaid_set)
|
||||
memcpy(ifo->ia->iaid, ifo->iaid,
|
||||
sizeof(ifo->iaid));
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
@ -496,10 +509,23 @@ dhcpcd_handlecarrier(struct dhcpcd_ctx *ctx, int carrier, unsigned int flags,
|
||||
if (ifp == NULL || !(ifp->options->options & DHCPCD_LINK))
|
||||
return;
|
||||
|
||||
if (carrier == LINK_UNKNOWN)
|
||||
switch(carrier) {
|
||||
case LINK_UNKNOWN:
|
||||
carrier = if_carrier(ifp); /* will set ifp->flags */
|
||||
else
|
||||
break;
|
||||
case LINK_UP:
|
||||
/* we have a carrier! however, we need to ignore the flags
|
||||
* set in the kernel message as sometimes this message is
|
||||
* reported before IFF_UP is set by the kernel even though
|
||||
* dhcpcd has already set it.
|
||||
*
|
||||
* So we check the flags now. If IFF_UP is still not set
|
||||
* then we should expect an accompanying link_down message */
|
||||
if_setflag(ifp, 0); /* will set ifp->flags */
|
||||
break;
|
||||
default:
|
||||
ifp->flags = flags;
|
||||
}
|
||||
|
||||
if (carrier == LINK_UNKNOWN)
|
||||
syslog(LOG_ERR, "%s: carrier_status: %m", ifname);
|
||||
@ -547,6 +573,8 @@ warn_iaid_conflict(struct interface *ifp, uint8_t *iaid)
|
||||
TAILQ_FOREACH(ifn, ifp->ctx->ifaces, next) {
|
||||
if (ifn == ifp)
|
||||
continue;
|
||||
if (ifn->options->options & DHCPCD_PFXDLGONLY)
|
||||
continue;
|
||||
if (memcmp(ifn->options->iaid, iaid,
|
||||
sizeof(ifn->options->iaid)) == 0)
|
||||
break;
|
||||
@ -558,12 +586,26 @@ warn_iaid_conflict(struct interface *ifp, uint8_t *iaid)
|
||||
}
|
||||
|
||||
/* This is only a problem if the interfaces are on the same network. */
|
||||
if (ifn)
|
||||
if (ifn && strcmp(ifp->name, ifn->name))
|
||||
syslog(LOG_ERR,
|
||||
"%s: IAID conflicts with one assigned to %s",
|
||||
ifp->name, ifn->name);
|
||||
}
|
||||
|
||||
static void
|
||||
pre_start(struct interface *ifp)
|
||||
{
|
||||
|
||||
/* Add our link-local address before upping the interface
|
||||
* so our RFC7217 address beats the hwaddr based one.
|
||||
* This is also a safety check incase it was ripped out
|
||||
* from under us. */
|
||||
if (ifp->options->options & DHCPCD_IPV6 && ipv6_start(ifp) == -1) {
|
||||
syslog(LOG_ERR, "%s: ipv6_start: %m", ifp->name);
|
||||
ifp->options->options &= DHCPCD_IPV6;
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
dhcpcd_startinterface(void *arg)
|
||||
{
|
||||
@ -572,24 +614,11 @@ dhcpcd_startinterface(void *arg)
|
||||
size_t i;
|
||||
char buf[DUID_LEN * 3];
|
||||
|
||||
/* Add our link-local address before upping the interface
|
||||
* so our RFC7217 address beats the hwaddr based one.
|
||||
* This is also a safety check incase it was ripped out
|
||||
* from under us. */
|
||||
if (ifo->options & DHCPCD_IPV6 && ipv6_start(ifp) == -1) {
|
||||
syslog(LOG_ERR, "%s: ipv6_start: %m", ifp->name);
|
||||
ifo->options &= DHCPCD_IPV6;
|
||||
}
|
||||
pre_start(ifp);
|
||||
if (if_up(ifp) == -1)
|
||||
syslog(LOG_ERR, "%s: if_up: %m", ifp->name);
|
||||
|
||||
if (!(ifp->flags & IFF_UP) && if_carrier(ifp) != LINK_UNKNOWN) {
|
||||
if (if_up(ifp) == -1)
|
||||
syslog(LOG_ERR, "%s: if_up: %m",
|
||||
ifp->name);
|
||||
}
|
||||
|
||||
if (ifp->carrier == LINK_UNKNOWN)
|
||||
dhcpcd_handlecarrier(ifp->ctx, LINK_UNKNOWN, 0, ifp->name);
|
||||
if (ifp->carrier == LINK_DOWN) {
|
||||
if (ifp->carrier == LINK_DOWN && ifo->options & DHCPCD_LINK) {
|
||||
syslog(LOG_INFO, "%s: waiting for carrier", ifp->name);
|
||||
return;
|
||||
}
|
||||
@ -599,11 +628,17 @@ dhcpcd_startinterface(void *arg)
|
||||
if (ifp->ctx->duid == NULL) {
|
||||
if (duid_init(ifp) == 0)
|
||||
return;
|
||||
syslog(LOG_INFO, "DUID %s",
|
||||
hwaddr_ntoa(ifp->ctx->duid, ifp->ctx->duid_len,
|
||||
buf, sizeof(buf)));
|
||||
if (!(ifo->options & DHCPCD_PFXDLGONLY))
|
||||
syslog(LOG_INFO, "DUID %s",
|
||||
hwaddr_ntoa(ifp->ctx->duid,
|
||||
ifp->ctx->duid_len,
|
||||
buf, sizeof(buf)));
|
||||
}
|
||||
}
|
||||
|
||||
if (ifo->options & (DHCPCD_DUID | DHCPCD_IPV6) &&
|
||||
!(ifo->options & DHCPCD_PFXDLGONLY))
|
||||
{
|
||||
/* Report IAIDs */
|
||||
syslog(LOG_INFO, "%s: IAID %s", ifp->name,
|
||||
hwaddr_ntoa(ifo->iaid, sizeof(ifo->iaid),
|
||||
@ -624,10 +659,12 @@ dhcpcd_startinterface(void *arg)
|
||||
|
||||
if (ifo->options & DHCPCD_IPV6) {
|
||||
if (ifo->options & DHCPCD_IPV6RS &&
|
||||
!(ifo->options & DHCPCD_INFORM))
|
||||
!(ifo->options & (DHCPCD_INFORM | DHCPCD_PFXDLGONLY)))
|
||||
ipv6nd_startrs(ifp);
|
||||
|
||||
if (!(ifo->options & DHCPCD_IPV6RS)) {
|
||||
if (!(ifo->options & DHCPCD_IPV6RS) ||
|
||||
ifo->options & DHCPCD_IA_FORCED)
|
||||
{
|
||||
ssize_t nolease;
|
||||
|
||||
if (ifo->options & DHCPCD_IA_FORCED)
|
||||
@ -654,6 +691,8 @@ dhcpcd_startinterface(void *arg)
|
||||
"%s: dhcp6_start: %m", ifp->name);
|
||||
}
|
||||
}
|
||||
if (ifo->options & DHCPCD_PFXDLGONLY)
|
||||
return;
|
||||
|
||||
if (ifo->options & DHCPCD_IPV4)
|
||||
dhcp_start(ifp);
|
||||
@ -674,7 +713,7 @@ handle_link(void *arg)
|
||||
}
|
||||
|
||||
static void
|
||||
init_state(struct interface *ifp, int argc, char **argv)
|
||||
dhcpcd_initstate1(struct interface *ifp, int argc, char **argv)
|
||||
{
|
||||
struct if_options *ifo;
|
||||
|
||||
@ -700,34 +739,27 @@ init_state(struct interface *ifp, int argc, char **argv)
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
dhcpcd_initstate(struct interface *ifp)
|
||||
{
|
||||
|
||||
dhcpcd_initstate1(ifp, ifp->ctx->argc, ifp->ctx->argv);
|
||||
}
|
||||
|
||||
static void
|
||||
run_preinit(struct interface *ifp)
|
||||
{
|
||||
const char *reason;
|
||||
|
||||
reason = NULL; /* appease gcc */
|
||||
if (ifp->options->options & DHCPCD_LINK) {
|
||||
switch (if_carrier(ifp)) {
|
||||
case LINK_DOWN:
|
||||
ifp->carrier = LINK_DOWN;
|
||||
reason = "NOCARRIER";
|
||||
break;
|
||||
case LINK_UP:
|
||||
ifp->carrier = LINK_UP;
|
||||
reason = "CARRIER";
|
||||
break;
|
||||
default:
|
||||
ifp->carrier = LINK_UNKNOWN;
|
||||
return;
|
||||
}
|
||||
} else
|
||||
ifp->carrier = LINK_UNKNOWN;
|
||||
pre_start(ifp);
|
||||
if (ifp->ctx->options & DHCPCD_TEST)
|
||||
return;
|
||||
|
||||
if (!(ifp->ctx->options & DHCPCD_TEST))
|
||||
script_runreason(ifp, "PREINIT");
|
||||
script_runreason(ifp, "PREINIT");
|
||||
|
||||
if (ifp->carrier != LINK_UNKNOWN && !(ifp->ctx->options & DHCPCD_TEST))
|
||||
script_runreason(ifp, reason);
|
||||
if (ifp->carrier != LINK_UNKNOWN &&
|
||||
ifp->options->options & DHCPCD_LINK)
|
||||
script_runreason(ifp,
|
||||
ifp->carrier == LINK_UP ? "CARRIER" : "NOCARRIER");
|
||||
}
|
||||
|
||||
int
|
||||
@ -735,7 +767,7 @@ dhcpcd_handleinterface(void *arg, int action, const char *ifname)
|
||||
{
|
||||
struct dhcpcd_ctx *ctx;
|
||||
struct if_head *ifs;
|
||||
struct interface *ifp, *ifn, *ifl = NULL;
|
||||
struct interface *ifp, *iff, *ifn;
|
||||
const char * const argv[] = { ifname };
|
||||
int i;
|
||||
|
||||
@ -746,6 +778,7 @@ dhcpcd_handleinterface(void *arg, int action, const char *ifname)
|
||||
errno = ESRCH;
|
||||
return -1;
|
||||
}
|
||||
syslog(LOG_DEBUG, "%s: interface departed", ifp->name);
|
||||
ifp->options->options |= DHCPCD_DEPARTED;
|
||||
stop_interface(ifp);
|
||||
return 0;
|
||||
@ -767,22 +800,24 @@ dhcpcd_handleinterface(void *arg, int action, const char *ifname)
|
||||
continue;
|
||||
i = 0;
|
||||
/* Check if we already have the interface */
|
||||
ifl = if_find(ctx, ifp->name);
|
||||
if (ifl) {
|
||||
iff = if_find(ctx, ifp->name);
|
||||
if (iff) {
|
||||
syslog(LOG_DEBUG, "%s: interface updated", iff->name);
|
||||
/* The flags and hwaddr could have changed */
|
||||
ifl->flags = ifp->flags;
|
||||
ifl->hwlen = ifp->hwlen;
|
||||
iff->flags = ifp->flags;
|
||||
iff->hwlen = ifp->hwlen;
|
||||
if (ifp->hwlen != 0)
|
||||
memcpy(ifl->hwaddr, ifp->hwaddr, ifl->hwlen);
|
||||
memcpy(iff->hwaddr, ifp->hwaddr, iff->hwlen);
|
||||
} else {
|
||||
syslog(LOG_DEBUG, "%s: interface added", ifp->name);
|
||||
TAILQ_REMOVE(ifs, ifp, next);
|
||||
TAILQ_INSERT_TAIL(ctx->ifaces, ifp, next);
|
||||
}
|
||||
if (action > 0) {
|
||||
init_state(ifp, ctx->argc, ctx->argv);
|
||||
dhcpcd_initstate(ifp);
|
||||
run_preinit(ifp);
|
||||
dhcpcd_startinterface(ifp);
|
||||
iff = ifp;
|
||||
}
|
||||
if (action > 0)
|
||||
dhcpcd_startinterface(iff);
|
||||
}
|
||||
|
||||
/* Free our discovered list */
|
||||
@ -857,7 +892,7 @@ reconf_reboot(struct dhcpcd_ctx *ctx, int action, int argc, char **argv, int oi)
|
||||
if_free(ifp);
|
||||
} else {
|
||||
TAILQ_INSERT_TAIL(ctx->ifaces, ifp, next);
|
||||
init_state(ifp, argc, argv);
|
||||
dhcpcd_initstate1(ifp, argc, argv);
|
||||
run_preinit(ifp);
|
||||
dhcpcd_startinterface(ifp);
|
||||
}
|
||||
@ -870,7 +905,7 @@ reconf_reboot(struct dhcpcd_ctx *ctx, int action, int argc, char **argv, int oi)
|
||||
static void
|
||||
stop_all_interfaces(struct dhcpcd_ctx *ctx, int do_release)
|
||||
{
|
||||
struct interface *ifp;
|
||||
struct interface *ifp, *ifpm;
|
||||
|
||||
/* drop_dhcp could change the order, so we do it like this. */
|
||||
for (;;) {
|
||||
@ -878,6 +913,10 @@ stop_all_interfaces(struct dhcpcd_ctx *ctx, int do_release)
|
||||
ifp = TAILQ_LAST(ctx->ifaces, if_head);
|
||||
if (ifp == NULL)
|
||||
break;
|
||||
/* Stop the master interface only */
|
||||
ifpm = if_find(ifp->ctx, ifp->name);
|
||||
if (ifpm)
|
||||
ifp = ifpm;
|
||||
if (do_release) {
|
||||
ifp->options->options |= DHCPCD_RELEASE;
|
||||
ifp->options->options &= ~DHCPCD_PERSISTENT;
|
||||
@ -1250,10 +1289,13 @@ main(int argc, char **argv)
|
||||
i = 1;
|
||||
break;
|
||||
case 'U':
|
||||
i = 2;
|
||||
if (i == 3)
|
||||
i = 4;
|
||||
else if (i != 4)
|
||||
i = 3;
|
||||
break;
|
||||
case 'V':
|
||||
i = 3;
|
||||
i = 2;
|
||||
break;
|
||||
case '?':
|
||||
usage();
|
||||
@ -1267,25 +1309,36 @@ main(int argc, char **argv)
|
||||
ctx.ifv = argv + optind;
|
||||
|
||||
ifo = read_config(&ctx, NULL, NULL, NULL);
|
||||
if (ifo == NULL)
|
||||
goto exit_failure;
|
||||
opt = add_options(&ctx, NULL, ifo, argc, argv);
|
||||
if (opt != 1) {
|
||||
if (opt == 0)
|
||||
usage();
|
||||
goto exit_failure;
|
||||
}
|
||||
if (i == 3) {
|
||||
if (i == 2) {
|
||||
printf("Interface options:\n");
|
||||
if (optind == argc - 1) {
|
||||
free_options(ifo);
|
||||
ifo = read_config(&ctx, argv[optind], NULL, NULL);
|
||||
if (ifo == NULL)
|
||||
goto exit_failure;
|
||||
add_options(&ctx, NULL, ifo, argc, argv);
|
||||
}
|
||||
if_printoptions();
|
||||
#ifdef INET
|
||||
if (family == 0 || family == AF_INET) {
|
||||
printf("\nDHCPv4 options:\n");
|
||||
dhcp_printoptions(&ctx);
|
||||
dhcp_printoptions(&ctx,
|
||||
ifo->dhcp_override, ifo->dhcp_override_len);
|
||||
}
|
||||
#endif
|
||||
#ifdef INET6
|
||||
if (family == 0 || family == AF_INET6) {
|
||||
printf("\nDHCPv6 options:\n");
|
||||
dhcp6_printoptions(&ctx);
|
||||
dhcp6_printoptions(&ctx,
|
||||
ifo->dhcp6_override, ifo->dhcp6_override_len);
|
||||
}
|
||||
#endif
|
||||
goto exit_success;
|
||||
@ -1296,6 +1349,8 @@ main(int argc, char **argv)
|
||||
ctx.options |= DHCPCD_TEST;
|
||||
else
|
||||
ctx.options |= DHCPCD_DUMPLEASE;
|
||||
if (i == 4)
|
||||
ctx.options |= DHCPCD_PFXDLGONLY;
|
||||
ctx.options |= DHCPCD_PERSISTENT;
|
||||
ctx.options &= ~DHCPCD_DAEMONISE;
|
||||
}
|
||||
@ -1344,8 +1399,7 @@ main(int argc, char **argv)
|
||||
}
|
||||
snprintf(pidfile, sizeof(pidfile),
|
||||
PIDFILE, "-", argv[optind], per);
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
snprintf(pidfile, sizeof(pidfile), PIDFILE, "", "", "");
|
||||
ctx.options |= DHCPCD_MASTER;
|
||||
}
|
||||
@ -1354,12 +1408,48 @@ main(int argc, char **argv)
|
||||
if (chdir("/") == -1)
|
||||
syslog(LOG_ERR, "chdir `/': %m");
|
||||
|
||||
/* Freeing allocated addresses from dumping leases can trigger
|
||||
* eloop removals as well, so init here. */
|
||||
ctx.eloop = eloop_init();
|
||||
if (ctx.eloop == NULL) {
|
||||
syslog(LOG_ERR, "%s: %m", __func__);
|
||||
goto exit_failure;
|
||||
}
|
||||
|
||||
if (ctx.options & DHCPCD_DUMPLEASE) {
|
||||
if (optind != argc - 1) {
|
||||
syslog(LOG_ERR, "dumplease requires an interface");
|
||||
goto exit_failure;
|
||||
}
|
||||
if (dhcp_dump(&ctx, argv[optind]) == -1)
|
||||
i = 0;
|
||||
/* We need to try and find the interface so we can
|
||||
* load the hardware address to compare automated IAID */
|
||||
ctx.ifaces = if_discover(&ctx, 1, argv + optind);
|
||||
if (ctx.ifaces == NULL)
|
||||
goto exit_failure;
|
||||
ifp = TAILQ_FIRST(ctx.ifaces);
|
||||
if (ifp == NULL) {
|
||||
ifp = calloc(1, sizeof(*ifp));
|
||||
if (ifp == NULL) {
|
||||
syslog(LOG_ERR, "%s: %m", __func__);
|
||||
goto exit_failure;
|
||||
}
|
||||
strlcpy(ifp->name, argv[optind], sizeof(ifp->name));
|
||||
ifp->ctx = &ctx;
|
||||
TAILQ_INSERT_HEAD(ctx.ifaces, ifp, next);
|
||||
}
|
||||
configure_interface(ifp, ctx.argc, ctx.argv);
|
||||
if (ctx.options & DHCPCD_PFXDLGONLY)
|
||||
ifp->options->options |= DHCPCD_PFXDLGONLY;
|
||||
if (family == 0 || family == AF_INET) {
|
||||
if (dhcp_dump(ifp) == -1)
|
||||
i = 1;
|
||||
}
|
||||
if (family == 0 || family == AF_INET6) {
|
||||
if (dhcp6_dump(ifp) == -1)
|
||||
i = 1;
|
||||
}
|
||||
if (i == -1)
|
||||
goto exit_failure;
|
||||
goto exit_success;
|
||||
}
|
||||
@ -1399,12 +1489,6 @@ main(int argc, char **argv)
|
||||
syslog(LOG_WARNING,
|
||||
PACKAGE " will not work correctly unless run as root");
|
||||
|
||||
ctx.eloop = eloop_init();
|
||||
if (ctx.eloop == NULL) {
|
||||
syslog(LOG_ERR, "%s: %m", __func__);
|
||||
goto exit_failure;
|
||||
}
|
||||
|
||||
#ifdef USE_SIGNALS
|
||||
if (sig != 0) {
|
||||
pid = read_pid(pidfile);
|
||||
@ -1556,7 +1640,7 @@ main(int argc, char **argv)
|
||||
}
|
||||
|
||||
TAILQ_FOREACH(ifp, ctx.ifaces, next) {
|
||||
init_state(ifp, argc, argv);
|
||||
dhcpcd_initstate1(ifp, argc, argv);
|
||||
}
|
||||
|
||||
if (ctx.options & DHCPCD_BACKGROUND && dhcpcd_daemonise(&ctx))
|
||||
@ -1625,7 +1709,6 @@ exit1:
|
||||
|
||||
free_options(ifo);
|
||||
free_globals(&ctx);
|
||||
if_rarestore(&ctx);
|
||||
ipv4_ctxfree(&ctx);
|
||||
ipv6_ctxfree(&ctx);
|
||||
dev_stop(&ctx, !(ctx.options & DHCPCD_FORKED));
|
||||
|
34
external/bsd/dhcpcd/dist/dhcpcd.conf.5.in
vendored
34
external/bsd/dhcpcd/dist/dhcpcd.conf.5.in
vendored
@ -1,4 +1,4 @@
|
||||
.\" $NetBSD: dhcpcd.conf.5.in,v 1.8 2014/06/14 20:55:37 roy Exp $
|
||||
.\" $NetBSD: dhcpcd.conf.5.in,v 1.9 2014/07/14 11:49:48 roy Exp $
|
||||
.\" Copyright (c) 2006-2014 Roy Marples
|
||||
.\" All rights reserved
|
||||
.\"
|
||||
@ -23,7 +23,7 @@
|
||||
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.Dd June 6, 2014
|
||||
.Dd July 7, 2014
|
||||
.Dt DHCPCD.CONF 5
|
||||
.Os
|
||||
.Sh NAME
|
||||
@ -215,7 +215,7 @@ DNS if the domain part does not match theirs.
|
||||
Also, see the
|
||||
.Ic env
|
||||
option above to control how the hostname is set on the host.
|
||||
.It Ic ia_na Op Ar iaid
|
||||
.It Ic ia_na Op Ar iaid Op / address
|
||||
Request a DHCPv6 Normal Address for
|
||||
.Ar iaid .
|
||||
.Ar iaid
|
||||
@ -231,7 +231,7 @@ Request a DHCPv6 Temporary Address for
|
||||
You can request more than one ia_ta by specifying a unique
|
||||
.Ar iaid
|
||||
for each one.
|
||||
.It Ic ia_pd Op Ar iaid Op Ar interface Op / Ar sla_id Op / Ar prefix_len
|
||||
.It Ic ia_pd Op Ar iaid Oo / Ar prefix / Ar prefix_len Oc Op Ar interface Op / Ar sla_id Op / Ar prefix_len
|
||||
Request a DHCPv6 Delegated Prefix for
|
||||
.Ar iaid .
|
||||
This option must be used in an
|
||||
@ -251,7 +251,10 @@ Otherwise addresses are only assigned for each
|
||||
and
|
||||
.Ar sla_id .
|
||||
Each assigned address will have a suffix of 1.
|
||||
You cannot assign a prefix to the requesting interface.
|
||||
You cannot assign a prefix to the requesting interface unless the
|
||||
DHCPv6 server supports
|
||||
.Li RFC6603
|
||||
Prefix Exclude Option.
|
||||
.Nm dhcpcd
|
||||
has to be running for all the interfaces it is delegating to.
|
||||
A default
|
||||
@ -291,6 +294,18 @@ IPv6RS should be disabled globally when requesting a Prefix Delegation like so:
|
||||
.D1 interface eth1
|
||||
.D1 ipv4
|
||||
.D1 ipv6rs
|
||||
.It Ic ia_pd_mix
|
||||
To be RFC compliant,
|
||||
.Nm dhcpcd
|
||||
cannot mix Prefix Delegation with other DHCPv6 address types in the same
|
||||
session.
|
||||
This has a number of issues: additional DHCP traffic and potential collisions
|
||||
between options.
|
||||
.Ic ia_pd_mix
|
||||
enables
|
||||
.Li draft-ietf-dhc-dhcpv6-stateful-issues-06
|
||||
support so that Prefix Delegation can be mixed with other address types in
|
||||
the same session.
|
||||
.It Ic ipv4only
|
||||
Only configure IPv4.
|
||||
.It Ic ipv6only
|
||||
@ -458,6 +473,9 @@ Subsequent options are only parsed for this wireless
|
||||
.Ar ssid .
|
||||
.It Ic slaac Op Ar hwaddr | Ar private
|
||||
Selects the interface identifier used for SLAAC generated IPv6 addresses.
|
||||
If
|
||||
.Ar private
|
||||
is used, a RFC7217 address is generated.
|
||||
.It Ic static Ar value
|
||||
Configures a static
|
||||
.Ar value .
|
||||
@ -740,11 +758,5 @@ Same as
|
||||
.Sh AUTHORS
|
||||
.An Roy Marples Aq Mt roy@marples.name
|
||||
.Sh BUGS
|
||||
When configuring DHCPv6 you can only select one IA type.
|
||||
I can't think of a use case where you would want different types,
|
||||
so if you have one then please bring it up for discussion on the
|
||||
.Aq Mt dhcpcd-discuss@marples.name
|
||||
mailing list.
|
||||
.Pp
|
||||
Please report them to
|
||||
.Lk http://roy.marples.name/projects/dhcpcd
|
||||
|
71
external/bsd/dhcpcd/dist/if-bsd.c
vendored
71
external/bsd/dhcpcd/dist/if-bsd.c
vendored
@ -1,5 +1,5 @@
|
||||
#include <sys/cdefs.h>
|
||||
__RCSID("$NetBSD: if-bsd.c,v 1.6 2014/06/14 20:55:37 roy Exp $");
|
||||
__RCSID("$NetBSD: if-bsd.c,v 1.7 2014/07/14 11:49:48 roy Exp $");
|
||||
|
||||
/*
|
||||
* dhcpcd - DHCP client daemon
|
||||
@ -891,9 +891,7 @@ if_managelink(struct dhcpcd_ctx *ctx)
|
||||
case AF_INET6:
|
||||
sin6 = (struct sockaddr_in6*)(void *)
|
||||
rti_info[RTAX_IFA];
|
||||
memcpy(ia6.s6_addr,
|
||||
sin6->sin6_addr.s6_addr,
|
||||
sizeof(ia6.s6_addr));
|
||||
ia6 = sin6->sin6_addr;
|
||||
if (rtm->rtm_type == RTM_NEWADDR) {
|
||||
ifa_flags = if_addrflags6(ifname, &ia6);
|
||||
if (ifa_flags == -1)
|
||||
@ -1022,45 +1020,6 @@ if_nd6reachable(const char *ifname, struct in6_addr *addr)
|
||||
return flags;
|
||||
}
|
||||
|
||||
void
|
||||
if_rarestore(struct dhcpcd_ctx *ctx)
|
||||
{
|
||||
|
||||
if (ctx->options & DHCPCD_FORKED)
|
||||
return;
|
||||
|
||||
for (; ctx->ra_restore_len > 0; ctx->ra_restore_len--) {
|
||||
#ifdef ND6_IFF_ACCEPT_RTADV
|
||||
if (!(ctx->options & DHCPCD_FORKED)) {
|
||||
syslog(LOG_DEBUG,
|
||||
"%s: restoring kernel IPv6 RA support",
|
||||
ctx->ra_restore[ctx->ra_restore_len - 1]);
|
||||
if (set_if_nd6_flag(
|
||||
ctx->ra_restore[ctx->ra_restore_len -1],
|
||||
ND6_IFF_ACCEPT_RTADV) == -1)
|
||||
syslog(LOG_ERR, "%s: set_if_nd6_flag: %m",
|
||||
ctx->ra_restore[ctx->ra_restore_len - 1]);
|
||||
#ifdef ND6_IFF_OVERRIDE_RTADV
|
||||
if (ctx->ra_kernel_set == 0 && del_if_nd6_flag(
|
||||
ctx->ra_restore[ctx->ra_restore_len -1],
|
||||
ND6_IFF_OVERRIDE_RTADV) == -1)
|
||||
syslog(LOG_ERR, "%s: del_if_nd6_flag: %m",
|
||||
ctx->ra_restore[ctx->ra_restore_len - 1]);
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
free(ctx->ra_restore[ctx->ra_restore_len - 1]);
|
||||
}
|
||||
free(ctx->ra_restore);
|
||||
ctx->ra_restore = NULL;
|
||||
|
||||
if (ctx->ra_kernel_set) {
|
||||
syslog(LOG_DEBUG, "restoring kernel IPv6 RA support");
|
||||
if (set_inet6_sysctl(IPV6CTL_ACCEPT_RTADV, 1) == -1)
|
||||
syslog(LOG_ERR, "IPV6CTL_ACCEPT_RTADV: %m");
|
||||
}
|
||||
}
|
||||
|
||||
static int
|
||||
if_raflush(void)
|
||||
{
|
||||
@ -1088,10 +1047,6 @@ if_checkipv6(struct dhcpcd_ctx *ctx, const char *ifname, int own)
|
||||
#ifdef ND6_IFF_OVERRIDE_RTADV
|
||||
int override;
|
||||
#endif
|
||||
#ifdef ND6_IFF_ACCEPT_RTADV
|
||||
size_t i;
|
||||
char *p, **nrest;
|
||||
#endif
|
||||
|
||||
#ifdef ND6_IFF_IFDISABLED
|
||||
if (del_if_nd6_flag(ifname, ND6_IFF_IFDISABLED) == -1) {
|
||||
@ -1169,7 +1124,7 @@ if_checkipv6(struct dhcpcd_ctx *ctx, const char *ifname, int own)
|
||||
return ra;
|
||||
}
|
||||
#ifdef ND6_IFF_OVERRIDE_RTADV
|
||||
if (override == 0 && ctx->ra_kernel_set == 0 &&
|
||||
if (override == 0 &&
|
||||
set_if_nd6_flag(ifname, ND6_IFF_OVERRIDE_RTADV)
|
||||
== -1)
|
||||
{
|
||||
@ -1180,25 +1135,6 @@ if_checkipv6(struct dhcpcd_ctx *ctx, const char *ifname, int own)
|
||||
return ra;
|
||||
}
|
||||
#endif
|
||||
for (i = 0; i < ctx->ra_restore_len; i++)
|
||||
if (strcmp(ctx->ra_restore[i], ifname) == 0)
|
||||
break;
|
||||
if (i == ctx->ra_restore_len) {
|
||||
p = strdup(ifname);
|
||||
if (p == NULL) {
|
||||
syslog(LOG_ERR, "%s: %m", __func__);
|
||||
return 0;
|
||||
}
|
||||
nrest = realloc(ctx->ra_restore,
|
||||
(ctx->ra_restore_len + 1) * sizeof(char *));
|
||||
if (nrest == NULL) {
|
||||
syslog(LOG_ERR, "%s: %m", __func__);
|
||||
free(p);
|
||||
return 0;
|
||||
}
|
||||
ctx->ra_restore = nrest;
|
||||
ctx->ra_restore[ctx->ra_restore_len++] = p;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
return ra;
|
||||
@ -1220,7 +1156,6 @@ if_checkipv6(struct dhcpcd_ctx *ctx, const char *ifname, int own)
|
||||
return ra;
|
||||
}
|
||||
ra = 0;
|
||||
ctx->ra_kernel_set = 1;
|
||||
|
||||
/* Flush the kernel knowledge of advertised routers
|
||||
* and prefixes so the kernel does not expire prefixes
|
||||
|
138
external/bsd/dhcpcd/dist/if-options.c
vendored
138
external/bsd/dhcpcd/dist/if-options.c
vendored
@ -1,5 +1,5 @@
|
||||
#include <sys/cdefs.h>
|
||||
__RCSID("$NetBSD: if-options.c,v 1.9 2014/06/14 20:55:37 roy Exp $");
|
||||
__RCSID("$NetBSD: if-options.c,v 1.10 2014/07/14 11:49:48 roy Exp $");
|
||||
|
||||
/*
|
||||
* dhcpcd - DHCP client daemon
|
||||
@ -96,6 +96,7 @@
|
||||
#define O_CONTROLGRP O_BASE + 34
|
||||
#define O_SLAAC O_BASE + 35
|
||||
#define O_GATEWAY O_BASE + 36
|
||||
#define O_PFXDLGMIX O_BASE + 37
|
||||
|
||||
const struct option cf_options[] = {
|
||||
{"background", no_argument, NULL, 'b'},
|
||||
@ -182,6 +183,7 @@ const struct option cf_options[] = {
|
||||
{"controlgroup", required_argument, NULL, O_CONTROLGRP},
|
||||
{"slaac", required_argument, NULL, O_SLAAC},
|
||||
{"gateway", no_argument, NULL, O_GATEWAY},
|
||||
{"ia_pd_mix", no_argument, NULL, O_PFXDLGMIX},
|
||||
{NULL, 0, NULL, '\0'}
|
||||
};
|
||||
|
||||
@ -521,7 +523,9 @@ parse_addr(__unused struct in_addr *addr, __unused struct in_addr *net,
|
||||
|
||||
static const char *
|
||||
set_option_space(struct dhcpcd_ctx *ctx,
|
||||
const char *arg, const struct dhcp_opt **d, size_t *dl,
|
||||
const char *arg,
|
||||
const struct dhcp_opt **d, size_t *dl,
|
||||
const struct dhcp_opt **od, size_t *odl,
|
||||
struct if_options *ifo,
|
||||
uint8_t *request[], uint8_t *require[], uint8_t *no[])
|
||||
{
|
||||
@ -530,6 +534,8 @@ set_option_space(struct dhcpcd_ctx *ctx,
|
||||
if (strncmp(arg, "dhcp6_", strlen("dhcp6_")) == 0) {
|
||||
*d = ctx->dhcp6_opts;
|
||||
*dl = ctx->dhcp6_opts_len;
|
||||
*od = ifo->dhcp6_override;
|
||||
*odl = ifo->dhcp6_override_len;
|
||||
*request = ifo->requestmask6;
|
||||
*require = ifo->requiremask6;
|
||||
*no = ifo->nomask6;
|
||||
@ -540,9 +546,13 @@ set_option_space(struct dhcpcd_ctx *ctx,
|
||||
#ifdef INET
|
||||
*d = ctx->dhcp_opts;
|
||||
*dl = ctx->dhcp_opts_len;
|
||||
*od = ifo->dhcp_override;
|
||||
*odl = ifo->dhcp_override_len;
|
||||
#else
|
||||
*d = NULL;
|
||||
*dl = 0;
|
||||
*od = NULL;
|
||||
*odl = 0;
|
||||
#endif
|
||||
*request = ifo->requestmask;
|
||||
*require = ifo->requiremask;
|
||||
@ -633,15 +643,14 @@ parse_option(struct dhcpcd_ctx *ctx, const char *ifname, struct if_options *ifo,
|
||||
struct in_addr addr, addr2;
|
||||
in_addr_t *naddr;
|
||||
struct rt *rt;
|
||||
const struct dhcp_opt *d;
|
||||
const struct dhcp_opt *d, *od;
|
||||
uint8_t *request, *require, *no;
|
||||
struct dhcp_opt **dop, *ndop;
|
||||
size_t *dop_len, dl;
|
||||
size_t *dop_len, dl, odl;
|
||||
struct vivco *vivco;
|
||||
struct token *token;
|
||||
struct group *grp;
|
||||
#ifdef _REENTRANT
|
||||
#error foo
|
||||
struct group grpbuf;
|
||||
#endif
|
||||
#ifdef INET6
|
||||
@ -736,10 +745,10 @@ parse_option(struct dhcpcd_ctx *ctx, const char *ifname, struct if_options *ifo,
|
||||
}
|
||||
break;
|
||||
case 'o':
|
||||
arg = set_option_space(ctx, arg, &d, &dl, ifo,
|
||||
arg = set_option_space(ctx, arg, &d, &dl, &od, &odl, ifo,
|
||||
&request, &require, &no);
|
||||
if (make_option_mask(d, dl, request, arg, 1) != 0 ||
|
||||
make_option_mask(d, dl, no, arg, -1) != 0)
|
||||
if (make_option_mask(d, dl, od, odl, request, arg, 1) != 0 ||
|
||||
make_option_mask(d, dl, od, odl, no, arg, -1) != 0)
|
||||
{
|
||||
syslog(LOG_ERR, "unknown option `%s'", arg);
|
||||
return -1;
|
||||
@ -955,22 +964,22 @@ parse_option(struct dhcpcd_ctx *ctx, const char *ifname, struct if_options *ifo,
|
||||
ifo->options |= DHCPCD_MASTER;
|
||||
break;
|
||||
case 'O':
|
||||
arg = set_option_space(ctx, arg, &d, &dl, ifo,
|
||||
arg = set_option_space(ctx, arg, &d, &dl, &od, &odl, ifo,
|
||||
&request, &require, &no);
|
||||
if (make_option_mask(d, dl, request, arg, -1) != 0 ||
|
||||
make_option_mask(d, dl, require, arg, -1) != 0 ||
|
||||
make_option_mask(d, dl, no, arg, 1) != 0)
|
||||
if (make_option_mask(d, dl, od, odl, request, arg, -1) != 0 ||
|
||||
make_option_mask(d, dl, od, odl, require, arg, -1) != 0 ||
|
||||
make_option_mask(d, dl, od, odl, no, arg, 1) != 0)
|
||||
{
|
||||
syslog(LOG_ERR, "unknown option `%s'", arg);
|
||||
return -1;
|
||||
}
|
||||
break;
|
||||
case 'Q':
|
||||
arg = set_option_space(ctx, arg, &d, &dl, ifo,
|
||||
arg = set_option_space(ctx, arg, &d, &dl, &od, &odl, ifo,
|
||||
&request, &require, &no);
|
||||
if (make_option_mask(d, dl, require, arg, 1) != 0 ||
|
||||
make_option_mask(d, dl, request, arg, 1) != 0 ||
|
||||
make_option_mask(d, dl, no, arg, -1) != 0)
|
||||
if (make_option_mask(d, dl, od, odl, require, arg, 1) != 0 ||
|
||||
make_option_mask(d, dl, od, odl, request, arg, 1) != 0 ||
|
||||
make_option_mask(d, dl, od, odl, no, arg, -1) != 0)
|
||||
{
|
||||
syslog(LOG_ERR, "unknown option `%s'", arg);
|
||||
return -1;
|
||||
@ -1159,8 +1168,11 @@ parse_option(struct dhcpcd_ctx *ctx, const char *ifname, struct if_options *ifo,
|
||||
}
|
||||
break;
|
||||
case O_DESTINATION:
|
||||
if (make_option_mask(ctx->dhcp_opts, ctx->dhcp_opts_len,
|
||||
ifo->dstmask, arg, 2) != 0) {
|
||||
arg = set_option_space(ctx, arg, &d, &dl, &od, &odl, ifo,
|
||||
&request, &require, &no);
|
||||
if (make_option_mask(d, dl, od, odl,
|
||||
ifo->dstmask, arg, 2) != 0)
|
||||
{
|
||||
if (errno == EINVAL)
|
||||
syslog(LOG_ERR, "option `%s' does not take"
|
||||
" an IPv4 address", arg);
|
||||
@ -1223,35 +1235,41 @@ parse_option(struct dhcpcd_ctx *ctx, const char *ifname, struct if_options *ifo,
|
||||
}
|
||||
i = D6_OPTION_IA_PD;
|
||||
}
|
||||
if (arg != NULL && ifname == NULL) {
|
||||
if (ifname == NULL && arg) {
|
||||
syslog(LOG_ERR,
|
||||
"IA with IAID must belong in an interface block");
|
||||
return -1;
|
||||
}
|
||||
ifo->options |= DHCPCD_IA_FORCED;
|
||||
if (ifo->ia_type != 0 && ifo->ia_type != i) {
|
||||
syslog(LOG_ERR, "cannot specify a different IA type");
|
||||
return -1;
|
||||
}
|
||||
ifo->ia_type = (uint16_t)i;
|
||||
if (arg == NULL)
|
||||
break;
|
||||
fp = strwhite(arg);
|
||||
if (fp)
|
||||
if (fp) {
|
||||
*fp++ = '\0';
|
||||
if (parse_iaid(iaid, arg, sizeof(iaid)) == -1)
|
||||
return -1;
|
||||
fp = strskipwhite(fp);
|
||||
}
|
||||
if (arg) {
|
||||
p = strchr(arg, '/');
|
||||
if (p)
|
||||
*p++ = '\0';
|
||||
if (parse_iaid(iaid, arg, sizeof(iaid)) == -1)
|
||||
return -1;
|
||||
}
|
||||
ia = NULL;
|
||||
for (sl = 0; sl < ifo->ia_len; sl++) {
|
||||
if (ifo->ia[sl].iaid[0] == iaid[0] &&
|
||||
if ((arg == NULL && !ifo->ia[sl].iaid_set) ||
|
||||
(ifo->ia[sl].iaid_set &&
|
||||
ifo->ia[sl].iaid[0] == iaid[0] &&
|
||||
ifo->ia[sl].iaid[1] == iaid[1] &&
|
||||
ifo->ia[sl].iaid[2] == iaid[2] &&
|
||||
ifo->ia[sl].iaid[3] == iaid[3])
|
||||
ifo->ia[sl].iaid[3] == iaid[3]))
|
||||
{
|
||||
ia = &ifo->ia[sl];
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (ia && ia->ia_type != (uint16_t)i) {
|
||||
syslog(LOG_ERR, "Cannot mix IA for the same IAID");
|
||||
break;
|
||||
}
|
||||
if (ia == NULL) {
|
||||
ia = realloc(ifo->ia,
|
||||
sizeof(*ifo->ia) * (ifo->ia_len + 1));
|
||||
@ -1261,14 +1279,47 @@ parse_option(struct dhcpcd_ctx *ctx, const char *ifname, struct if_options *ifo,
|
||||
}
|
||||
ifo->ia = ia;
|
||||
ia = &ifo->ia[ifo->ia_len++];
|
||||
ia->iaid[0] = iaid[0];
|
||||
ia->iaid[1] = iaid[1];
|
||||
ia->iaid[2] = iaid[2];
|
||||
ia->iaid[3] = iaid[3];
|
||||
ia->sla = NULL;
|
||||
ia->ia_type = (uint16_t)i;
|
||||
if (arg) {
|
||||
ia->iaid[0] = iaid[0];
|
||||
ia->iaid[1] = iaid[1];
|
||||
ia->iaid[2] = iaid[2];
|
||||
ia->iaid[3] = iaid[3];
|
||||
ia->iaid_set = 1;
|
||||
} else
|
||||
ia->iaid_set = 0;
|
||||
if (!ia->iaid_set ||
|
||||
p == NULL ||
|
||||
ia->ia_type == D6_OPTION_IA_TA)
|
||||
{
|
||||
memset(&ia->addr, 0, sizeof(ia->addr));
|
||||
ia->prefix_len = 0;
|
||||
} else {
|
||||
arg = p;
|
||||
p = strchr(arg, '/');
|
||||
if (p)
|
||||
*p++ = '\0';
|
||||
if (inet_pton(AF_INET6, arg, &ia->addr) == -1) {
|
||||
syslog(LOG_ERR, "%s: %m", arg);
|
||||
memset(&ia->addr, 0, sizeof(ia->addr));
|
||||
}
|
||||
if (p && ia->ia_type == D6_OPTION_IA_PD) {
|
||||
i = atoint(p);
|
||||
if (i != -1 && (i < 8 || i > 120)) {
|
||||
errno = EINVAL;
|
||||
i = -1;
|
||||
}
|
||||
if (i == -1) {
|
||||
syslog(LOG_ERR, "%s: %m", p);
|
||||
ia->prefix_len = 0;
|
||||
} else
|
||||
ia->prefix_len = (uint8_t)i;
|
||||
}
|
||||
}
|
||||
ia->sla_len = 0;
|
||||
ia->sla = NULL;
|
||||
}
|
||||
if (ifo->ia_type != D6_OPTION_IA_PD)
|
||||
if (ia->ia_type != D6_OPTION_IA_PD)
|
||||
break;
|
||||
for (p = fp; p; p = fp) {
|
||||
fp = strwhite(p);
|
||||
@ -1287,12 +1338,6 @@ parse_option(struct dhcpcd_ctx *ctx, const char *ifname, struct if_options *ifo,
|
||||
np = strchr(p, '/');
|
||||
if (np)
|
||||
*np++ = '\0';
|
||||
if (strcmp(ifname, p) == 0) {
|
||||
syslog(LOG_ERR,
|
||||
"%s: cannot assign IA_PD to itself",
|
||||
ifname);
|
||||
goto err_sla;
|
||||
}
|
||||
if (strlcpy(sla->ifname, p,
|
||||
sizeof(sla->ifname)) >= sizeof(sla->ifname))
|
||||
{
|
||||
@ -1856,6 +1901,9 @@ err_sla:
|
||||
else
|
||||
ifo->options &= ~DHCPCD_SLAACPRIVATE;
|
||||
break;
|
||||
case O_PFXDLGMIX:
|
||||
ifo->options |= DHCPCD_PFXDLGMIX;
|
||||
break;
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
@ -2127,6 +2175,10 @@ read_config(struct dhcpcd_ctx *ctx,
|
||||
skip = 1;
|
||||
continue;
|
||||
}
|
||||
/* Skip arping if we have selected a profile but not parsing
|
||||
* one. */
|
||||
if (profile && !have_profile && strcmp(option, "arping") == 0)
|
||||
continue;
|
||||
if (skip)
|
||||
continue;
|
||||
parse_config_line(ctx, ifname, ifo, option, line, &ldop, &edop);
|
||||
|
31
external/bsd/dhcpcd/dist/ipv6nd.c
vendored
31
external/bsd/dhcpcd/dist/ipv6nd.c
vendored
@ -1,5 +1,5 @@
|
||||
#include <sys/cdefs.h>
|
||||
__RCSID("$NetBSD: ipv6nd.c,v 1.8 2014/06/14 20:55:37 roy Exp $");
|
||||
__RCSID("$NetBSD: ipv6nd.c,v 1.9 2014/07/14 11:49:48 roy Exp $");
|
||||
|
||||
/*
|
||||
* dhcpcd - DHCP client daemon
|
||||
@ -282,7 +282,7 @@ ipv6nd_sendrsprobe(void *arg)
|
||||
dst.sin6_len = sizeof(dst);
|
||||
#endif
|
||||
dst.sin6_scope_id = ifp->index;
|
||||
if (inet_pton(AF_INET6, ALLROUTERS, &dst.sin6_addr.s6_addr) != 1) {
|
||||
if (inet_pton(AF_INET6, ALLROUTERS, &dst.sin6_addr) != 1) {
|
||||
syslog(LOG_ERR, "%s: %m", __func__);
|
||||
return;
|
||||
}
|
||||
@ -627,8 +627,7 @@ ipv6nd_dadcallback(void *arg)
|
||||
ap->dadcounter = dadcounter;
|
||||
ap->flags &= ~(IPV6_AF_ADDED | IPV6_AF_DADCOMPLETED);
|
||||
ap->flags |= IPV6_AF_NEW;
|
||||
p = inet_ntop(AF_INET6, ap->addr.s6_addr,
|
||||
buf, sizeof(buf));
|
||||
p = inet_ntop(AF_INET6, &ap->addr, buf, sizeof(buf));
|
||||
if (p)
|
||||
snprintf(ap->saddr,
|
||||
sizeof(ap->saddr),
|
||||
@ -734,8 +733,7 @@ ipv6nd_handlera(struct ipv6_ctx *ctx, struct interface *ifp,
|
||||
|
||||
TAILQ_FOREACH(rap, ctx->ra_routers, next) {
|
||||
if (ifp == rap->iface &&
|
||||
memcmp(rap->from.s6_addr, ctx->from.sin6_addr.s6_addr,
|
||||
sizeof(rap->from.s6_addr)) == 0)
|
||||
IN6_ARE_ADDR_EQUAL(&rap->from, &ctx->from.sin6_addr))
|
||||
break;
|
||||
}
|
||||
|
||||
@ -764,8 +762,7 @@ ipv6nd_handlera(struct ipv6_ctx *ctx, struct interface *ifp,
|
||||
return;
|
||||
}
|
||||
rap->iface = ifp;
|
||||
memcpy(rap->from.s6_addr, ctx->from.sin6_addr.s6_addr,
|
||||
sizeof(rap->from.s6_addr));
|
||||
rap->from = ctx->from.sin6_addr;
|
||||
strlcpy(rap->sfrom, ctx->sfrom, sizeof(rap->sfrom));
|
||||
TAILQ_INIT(&rap->addrs);
|
||||
TAILQ_INIT(&rap->options);
|
||||
@ -852,9 +849,8 @@ ipv6nd_handlera(struct ipv6_ctx *ctx, struct interface *ifp,
|
||||
}
|
||||
TAILQ_FOREACH(ap, &rap->addrs, next)
|
||||
if (ap->prefix_len ==pi->nd_opt_pi_prefix_len &&
|
||||
memcmp(ap->prefix.s6_addr,
|
||||
pi->nd_opt_pi_prefix.s6_addr,
|
||||
sizeof(ap->prefix.s6_addr)) == 0)
|
||||
IN6_ARE_ADDR_EQUAL(&ap->prefix,
|
||||
&pi->nd_opt_pi_prefix))
|
||||
break;
|
||||
if (ap == NULL) {
|
||||
if (!(pi->nd_opt_pi_flags_reserved &
|
||||
@ -868,9 +864,7 @@ ipv6nd_handlera(struct ipv6_ctx *ctx, struct interface *ifp,
|
||||
ap->iface = rap->iface;
|
||||
ap->flags = IPV6_AF_NEW;
|
||||
ap->prefix_len = pi->nd_opt_pi_prefix_len;
|
||||
memcpy(ap->prefix.s6_addr,
|
||||
pi->nd_opt_pi_prefix.s6_addr,
|
||||
sizeof(ap->prefix.s6_addr));
|
||||
ap->prefix = pi->nd_opt_pi_prefix;
|
||||
if (pi->nd_opt_pi_flags_reserved &
|
||||
ND_OPT_PI_FLAG_AUTO)
|
||||
{
|
||||
@ -884,7 +878,7 @@ ipv6nd_handlera(struct ipv6_ctx *ctx, struct interface *ifp,
|
||||
break;
|
||||
}
|
||||
cbp = inet_ntop(AF_INET6,
|
||||
ap->addr.s6_addr,
|
||||
&ap->addr,
|
||||
buf, sizeof(buf));
|
||||
if (cbp)
|
||||
snprintf(ap->saddr,
|
||||
@ -947,7 +941,7 @@ ipv6nd_handlera(struct ipv6_ctx *ctx, struct interface *ifp,
|
||||
op += sizeof(rdnss->nd_opt_rdnss_lifetime);
|
||||
l = 0;
|
||||
for (n = ndo->nd_opt_len - 1; n > 1; n -= 2,
|
||||
op += sizeof(addr.s6_addr))
|
||||
op += sizeof(addr))
|
||||
{
|
||||
r = ipv6_printaddr(NULL, 0, op, ifp->name);
|
||||
if (r != -1)
|
||||
@ -961,7 +955,7 @@ ipv6nd_handlera(struct ipv6_ctx *ctx, struct interface *ifp,
|
||||
if (opt == NULL)
|
||||
continue;
|
||||
for (n = ndo->nd_opt_len - 1; n > 1; n -= 2,
|
||||
op += sizeof(addr.s6_addr))
|
||||
op += sizeof(addr))
|
||||
{
|
||||
r = ipv6_printaddr(tmp, l, op,
|
||||
ifp->name);
|
||||
@ -1401,8 +1395,7 @@ ipv6nd_handlena(struct ipv6_ctx *ctx, struct interface *ifp,
|
||||
|
||||
TAILQ_FOREACH(rap, ctx->ra_routers, next) {
|
||||
if (rap->iface == ifp &&
|
||||
memcmp(rap->from.s6_addr, nd_na->nd_na_target.s6_addr,
|
||||
sizeof(rap->from.s6_addr)) == 0)
|
||||
IN6_ARE_ADDR_EQUAL(&rap->from, &nd_na->nd_na_target))
|
||||
break;
|
||||
}
|
||||
if (rap == NULL) {
|
||||
|
27
external/bsd/dhcpcd/dist/script.c
vendored
27
external/bsd/dhcpcd/dist/script.c
vendored
@ -1,5 +1,5 @@
|
||||
#include <sys/cdefs.h>
|
||||
__RCSID("$NetBSD: script.c,v 1.6 2014/06/14 20:55:37 roy Exp $");
|
||||
__RCSID("$NetBSD: script.c,v 1.7 2014/07/14 11:49:48 roy Exp $");
|
||||
|
||||
/*
|
||||
* dhcpcd - DHCP client daemon
|
||||
@ -315,7 +315,8 @@ make_env(const struct interface *ifp, const char *reason, char ***argv)
|
||||
snprintf(env[7], e, "ifmtu=%d", if_getmtu(ifp->name));
|
||||
l = e = strlen("interface_order=");
|
||||
TAILQ_FOREACH(ifp2, ifp->ctx->ifaces, next) {
|
||||
e += strlen(ifp2->name) + 1;
|
||||
if (!(ifp2->options->options & DHCPCD_PFXDLGONLY))
|
||||
e += strlen(ifp2->name) + 1;
|
||||
}
|
||||
EMALLOC(8, e);
|
||||
p = env[8];
|
||||
@ -323,11 +324,13 @@ make_env(const struct interface *ifp, const char *reason, char ***argv)
|
||||
e -= l;
|
||||
p += l;
|
||||
TAILQ_FOREACH(ifp2, ifp->ctx->ifaces, next) {
|
||||
l = strlcpy(p, ifp2->name, e);
|
||||
p += l;
|
||||
e -= l;
|
||||
*p++ = ' ';
|
||||
e--;
|
||||
if (!(ifp2->options->options & DHCPCD_PFXDLGONLY)) {
|
||||
l = strlcpy(p, ifp2->name, e);
|
||||
p += l;
|
||||
e -= l;
|
||||
*p++ = ' ';
|
||||
e--;
|
||||
}
|
||||
}
|
||||
*--p = '\0';
|
||||
if (strcmp(reason, "TEST") == 0) {
|
||||
@ -396,6 +399,16 @@ make_env(const struct interface *ifp, const char *reason, char ***argv)
|
||||
}
|
||||
#endif
|
||||
#ifdef INET6
|
||||
if (dhcp6 && d6_state && ifo->options & DHCPCD_PFXDLGONLY) {
|
||||
nenv = realloc(env, sizeof(char *) * (elen + 2));
|
||||
if (nenv == NULL)
|
||||
goto eexit;
|
||||
env = nenv;
|
||||
env[elen] = strdup("ifclass=pd");
|
||||
if (env[elen] == NULL)
|
||||
goto eexit;
|
||||
elen++;
|
||||
}
|
||||
if (dhcp6 && d6_state && d6_state->old) {
|
||||
n = dhcp6_env(NULL, NULL, ifp,
|
||||
d6_state->old, d6_state->old_len);
|
||||
|
Loading…
Reference in New Issue
Block a user