Added ARCNET raw packet handling for Linux.
This commit is contained in:
@@ -6,12 +6,14 @@ BASEDIR = .
|
|||||||
#CFLAGS = -Wall -I. -O2 -g
|
#CFLAGS = -Wall -I. -O2 -g
|
||||||
# Note: you can strip out symbols using the strip command
|
# Note: you can strip out symbols using the strip command
|
||||||
# to get an idea of how big the compile really is.
|
# to get an idea of how big the compile really is.
|
||||||
#CFLAGS = -Wall -I. -Iports/linux -g -DBACDL_MSTP=1
|
|
||||||
#CFLAGS = -Wall -I. -Iports/linux -g -DBACDL_ETHERNET=1
|
#CFLAGS = -Wall -I. -Iports/linux -g -DBACDL_ETHERNET=1
|
||||||
CFLAGS = -Wall -I. -Iports/linux -g -DBACDL_BIP=1
|
CFLAGS = -Wall -I. -Iports/linux -g -DBACDL_ARCNET=1
|
||||||
|
#CFLAGS = -Wall -I. -Iports/linux -g -DBACDL_MSTP=1
|
||||||
|
#CFLAGS = -Wall -I. -Iports/linux -g -DBACDL_BIP=1
|
||||||
|
|
||||||
SRCS = ports/linux/main.c \
|
SRCS = ports/linux/main.c \
|
||||||
ports/linux/ethernet.c \
|
ports/linux/ethernet.c \
|
||||||
|
ports/linux/arcnet.c \
|
||||||
ports/linux/bip-init.c \
|
ports/linux/bip-init.c \
|
||||||
bip.c \
|
bip.c \
|
||||||
dlmstp.c \
|
dlmstp.c \
|
||||||
|
|||||||
+16
-3
@@ -34,15 +34,21 @@
|
|||||||
#ifndef ARCNET_H
|
#ifndef ARCNET_H
|
||||||
#define ARCNET_H
|
#define ARCNET_H
|
||||||
|
|
||||||
|
#include <stdbool.h>
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
|
#include <stddef.h>
|
||||||
#include "bacdef.h"
|
#include "bacdef.h"
|
||||||
|
|
||||||
// specific defines for ARCNET
|
// specific defines for ARCNET
|
||||||
#define MAX_HEADER (1+1+2+2+1+1+1+1)
|
#define MAX_HEADER (1+1+2+2+1+1+1+1)
|
||||||
#define MAX_MPDU (MAX_HEADER+MAX_PDU)
|
#define MAX_MPDU (MAX_HEADER+MAX_PDU)
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
extern "C" {
|
||||||
|
#endif /* __cplusplus */
|
||||||
|
|
||||||
bool arcnet_valid(void);
|
bool arcnet_valid(void);
|
||||||
bool arcnet_cleanup(void);
|
void arcnet_cleanup(void);
|
||||||
bool arcnet_init(char *interface_name);
|
bool arcnet_init(char *interface_name);
|
||||||
|
|
||||||
/* function to send a packet out the 802.2 socket */
|
/* function to send a packet out the 802.2 socket */
|
||||||
@@ -60,13 +66,20 @@ int arcnet_send_pdu(
|
|||||||
uint8_t *pdu, // any data to be sent - may be null
|
uint8_t *pdu, // any data to be sent - may be null
|
||||||
unsigned pdu_len); // number of bytes of data
|
unsigned pdu_len); // number of bytes of data
|
||||||
|
|
||||||
// receives an 802.2 framed packet
|
// receives an framed packet
|
||||||
// returns the number of octets in the PDU, or zero on failure
|
// returns the number of octets in the PDU, or zero on failure
|
||||||
uint16_t arcnet_receive(
|
uint16_t arcnet_receive(
|
||||||
BACNET_ADDRESS *src, // source address
|
BACNET_ADDRESS *src, // source address
|
||||||
uint8_t *pdu, // PDU data
|
uint8_t *pdu, // PDU data
|
||||||
uint16_t max_pdu); // amount of space available in the PDU
|
uint16_t max_pdu, // amount of space available in the PDU
|
||||||
|
unsigned timeout); // milliseconds to wait for a packet
|
||||||
|
|
||||||
void arcnet_get_my_address(BACNET_ADDRESS *my_address);
|
void arcnet_get_my_address(BACNET_ADDRESS *my_address);
|
||||||
|
void arcnet_get_broadcast_address(
|
||||||
|
BACNET_ADDRESS *dest); // destination address
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
}
|
||||||
|
#endif /* __cplusplus */
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -46,6 +46,12 @@ int datalink_send_pdu(
|
|||||||
uint8_t *pdu, // any data to be sent - may be null
|
uint8_t *pdu, // any data to be sent - may be null
|
||||||
unsigned pdu_len) // number of bytes of data
|
unsigned pdu_len) // number of bytes of data
|
||||||
{
|
{
|
||||||
|
#ifdef BACDL_ARCNET
|
||||||
|
return arcnet_send_pdu(
|
||||||
|
dest,
|
||||||
|
pdu,
|
||||||
|
pdu_len);
|
||||||
|
#endif
|
||||||
#ifdef BACDL_MSTP
|
#ifdef BACDL_MSTP
|
||||||
return dlmstp_send_pdu(
|
return dlmstp_send_pdu(
|
||||||
dest,
|
dest,
|
||||||
@@ -73,6 +79,13 @@ uint16_t datalink_receive(
|
|||||||
uint16_t max_pdu, // amount of space available in the PDU
|
uint16_t max_pdu, // amount of space available in the PDU
|
||||||
unsigned timeout) // number of milliseconds to wait for a packet
|
unsigned timeout) // number of milliseconds to wait for a packet
|
||||||
{
|
{
|
||||||
|
#ifdef BACDL_ARCNET
|
||||||
|
return arcnet_receive(
|
||||||
|
src,
|
||||||
|
pdu,
|
||||||
|
max_pdu,
|
||||||
|
timeout);
|
||||||
|
#endif
|
||||||
#ifdef BACDL_MSTP
|
#ifdef BACDL_MSTP
|
||||||
return dlmstp_receive(
|
return dlmstp_receive(
|
||||||
src,
|
src,
|
||||||
@@ -99,6 +112,9 @@ uint16_t datalink_receive(
|
|||||||
void datalink_get_broadcast_address(
|
void datalink_get_broadcast_address(
|
||||||
BACNET_ADDRESS *dest) // destination address
|
BACNET_ADDRESS *dest) // destination address
|
||||||
{
|
{
|
||||||
|
#ifdef BACDL_ARCNET
|
||||||
|
arcnet_get_broadcast_address(dest);
|
||||||
|
#endif
|
||||||
#ifdef BACDL_MSTP
|
#ifdef BACDL_MSTP
|
||||||
dlmstp_get_broadcast_address(dest);
|
dlmstp_get_broadcast_address(dest);
|
||||||
#endif
|
#endif
|
||||||
@@ -113,6 +129,9 @@ void datalink_get_broadcast_address(
|
|||||||
void datalink_get_my_address(
|
void datalink_get_my_address(
|
||||||
BACNET_ADDRESS *my_address)
|
BACNET_ADDRESS *my_address)
|
||||||
{
|
{
|
||||||
|
#ifdef BACDL_ARCNET
|
||||||
|
arcnet_get_my_address(my_address);
|
||||||
|
#endif
|
||||||
#ifdef BACDL_MSTP
|
#ifdef BACDL_MSTP
|
||||||
dlmstp_get_my_address(my_address);
|
dlmstp_get_my_address(my_address);
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -43,6 +43,10 @@
|
|||||||
#include "ethernet.h"
|
#include "ethernet.h"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#ifdef BACDL_ARCNET
|
||||||
|
#include "arcnet.h"
|
||||||
|
#endif
|
||||||
|
|
||||||
#ifdef BACDL_MSTP
|
#ifdef BACDL_MSTP
|
||||||
#include "dlmstp.h"
|
#include "dlmstp.h"
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -0,0 +1,321 @@
|
|||||||
|
#include <stdint.h>
|
||||||
|
#include "bacdef.h"
|
||||||
|
#include "arcnet.h"
|
||||||
|
#include "net.h"
|
||||||
|
|
||||||
|
// my local device data - MAC address
|
||||||
|
uint8_t ARCNET_MAC_Address = 0;
|
||||||
|
// ARCNET file handle
|
||||||
|
static int ARCNET_Sock_FD = -1;
|
||||||
|
// ARCNET socket address (has the interface name)
|
||||||
|
static struct sockaddr ARCNET_Socket_Address;
|
||||||
|
// Broadcast address
|
||||||
|
#define ARCNET_BROADCAST 0
|
||||||
|
|
||||||
|
bool arcnet_valid(void)
|
||||||
|
{
|
||||||
|
return (ARCNET_Sock_FD >= 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
void arcnet_cleanup(void)
|
||||||
|
{
|
||||||
|
if (arcnet_valid())
|
||||||
|
close(ARCNET_Sock_FD);
|
||||||
|
ARCNET_Sock_FD = -1;
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int arcnet_bind(char *interface_name)
|
||||||
|
{
|
||||||
|
int sock_fd = -1; // return value
|
||||||
|
struct ifreq ifr;
|
||||||
|
int rv; // return value - error value from df or ioctl call
|
||||||
|
|
||||||
|
fprintf(stderr,"arcnet: opening \"%s\"\n",interface_name);
|
||||||
|
// note: on some systems you may have to add or enable in
|
||||||
|
// modules.conf (or in modutils/alias on Debian with update-modules)
|
||||||
|
// alias net-pf-17 af_packet
|
||||||
|
// Then follow it by: # modprobe af_packet
|
||||||
|
if ((sock_fd = socket(PF_PACKET, SOCK_PACKET, htons(ETH_P_ALL))) < 0)
|
||||||
|
{
|
||||||
|
/* Error occured */
|
||||||
|
fprintf(stderr,
|
||||||
|
"arcnet: Error opening socket: %s\n",
|
||||||
|
strerror(errno));
|
||||||
|
fprintf(stderr,
|
||||||
|
"You might need to add the following to modules.conf\n"
|
||||||
|
"(or in /etc/modutils/alias on Debian with update-modules):\n"
|
||||||
|
"alias net-pf-17 af_packet\n"
|
||||||
|
"Also, add af_packet to /etc/modules.\n"
|
||||||
|
"Then follow it by:\n"
|
||||||
|
"# modprobe af_packet\n");
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ARCNET_Sock_FD >= 0)
|
||||||
|
{
|
||||||
|
/* Bind the socket to an interface name so we only get packets from it */
|
||||||
|
ARCNET_Socket_Address.sa_family = ARPHRD_ARCNET;
|
||||||
|
//ARCNET_Socket_Address.sa_family = PF_INET;
|
||||||
|
/* Clear the memory before copying */
|
||||||
|
memset(ARCNET_Socket_Address.sa_data, '\0',
|
||||||
|
sizeof(ARCNET_Socket_Address.sa_data));
|
||||||
|
/* Strcpy the interface name into the address */
|
||||||
|
strncpy(ARCNET_Socket_Address.sa_data, interface_name,
|
||||||
|
sizeof(ARCNET_Socket_Address.sa_data)-1);
|
||||||
|
fprintf(stderr,"arcnet: binding \"%s\"\n",ARCNET_Socket_Address.sa_data);
|
||||||
|
if (bind(sock_fd, &ARCNET_Socket_Address,
|
||||||
|
sizeof(ARCNET_Socket_Address)) != 0)
|
||||||
|
{
|
||||||
|
/* Bind problem, close socket and return */
|
||||||
|
fprintf(stderr,
|
||||||
|
"arcnet: Unable to bind socket : %s\n",
|
||||||
|
strerror(errno));
|
||||||
|
fprintf(stderr,
|
||||||
|
"You might need to add the following to modules.conf\n"
|
||||||
|
"(or in /etc/modutils/alias on Debian with update-modules):\n"
|
||||||
|
"alias net-pf-17 af_packet\n"
|
||||||
|
"Also, add af_packet to /etc/modules.\n"
|
||||||
|
"Then follow it by:\n"
|
||||||
|
"# modprobe af_packet\n");
|
||||||
|
/* Close the socket */
|
||||||
|
close(sock_fd);
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
strncpy(ifr.ifr_name, interface_name, sizeof(ifr.ifr_name));
|
||||||
|
rv = ioctl(sock_fd, SIOCGIFHWADDR, &ifr);
|
||||||
|
if (rv != -1) /* worked okay */
|
||||||
|
ARCNET_MAC_Address = ifr.ifr_hwaddr.sa_data[0];
|
||||||
|
fprintf(stderr,"arcnet: MAC=%02Xh\n",ARCNET_MAC_Address);
|
||||||
|
|
||||||
|
atexit(arcnet_cleanup);
|
||||||
|
|
||||||
|
return sock_fd;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool arcnet_init(char *interface_name)
|
||||||
|
{
|
||||||
|
ARCNET_Sock_FD = arcnet_bind(interface_name);
|
||||||
|
|
||||||
|
return arcnet_valid();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* function to send a packet out the socket */
|
||||||
|
/* returns number of bytes sent on success, negative on failure */
|
||||||
|
int arcnet_send(
|
||||||
|
BACNET_ADDRESS *dest, // destination address
|
||||||
|
BACNET_ADDRESS *src, // source address
|
||||||
|
uint8_t *pdu, // any data to be sent - may be null
|
||||||
|
unsigned pdu_len) // number of bytes of data
|
||||||
|
{
|
||||||
|
int bytes = 0;
|
||||||
|
uint8_t mtu[512] = { 0 };
|
||||||
|
int mtu_len = 0;
|
||||||
|
struct archdr *pkt = (struct archdr *)mtu;
|
||||||
|
|
||||||
|
// don't waste time if the socket is not valid
|
||||||
|
if (ARCNET_Sock_FD < 0)
|
||||||
|
{
|
||||||
|
fprintf(stderr, "arcnet: socket is invalid!\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
/* load destination MAC address */
|
||||||
|
if (dest->mac_len == 1)
|
||||||
|
pkt->hard.dest = dest->mac[0];
|
||||||
|
else
|
||||||
|
{
|
||||||
|
fprintf(stderr, "arcnet: invalid destination MAC address!\n");
|
||||||
|
return -2;
|
||||||
|
}
|
||||||
|
if (src->mac_len == 1)
|
||||||
|
pkt->hard.source = src->mac[0];
|
||||||
|
else
|
||||||
|
{
|
||||||
|
fprintf(stderr, "arcnet: invalid source MAC address!\n");
|
||||||
|
return -3;
|
||||||
|
}
|
||||||
|
if ((ARC_HDR_SIZE + pdu_len) > 512)
|
||||||
|
{
|
||||||
|
fprintf(stderr, "arcnet: PDU is too big to send!\n");
|
||||||
|
return -4;
|
||||||
|
}
|
||||||
|
/* Logical PDU portion */
|
||||||
|
pkt->soft.raw[0] = 0xCD; /* SC for BACnet */
|
||||||
|
pkt->soft.raw[1] = 0x82; /* DSAP for BACnet */
|
||||||
|
pkt->soft.raw[2] = 0x82; /* SSAP for BACnet */
|
||||||
|
pkt->soft.raw[3] = 0x03; /* Control byte in header */
|
||||||
|
memcpy(&pkt->soft.raw[4], pdu, pdu_len);
|
||||||
|
/* packet length */
|
||||||
|
mtu_len = ARC_HDR_SIZE + 4 /*SC,DSAP,SSAP,LLC*/ + pdu_len;
|
||||||
|
/* Send the packet */
|
||||||
|
bytes =
|
||||||
|
sendto(ARCNET_Sock_FD, &mtu, mtu_len, 0,
|
||||||
|
(struct sockaddr *) &ARCNET_Socket_Address,
|
||||||
|
sizeof(ARCNET_Socket_Address));
|
||||||
|
/* did it get sent? */
|
||||||
|
if (bytes < 0)
|
||||||
|
fprintf(stderr,"arcnet: Error sending packet: %s\n",
|
||||||
|
strerror(errno));
|
||||||
|
|
||||||
|
return bytes;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* function to send a PDU out the socket */
|
||||||
|
/* returns number of bytes sent on success, negative on failure */
|
||||||
|
int arcnet_send_pdu(
|
||||||
|
BACNET_ADDRESS *dest, // destination address
|
||||||
|
uint8_t *pdu, // any data to be sent - may be null
|
||||||
|
unsigned pdu_len) // number of bytes of data
|
||||||
|
{
|
||||||
|
BACNET_ADDRESS src = {0}; // source address
|
||||||
|
|
||||||
|
src.mac[0] = ARCNET_MAC_Address;
|
||||||
|
src.mac_len = 1;
|
||||||
|
return arcnet_send(dest, // destination address
|
||||||
|
&src, // source address
|
||||||
|
pdu, // any data to be sent - may be null
|
||||||
|
pdu_len); // number of bytes of data
|
||||||
|
}
|
||||||
|
|
||||||
|
// receives an framed packet
|
||||||
|
// returns the number of octets in the PDU, or zero on failure
|
||||||
|
uint16_t arcnet_receive(
|
||||||
|
BACNET_ADDRESS *src, // source address
|
||||||
|
uint8_t *pdu, // PDU data
|
||||||
|
uint16_t max_pdu, // amount of space available in the PDU
|
||||||
|
unsigned timeout) // milliseconds to wait for a packet
|
||||||
|
{
|
||||||
|
int received_bytes;
|
||||||
|
uint8_t buf[512] = {0}; // data
|
||||||
|
uint16_t pdu_len = 0; // return value
|
||||||
|
fd_set read_fds;
|
||||||
|
int max;
|
||||||
|
struct timeval select_timeout;
|
||||||
|
struct archdr *pkt = (struct archdr *)buf;
|
||||||
|
|
||||||
|
/* Make sure the socket is open */
|
||||||
|
if (ARCNET_Sock_FD <= 0)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
/* we could just use a non-blocking socket, but that consumes all
|
||||||
|
the CPU time. We can use a timeout; it is only supported as
|
||||||
|
a select. */
|
||||||
|
if (timeout >= 1000)
|
||||||
|
{
|
||||||
|
select_timeout.tv_sec = timeout / 1000;
|
||||||
|
select_timeout.tv_usec =
|
||||||
|
1000 * (timeout - select_timeout.tv_sec * 1000);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
select_timeout.tv_sec = 0;
|
||||||
|
select_timeout.tv_usec = 1000 * timeout;
|
||||||
|
}
|
||||||
|
FD_ZERO(&read_fds);
|
||||||
|
FD_SET(ARCNET_Sock_FD, &read_fds);
|
||||||
|
max = ARCNET_Sock_FD;
|
||||||
|
|
||||||
|
if (select(max + 1, &read_fds, NULL, NULL, &select_timeout) > 0)
|
||||||
|
received_bytes = read(ARCNET_Sock_FD, &buf[0], sizeof(buf));
|
||||||
|
else
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
/* See if there is a problem */
|
||||||
|
if (received_bytes < 0) {
|
||||||
|
// EAGAIN Non-blocking I/O has been selected
|
||||||
|
// using O_NONBLOCK and no data
|
||||||
|
// was immediately available for reading.
|
||||||
|
if (errno != EAGAIN)
|
||||||
|
fprintf(stderr,"ethernet: Read error in receiving packet: %s\n",
|
||||||
|
strerror(errno));
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (received_bytes == 0)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
printf("arcnet: received %u bytes from %02Xh (proto==%02Xh)\n",
|
||||||
|
received_bytes, pkt->hard.source, pkt->soft.raw[0]);
|
||||||
|
|
||||||
|
if (pkt->hard.source == ARCNET_MAC_Address) {
|
||||||
|
fprintf(stderr,"arcnet: self sent packet?\n");
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
if (pkt->soft.raw[0] != 0xCD) {
|
||||||
|
fprintf(stderr,"arcnet: Non-BACnet packet.\n");
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
if ((pkt->hard.dest != ARCNET_MAC_Address) &&
|
||||||
|
(pkt->hard.dest != ARCNET_BROADCAST))
|
||||||
|
{
|
||||||
|
fprintf(stderr,"arcnet: This packet is not for us.\n");
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
if ((pkt->soft.raw[1] != 0x82) || /* DSAP */
|
||||||
|
(pkt->soft.raw[2] != 0x82) || /* LSAP */
|
||||||
|
(pkt->soft.raw[3] != 0x03)) /* LLC Control */
|
||||||
|
{
|
||||||
|
fprintf(stderr,"arcnet: BACnet packet has invalid LLC.\n");
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
/* It must be addressed to us or be a Broadcast */
|
||||||
|
if ((pkt->hard.dest != ARCNET_MAC_Address) &&
|
||||||
|
(pkt->hard.dest != ARCNET_BROADCAST))
|
||||||
|
{
|
||||||
|
fprintf(stderr,"arcnet: This packet is not for us.\n");
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
/* copy the source address */
|
||||||
|
src->mac_len = 1;
|
||||||
|
src->mac[0] = pkt->hard.source;
|
||||||
|
/* compute the PDU length */
|
||||||
|
pdu_len = received_bytes - ARC_HDR_SIZE;
|
||||||
|
pdu_len -= 4 /* SC, DSAP, SSAP, LLC Control */ ;
|
||||||
|
// copy the buffer into the PDU
|
||||||
|
if (pdu_len < max_pdu)
|
||||||
|
memmove(&pdu[0],&pkt->soft.raw[4],pdu_len);
|
||||||
|
// silently ignore packets that are too large
|
||||||
|
else
|
||||||
|
pdu_len = 0;
|
||||||
|
|
||||||
|
return pdu_len;
|
||||||
|
}
|
||||||
|
|
||||||
|
void arcnet_get_my_address(BACNET_ADDRESS *my_address)
|
||||||
|
{
|
||||||
|
int i = 0;
|
||||||
|
|
||||||
|
my_address->mac_len = 1;
|
||||||
|
my_address->mac[0] = ARCNET_MAC_Address;
|
||||||
|
my_address->net = 0; // local only, no routing
|
||||||
|
my_address->len = 0;
|
||||||
|
for (i = 0; i < MAX_MAC_LEN; i++)
|
||||||
|
{
|
||||||
|
my_address->adr[i] = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
void arcnet_get_broadcast_address(
|
||||||
|
BACNET_ADDRESS *dest) // destination address
|
||||||
|
{
|
||||||
|
int i = 0; // counter
|
||||||
|
|
||||||
|
if (dest)
|
||||||
|
{
|
||||||
|
dest->mac[0] = ARCNET_BROADCAST;
|
||||||
|
dest->mac_len = 1;
|
||||||
|
dest->net = BACNET_BROADCAST_NETWORK;
|
||||||
|
dest->len = 0; // len=0 denotes broadcast address
|
||||||
|
for (i = 0; i < MAX_MAC_LEN; i++)
|
||||||
|
{
|
||||||
|
dest->adr[i] = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
@@ -316,7 +316,7 @@ uint16_t ethernet_receive(
|
|||||||
max = eth802_sockfd;
|
max = eth802_sockfd;
|
||||||
|
|
||||||
if (select(max + 1, &read_fds, NULL, NULL, &select_timeout) > 0)
|
if (select(max + 1, &read_fds, NULL, NULL, &select_timeout) > 0)
|
||||||
received_bytes = read(eth802_sockfd, &buf[0], MAX_MPDU);
|
received_bytes = read(eth802_sockfd, &buf[0], sizeof(buf));
|
||||||
else
|
else
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
|
|||||||
@@ -79,6 +79,7 @@
|
|||||||
#include <sys/socket.h>
|
#include <sys/socket.h>
|
||||||
#include <net/route.h>
|
#include <net/route.h>
|
||||||
#include <net/if.h>
|
#include <net/if.h>
|
||||||
|
#include <net/if_arp.h>
|
||||||
#include <features.h> /* for the glibc version number */
|
#include <features.h> /* for the glibc version number */
|
||||||
#if __GLIBC__ >= 2 && __GLIBC_MINOR >= 1
|
#if __GLIBC__ >= 2 && __GLIBC_MINOR >= 1
|
||||||
#include <netpacket/packet.h>
|
#include <netpacket/packet.h>
|
||||||
@@ -86,7 +87,8 @@
|
|||||||
#else
|
#else
|
||||||
#include <asm/types.h>
|
#include <asm/types.h>
|
||||||
#include <linux/if_packet.h>
|
#include <linux/if_packet.h>
|
||||||
#include <linux/if_ether.h> /* The L2 protocols */
|
#include <linux/if_arcnet.h>
|
||||||
|
#include <linux/if_ether.h>
|
||||||
#endif
|
#endif
|
||||||
#include <netinet/in.h>
|
#include <netinet/in.h>
|
||||||
#include <arpa/inet.h>
|
#include <arpa/inet.h>
|
||||||
|
|||||||
Reference in New Issue
Block a user