日期:2014-05-16  浏览次数:20736 次

Linux抓包程序

#include <stdio.h>
#include <stdlib.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <netinet/ip.h>
#include <string.h>
#include <netdb.h>
#include <netinet/tcp.h>
#include <netinet/udp.h>
#include <stdlib.h>
#include <unistd.h>
#include <signal.h>
#include <net/if.h>
#include <sys/ioctl.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <linux/if_ether.h>
#include <net/ethernet.h>
void die(char *why, int n)
{
    perror(why);
    exit(n);
}
int do_promisc(char *nif, int sock )
{
    struct ifreq ifr;
    strncpy(ifr.ifr_name, nif,strlen(nif)+1);
    if((ioctl(sock, SIOCGIFFLAGS, &ifr) == -1)) //获得flag
    {
        die("ioctl", 2);
    }
    ifr.ifr_flags |= IFF_PROMISC; //重置flag标志
    if(ioctl(sock, SIOCSIFFLAGS, &ifr) == -1 ) //改变模式
    {
        die("ioctl", 3);
    }
    return 0;
}
//修改网卡成PROMISC(混杂)模式
/*   =============================================================================================================下面是实现捕获和分析UDP协议数据包的函数定义  
=============================================================================================================*/   
void udp_protocol_packet_callback( u_char *packet_content)   
{   
    struct udphdr *udp_protocol;   
    // UDP协议数据变量   
    u_short source_port;   
    // 源端口号 
    u_short destination_port;   
    // 目的端口号    
    udp_protocol = (struct udphdr*)(packet_content + 14+20);   
    // 获得UDP协议数据内容 
    source_port = ntohs(udp_protocol->source);   
    // 获得源端口号 
    destination_port = ntohs(udp_protocol->dest);   
    // 获得目的端口号  
    printf("----------  UDP Protocol  (Transport  Layer)  ----------\n");   
    printf("Source port:%d\n", source_port);   
    printf("Destination port:%d\n", destination_port);   
    switch (destination_port)   
    //根据端口号判断应用层协议类型   
    {   
    case 138:   
        printf("NETBIOS Datagram Service\n");   
        break;   
        // 端口号为138,表示上层协议为NETBIOS 数据报服务    
    case 137:   
        printf("NETBIOS Name Service\n");   
        break;   
        // 端口号为137,表示上层协议为NETBIOS 名字服务    
    case 139:   
        printf("NETBIOS session service\n");   
        break;   
        // 端口号为139,表示上层协议为NETBIOS 会话服务    
    case 53:   
        printf("name-domain server \n");   
        break;   
        // 端口号为53,表示上层协议为域名服务 
    case 4000:   
        printf("QQ server \n");   
        break; 
    case 1863:   
        printf("MSN server \n");   
        break; 
    case 9001:   
        printf("OTHERS \n");   
        break;     
    default:   
        printf("NOT WELL-KNOWN PROTOCOL.\n");
        break; //其他没有分析 
    }   
}    /*   =============================================================================================================下面是实现捕获和分析TCP协议数据包的函数定义  
=============================================================================================================
*/   
void tcp_protocol_packet_callback( u_char *packet_content)   
{   
    struct tcphdr *tcp_protocol;   
    // TCP协议数据变量   
    u_short source_port;   
    // 源端口号 
    u_short destination_port;   
    // 目的端口号    
    tcp_protocol = (struct tcphdr*)(packet_content + 14+20);   
    // 获得UDP协议数据内容 
    source_port = ntohs(tcp_protocol->source);   
    // 获得源端口号 
    destination_port = ntohs(tcp_protocol->dest);   
    // 获得目的端口号  
    printf("----------  TCP Protocol  (Transport  Layer)  ----------\n");   
    printf("Source port:%d\n", source_port);   
    printf("Destination port:%d\n", destination_port);   
    switch (destination_port)   
    //根据端口号判断应用层协议类型   
    {   
    case 7:
        printf("ECHO server \n");
        break;
    case 21:
        printf("FTP server \n");
        break;
    case 23:
        printf("TELNET server \n");
        break;
    case 25:
        printf("SMTP server \n");
        break;
    case 53:
        printf("DNS s