Import dhcpcd-5.1.2 with these changes:

* ClientID is now reported when interface starts.
* -w, --wait forces dhcpcd to wait until an interface gets a lease or
  times out.
* Ensure DHCP socket is open when sending a DECLINE.
* Uses new hwaddr if existing interface is downed and then changed.
* No longer works on firewire interfaces by default.

dhcpcd-5.1.2 has a new behaviour change - when starting up and at least 1
interface has a carrier then it tries to get a lease or times out.
It still daemonises regardless. This, along with the -b and -w flags
allows total control over the desired behaviour of dhcpcd.
This commit is contained in:
roy 2009-10-16 21:50:41 +00:00
parent 336cbcc88d
commit 3b87816311
12 changed files with 223 additions and 170 deletions

View File

@ -82,9 +82,8 @@ handle_arp_failure(struct interface *iface)
handle_ipv4ll_failure(iface);
return;
}
if (iface->state->lease.frominfo)
unlink(iface->leasefile);
else
unlink(iface->leasefile);
if (!iface->state->lease.frominfo)
send_decline(iface);
close_sockets(iface);
delete_timeout(NULL, iface);

View File

@ -4,4 +4,4 @@
#define LIBEXECDIR "/libexec"
#define DBDIR "/var/db"
#define RUNDIR "/var/run"
#include "compat/getline.h"
#include "compat/getline.h"

View File

@ -28,7 +28,7 @@
#define CONFIG_H
#define PACKAGE "dhcpcd"
#define VERSION "5.1.1"
#define VERSION "5.1.2"
#ifndef CONFIG
# define CONFIG SYSCONFDIR "/" PACKAGE ".conf"

View File

@ -33,6 +33,8 @@
#include <stdint.h>
#include "common.h"
/* Max MTU - defines dhcp option length */
#define MTU_MAX 1500
#define MTU_MIN 576

View File

