c语言编写以太网mac帧,C语言中利用AF_PACKET 原始套接字发送一个任意以太网帧 (二)...

arpsend_dgram.c

点击(此处)折叠或打开

#include

#include

#include

#include

#include

#include

#include

#include

#include

#include

#include

#include

#include

#include

#include

#include

#define BUFLEN 42

/*

************************eth structure**************************************

struct ethhdr {

unsigned char h_dest[ETH_ALEN];

unsigned char h_source[ETH_ALEN];

__be16 h_proto;

} __attribute__((packed));

struct ether_header

{

u_int8_t ether_dhost[ETH_ALEN]; // destination eth addr

u_int8_t ether_shost[ETH_ALEN]; // source ether addr

u_int16_t ether_type; // packet type ID field

} __attribute__ ((__packed__));

**************************arp structrure (if_arp.h)**************************

struct arphdr

{

__be16 ar_hrd; //format of hardware address

__be16 ar_pro; // format of protocol address *\/

unsigned char ar_hln; // length of hardware address *\/

unsigned char ar_pln; // length of protocol address *\/

__be16 ar_op; // ARP opcode (command) *\/

#if 0

// Ethernet looks like this : This bit is variable sized however...*\/

unsigned char ar_sha[ETH_ALEN]; // sender hardware address *\/

unsigned char ar_sip[4]; // sender IP address *\/

unsigned char ar_tha[ETH_ALEN]; // target hardware address *\/

unsigned char ar_tip[4]; // target IP address *\/

#endif

};

*************************ether_arp structure********************************

__BEGIN_DECLS

//

* Ethernet Address Resolution Protocol.

*

* See RFC 826 for protocol description. Structure below is adapted

* to resolving internet addresses. Field names used correspond to

* RFC 826.

*\/

struct ether_arp {

struct arphdr ea_hdr; // fixed-size header *\/

u_int8_t arp_sha[ETH_ALEN]; // sender hardware address *\/

u_int8_t arp_spa[4]; // sender protocol address *\/

u_int8_t arp_tha[ETH_ALEN]; // target hardware address *\/

u_int8_t arp_tpa[4]; // target protocol address *\/

};

#define arp_hrd ea_hdr.ar_hrd

#define arp_pro ea_hdr.ar_pro

#define arp_hln ea_hdr.ar_hln

#define arp_pln ea_hdr.ar_pln

#define arp_op ea_hdr.ar_op

**************************ifreq structure************************************

struct ifreq

{

#define IFHWADDRLEN 6

union

{

char ifrn_name[IFNAMSIZ];

} ifr_ifrn;

union {

struct sockaddr ifru_addr;

struct sockaddr ifru_dstaddr;

struct sockaddr ifru_broadaddr;

struct sockaddr ifru_netmask;

struct sockaddr ifru_hwaddr;

short ifru_flags;

int ifru_ivalue;

int ifru_mtu;

struct ifmap ifru_map;

char ifru_slave[IFNAMSIZ];

char ifru_newname[IFNAMSIZ];

void __user * ifru_data;

struct if_settings ifru_settings;

} ifr_ifru;

};

#define ifr_name ifr_ifrn.ifrn_name

#define ifr_hwaddr ifr_ifru.ifru_hwaddr

#define ifr_addr ifr_ifru.ifru_addr

#define ifr_dstaddr ifr_ifru.ifru_dstaddr

#define ifr_broadaddr ifr_ifru.ifru_broadaddr

#define ifr_netmask ifr_ifru.ifru_netmask

#define ifr_flags ifr_ifru.ifru_flags

#define ifr_metric ifr_ifru.ifru_ivalue

#define ifr_mtu ifr_ifru.ifru_mtu

#define ifr_map ifr_ifru.ifru_map

#define ifr_slave ifr_ifru.ifru_slave

#define ifr_data ifr_ifru.ifru_data

#define ifr_ifindex ifr_ifru.ifru_ivalue

#define ifr_bandwidth ifr_ifru.ifru_ivalue

#define ifr_qlen ifr_ifru.ifru_ivalue

#define ifr_newname ifr_ifru.ifru_newname

#define ifr_settings ifr_ifru.ifru_settings

*/

int main(int argc, char *argv[])

{

int skfd,n;

struct ether_arp *arp;

struct ifreq ifr;

unsigned char buff[BUFLEN];

unsigned char src_mac[ETH_ALEN];

struct sockaddr_ll toaddr;

struct in_addr targetIP,srcIP;

if(argc != 3) {

printf("Usage: %s outinterface dstIP\n",argv[0]);

exit(1);

}

skfd = socket(AF_PACKET,SOCK_DGRAM,htons(ETH_P_ARP));

if(skfd < 0 ) {

perror("Create Error");

exit(1);

}

bzero(&toaddr,sizeof(toaddr));

bzero(&ifr,sizeof(ifr));

strcpy(ifr.ifr_name,argv[1]);

if(-1 == ioctl(skfd,SIOCGIFINDEX,&ifr)) {

perror("get interface index error");

exit(1);

}

toaddr.sll_ifindex = ifr.ifr_ifindex;

printf("interface Index:%d\n",ifr.ifr_ifindex);

if(-1 == ioctl(skfd,SIOCGIFHWADDR,&ifr)) {

perror("get dev mac addr error");

exit(1);

}

memcpy(src_mac,ifr.ifr_hwaddr.sa_data,ETH_ALEN);

printf("Src mac is %02x:%02x:%02x:%02x:%02x:%02x\n",src_mac[0],src_mac[1],

src_mac[2],src_mac[3],src_mac[4],

src_mac[5]);

if(-1 == ioctl(skfd,SIOCGIFADDR,&ifr)) {

perror("get ip addr");

exit(1);

}

srcIP.s_addr = ((struct sockaddr_in*)&(ifr.ifr_addr))->sin_addr.s_addr;

printf("IP addr:%s\n",inet_ntoa(((struct sockaddr_in*)&(ifr.ifr_addr))->sin_addr));

/*construct arp header*/

arp = (struct ether_arp*)(buff);

arp->arp_hrd = htons(ARPHRD_ETHER);

arp->arp_pro = htons(ETHERTYPE_IP);

arp->arp_hln = ETH_ALEN;

arp->arp_pln = 4;

arp->arp_op = htons(ARPOP_REQUEST);

memcpy(arp->arp_sha,src_mac,ETH_ALEN);

memcpy(arp->arp_spa,&srcIP,sizeof(srcIP));

memset(arp->arp_tha,0,ETH_ALEN);

inet_pton(AF_INET,argv[2],&targetIP);

memcpy(arp->arp_tpa,&targetIP,4);

//toaddr.sll_family = PF_PACKET;

//toaddr.sll_halen = ETHER_ADDR_LEN;

toaddr.sll_protocol = htons(ETH_P_ARP);

n = sendto(skfd,buff,BUFLEN,0,(struct sockaddr*)&toaddr,sizeof(toaddr));

printf("send arp request %d bytes\n",n);

close(skfd);

return 0;

}

编译&运行:

抓包结果:

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值