Saturday, March 13, 2010

Kid Ping Utility

/*****************************************************
* Author : Chaitanya bhargav M
* Date : 13 March 2010
* License : Free, but unreliable
* Description : Simpler ping without any options,
created just for fun!
*****************************************************/

#include<stdio.h>
#include<unistd.h>
#include<netinet/in.h>
#include<sys/socket.h>
#include<sys/types.h>
#include<sys/time.h>
#include<sys/param.h>
#include<linux/if_ether.h>
#include<linux/ip.h>
#include<linux/icmp.h>
#include<linux/if_packet.h>
#include<net/if.h>
#include<string.h>
#include<stdlib.h>
#include<signal.h>

int sock_fd,transmitted = 0,received = 0;
float t_sum = 0;

void sig_handler(int sigNum)
{
printf("\n=======================ping stats======================");
printf("\n%d packets transmitted, %d received, avg.delay = %.3fms\n",transmitted,received,(t_sum/received));
printf("Packet loss = %d%%,",((transmitted-received)/(transmitted))*100);
printf(" Thanks for using! -Chaitu\n");
close(sock_fd);
exit(127);
}

#pragma pack(1)
struct _icmp_{
struct icmphdr icmp;
unsigned char data[22];
}packet;

unsigned short check_sum(unsigned char *buf, int len);
char *ip_ntoa(unsigned int ipAddr)
{
char *ip = (char *)malloc(16);
sprintf(ip,"%d.%d.%d.%d",(ipAddr&0xff000000)>>24,
(ipAddr&0x00ff0000)>>16,
(ipAddr&0x0000ff00)>>8,
(ipAddr&0x000000ff));
return ip;
}

struct timezone tz;
int main(int argc, char *argv[])
{
int retVal,sin_size,data_len;
unsigned short seq = 0x0000;
struct iphdr *ip;
struct icmphdr *icmp;
struct sockaddr_in whereto,sin ;
struct timeval *tp = (struct timeval *)&packet.data[0];
struct timeval *tp1;
struct timeval tv;
float delay;

if(argc != 2)
{
printf("Usage:\n ./pinger \n");
exit(127);
}

whereto.sin_family = AF_INET;
whereto.sin_addr.s_addr = inet_addr(argv[1]);
memset(&packet.data[0],0,22);
unsigned char buf[1518];

sock_fd = socket(AF_INET, SOCK_RAW, IPPROTO_ICMP);
if(sock_fd < 0)
{
perror("socket");
exit(127);
}

signal(SIGINT,sig_handler);

while(1)
{
/* Send the packet */
gettimeofday(tp, &tz);
packet.icmp.type = ICMP_ECHO;
packet.icmp.code = 0;
packet.icmp.checksum = 0;
packet.icmp.un.echo.id = htons(0xc000);
packet.icmp.un.echo.sequence = htons(++seq);
packet.icmp.checksum = htons(check_sum((unsigned char *)&packet.icmp.type,30));
retVal = sendto(sock_fd, (unsigned char *)&packet, 30, 0,(struct sockaddr *) &whereto, sizeof(struct sockaddr));
if(retVal < 0)
{
perror("send to");
close(sock_fd);
exit(127);
}
transmitted++;

/* Receive Packet */
data_len = recvfrom(sock_fd, buf, 1518, 0 ,(struct sockaddr *)&sin, &sin_size);
ip = (struct iphdr *)buf;
icmp = (struct icmphdr *)(buf + ((ip->ihl) << 2));
if(icmp->type == ICMP_ECHOREPLY)
{
if(icmp->un.echo.id == htons(0xc000))
{
if(icmp->un.echo.sequence == htons(seq))
{
gettimeofday(&tv, &tz);
delay = (tv.tv_sec) - (tp->tv_sec) + (tv.tv_usec) - (tp->tv_usec);
printf("64 bytes from %s icmp_seq=%d ttl=%d delay=%.3fms\n",ip_ntoa(ntohl(ip->saddr)),seq,ip->ttl,(delay/1000));
received++;
t_sum += (delay/1000);
}
}
}
sleep(1);
}
return ;
}

unsigned short check_sum(unsigned char *buf, int len)
{
unsigned short len_16 = 0;
unsigned int len_32 = 0;
int i;

for(i =0; i < len; i+=2)
{
len_16 = (buf[i] << 8)&0xff00 | buf[i+1]&0xff;
len_32 += len_16;
}
if(len_32 >> 16)
{
len_32 = ((len_32>>16)&0xffff) + (len_32&0xffff);
}
if(len_32 >> 16)
{
len_32 = ((len_32>>16)&0xffff) + (len_32&0xffff);
}
len_32 = ~len_32;

return (len_32&0xffff);
}

Sunday, March 7, 2010

Kid Sniffer

/**************************************************************************
* Author : Chaitanya bhargav M
* date Created : 07 March 2010
* License : free, but unreliable
* ************************************************************************/
#include unistd.h
#include stdio.h
#include net/if.h
#include sys/socket.h
#include sys/types.h
#include sys/time.h
#include string.h
#include stdlib.h
#include linux/in.h
#include netinet/ether.h
#include linux/if_ether.h
#include linux/if_packet.h
#include linux/ip.h
#include linux/icmp.h
#include linux/udp.h
#include linux/tcp.h
#include signal.h
#include linux/if_vlan.h
#include linux/if_arp.h