@ -137,7 +137,7 @@ read_pid(void)
static void
usage(void)
{
printf("usage: "PACKAGE" [-dgknpqxyADEGHKLOTV] [-c script] [-f file]"
printf("usage: "PACKAGE" [-dgknpqwxyADEGHKLOTV] [-c script] [-f file]"
" [-e var=val]\n"
" [-h hostname] [-i classID ] [-l leasetime]"
" [-m metric] [-o option]\n"
@ -185,11 +185,18 @@ cleanup(void)
}
/* ARGSUSED */
_noreturn void
void
handle_exit_timeout(_unused void *arg)
{
int timeout;
syslog(LOG_ERR, "timed out");
exit(EXIT_FAILURE);
if (!(options & DHCPCD_TIMEOUT_IPV4LL))
exit(EXIT_FAILURE);
options &= ~DHCPCD_TIMEOUT_IPV4LL;
timeout = (PROBE_NUM * PROBE_MAX) + PROBE_WAIT + 1;
syslog(LOG_WARNING, "allowing %d seconds for IPv4LL timeout", timeout);
add_timeout_sec(timeout, handle_exit_timeout, NULL);
}
void
@ -387,12 +394,6 @@ start_expire(void *arg)
start_interface(iface);
}
void
send_decline(struct interface *iface)
{
send_message(iface, DHCP_DECLINE, NULL);
}
static void
log_dhcp(int lvl, const char *msg,
const struct interface *iface, const struct dhcp_message *dhcp)
@ -715,6 +716,13 @@ send_release(struct interface *iface)
unlink(iface->leasefile);
}
void
send_decline(struct interface *iface)
{
open_sockets(iface);
send_message(iface, DHCP_DECLINE, NULL);
}
static void
configure_interface1(struct interface *iface)
{
@ -728,7 +736,7 @@ configure_interface1(struct interface *iface)
if (iface->flags & IFF_NOARP ||
ifo->options & (DHCPCD_INFORM | DHCPCD_STATIC))
ifo->options &= ~(DHCPCD_ARP | DHCPCD_IPV4LL);
if (ifo->options & DHCPCD_LINK && carrier_status(iface->name) == -1)
if (ifo->options & DHCPCD_LINK && carrier_status(iface) == -1)
ifo->options &= ~DHCPCD_LINK;
if (ifo->metric != -1)
@ -773,6 +781,9 @@ configure_interface1(struct interface *iface)
iface->hwlen);
}
}
if (ifo->options & DHCPCD_CLIENTID)
syslog(LOG_DEBUG, "%s: using ClientID %s", iface->name,
hwaddr_ntoa(iface->clientid + 1, *iface->clientid));
}
int
@ -821,6 +832,7 @@ static void
handle_carrier(const char *ifname)
{
struct interface *iface;
int carrier;
if (!(options & DHCPCD_LINK))
return;
@ -829,11 +841,10 @@ handle_carrier(const char *ifname)
break;
if (!iface || !(iface->state->options->options & DHCPCD_LINK))
return;
switch (carrier_status(iface->name)) {
case -1:
syslog(LOG_ERR, "carrier_status: %m");
break;
case 0:
carrier = carrier_status(iface);
if (carrier == -1)
syslog(LOG_ERR, "%s: carrier_status: %m", ifname);
else if (carrier == 0 || !(iface->flags & IFF_RUNNING)) {
if (iface->carrier != LINK_DOWN) {
iface->carrier = LINK_DOWN;
syslog(LOG_INFO, "%s: carrier lost", iface->name);
@ -841,8 +852,7 @@ handle_carrier(const char *ifname)
delete_timeouts(iface, start_expire, NULL);
drop_config(iface, "NOCARRIER");
}
break;
default:
} else if (carrier == 1 && (iface->flags & IFF_RUNNING)) {
if (iface->carrier != LINK_UP) {
iface->carrier = LINK_UP;
syslog(LOG_INFO, "%s: carrier acquired", iface->name);
@ -854,7 +864,6 @@ handle_carrier(const char *ifname)
run_script(iface);
start_interface(iface);
}
break;
}
}
@ -1165,7 +1174,7 @@ init_state(struct interface *iface, int argc, char **argv)
run_script(iface);
if (ifs->options->options & DHCPCD_LINK) {
switch (carrier_status(iface->name)) {
switch (carrier_status(iface)) {
case 0:
iface->carrier = LINK_DOWN;
ifs->reason = "NOCARRIER";
@ -1220,13 +1229,19 @@ handle_interface(int action, const char *ifname)
break;
ifl = ifn;
}
if (ifn)
continue;
if (ifn) {
/* The flags and hwaddr could have changed */
ifn->flags = ifp->flags;
ifn->hwlen = ifp->hwlen;
if (ifp->hwlen != 0)
memcpy(ifn->hwaddr, ifp->hwaddr, ifn->hwlen);
} else {
if (ifl)
ifl->next = ifp;
else
ifaces = ifp;
}
init_state(ifp, 0, NULL);
if (ifl)
ifl->next = ifp;
else
ifaces = ifp;
start_interface(ifp);
}
}
@ -1665,6 +1680,10 @@ main(int argc, char **argv)
if (pid == 0 || kill(pid, sig) != 0) {
if (sig != SIGALRM)
syslog(LOG_ERR, ""PACKAGE" not running");
if (pid != 0 && errno != ESRCH) {
syslog(LOG_ERR, "kill: %m");
exit(EXIT_FAILURE);
}
unlink(pidfile);
if (sig != SIGALRM)
exit(EXIT_FAILURE);
@ -1736,7 +1755,7 @@ main(int argc, char **argv)
}
}
if (init_socket() == -1) {
if (init_sockets() == -1) {
syslog(LOG_ERR, "init_socket: %m");
exit(EXIT_FAILURE);
}
@ -1750,17 +1769,6 @@ main(int argc, char **argv)
ifc = argc - optind;
ifv = argv + optind;
if (options & DHCPCD_BACKGROUND ||
(ifc == 0 && options & DHCPCD_LINK && options & DHCPCD_DAEMONISE))
{
daemonise();
} else if (options & DHCPCD_DAEMONISE && ifo->timeout > 0) {
oi = ifo->timeout;
if (ifo->options & DHCPCD_IPV4LL)
oi += 10;
add_timeout_sec(oi, handle_exit_timeout, NULL);
}
free_options(ifo);
ifaces = discover_interfaces(ifc, ifv);
for (i = 0; i < ifc; i++) {
@ -1774,15 +1782,37 @@ main(int argc, char **argv)
if (!ifaces) {
if (ifc == 0)
syslog(LOG_ERR, "no valid interfaces found");
else
exit(EXIT_FAILURE);
if (!(options & DHCPCD_LINK)) {
syslog(LOG_ERR, "aborting as we're not backgrounding"
" with link detection");
syslog(LOG_ERR,
"aborting as link detection is disabled");
exit(EXIT_FAILURE);
}
}
for (iface = ifaces; iface; iface = iface->next)
if (options & DHCPCD_BACKGROUND)
daemonise();
opt = 0;
for (iface = ifaces; iface; iface = iface->next) {
init_state(iface, argc, argv);
if (iface->carrier != LINK_DOWN)
opt = 1;
}
if (opt == 0 &&
options & DHCPCD_LINK &&
!(options & DHCPCD_WAITIP))
{
syslog(LOG_WARNING, "no interfaces have a carrier");
daemonise();
} else if (options & DHCPCD_DAEMONISE && ifo->timeout > 0) {
if (options & DHCPCD_IPV4LL)
options |= DHCPCD_TIMEOUT_IPV4LL;
add_timeout_sec(ifo->timeout, handle_exit_timeout, NULL);
}
free_options(ifo);
sort_interfaces();
for (iface = ifaces; iface; iface = iface->next)
add_timeout_sec(0, start_interface, iface);

View File

@ -22,7 +22,7 @@
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
.\" SUCH DAMAGE.
.\"
.Dd September 2, 2009
.Dd October 16, 2009
.Dt DHCPCD.CONF 5 SMM
.Os
.Sh NAME
@ -272,6 +272,8 @@ Set un-encapulated vendor option to hello world.
.It Ic vendorclassid Ar string
Change the default vendorclassid sent from dhcpcd-version.
If not set then none is sent.
.It Ic waitip
Wait for an address to be assigned before forking to the background.
.El
.Sh SEE ALSO
.Xr dhcpcd-run-hooks 8 ,

36
external/bsd/dhcpcd/dist/getline.h vendored Normal file
View File

@ -0,0 +1,36 @@
/*
* dhcpcd - DHCP client daemon
* Copyright (c) 2006-2009 Roy Marples <roy@marples.name>
* All rights reserved
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef GETLINE_H
#define GETLINE_H
#include <sys/types.h>
#include <stdio.h>
ssize_t getline(char ** __restrict buf, size_t * __restrict buflen,
FILE * __restrict fp);
#endif

View File

@ -70,15 +70,14 @@
? \
(((struct sockaddr_in *)(void *)sa)->sin_addr).s_addr : 0
static int a_fd = -1;
static int r_fd = -1;
int
init_socket(void)
init_sockets(void)
{
if ((a_fd = socket(AF_INET, SOCK_DGRAM, 0)) == -1)
if ((socket_afnet = socket(AF_INET, SOCK_DGRAM, 0)) == -1)
return -1;
set_cloexec(a_fd);
set_cloexec(socket_afnet);
if ((r_fd = socket(PF_ROUTE, SOCK_RAW, 0)) == -1)
return -1;
set_cloexec(r_fd);
@ -102,7 +101,7 @@ getifssid(const char *ifname, char *ssid)
strlcpy(ifr.ifr_name, ifname, sizeof(ifr.ifr_name));
memset(&nwid, 0, sizeof(nwid));
ifr.ifr_data = (void *)&nwid;
if (ioctl(a_fd, SIOCG80211NWID, &ifr) == 0) {
if (ioctl(socket_afnet, SIOCG80211NWID, &ifr) == 0) {
retval = nwid.i_len;
memcpy(ssid, nwid.i_nwid, nwid.i_len);
ssid[nwid.i_len] = '\0';
@ -113,7 +112,7 @@ getifssid(const char *ifname, char *ssid)
ireq.i_type = IEEE80211_IOC_SSID;
ireq.i_val = -1;
ireq.i_data = &nwid;
if (ioctl(a_fd, SIOCG80211, &ireq) == 0) {
if (ioctl(socket_afnet, SIOCG80211, &ireq) == 0) {
retval = ireq.i_len;
memcpy(ssid, nwid, ireq.i_len);
ssid[ireq.i_len] = '\0';
@ -152,9 +151,9 @@ if_address(const struct interface *iface, const struct in_addr *address,
#undef ADDADDR
if (action < 0)
retval = ioctl(a_fd, SIOCDIFADDR, &ifa);
retval = ioctl(socket_afnet, SIOCDIFADDR, &ifa);
else
retval = ioctl(a_fd, SIOCAIFADDR, &ifa);
retval = ioctl(socket_afnet, SIOCAIFADDR, &ifa);
return retval;
}

View File

@ -72,6 +72,7 @@ const struct option cf_options[] = {
{"timeout", required_argument, NULL, 't'},
{"userclass", required_argument, NULL, 'u'},
{"vendor", required_argument, NULL, 'v'},
{"waitip", no_argument, NULL, 'w'},
{"exit", no_argument, NULL, 'x'},
{"allowinterfaces", required_argument, NULL, 'z'},
{"reboot", required_argument, NULL, 'y'},
@ -507,6 +508,9 @@ parse_option(struct if_options *ifo, int opt, const char *arg)
ifo->vendor[0] += s + 2;
}
break;
case 'w':
ifo->options |= DHCPCD_WAITIP;
break;
case 'y':
ifo->reboot = atoint(arg);
if (ifo->reboot < 0) {

View File

@ -37,7 +37,7 @@
/* Don't set any optional arguments here so we retain POSIX
* compatibility with getopt */
#define IF_OPTS "bc:de:f:gh:i:kl:m:no:pqr:s:t:u:v:xy:z:ABC:DEF:GI:KLN:O:Q:TVW:X:Z:"
#define IF_OPTS "bc:de:f:gh:i:kl:m:no:pqr:s:t:u:v:wxy:z:ABC:DEF:GI:KLN:O:Q:TVW:X:Z:"
#define DEFAULT_TIMEOUT 30
#define DEFAULT_REBOOT 10
@ -70,6 +70,8 @@
#define DHCPCD_QUIET (1 << 21)
#define DHCPCD_BACKGROUND (1 << 22)
#define DHCPCD_VENDORRAW (1 << 23)
#define DHCPCD_TIMEOUT_IPV4LL (1 << 24)
#define DHCPCD_WAITIP (1 << 25)
extern const struct option cf_options[];

View File

@ -71,6 +71,8 @@
static char hwaddr_buffer[(HWADDR_LEN * 3) + 1];
int socket_afnet = -1;
int
inet_ntocidr(struct in_addr address)
{
@ -183,18 +185,12 @@ hwaddr_aton(unsigned char *buffer, const char *addr)
struct interface *
init_interface(const char *ifname)
{
int s;
struct ifreq ifr;
struct interface *iface = NULL;
memset(&ifr, 0, sizeof(ifr));
strlcpy(ifr.ifr_name, ifname, sizeof(ifr.ifr_name));
if ((s = socket(AF_INET, SOCK_DGRAM, 0)) == -1)
return NULL;
strlcpy(ifr.ifr_name, ifname, sizeof(ifr.ifr_name));
if (ioctl(s, SIOCGIFFLAGS, &ifr) == -1)
if (ioctl(socket_afnet, SIOCGIFFLAGS, &ifr) == -1)
goto eexit;
iface = xzalloc(sizeof(*iface));
@ -208,13 +204,13 @@ init_interface(const char *ifname)
iface->metric += 100;
}
if (ioctl(s, SIOCGIFMTU, &ifr) == -1)
if (ioctl(socket_afnet, SIOCGIFMTU, &ifr) == -1)
goto eexit;
/* Ensure that the MTU is big enough for DHCP */
if (ifr.ifr_mtu < MTU_MIN) {
ifr.ifr_mtu = MTU_MIN;
strlcpy(ifr.ifr_name, ifname, sizeof(ifr.ifr_name));
if (ioctl(s, SIOCSIFMTU, &ifr) == -1)
if (ioctl(socket_afnet, SIOCSIFMTU, &ifr) == -1)
goto eexit;
}
@ -230,7 +226,6 @@ eexit:
free(iface);
iface = NULL;
exit:
close(s);
return iface;
}
@ -250,6 +245,72 @@ free_interface(struct interface *iface)
free(iface);
}
int
carrier_status(struct interface *iface)
{
int ret;
struct ifreq ifr;
#ifdef SIOCGIFMEDIA
struct ifmediareq ifmr;
#endif
#ifdef __linux__
char *p;
#endif
memset(&ifr, 0, sizeof(ifr));
strlcpy(ifr.ifr_name, iface->name, sizeof(ifr.ifr_name));
#ifdef __linux__
/* We can only test the real interface up */
if ((p = strchr(ifr.ifr_name, ':')))
*p = '\0';
#endif
if (ioctl(socket_afnet, SIOCGIFFLAGS, &ifr) == -1)
return -1;
iface->flags = ifr.ifr_flags;
ret = -1;
#ifdef SIOCGIFMEDIA
memset(&ifmr, 0, sizeof(ifmr));
strlcpy(ifmr.ifm_name, iface->name, sizeof(ifmr.ifm_name));
if (ioctl(socket_afnet, SIOCGIFMEDIA, &ifmr) != -1 &&
ifmr.ifm_status & IFM_AVALID)
ret = (ifmr.ifm_status & IFM_ACTIVE) ? 1 : 0;
#endif
if (ret == -1)
ret = (ifr.ifr_flags & IFF_RUNNING) ? 1 : 0;
return ret;
}
int
up_interface(struct interface *iface)
{
struct ifreq ifr;
int retval = -1;
#ifdef __linux__
char *p;
#endif
memset(&ifr, 0, sizeof(ifr));
strlcpy(ifr.ifr_name, iface->name, sizeof(ifr.ifr_name));
#ifdef __linux__
/* We can only bring the real interface up */
if ((p = strchr(ifr.ifr_name, ':')))
*p = '\0';
#endif
if (ioctl(socket_afnet, SIOCGIFFLAGS, &ifr) == 0) {
if ((ifr.ifr_flags & IFF_UP))
retval = 0;
else {
ifr.ifr_flags |= IFF_UP;
if (ioctl(socket_afnet, SIOCSIFFLAGS, &ifr) == 0)
retval = 0;
}
iface->flags = ifr.ifr_flags;
}
return retval;
}
struct interface *
discover_interfaces(int argc, char * const *argv)
{
@ -327,13 +388,13 @@ discover_interfaces(int argc, char * const *argv)
if ((ifp = init_interface(p)) == NULL)
continue;
/* Bring the interface up */
if (!(ifp->flags & IFF_UP) && up_interface(p) != 0)
/* Some drivers return ENODEV here when they are disabled by a switch.
* We just blunder on as the carrier will be down anyway.
* When the switch is enabled, it should bring the interface up.
* Then we'll spot the carrier and start working. */
syslog(LOG_ERR, "%s: up_interface: %m", p);
/* Bring the interface up if not already */
if (!(ifp->flags & IFF_UP) &&
#ifdef SIOCGIFMEDIA
carrier_status(ifp) != -1 &&
#endif
up_interface(ifp) != 0)
syslog(LOG_ERR, "%s: up_interface: %m", ifp->name);
/* Don't allow loopback unless explicit */
if (ifp->flags & IFF_LOOPBACK) {
@ -364,22 +425,19 @@ discover_interfaces(int argc, char * const *argv)
if (ifp->hwlen != 0)
memcpy(ifp->hwaddr, sll->sll_addr, ifp->hwlen);
#endif
}
if (!(ifp->flags & IFF_POINTOPOINT)) {
switch(ifp->family) {
case ARPHRD_ETHER: /* FALLTHROUGH */
case ARPHRD_IEEE1394:
break;
default:
if (argc == 0 && ifac == 0) {
free_interface(ifp);
continue;
}
/* We only work on ethernet by default */
if (!(ifp->flags & IFF_POINTOPOINT) &&
ifp->family != ARPHRD_ETHER)
{
if (argc == 0 && ifac == 0) {
free_interface(ifp);
continue;
}
if (ifp->family != ARPHRD_IEEE1394)
syslog(LOG_WARNING,
"%s: unknown hardware family", p);
}
}
if (ifl)
ifl->next = ifp;
@ -433,98 +491,17 @@ do_address(const char *ifname,
freeifaddrs(ifaddrs);
return retval;
}
int
up_interface(const char *ifname)
{
int s;
struct ifreq ifr;
int retval = -1;
#ifdef __linux__
char *p;
#endif
if ((s = socket(AF_INET, SOCK_DGRAM, 0)) == -1)
return -1;
memset(&ifr, 0, sizeof(ifr));
strlcpy(ifr.ifr_name, ifname, sizeof(ifr.ifr_name));
#ifdef __linux__
/* We can only bring the real interface up */
if ((p = strchr(ifr.ifr_name, ':')))
*p = '\0';
#endif
if (ioctl(s, SIOCGIFFLAGS, &ifr) == 0) {
if ((ifr.ifr_flags & IFF_UP))
retval = 0;
else {
ifr.ifr_flags |= IFF_UP;
if (ioctl(s, SIOCSIFFLAGS, &ifr) == 0)
retval = 0;
}
}
close(s);
return retval;
}
int
carrier_status(const char *ifname)
{
int s;
struct ifreq ifr;
int retval = -1;
#ifdef SIOCGIFMEDIA
struct ifmediareq ifmr;
#endif
#ifdef __linux__
char *p;
#endif
if ((s = socket(AF_INET, SOCK_DGRAM, 0)) == -1)
return -1;
memset(&ifr, 0, sizeof(ifr));
strlcpy(ifr.ifr_name, ifname, sizeof(ifr.ifr_name));
#ifdef __linux__
/* We can only test the real interface up */
if ((p = strchr(ifr.ifr_name, ':')))
*p = '\0';
#endif
if ((retval = ioctl(s, SIOCGIFFLAGS, &ifr)) == 0) {
if (ifr.ifr_flags & IFF_UP && ifr.ifr_flags & IFF_RUNNING)
retval = 1;
else
retval = 0;
}
#ifdef SIOCGIFMEDIA
if (retval == 1) {
memset(&ifmr, 0, sizeof(ifmr));
strlcpy(ifmr.ifm_name, ifr.ifr_name, sizeof(ifmr.ifm_name));
retval = -1;
if (ioctl(s, SIOCGIFMEDIA, &ifmr) != -1 &&
ifmr.ifm_status & IFM_AVALID)
retval = (ifmr.ifm_status & IFM_ACTIVE) ? 1 : 0;
}
#endif
close(s);
return retval;
}
int
do_mtu(const char *ifname, short int mtu)
{
struct ifreq ifr;
int r;
int s;
if ((s = socket(AF_INET, SOCK_DGRAM, 0)) == -1)
return -1;
memset(&ifr, 0, sizeof(ifr));
strlcpy(ifr.ifr_name, ifname, sizeof(ifr.ifr_name));
ifr.ifr_mtu = mtu;
r = ioctl(s, mtu ? SIOCSIFMTU : SIOCGIFMTU, &ifr);
close(s);
r = ioctl(socket_afnet, mtu ? SIOCSIFMTU : SIOCGIFMTU, &ifr);
if (r == -1)
return -1;
return ifr.ifr_mtu;

View File

@ -87,6 +87,8 @@ struct rt {
struct rt *next;
};
extern int socket_afnet;
uint32_t get_netmask(uint32_t);
char *hwaddr_ntoa(const unsigned char *, size_t);
size_t hwaddr_aton(unsigned char *, const char *);
@ -102,7 +104,7 @@ int do_mtu(const char *, short int);
int inet_ntocidr(struct in_addr);
int inet_cidrtoaddr(int, struct in_addr *);
int up_interface(const char *);
int up_interface(struct interface *);
int do_address(const char *,
struct in_addr *, struct in_addr *, struct in_addr *, int);
int if_address(const struct interface *,
@ -130,7 +132,7 @@ int if_route(const struct interface *, const struct in_addr *,
void free_routes(struct rt *);
int open_udp_socket(struct interface *);
const size_t udp_dhcp_len;
extern const size_t udp_dhcp_len;
ssize_t make_udp_packet(uint8_t **, const uint8_t *, size_t,
struct in_addr, struct in_addr);
ssize_t get_udp_data(const uint8_t **, const uint8_t *);
@ -143,8 +145,8 @@ ssize_t send_raw_packet(const struct interface *, int,
const void *, ssize_t);
ssize_t get_raw_packet(struct interface *, int, void *, ssize_t);
int init_socket(void);
int init_sockets(void);
int open_link_socket(void);
int manage_link(int);
int carrier_status(const char *);
int carrier_status(struct interface *);
#endif