您的位置:首页 > 运维架构 > Linux

raw socket 编程资料(linux环境)

2013-03-01 14:02 225 查看
#include <stdio.h>
#include <unistd.h>
#include <sys/socket.h>
#include <sys/types.h>
#include <linux/if_ether.h>
#include <arpa/inet.h>

//定义常量

#define EPT_IP   0x0800    /* type: IP */
#define EPT_ARP   0x0806    /* type: ARP */
#define EPT_RARP 0x8035    /* type: RARP */
#define ARP_HARDWARE 0x0001    /* Dummy type for 802.3 frames */
#define ARP_REQUEST 0x0001    /* ARP request */
#define ARP_REPLY 0x0002    /* ARP reply */

//定义以太网首部
typedef struct ehhdr
{
unsigned char eh_dst[6];   /* destination ethernet addrress */
unsigned char eh_src[6];   /* source ethernet addresss */
unsigned short eh_type;   /* ethernet pachet type */
}EHHDR, *PEHHDR;

//定义以太网arp字段
typedef struct arphdr
{
//arp首部
unsigned short arp_hrd;    /* format of hardware address */
unsigned short arp_pro;    /* format of protocol address */
unsigned char arp_hln;    /* length of hardware address */
unsigned char arp_pln;    /* length of protocol address */
unsigned short arp_op;     /* ARP/RARP operation */

unsigned char arp_sha[6];    /* sender hardware address */
unsigned long arp_spa;    /* sender protocol address */
unsigned char arp_tha[6];    /* target hardware address */
unsigned long arp_tpa;    /* target protocol address */
}ARPHDR, *PARPHDR;

//定义整个arp报文包,总长度42字节
typedef struct arpPacket
{
EHHDR ehhdr;
ARPHDR arphdr;
} ARPPACKET, *PARPPACKET;

typedef struct _iphdr //定义IP首部
{
unsigned char h_verlen; //4位首部长度+4位IP版本号
unsigned char tos; //8位服务类型TOS
unsigned short total_len; //16位总长度(字节)
unsigned short ident; //16位标识
unsigned short frag_and_flags; //3位标志位
unsigned char ttl; //8位生存时间 TTL
unsigned char proto; //8位协议 (TCP, UDP 或其他)
unsigned short checksum; //16位IP首部校验和
unsigned int sourceIP; //32位源IP地址
unsigned int destIP; //32位目的IP地址
}IP_HEADER;

typedef struct _udphdr //定义UDP首部
{
unsigned short uh_sport;    //16位源端口
unsigned short uh_dport;    //16位目的端口
unsigned short uh_len;//16位UDP包长度
unsigned short uh_sum;//16位校验和
}UDP_HEADER;

typedef struct _tcphdr //定义TCP首部
{
unsigned short th_sport; //16位源端口
unsigned short th_dport; //16位目的端口
unsigned int th_seq; //32位序列号
unsigned int th_ack; //32位确认号
unsigned char th_lenres;//4位首部长度/6位保留字
unsigned char th_flag; //6位标志位
unsigned short th_win; //16位窗口大小
unsigned short th_sum; //16位校验和
unsigned short th_urp; //16位紧急数据偏移量
}TCP_HEADER;

typedef struct _icmphdr {
unsigned char  icmp_type; // 类型
unsigned char  icmp_code; // 代码
unsigned short icmp_cksum; //校验和
unsigned short icmp_id;
unsigned short icmp_seq;
// This is not the std header, but we reserve space for time
unsigned short icmp_timestamp;
}ICMP_HEADER;
void analyseIP(IP_HEADER *ip)
{
unsigned char* p = (unsigned char*)&ip->sourceIP;
if(ip->proto == IPPROTO_TCP)
printf("Source IP: %u.%u.%u.%u   ",p[0],p[1],p[2],p[3]);
p = (unsigned char*)&ip->destIP;
if(ip->proto == IPPROTO_TCP)
printf("Destination IP: %u.%u.%u.%u\n",p[0],p[1],p[2],p[3]);

}

void analyseTCP(TCP_HEADER *tcp)
{
printf("TCP -----\n");
printf("Source port: %u\n", ntohs(tcp->th_sport));
printf("Dest port: %u\n", ntohs(tcp->th_dport));
}

void analyseUDP(UDP_HEADER *udp)
{
//printf("UDP -----\n");
//printf("Source port: %u\n", ntohs(udp->uh_sport));
//printf("Dest port: %u\n", ntohs(udp->uh_dport));
}

void analyseICMP(ICMP_HEADER *icmp)
{
//printf("ICMP -----\n");
//printf("type: %u\n", icmp->icmp_type);
//printf("sub code: %u\n", icmp->icmp_code);
}

class rawsocket
{
public:
int Init()
{
if((sock=socket(PF_PACKET,SOCK_RAW,htons(ETH_P_ALL)))==-1)return 0;
return 1;
}
int Recv(char *buf,int maxlen)
{
return recvfrom(sock,buf,maxlen,0,NULL,NULL);
}
private:
int sock;
};

#include <string>
using namespace std;

char toch(unsigned char ch)
{
if(ch<10)return ch+'0';
else return ch-10+'a';
}
string mactostr(unsigned char *mac)
{
int i;
string str="";
for(i=0;i<6;i++)
{
str+=toch((mac[i]&0xf0)>>4);
str+=toch((mac[i]&0x0f));
if(i<5)str+=':';
}
return str;
}

char Buf[2000],*buf;

#include<time.h>
int main()
{
int L;
int perminute,persecond,tempmin,tempsec;
time_t second,minute,now;
unsigned short *iptype;
IP_HEADER *ip;
rawsocket sniffer;
if(sniffer.Init())
{
second=minute=time(NULL);
tempmin=tempsec=0;
persecond=perminute=0;
while(1)
{
L=sniffer.Recv(Buf,1518);Buf[L-4]=0;
tempsec+=L;
tempmin+=L;
PEHHDR Pehhdr=(PEHHDR)Buf;
if((now=time(NULL))>second)
{
second=now;
persecond=tempsec;
tempsec=0;
if(now-60>=minute)
{
perminute=tempmin;
minute=now;
tempmin=0;
}
printf("流量每秒%d字节,每分钟%d字节\n",persecond,perminute);
}
continue;
buf=Buf+14;
ip = ( IP_HEADER *)(buf);
if(ip->proto == IPPROTO_TCP)
printf("\n\n\n%s==>%s::%x\n\n",mactostr(Pehhdr->eh_src).c_str(),mactostr(Pehhdr->eh_dst).c_str(),Pehhdr->eh_type);
analyseIP(ip);
int iplen=(ip->h_verlen&0x0f)*4;
if (ip->proto == IPPROTO_TCP)
{
TCP_HEADER *tcp = (TCP_HEADER *)(buf+iplen);
analyseTCP(tcp);
int tcpheaderlen=(tcp->th_lenres&0xf0)>>2;
printf("%s\n\n",buf+iplen+tcpheaderlen);
}
else if (ip->proto == IPPROTO_UDP)
{
UDP_HEADER *udp = (UDP_HEADER *)(buf + iplen);
analyseUDP(udp);
}
else if (ip->proto == IPPROTO_ICMP)
{
ICMP_HEADER *icmp = (ICMP_HEADER *)(buf + iplen);
analyseICMP(icmp);
}
else if (ip->proto == IPPROTO_IGMP)
{
//printf("IGMP----\n");
}
else
{
//printf("other protocol! code:%d\n",ip->proto);
}
}
}
else printf("init failed\n");
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: