linux下用raw socket收发包实例

本文提供了一个在Linux环境下利用raw socket收发网络包的实例,包括创建socket、设置网络接口为混杂模式、获取硬件地址、发送和接收数据包的函数。示例代码展示了如何初始化网络接口、获取MAC地址并发送、接收自定义大小的数据包。
摘要由CSDN通过智能技术生成

http://nking.blog.sohu.com/141645994.html


http://blog.csdn.net/shanzhizi

#include <sys/types.h>       // socket
#include <sys/socket.h>      // socket
#include <sys/ioctl.h>       // ioctl
#include <net/if.h>          // ifreq 
#include <string.h>          // strcpy
#include <stdio.h>           // printf
#include <linux/if_packet.h> // sockaddr_ll




#define BOOL   unsigned char
#define U8     unsigned char
#define U16    unsigned short 
#define TRUE   1
#define FALSE  0




static int fd;
static unsigned char if_mac[6];
static int if_index;


U8  gBuf[2000] = {0};
U8  gTxBuf[2000];
U16 gLen=0;




BOOL InitEtherNetIf(void)
    {
    struct ifreq req;


 if ( (fd = socket(PF_PACKET, SOCK_RAW, htons(0x0003) ) ) < 0 )
  {                         
  printf( "failed to create raw socket!\n" );
  return FALSE;
  }


 strcpy( req.ifr_name, "eth0" );
 if ( ioctl( fd, SIOCGIFFLAGS, &req ) < 0 )
  {
  printf( "failed to do ioctl!" );
  return FALSE;
  }


 req.ifr_flags |= IFF_PROMISC;


 if ( ioctl( fd, SIOCSIFFLAGS, &req ) < 0 )
  {
  printf( "failed to set eth0 into promisc mode!" );
  return FALSE;
  }


 if ( ioctl( fd, SIOCGIFHWADDR, &req ) < 0 )
  {
  printf( "failed to get IF hw address!" );
  return FALSE;
  }


 memcpy( if_mac, req.ifr_hwaddr.sa_data, sizeof(if_mac) );


 if ( ioctl( fd, SIOCGIFINDEX, &req ) < 0 )
  {
  printf( "failed to get IF hw address!" );
  return FALSE;
  }


 if_index = req.ifr_ifindex;
 return TRUE;
    }


 


BOOL GetPacket(U8 *buf, U16 *len) 
    {
    int length = 0;
 
 length = recvfrom( fd, buf, 2000, 0, NULL, NULL );
 if ( length < 0 )
  {
  return 0;
  } 
 else
  {
  *len = length;
  return 1;
  }
    }


 


BOOL SendPacket(U8 *buf, U16 len)
     {
 struct sockaddr_ll link;
 link.sll_ifindex = if_index;
   
 memcpy( link.sll_addr, buf, link.sll_halen );


 if ( sendto( fd, buf, len, 0, (struct sockaddr *)&link, sizeof(link) ) < 0 )
  {
  printf( "failed to send to RAW socket!\r\n" );   
  return 0;
  }
 return 1;
 }


 


BOOL GetMacAddress(U8 *mac)
    {
    memcpy(mac, if_mac, sizeof(if_mac));
    return TRUE;
    }


 


void DispalyBuf(U8 *buf,U16 size)
    {
     int i;
     for(i=0;i<size;i++)
      {      
  if((0==i%16)&&(i>0)) printf("\n");
  printf("%02x ",buf[i]); 
      }
    printf("\n");
    }
    
    
    
int main(void)
    {
    BOOL ret;   


    for(ret =0;ret<64;ret++) gTxBuf[ret]=ret;


    if(InitEtherNetIf())
    {
  printf("send:\n");
  DispalyBuf(gTxBuf,64);
        SendPacket(gTxBuf,64);
  while(1)
     {
      if(GetPacket(gBuf,&gLen))   DispalyBuf(gBuf,gLen);
     } 
    }
    }

评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值