struct arphdr ar;
size_t len;
uint8_t *p;
+ const struct iarp_state *state;
ar.ar_hrd = htons(ifp->family);
ar.ar_pro = htons(ETHERTYPE_IP);
APPEND(&sip, sizeof(sip));
ZERO(ifp->hwlen);
APPEND(&tip, sizeof(tip));
- return if_sendrawpacket(ifp, ETHERTYPE_ARP, arp_buffer, len);
+
+ state = ARP_CSTATE(ifp);
+ return if_sendraw(ifp, state->fd, ETHERTYPE_ARP, arp_buffer, len);
eexit:
errno = ENOBUFS;
state = ARP_STATE(ifp);
flags = 0;
while (!(flags & RAW_EOF)) {
- bytes = if_readrawpacket(ifp, ETHERTYPE_ARP,
+ bytes = if_readraw(ifp, state->fd,
arp_buffer, sizeof(arp_buffer), &flags);
if (bytes == -1) {
logger(ifp->ctx, LOG_ERR,
state = ARP_STATE(ifp);
if (state->fd == -1) {
- state->fd = if_openrawsocket(ifp, ETHERTYPE_ARP);
+ state->fd = if_openraw(ifp, ETHERTYPE_ARP);
if (state->fd == -1) {
logger(ifp->ctx, LOG_ERR, "%s: %s: %m",
__func__, ifp->name);
TAILQ_FIRST(&state->arp_states) == NULL)
{
eloop_event_delete(ifp->ctx->eloop, state->fd);
- close(state->fd);
+ if_closeraw(state->fd);
free(state);
ifp->if_data[IF_DATA_ARP] = NULL;
}
if (state->raw_fd != -1) {
eloop_event_delete(ifp->ctx->eloop, state->raw_fd);
- close(state->raw_fd);
+ if_closeraw(state->raw_fd);
state->raw_fd = -1;
}
size_t ulen;
r = 0;
- udp = dhcp_makeudppacket(&ulen, (uint8_t *)bootp, len, from, to);
+ udp = dhcp_makeudppacket(&ulen, (uint8_t *)bootp, len, from,to);
if (udp == NULL) {
logger(ifp->ctx, LOG_ERR, "dhcp_makeudppacket: %m");
} else {
- r = if_sendrawpacket(ifp, ETHERTYPE_IP,
- (uint8_t *)udp, ulen);
+ r = if_sendraw(ifp, state->raw_fd,
+ ETHERTYPE_IP, (uint8_t *)udp, ulen);
free(udp);
}
/* If we failed to send a raw packet this normally means
* stopping the interface. */
if (r == -1) {
logger(ifp->ctx, LOG_ERR,
- "%s: if_sendrawpacket: %m", ifp->name);
+ "%s: if_sendraw: %m", ifp->name);
switch(errno) {
case ENETDOWN:
case ENETRESET:
flags = 0;
bootp = NULL;
while (!(flags & RAW_EOF)) {
- bytes = (size_t)if_readrawpacket(ifp, ETHERTYPE_IP,
+ bytes = (size_t)if_readraw(ifp, state->raw_fd,
buf, sizeof(buf), &flags);
if ((ssize_t)bytes == -1) {
logger(ifp->ctx, LOG_ERR,
state = D_STATE(ifp);
if (state->raw_fd == -1) {
- state->raw_fd = if_openrawsocket(ifp, ETHERTYPE_IP);
+ state->raw_fd = if_openraw(ifp, ETHERTYPE_IP);
if (state->raw_fd == -1) {
if (errno == ENOENT) {
logger(ifp->ctx, LOG_ERR,
#ifdef INET
const char *if_pfname = "Berkley Packet Filter";
+void
+if_closeraw(int fd)
+{
+
+ close(fd);
+}
+
int
-if_openrawsocket(struct interface *ifp, uint16_t protocol)
+if_openraw(struct interface *ifp, uint16_t protocol)
{
struct ipv4_state *state;
int fd = -1;
}
ssize_t
-if_sendrawpacket(const struct interface *ifp, uint16_t protocol,
+if_sendraw(__unused const struct interface *ifp, int fd, uint16_t protocol,
const void *data, size_t len)
{
struct iovec iov[2];
struct ether_header hw;
- int fd;
memset(&hw, 0, ETHER_HDR_LEN);
memset(&hw.ether_dhost, 0xff, ETHER_ADDR_LEN);
iov[0].iov_len = ETHER_HDR_LEN;
iov[1].iov_base = UNCONST(data);
iov[1].iov_len = len;
- fd = ipv4_protocol_fd(ifp, protocol);
return writev(fd, iov, 2);
}
/* BPF requires that we read the entire buffer.
* So we pass the buffer in the API so we can loop on >1 packet. */
ssize_t
-if_readrawpacket(struct interface *ifp, uint16_t protocol,
- void *data, size_t len, int *flags)
+if_readraw(struct interface *ifp, int fd, void *data, size_t len, int *flags)
{
- int fd;
struct bpf_hdr packet;
ssize_t bytes;
const unsigned char *payload;
struct ipv4_state *state;
state = IPV4_STATE(ifp);
- fd = ipv4_protocol_fd(ifp, protocol);
-
*flags = 0;
for (;;) {
if (state->buffer_len == 0) {
#ifdef INET
const char *if_pfname = "Packet Socket";
+void
+if_closeraw(int fd)
+{
+
+ close(fd);
+}
+
int
-if_openrawsocket(struct interface *ifp, uint16_t protocol)
+if_openraw(struct interface *ifp, uint16_t protocol)
{
int s;
union sockunion {
}
ssize_t
-if_sendrawpacket(const struct interface *ifp, uint16_t protocol,
+if_sendraw(const struct interface *ifp, int fd, uint16_t protocol,
const void *data, size_t len)
{
union sockunion {
struct sockaddr_ll sll;
struct sockaddr_storage ss;
} su;
- int fd;
memset(&su, 0, sizeof(su));
su.sll.sll_family = AF_PACKET;
&ipv4_bcast_addr, sizeof(ipv4_bcast_addr));
} else
memset(&su.sll.sll_addr, 0xff, ifp->hwlen);
- fd = ipv4_protocol_fd(ifp, protocol);
return sendto(fd, data, len, 0, &su.sa, sizeof(su.sll));
}
ssize_t
-if_readrawpacket(struct interface *ifp, uint16_t protocol,
+if_readraw(__unused struct interface *ifp, int fd,
void *data, size_t len, int *flags)
{
struct iovec iov = {
#endif
ssize_t bytes;
- int fd = -1;
#ifdef PACKET_AUXDATA
msg.msg_control = cmsgbuf;
msg.msg_controllen = sizeof(cmsgbuf);
#endif
- fd = ipv4_protocol_fd(ifp, protocol);
bytes = recvmsg(fd, &msg, 0);
if (bytes == -1)
return -1;
#ifdef INET
const char *if_pfname = "SunOS";
+void
+if_closeraw(int fd)
+{
+
+ UNUSED(fd);
+}
+
int
-if_openrawsocket(struct interface *ifp, uint16_t protocol)
+if_openraw(struct interface *ifp, uint16_t protocol)
{
UNUSED(ifp);
}
ssize_t
-if_sendrawpacket(const struct interface *ifp, uint16_t protocol,
+if_sendraw(const struct interface *ifp, int fd, uint16_t protocol,
const void *data, size_t len)
{
UNUSED(ifp);
+ UNUSED(fd);
UNUSED(protocol);
UNUSED(data);
UNUSED(len);
}
ssize_t
-if_readrawpacket(struct interface *ifp, uint16_t protocol,
+if_readraw(struct interface *ifp, int fd,
void *data, size_t len, int *flags)
{
UNUSED(ifp);
- UNUSED(protocol);
+ UNUSED(fd);
UNUSED(data);
UNUSED(len);
UNUSED(flags);
#ifdef INET
extern const char *if_pfname;
-int if_openrawsocket(struct interface *, uint16_t);
-ssize_t if_sendrawpacket(const struct interface *,
- uint16_t, const void *, size_t);
-ssize_t if_readrawpacket(struct interface *, uint16_t, void *, size_t, int *);
+int if_openraw(struct interface *, uint16_t);
+ssize_t if_sendraw(const struct interface *, int, uint16_t,
+ const void *, size_t);
+ssize_t if_readraw(struct interface *, int, void *, size_t, int *);
+void if_closeraw(int);
int if_address(const struct interface *,
const struct in_addr *, const struct in_addr *,
return 0;
}
-int
-ipv4_protocol_fd(const struct interface *ifp, uint16_t protocol)
-{
-
- if (protocol == ETHERTYPE_ARP) {
- const struct iarp_state *istate;
-
- istate = ARP_CSTATE(ifp);
- assert(istate != NULL);
- return istate->fd;
- } else {
- const struct dhcp_state *dstate;
-
- dstate = D_CSTATE(ifp);
- assert(dstate != NULL);
- return dstate->raw_fd;
- }
-}
-
/* Interface comparer for working out ordering. */
int
ipv4_ifcmp(const struct interface *si, const struct interface *ti)
#ifdef INET
struct ipv4_state *ipv4_getstate(struct interface *);
int ipv4_init(struct dhcpcd_ctx *);
-int ipv4_protocol_fd(const struct interface *, uint16_t);
int ipv4_ifcmp(const struct interface *, const struct interface *);
uint8_t inet_ntocidr(struct in_addr);
int inet_cidrtoaddr(int, struct in_addr *);