程序的源码
头文件2 }: X: d7 G3 v; J& `# a
/*myarp.h used by myarp.c */+ ^+ I" J+ u* ^' t% Y
#ifndef _MYARP_H2 J0 w/ j# @! D' @5 \* Q1 x3 d
#define _MYARP_H
" Z" F0 g3 F1 l: Q#include <stdio.h>: n b% S! h: n a4 d7 g* i
#include <string.h>
1 W c6 ]2 b+ J+ l#include <sys/types.h>
( J! W4 I4 U* S' @* Z#include <netdb.h>
9 v: V+ q4 p ~0 {1 f#include <arpa/inet.h>( f& J6 f4 j' j- x: M* P- R9 Q
#include <netinet/in.h>
, c6 } f) l l5 c#include <net/if_arp.h>
% n4 |" r" }- j) x' S# v# z#include <signal.h>, G; k( H8 }% q
#include <sys/socket.h>6 g$ Q# X: x3 @, N; v
#include <sys/ioctl.h>+ K6 u% D7 s. N* |9 T, z0 o
#include <net/if.h>: d: N$ j' a4 U2 m, P
#include <net/ethernet.h>1 B8 D* N# R& ~7 C
#include <netinet/ip.h>) t" K. v7 z8 v
#define INTERFACE "eth0"
) }/ s8 ~- i9 q: S6 c4 @8 m#define MAX_WAIT_TIME 5
/ U3 [% b1 h) s# p" D#define PACKET_SIZE 40964 a. u0 x# |1 |6 w1 P
struct myarphdr
' X4 v, G* O6 q% g, ^, \{ unsigned char ether_dhost[ETH_ALEN];
& @; [% _8 j8 _/ \7 c% Aunsigned char ether_shost[ETH_ALEN];
8 |- Y2 y+ d! \7 R" Y$ C: v' s1 J+ Gunsigned short ether_type;
?' ~0 i# O) n* w" e4 J* ]unsigned short ar_hrd;
5 Z3 ~$ P% C3 ?' N Aunsigned short ar_pro;
0 L1 Z0 c4 [6 I4 [ S, Munsigned char ar_hln;
3 J( O5 n+ a0 L, Uunsigned char ar_pln;
# V8 \1 P( ]+ bunsigned char ar_op;
3 j# d6 e3 x2 n }+ F$ }unsigned char ar_sha[ETH_ALEN];
- w0 Q: a/ M- Ounsigned char ar_sip[4];( B: d& v; x& l9 y# b
unsigned char ar_tha[ETH_ALEN];9 S: ?+ F9 T6 Q- t+ V3 ^8 p
unsigned char ar_tip[4]; L9 u- S2 X; k# x0 F* J+ K+ [
unsigned char padding[18];: `" J$ O3 ^( P5 O. V
};
: l! C# f- Q4 _" c. {void onTerm();
/ @, X4 M/ U; u+ A1 a5 @" O#endif
+ T! ]! _0 e3 f/ l. b# \1 a/ ~ - h5 T1 q# z) `" @1 s
---------------------------------------# v8 S. q4 t% ^% u
主程序: A8 W, d0 U5 j6 O5 I$ x- d
#include "myarp.h"
0 c- ^& h+ ^" e T; \2 }! Q) o5 M8 ^
1 D' D4 w; n* p0 |9 c3 f
struct myarppack) k A0 v/ @& i7 P
{
- F0 I) H; }7 J% p4 D struct ether_header eth_hdr;
% |- h4 ]1 S9 [- c# a struct myarphdr arp_hdr;. S5 }! J' G5 a3 v9 ~
};. ^8 g+ v3 j+ w8 T
int sockfd;
* ~0 I0 X; v, {7 c. p J6 \void onTerm()
9 U# a# Q; y/ I{
- A: W: Q1 m( ?" C! V7 B printf("Time out.\n");0 B3 A9 P* N* _- Z5 n
close(sockfd);
( n$ j8 ~1 v) Y) {/ M! X exit(1);9 `- n3 q* g, n
}# E! A2 l; S _1 l6 \
void print_mac(unsigned char *mac)
; g# E$ w( |. I5 s{$ b1 ]; O" x! V+ q
printf(" %02x:%02x:%02x:%02x:%02x:%02x\n",\
3 X) c+ Y. m& M4 t; R *mac, *(mac+1), *(mac+2), *(mac+3), *(mac+4), *(mac+5));
& D5 z; P, e N2 ^# A}
4 d8 }9 g: c8 R9 o1 j% t3 ~* hint main(int argc, char *argv[])' z, @: o. s& `& _
{
" E8 Q" H7 r; A# J* Q+ y. m+ R int n;% x0 ?( ]0 J' ^; a ^
char interface[16]; //"eth0"9 p+ N' g9 ~' ^. I! _
char packet[PACKET_SIZE];
) Q- B S( R! j struct in_addr srchost, dstaddr;0 ?- I+ ^: i4 g
struct ifreq ifr;
* M# R" Q% X3 \* ~% ]7 X struct sockaddr_in *sin_ptr;
' e% ~# U" A8 P- L6 Y1 m unsigned char *ptr;* p1 m- y* ]- l% D6 Q
struct myarppack *arp;9 [+ R5 p! d) d$ x0 r
struct sockaddr from, to;
: j/ _2 k; y: d# B* ?! N8 Z: G if (argc < 2) {' Z n/ D& W) x' u
printf("Usage: %s IP\n", argv[0]);0 Q+ z/ i! t. ~8 F4 z+ P x9 a$ r s* x
exit(1);
5 s/ h6 x9 c, n ]) b% b8 R }
- e6 c# f* x6 U, K strcpy(interface, INTERFACE);2 n. g2 u# g8 a* l+ F# g
dstaddr.s_addr = inet_addr(argv[1]);) v4 `- ?5 [2 r, \% V3 x2 \) H
//create socket, only support arp protocol
7 w7 I0 [0 D" x* y& J. Q* Z if ((sockfd = socket(AF_INET, SOCK_PACKET, htons(ETH_P_ARP))) < 0) {+ V1 r. G) q0 k0 y) ?; c
perror("Create arp socket errr");
/ Q0 ~" f; R! S* ~, q exit(-1);( v) n0 [1 t, l; n2 p
}% H$ k9 c7 y) z% ]& w1 x
//get local IP& \3 o( E; ?+ |4 E
strcpy(ifr.ifr_name, interface);
! t M. l* ]/ t! u% i+ ^ ifr.ifr_addr.sa_family = AF_INET;5 h x8 _9 L# {8 b
if (ioctl(sockfd, SIOCGIFADDR, &ifr) < 0) {
0 T% R* W$ f9 f+ }2 T& u perror("ioctl SIOCGIFADDR error");
5 f( u$ |8 ?, Y: w5 _& U exit(-1);
& F- u) X& R9 ? }
9 L8 E% {+ k6 o" Q sin_ptr = (struct sockaddr_in *)(&(ifr.ifr_addr));4 B) ~# J& H; q; P
srchost = sin_ptr->sin_addr;7 A, Y1 E. w$ X" f- O2 z" I
//get local MAC
: b+ s: c2 |8 _: C1 R' ~( T if (ioctl(sockfd, SIOCGIFHWADDR, &ifr) < 0) {
+ Y) F# B' O/ b) r+ P/ K0 q4 z perror("ioctl SIOCGIFHWADDR error");
$ N0 J: z/ L# z1 \ exit(-1);; e+ r2 t: h, B) x
}. k) y. Y; G3 D1 v
ptr = (char *)(&(ifr.ifr_ifru.ifru_hwaddr.sa_data[0]));
/ B5 L; N9 O& h" M ^; U( E printf("Request machine: %s --->", inet_ntoa(srchost));
. K- w" V, D3 j print_mac(ptr); r3 b, P: o$ P& H4 p0 ?( V
arp = (struct myarppack *)packet;
! [% @/ O/ L. j; V //feed ethernet head and arp head
+ f; J4 c) `- p* ? Z6 H: c memset(arp->eth_hdr.ether_dhost, 0xff, 6);! U# w+ P5 d2 D) h: E2 e0 w; t
bcopy(ptr, arp->eth_hdr.ether_shost, 6);/ @! L8 \7 k A3 ^" a
arp->eth_hdr.ether_type = htons(ETHERTYPE_ARP);( O) S: K. y7 q" w; a
arp->arp_hdr.ar_hrd = htons(ARPHRD_ETHER);* G8 Z! W' t. ~" k1 b3 P
arp->arp_hdr.ar_pro = htons(ETHERTYPE_IP);7 }& u) m ~* A3 m. g% P! f
arp->arp_hdr.ar_hln = 6;
: C, m& h( K- [* S% V* e arp->arp_hdr.ar_pln = 4;
. B% t# `$ ~$ _4 g: N arp->arp_hdr.ar_op = htons(ARPOP_REQUEST);
* {$ n" _9 Z- c bcopy(ptr, arp->arp_hdr.ar_sha, 6);: X6 ?4 a2 o3 p, f P. ]
bcopy(&srchost, arp->arp_hdr.ar_sip, 4);
' a2 |- z8 m) y bzero(arp->arp_hdr.ar_tha, 6);+ {# N/ h9 Y0 Y* X7 h! S$ t
bcopy(&dstaddr, arp->arp_hdr.ar_tip, 4);! `; T; T+ }: ?7 C: a' h. {$ e: a
bzero(arp->arp_hdr.padding, 18);! [; t. ]; m$ I* u# e& S( Z
//send arp request+ f& E( O# F$ ~' G- I b* ?4 @! C
strcpy(to.sa_data, interface);
4 f& c0 Q" [/ S4 x" I3 S if ((n = sendto(sockfd, packet, sizeof(struct myarppack), 0, &to, sizeof(to))) < 0) {1 I9 u7 G1 y! ^+ I! j# R
perror("send arp request error");; b* k8 w K6 k' f6 S4 ? x
exit(-1);
?$ H/ s# }5 d9 I }! x7 Y) f+ B* G$ x5 }
//receive# e( |" N) z/ S5 l
strcpy(from.sa_data, interface);
: u/ O- C* [6 r2 v3 l1 h signal(SIGALRM, onTerm);
; o2 @' e( Q% }, }8 f while(2) {
9 s& v' L" |% V# [ alarm(MAX_WAIT_TIME);9 g# ]7 d" g* U- I' W4 _0 p
if ((n = recvfrom(sockfd, packet, PACKET_SIZE, 0, &from, &n)) >0) {/ {4 l1 T& y% Z# q. P L& z- ^# `
//only show replay which is from request ip
! a/ V1 I0 |1 U5 c5 X if (arp->arp_hdr.ar_op == htons(ARPOP_REPLY) ||! C( T: X9 d9 N" s$ M
!memcmp(arp->arp_hdr.ar_sip, &dstaddr, 4)) {
# l. \0 i$ d: j7 M3 Q* x/ ] printf("Reply machine: %s --->",\. G* @( R+ t+ {3 o
inet_ntoa(*((struct in_addr *)&(arp->arp_hdr.ar_sip[0]))));
6 U5 h& y: `; o- O- E2 n- p print_mac((unsigned char *)&(arp->arp_hdr.ar_sha));
+ C3 g6 q' L/ @" Y: C" d/ Q }
6 Y" W4 b3 S+ d break;7 x0 M& [0 d+ f. S: T
}
( X7 B4 l) I# }) R$ f }- C$ _5 p8 @' l1 i2 P
return 0;' O% D2 H$ O. M& J$ j6 c( O/ w
}