/**************************
* Namesake signal Handler
**************************/
void signal_handle(int sigNum)
{
printf("Received the signal : %d",sigNum);
exit(128);
}

/*********************************************************
* Converts ipAddress in integer to dotted decimal format
*********************************************************/
char *ip_ntoa(unsigned int ip)
{
char *str = (char *)malloc(16*sizeof(char));
sprintf(str,"%d.%d.%d.%d",(ip&0xff000000)>>24,
(ip&0x00ff0000)>>16,
(ip&0x0000ff00)>>8,
(ip&0x000000ff));
return str;
}

/*****************************
* Process packets in Layer 3
*****************************/
void process_ip_packet(unsigned char *buf, int len)
{
struct iphdr *ip;
struct icmphdr *icmp;
struct udphdr *udp;
struct tcphdr *tcp;

//printf("Received a packet with size:%d\n",len);
ip = (struct iphdr *)(buf );
printf("ip_src:%s > ip_dst:%s,", ip_ntoa(ntohl(ip->saddr)),ip_ntoa(ntohl(ip->daddr)));
switch( ip->protocol)
{
case IPPROTO_ICMP:
icmp = (struct icmphdr *)(buf + (ip->ihl << 2));
if(icmp->type == ICMP_ECHO)
{
printf("ICMP Echo req \n");
}
else if(icmp->type == ICMP_ECHOREPLY)
{
printf("ICMP Echo reply \n");
}
else if(icmp->type == ICMP_DEST_UNREACH)
{
printf("ICMP Destination Unreachable\n");
}
break;
case IPPROTO_UDP:
udp = (struct udphdr *)(buf + (ip->ihl << 2));
printf("UDP, src: %d, dest: %d\n",ntohs(udp->source), ntohs(udp->dest));
break;
case IPPROTO_TCP:
tcp = (struct tcphdr *)(buf + (ip->ihl << 2));
printf("TCP, src: %d, dest: %d\n",ntohs(tcp->source), ntohs(tcp->dest));
break;
default:
printf("Unconcerned IP Protocol:0x%04x\n",ip->protocol);
break;
}
return ;
}

/********************************
* Process packets in Link Layer
********************************/
void process_frame(unsigned char *buffer, int len)
{
//printf("Received a packet with size:%d\n",len);
struct ethhdr *eth;
struct vlan_ethhdr *vlaneth;
struct iphdr *ip;
struct arp_hdr *arp;

eth = (struct ethhdr *) buffer;
printf("%02x:%02x:%02x:%02x:%02x:%02x > %02x:%02x:%02x:%02x:%02x:%02x,",eth->h_source[0],eth->h_source[1],
eth->h_source[2],eth->h_source[3],
eth->h_source[4],eth->h_source[5],
eth->h_dest[0],eth->h_dest[1],
eth->h_dest[2],eth->h_dest[3],
eth->h_dest[4],eth->h_dest[5]);
switch(ntohs(eth->h_proto))
{
case ETH_P_ARP:
arp = (struct arp_hdr *)(buffer + ETH_HLEN);
if(ntohs(arp->ar_op) == ARPOP_REQUEST)
{
printf("ARP Request for IP:%d.%d.%d.%d tell IP:%d.%d.%d.%d\n",arp->ar_tip[0],arp->ar_tip[1],arp->ar_tip[2],arp->ar_tip[3],
arp->ar_sip[0],arp->ar_sip[1],arp->ar_sip[2],arp->ar_sip[3]);
}
else if(ntohs(arp->ar_op) == ARPOP_REPLY)
{
printf("ARP Reply for IP:%d.%d.%d.%d is MAC:%02x:%02x:%02x:%02x:%02x:%02x\n",arp->ar_sip[0],arp->ar_sip[1],arp->ar_sip[2],arp->ar_sip[3],
arp->ar_sha[0],arp->ar_sha[1],arp->ar_sha[2],arp->ar_sha[3],arp->ar_sha[4],arp->ar_sha[5]); }
break;

case ETH_P_8021Q:
break;

case ETH_P_IP:
process_ip_packet( buffer+ETH_HLEN, len-ETH_HLEN);
break;

case ETH_P_IPV6:
printf("IPV6 packet\n");
break;

default:
printf("Some strange protocol:0x%04x\n",ntohs(eth->h_proto));
break;
}
return ;
}

/**************************************************
* Main Function: Accessing the packets from stack
**************************************************/
int main(int argc, char *argv[])
{
int fd,retVal = 0,sin_size,data_size;
unsigned char buffer[1522];
struct sockaddr_in sin;

fd = socket(PF_PACKET, SOCK_RAW,htons(ETH_P_ALL) );
if(fd == -1)
{
perror("Raw socket");
exit(127);
}

signal(SIGINT, signal_handle);
signal(SIGSEGV, signal_handle);
signal(SIGFPE, signal_handle);

sin_size = sizeof sin;
while(1)
{
data_size = recvfrom(fd, buffer, 1518, 0,(struct sockaddr *) &sin, &sin_size);
process_frame(buffer, data_size);
}

return 0;
}

//============= E O F =================