make link structure, prepare ARP structure
This commit is contained in:
parent
9294334bf1
commit
a37fa22b37
1 changed files with 67 additions and 16 deletions
83
main.c
83
main.c
|
|
@ -8,11 +8,10 @@
|
||||||
#include <netinet/in.h>
|
#include <netinet/in.h>
|
||||||
#include <net/ethernet.h>
|
#include <net/ethernet.h>
|
||||||
#include <linux/if_packet.h>
|
#include <linux/if_packet.h>
|
||||||
#include <linux/if_arp.h>
|
|
||||||
|
|
||||||
typedef uint8_t mac_t[6];
|
#define MTU 1500
|
||||||
|
|
||||||
void parse_mac(const char* str, mac_t mac) {
|
void parse_mac(const char* str, uint8_t* mac) {
|
||||||
char* s = strdup(str);
|
char* s = strdup(str);
|
||||||
char* octet = strtok(s, ":");
|
char* octet = strtok(s, ":");
|
||||||
int i = 0;
|
int i = 0;
|
||||||
|
|
@ -26,27 +25,79 @@ void parse_mac(const char* str, mac_t mac) {
|
||||||
free(s);
|
free(s);
|
||||||
}
|
}
|
||||||
|
|
||||||
int main(int argc, char** argv) {
|
void print_mac(uint8_t* mac) {
|
||||||
// ifname hostMAC gatewayMAC targetMAC
|
printf("%02x:%02x:%02x:%02x:%02x:%02x\n",
|
||||||
|
mac[0], mac[1], mac[2], mac[3], mac[4], mac[5]);
|
||||||
|
}
|
||||||
|
|
||||||
mac_t host, gateway, target;
|
struct linkinterface {
|
||||||
parse_mac(argv[2], host);
|
char* if_name;
|
||||||
parse_mac(argv[3], gateway);
|
socklen_t if_len;
|
||||||
parse_mac(argv[4], target);
|
|
||||||
|
|
||||||
int raw = socket(PF_PACKET, SOCK_RAW, htons(ETH_P_ALL));
|
uint8_t host[ETH_ALEN];
|
||||||
if (raw < 0) {
|
uint8_t gateway[ETH_ALEN];
|
||||||
perror("socket");
|
|
||||||
|
int fd; // raw socket
|
||||||
|
};
|
||||||
|
|
||||||
|
struct linkinterface* link_parse(const char* if_name, const char* host, const char* gateway) {
|
||||||
|
struct linkinterface* link = (struct linkinterface*)malloc(sizeof(struct linkinterface));
|
||||||
|
link->if_name = strdup(if_name);
|
||||||
|
link->if_len = strlen(link->if_name);
|
||||||
|
|
||||||
|
parse_mac(host, link->host);
|
||||||
|
parse_mac(gateway, link->gateway);
|
||||||
|
}
|
||||||
|
|
||||||
|
int link_open(struct linkinterface* link) {
|
||||||
|
link->fd = socket(PF_PACKET, SOCK_RAW, htons(ETH_P_ALL));
|
||||||
|
if (link->fd < 0) {
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
setsockopt(raw, SOL_SOCKET, SO_BINDTODEVICE, argv[1], strlen(argv[1]));
|
setsockopt(link->fd, SOL_SOCKET, SO_BINDTODEVICE, link->if_name, link->if_name);
|
||||||
|
}
|
||||||
|
|
||||||
|
void link_free(struct linkinterface* link) {
|
||||||
|
close(link->fd);
|
||||||
|
free(link->if_name);
|
||||||
|
free(link);
|
||||||
|
}
|
||||||
|
|
||||||
|
typedef struct arp_packet_s {
|
||||||
|
struct ether_header ether;
|
||||||
|
|
||||||
|
uint16_t hrd; // Hardware address space (e.g., Ethernet, Packet Radio Net.)
|
||||||
|
uint16_t pro; // Protocol address space. For Ethernet hardware, this is from the set of type fields ether_typ$<protocol>.
|
||||||
|
uint8_t hln; // byte length of each hardware address
|
||||||
|
uint8_t pln; // byte length of each protocol address
|
||||||
|
uint16_t op; // opcode (ares_op$REQUEST | ares_op$REPLY)
|
||||||
|
uint8_t sha[ETH_ALEN]; // Hardware address of sender of this packet
|
||||||
|
uint8_t spa[4]; // Protocol address of sender of this packet
|
||||||
|
uint8_t tha[ETH_ALEN]; // Hardware address of sender of this packet
|
||||||
|
uint8_t tpa[4]; // Protocol address of sender of this packet
|
||||||
|
} __attribute__((packed)) arp_packet_t;
|
||||||
|
|
||||||
|
#define ARP_OP_REQUEST 0x01
|
||||||
|
#define ARP_OP_REPLY 0x02
|
||||||
|
|
||||||
|
int main(int argc, char** argv) {
|
||||||
|
// ifname hostMAC gatewayMAC targetMAC
|
||||||
|
struct linkinterface* link = link_parse(argv[1], argv[2], argv[3]);
|
||||||
|
|
||||||
|
uint8_t target[ETH_ALEN];
|
||||||
|
parse_mac(argv[4], target);
|
||||||
|
|
||||||
|
link_open(link);
|
||||||
|
|
||||||
// test receive
|
// test receive
|
||||||
while (1) {
|
while (1) {
|
||||||
uint8_t packet[1500];
|
uint8_t packet[MTU];
|
||||||
ssize_t rd = recv(raw, packet, 1500, 0);
|
ssize_t rd = recv(link->fd, packet, MTU, 0);
|
||||||
printf("%lu\n", rd);
|
|
||||||
|
struct ether_header *ether = (struct ether_header *)&packet[0];
|
||||||
|
print_mac(ether->ether_shost);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
link_free(link);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
Loading…
Add table
Reference in a new issue