Some rawsock changes
This commit is contained in:
parent
3b1cdc7931
commit
1d53062f66
2 changed files with 33 additions and 34 deletions
61
rawsock.c
61
rawsock.c
|
|
@ -3,6 +3,10 @@
|
|||
#include <stdio.h>
|
||||
#include <pcap.h>
|
||||
|
||||
#ifndef MIN
|
||||
#define MIN(a, b) ((a) < (b) ? (a) : (b))
|
||||
#endif
|
||||
|
||||
struct rawsock
|
||||
{
|
||||
pcap_t *pcap;
|
||||
|
|
@ -10,9 +14,9 @@ struct rawsock
|
|||
int fd;
|
||||
};
|
||||
|
||||
struct rawsock *rawsock_create(const char *interface)
|
||||
struct rawsock *rawsock_create(const char *interface, uint16_t protocol)
|
||||
{
|
||||
char errbuf[PCAP_ERRBUF_SIZE];
|
||||
char buf[PCAP_ERRBUF_SIZE];
|
||||
struct bpf_program fp;
|
||||
struct rawsock *sock;
|
||||
int err;
|
||||
|
|
@ -23,16 +27,16 @@ struct rawsock *rawsock_create(const char *interface)
|
|||
return NULL;
|
||||
}
|
||||
|
||||
errbuf[0] = '\0';
|
||||
buf[0] = '\0';
|
||||
|
||||
sock->pcap = pcap_open_live(interface, BUFSIZ, 1, 1, errbuf);
|
||||
sock->pcap = pcap_open_live(interface, BUFSIZ, 1, 1, buf);
|
||||
if (!sock->pcap) {
|
||||
fprintf(stderr, "pcap_open_live: %s\n", errbuf);
|
||||
fprintf(stderr, "pcap_open_live: %s\n", buf);
|
||||
goto cleanup_malloc;
|
||||
}
|
||||
|
||||
if (*errbuf) {
|
||||
fprintf(stderr, "Warning: %s.\n", errbuf);
|
||||
if (*buf) {
|
||||
fprintf(stderr, "Warning: %s.\n", buf);
|
||||
}
|
||||
|
||||
if (pcap_datalink(sock->pcap) != DLT_EN10MB) {
|
||||
|
|
@ -40,8 +44,14 @@ struct rawsock *rawsock_create(const char *interface)
|
|||
goto cleanup_pcap;
|
||||
}
|
||||
|
||||
err = pcap_compile(sock->pcap, &fp, "ether proto 0x0912", 0,
|
||||
PCAP_NETMASK_UNKNOWN);
|
||||
sock->fd = pcap_get_selectable_fd(sock->pcap);
|
||||
if (sock->fd == -1) {
|
||||
fprintf(stderr, "No selectable file descriptor available.\n");
|
||||
goto cleanup_pcap;
|
||||
}
|
||||
|
||||
snprintf(buf, sizeof(buf), "ether proto %04x", protocol);
|
||||
err = pcap_compile(sock->pcap, &fp, buf, 0, PCAP_NETMASK_UNKNOWN);
|
||||
if (err) {
|
||||
pcap_perror(sock->pcap, "pcap_compile");
|
||||
goto cleanup_pcap;
|
||||
|
|
@ -52,12 +62,6 @@ struct rawsock *rawsock_create(const char *interface)
|
|||
goto cleanup_pcap;
|
||||
}
|
||||
|
||||
sock->fd = pcap_get_selectable_fd(sock->pcap);
|
||||
if (sock->fd == -1) {
|
||||
fprintf(stderr, "No selectable file descriptor available.\n");
|
||||
goto cleanup_pcap;
|
||||
}
|
||||
|
||||
return sock;
|
||||
|
||||
cleanup_pcap:
|
||||
|
|
@ -67,9 +71,10 @@ cleanup_malloc:
|
|||
return NULL;
|
||||
}
|
||||
|
||||
int rawsock_recv(struct rawsock *sock, uint8_t **buffer, unsigned *size)
|
||||
ssize_t rawsock_recv(struct rawsock *sock, uint8_t *buf, size_t len)
|
||||
{
|
||||
struct pcap_pkthdr* hdr;
|
||||
const u_char *capbuf;
|
||||
int status;
|
||||
fd_set fds;
|
||||
|
||||
|
|
@ -86,39 +91,33 @@ int rawsock_recv(struct rawsock *sock, uint8_t **buffer, unsigned *size)
|
|||
}
|
||||
}
|
||||
|
||||
status = pcap_next_ex(sock->pcap, &hdr, (const u_char**)buffer);
|
||||
status = pcap_next_ex(sock->pcap, &hdr, &capbuf);
|
||||
switch (status) {
|
||||
case 1:
|
||||
status = 0;
|
||||
*size = hdr->caplen;
|
||||
break;
|
||||
memcpy(buf, capbuf, MIN(len, hdr->caplen));
|
||||
return hdr->caplen;
|
||||
case 0:
|
||||
status = 1;
|
||||
break;
|
||||
return 0;
|
||||
case -1:
|
||||
pcap_perror(sock->pcap, "pcap_next_ex");
|
||||
status = -1;
|
||||
break;
|
||||
return -1;
|
||||
default:
|
||||
fprintf(stderr, "pcap_next_ex: returned %d.\n", status);
|
||||
status = -1;
|
||||
break;
|
||||
return -1;
|
||||
}
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
int rawsock_send(struct rawsock *sock, uint8_t *buffer, size_t size)
|
||||
int rawsock_send(struct rawsock *sock, uint8_t *buf, size_t len)
|
||||
{
|
||||
#if defined(_WIN32) || defined(_WIN64)
|
||||
if (pcap_sendpacket(sock->pcap, buffer, size) == 0) {
|
||||
if (pcap_sendpacket(sock->pcap, buf, len) == 0) {
|
||||
return 0;
|
||||
} else {
|
||||
pcap_perror(sock->pcap, "pcap_sendpacket");
|
||||
return -1;
|
||||
}
|
||||
#else
|
||||
if (pcap_inject(sock->pcap, buffer, size) != size) {
|
||||
if (pcap_inject(sock->pcap, buf, len) == len) {
|
||||
return 0;
|
||||
} else {
|
||||
pcap_perror(sock->pcap, "pcap_inject");
|
||||
|
|
|
|||
|
|
@ -2,8 +2,8 @@
|
|||
|
||||
struct rawsock;
|
||||
|
||||
struct rawsock *rawsock_create(const char *interface);
|
||||
struct rawsock *rawsock_create(const char *interface, uint16_t protocol);
|
||||
int rawsock_close(struct rawsock *sock);
|
||||
int rawsock_send(struct rawsock *sock, uint8_t *buffer, size_t size);
|
||||
int rawsock_recv(struct rawsock *sock, uint8_t **buffer, unsigned *size);
|
||||
int rawsock_send(struct rawsock *sock, uint8_t *buf, size_t len);
|
||||
ssize_t rawsock_recv(struct rawsock *sock, uint8_t *buf, size_t len);
|
||||
int rawsock_set_timeout(struct rawsock *sock, unsigned msec);
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue