./c0de/c/pingreply.txt

0.
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
60.
61.
62.
63.
64.
65.
66.
67.
68.
69.
70.
71.
72.
73.
74.
75.
76.
77.
78.
79.
80.
81.
82.
83.
84.
85.
86.
87.
88.
89.
90.
91.
92.
93.
94.
95.
96.
97.
98.
99.
100.
101.
102.
103.
104.
105.
106.
107.
108.
109.
110.
111.
112.
113.
114.
115.
116.
117.
118.
119.
120.
121.
122.
123.
124.
125.
126.
127.
128.
129.
130.
131.
132.
133.
134.
135.
136.
137.
138.
139.
140.
141.
142.
143.
144.
145.
146.
147.
148.
149.
150.
151.
152.
153.
154.
155.
156.
157.
158.
159.
160.
161.
162.
163.
164.
165.
166.
167.
168.
169.
170.
171.
172.
173.
174.
175.
176.
177.
178.
179.
180.
181.
182.
183.
184.
185.
186.
187.
188.
189.
190.
191.
192.
193.
194.
195.
196.
197.
198.
199.
200.
201.
202.
203.
204.
205.
206.
/*
ping.c
 
pings a host and gives stats on interupt
only takes ip addresses
have to be setuid for raw socket
drops privs after getting socket
 
tgo - http://anomalous-security.org
*/
 
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <signal.h>
 
#include <sys/socket.h>
#include <sys/types.h>
 
#include <netinet/in.h>
#include <netinet/ip_icmp.h>
#include <netinet/ip.h>
 
#define DATALEN 56
#define PACKETSIZE 1500
 
int sent  = 0;
int received = 0;
 
struct icmp *icmp;
char packet[PACKETSIZE+1];
int sock;
char *host;
 
 
void die(char *reason){
   perror(reason);
   exit(1);
}
 
void usage(char *prog){
   printf("%s <ip address>\n",prog);
   exit(1);   
}
 
/* stolen - everyone does it */
in_cksum(addr, len)
u_short *addr;
int len;
{
   register int nleft = len;
   register u_short *w = addr;
   register int sum = 0;
 
   /*
    *  Our algorithm is simple, using a 32 bit accumulator (sum),
    *  we add sequential 16 bit words to it, and at the end, fold
    *  back all the carry bits from the top 16 bits into the lower
    *  16 bits.
    */
   while( nleft > 1 )  {
      sum += *w++;
      nleft -= 2;
   }
 
   /* mop up an odd byte, if necessary */
   if( nleft == 1 )
      sum += *(u_char *)w;
 
   /*
    * add back carry outs from top 16 bits to low 16 bits
    */
    while (sum>>16)
        sum = (sum & 0xffff) + (sum >> 16);     /* add hi 16 to low 16 */
 
   return ( (~sum) & 0xFFFF);
}
 
void send_request(){
 
   struct sockaddr    where;
   struct sockaddr_in *whereto;
   int total = DATALEN + 8;
   memset(packet,0x00,sizeof(packet));
 
   whereto = (struct sockaddr_in *)&where;
 
   whereto->sin_family = AF_INET;
   whereto->sin_addr.s_addr = inet_addr(host);
 
   /* fill icmp structure to ping host */
   icmp = (struct icmp *)packet;
   icmp->icmp_code = 0;
   icmp->icmp_type = ICMP_ECHO;
   icmp->icmp_seq = htons(sent);
   icmp->icmp_id = htons(0x029a + sent);
   memset(icmp->icmp_data,0x41,DATALEN);
   gettimeofday((struct timeval *) icmp->icmp_data,NULL);
 
        icmp->icmp_cksum = 0;
   icmp->icmp_cksum = in_cksum(icmp,total);
 
   if( sendto(sock,packet,total,0,&where,sizeof(struct sockaddr)) < 0)
      die("sendto");
   sent++;
 
}
 
void get_response(){
 
   memset(packet,0x00,sizeof(packet));
   read(sock,&packet,1500);
   int type;
   struct sockaddr_in source;
 
        struct ip *ip = (struct ip *) (packet);
   icmp = (struct icmp *)(packet + sizeof(struct ip));
 
   type = icmp->icmp_type;
 
   if (type == ICMP_ECHOREPLY){
 
      received++;
 
      memcpy(&source.sin_addr, (struct sockaddr_in *)&ip->ip_src , sizeof(source.sin_addr) );
 
      printf("reply from: %s, id %d, sequence %d, length %d, ttl %d, type %d\n"
         ,inet_ntoa(source.sin_addr.s_addr)
         ,htons(icmp->icmp_id)
         ,htons(icmp->icmp_seq)
         ,htons(ip->ip_len)
         ,(short)ip->ip_ttl
         ,type
      );
 
   }
   else if ( type != ICMP_ECHO )
      printf("Error code %d received - check /usr/include/netinet/ip_icmp.h for value\n",type);
 
 
}
 
void alarm_called(int signo){
 
   /* sends ping request then sets alarm to go off one second later ( send another ping ) */
   send_request();
   alarm(1);
}
 
void print_stats(){
 
   /* called on SIGINT, print stats and exits */
 
   if (sent > 0){
      printf(
         "\n\n--- Stats for: %s ---\n"
         "Sent: %d\n"
         "Received: %d\n"
         "Percent: %d% returned\n"
         "---------------------\n"
         ,inet_ntoa(inet_addr(host))
         ,sent
         ,received
         ,(received/sent)*100
      );
   }else
      printf("no packets sent yet\n");
 
   exit(0);
}
 
int get_sock(){
 
   /* set socket and drop privs after getting socket */
   int sock;
 
   if((sock = socket(AF_INET,SOCK_RAW,IPPROTO_ICMP)) < 0)
      die("socket");
 
   setuid(getuid());
 
   return sock;
}
 
int main(int argc,char *argv[]){
 
   if (argc < 2) usage(argv[0]);
 
   /* set socket and host */
   sock = get_sock();   
   host = argv[1];
 
   /* sigalarm does 1 second interval pings */
   if ( signal(SIGALRM,alarm_called)  < 0 )
      die("signal");
 
   /* on control+c ( interupt ) print stats and exit */
   if ( signal(SIGINT,print_stats) < 0 )
      die("signal");
 
   /* signal alarm for first packet */
   alarm(1);
 
   /* keep reading responses */
   while(1) get_response();
} 

Back