595 lines
20 KiB
C
595 lines
20 KiB
C
|
#include <stdio.h>
|
|||
|
#include <sys/socket.h>
|
|||
|
#include <netinet/ether.h>
|
|||
|
#include <unistd.h>
|
|||
|
#include <string.h>
|
|||
|
#include <sys/types.h>//recvfrom
|
|||
|
#include <netinet/ether.h>//ETH_P_ALL
|
|||
|
#include <arpa/inet.h>//inet_ntop
|
|||
|
#include <net/if.h>//ifreq
|
|||
|
#include <sys/ioctl.h>//ioctl
|
|||
|
#include <netpacket/packet.h>//sockaddr_ll
|
|||
|
#include <pthread.h>
|
|||
|
#include <stdlib.h>
|
|||
|
#include <sqlite3.h>
|
|||
|
|
|||
|
void show(void);//菜单函数
|
|||
|
void * my_fun(void * arg);//线程的回调函数
|
|||
|
|
|||
|
//全局变量定义,方便线程使用
|
|||
|
int sockfd; //套接字
|
|||
|
int ret; //调用数据库是的返回值
|
|||
|
char * errmsg;
|
|||
|
sqlite3 *db;
|
|||
|
char ** dbResult;
|
|||
|
int nrow;
|
|||
|
int ncolumn;
|
|||
|
|
|||
|
int main()
|
|||
|
{
|
|||
|
//创建套接字,原始套接字
|
|||
|
sockfd = socket(PF_PACKET,SOCK_RAW,htons(ETH_P_ALL));
|
|||
|
if(sockfd > 0)
|
|||
|
{
|
|||
|
printf("原始套接字创建成功:%d\n",sockfd);
|
|||
|
}
|
|||
|
//**************************************************************************************************************************************************
|
|||
|
//数据库的打开使用
|
|||
|
//**************************************************************************************************************************************************
|
|||
|
|
|||
|
|
|||
|
//打开数据库
|
|||
|
ret = sqlite3_open("ip.db",&db);
|
|||
|
//如果ret==SQLITE_OK 那么就是这一条语言成功执行了
|
|||
|
if(ret == SQLITE_OK)
|
|||
|
{
|
|||
|
printf("防火墙数据库打开成功!\n");
|
|||
|
}
|
|||
|
else
|
|||
|
{
|
|||
|
printf("数据库打开失败!\n");
|
|||
|
}
|
|||
|
ret = sqlite3_open("mac.db",&db);
|
|||
|
if(ret == SQLITE_OK)
|
|||
|
{
|
|||
|
printf("ARP缓存数据库打开成功!\n");
|
|||
|
}
|
|||
|
else
|
|||
|
{
|
|||
|
printf("数据库打开失败!\n");
|
|||
|
}
|
|||
|
//使用非回调办法增加一张数据表
|
|||
|
sqlite3_get_table(db,"create table persons (IP text primary key);",&dbResult,&nrow,&ncolumn,&errmsg);
|
|||
|
// arp缓存的数据库
|
|||
|
sqlite3_get_table(db,"create table person (ip text primary key,mac text);",&dbResult,&nrow,&ncolumn,&errmsg);
|
|||
|
|
|||
|
//使用回调方法去增加数据
|
|||
|
|
|||
|
char str[128]="";
|
|||
|
printf("防火墙中的IP有:\n");
|
|||
|
//想要添加,从这个地方就可以添加
|
|||
|
char get_ip[16]="192.168.7.5";
|
|||
|
sprintf(str,"insert into persons values('%s');",get_ip);
|
|||
|
sqlite3_get_table(db,str,&dbResult,&nrow,&ncolumn,&errmsg);
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
//使用非回调函数查询数据
|
|||
|
ret == sqlite3_get_table(db,"select * from persons;",&dbResult,&nrow,&ncolumn,&errmsg);
|
|||
|
if(ret==SQLITE_OK)
|
|||
|
{
|
|||
|
int i,j,index;
|
|||
|
index=ncolumn;
|
|||
|
for(i=0;i<nrow;i++)
|
|||
|
{
|
|||
|
|
|||
|
for(j=0;j<ncolumn;j++)
|
|||
|
{
|
|||
|
printf(" %s ",dbResult[index]);
|
|||
|
index++;
|
|||
|
}
|
|||
|
printf("\n");
|
|||
|
}
|
|||
|
sqlite3_free_table(dbResult);
|
|||
|
|
|||
|
}
|
|||
|
//选择标志位
|
|||
|
int chose = 0;
|
|||
|
show();//菜单展示
|
|||
|
int pthread_flag = 0;
|
|||
|
while(1)
|
|||
|
{
|
|||
|
printf("请输入您的选择:");
|
|||
|
scanf("%d",&chose);
|
|||
|
getchar();
|
|||
|
if(1 == chose)
|
|||
|
{
|
|||
|
char add_ip[32]="";
|
|||
|
printf("请输入添加的黑名单IP:格式如:192.168.1.1\n");
|
|||
|
fgets(add_ip,sizeof(add_ip),stdin);
|
|||
|
add_ip[strlen(add_ip)-1]='\0';
|
|||
|
//printf("获得到了:%s\n",add_ip);
|
|||
|
//格式校验
|
|||
|
int a=0,b=0,c=0,d=0;
|
|||
|
sscanf(add_ip,"%d.%d.%d.%d",&a,&b,&c,&d);
|
|||
|
if((a >= 0 && a <= 255) && (b >= 0 && b <= 255) && (c >= 0 && c <= 255) && (d >= 0 && d<= 255))
|
|||
|
{
|
|||
|
//写入数据库
|
|||
|
char sqlite3_ip[64]="";
|
|||
|
sprintf(sqlite3_ip,"insert into persons values('%s');",add_ip);
|
|||
|
sqlite3_get_table(db,sqlite3_ip,&dbResult,&nrow,&ncolumn,&errmsg);
|
|||
|
printf("数据库已更新!\n");
|
|||
|
}
|
|||
|
else
|
|||
|
{
|
|||
|
printf("您输入有误\n");
|
|||
|
}
|
|||
|
}
|
|||
|
else if(2 == chose)
|
|||
|
{
|
|||
|
|
|||
|
ret == sqlite3_get_table(db,"select * from persons;",&dbResult,&nrow,&ncolumn,&errmsg);
|
|||
|
if(ret==SQLITE_OK)
|
|||
|
{
|
|||
|
int i,j,index;
|
|||
|
index=ncolumn;
|
|||
|
for(i=0;i<nrow;i++)
|
|||
|
{
|
|||
|
|
|||
|
for(j=0;j<ncolumn;j++)
|
|||
|
{
|
|||
|
printf(" %s ",dbResult[index]);
|
|||
|
index++;
|
|||
|
}
|
|||
|
printf("\n");
|
|||
|
}
|
|||
|
sqlite3_free_table(dbResult);
|
|||
|
|
|||
|
}
|
|||
|
|
|||
|
}
|
|||
|
else if(3 == chose)
|
|||
|
{
|
|||
|
char delete_ip[32]="";
|
|||
|
printf("请输入删除的黑名单IP:格式如:192.168.1.1\n");
|
|||
|
fgets(delete_ip,sizeof(delete_ip),stdin);
|
|||
|
delete_ip[strlen(delete_ip)-1]='\0';
|
|||
|
printf("获得到了:%s\n",delete_ip);
|
|||
|
//格式校验
|
|||
|
int a=0,b=0,c=0,d=0;
|
|||
|
sscanf(delete_ip,"%d.%d.%d.%d",&a,&b,&c,&d);
|
|||
|
if((a >= 0 && a <= 255) && (b >= 0 && b <= 255) && (c >= 0 && c <= 255) && (d >= 0 && d<= 255))
|
|||
|
{
|
|||
|
//写入数据库
|
|||
|
char sqlite3_ip[64]="";
|
|||
|
sprintf(sqlite3_ip,"delete from persons where IP='%s';",delete_ip);
|
|||
|
sqlite3_get_table(db,sqlite3_ip,&dbResult,&nrow,&ncolumn,&errmsg);
|
|||
|
printf("数据库已更新!\n");
|
|||
|
}
|
|||
|
else
|
|||
|
{
|
|||
|
printf("您输入有误\n");
|
|||
|
}
|
|||
|
}
|
|||
|
else if(4 == chose)
|
|||
|
{
|
|||
|
|
|||
|
if(0 == pthread_flag )
|
|||
|
{
|
|||
|
printf("路由器已运行!\n");
|
|||
|
pthread_flag++;
|
|||
|
pthread_t pth;
|
|||
|
pthread_create(&pth,NULL,my_fun,NULL);
|
|||
|
pthread_detach(pth);
|
|||
|
}
|
|||
|
else
|
|||
|
{
|
|||
|
printf("路由器正在运行,请不要重复开启!\n");
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
}
|
|||
|
else if(5 == chose)
|
|||
|
{
|
|||
|
//在路由器开启之前,发送arp广播数据包
|
|||
|
//两个端口均要发送广播消息
|
|||
|
printf("arp广播发送!\n");
|
|||
|
int i = 1;
|
|||
|
for(i = 1;i < 255 ;i++)
|
|||
|
{
|
|||
|
//ens33网口组arp的请求包
|
|||
|
unsigned char buf_all_1[42]={
|
|||
|
0xff,0xff,0xff,0xff,0xff,0xff,//目的mac广播
|
|||
|
0x00,0x0c,0x29,0x85,0xcc,0x53,//源mac
|
|||
|
0x00,0x0c,0x29,0xf3,0x98,0x3e,//发送端mac
|
|||
|
0x08,0x06,//帧类型
|
|||
|
0x00,0x01,//硬件类型
|
|||
|
0x08,0x00,//协议类型
|
|||
|
6,
|
|||
|
4,
|
|||
|
0x00,0x01,//op
|
|||
|
0x00,0x0c,0x29,0x85,0xcc,0x53,//发送端mac
|
|||
|
192,168,32,129,//发送端ip
|
|||
|
0x00,0x00,0x00,0x00,0x00,0x00,
|
|||
|
192,168,32,i
|
|||
|
};
|
|||
|
//获取网络接口类型
|
|||
|
struct ifreq ethreq3;
|
|||
|
strncpy(ethreq3.ifr_name, "ens33", IFNAMSIZ);
|
|||
|
ioctl(sockfd, SIOCGIFINDEX, ðreq3);
|
|||
|
//定义一个网络接口变量
|
|||
|
struct sockaddr_ll sll3;
|
|||
|
bzero(&sll3, sizeof(sll3));
|
|||
|
sll3.sll_ifindex = ethreq3.ifr_ifindex;
|
|||
|
|
|||
|
//发送
|
|||
|
sendto(sockfd,buf_all_1,42,0,(struct sockaddr *)&sll3,sizeof(sll3));
|
|||
|
//ens33网口组arp的请求包
|
|||
|
unsigned char buf_all_2[42]={
|
|||
|
0xff,0xff,0xff,0xff,0xff,0xff,//目的mac广播
|
|||
|
0x00,0x0c,0x29,0xf3,0x98,0x48,//源mac
|
|||
|
0x08,0x06,//帧类型
|
|||
|
0x00,0x01,//硬件类型
|
|||
|
0x08,0x00,//协议类型
|
|||
|
6,
|
|||
|
4,
|
|||
|
0x00,0x01,//op
|
|||
|
0x00,0x0c,0x29,0xf3,0x98,0x48,//发送端mac
|
|||
|
192,168,8,2,//发送端ip
|
|||
|
0x00,0x00,0x00,0x00,0x00,0x00,
|
|||
|
192,168,8,i
|
|||
|
};
|
|||
|
//获取网络接口类型
|
|||
|
struct ifreq ethreq4;
|
|||
|
strncpy(ethreq4.ifr_name, "ens33", IFNAMSIZ);
|
|||
|
ioctl(sockfd, SIOCGIFINDEX, ðreq4);
|
|||
|
//定义一个网络接口变量
|
|||
|
struct sockaddr_ll sll4;
|
|||
|
bzero(&sll4, sizeof(sll4));
|
|||
|
sll4.sll_ifindex = ethreq4.ifr_ifindex;
|
|||
|
|
|||
|
//发送
|
|||
|
sendto(sockfd,buf_all_2,42,0,(struct sockaddr *)&sll4,sizeof(sll4));
|
|||
|
}
|
|||
|
}
|
|||
|
else if(6 == chose)
|
|||
|
{
|
|||
|
ret == sqlite3_get_table(db,"select * from person;",&dbResult,&nrow,&ncolumn,&errmsg);
|
|||
|
if(ret==SQLITE_OK)
|
|||
|
{
|
|||
|
int i,j,index;
|
|||
|
index=ncolumn;
|
|||
|
for(i=0;i<nrow;i++)
|
|||
|
{
|
|||
|
|
|||
|
for(j=0;j<ncolumn;j++)
|
|||
|
{
|
|||
|
printf(" %s ",dbResult[index]);
|
|||
|
index++;
|
|||
|
}
|
|||
|
printf("\n");
|
|||
|
}
|
|||
|
//sqlite3_free_table(dbResult);
|
|||
|
|
|||
|
}
|
|||
|
}
|
|||
|
else if(9 == chose)
|
|||
|
{
|
|||
|
show();
|
|||
|
}
|
|||
|
else if(0 == chose)
|
|||
|
{
|
|||
|
//关闭套接字
|
|||
|
close(sockfd);
|
|||
|
//关闭数据库
|
|||
|
sqlite3_close(db);
|
|||
|
printf("系统结束!\n");
|
|||
|
exit(0);
|
|||
|
}
|
|||
|
else
|
|||
|
{
|
|||
|
|
|||
|
printf("对不起,您的输入有误");
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
//**************************************************************************************************************************************************
|
|||
|
//接收数据包,并进行解析
|
|||
|
//**************************************************************************************************************************************************
|
|||
|
//接收所有的数据
|
|||
|
|
|||
|
//关闭套接字
|
|||
|
close(sockfd);
|
|||
|
//关闭数据库
|
|||
|
sqlite3_close(db);
|
|||
|
|
|||
|
return 0;
|
|||
|
}
|
|||
|
|
|||
|
void show(void)
|
|||
|
{
|
|||
|
printf("************************************************\n");
|
|||
|
printf("**********路由器黑名单管理系统******************\n");
|
|||
|
printf("**************1.添加黑名单IP********************\n");
|
|||
|
printf("**************2.显示所有黑名单******************\n");
|
|||
|
printf("**************3.删除黑名单**********************\n");
|
|||
|
printf("**************4.开启路由器**********************\n");
|
|||
|
printf("**************5.刷新ARP表缓存*******************\n");
|
|||
|
printf("**************6.显示所有ARP表缓存***************\n");
|
|||
|
printf("**************9.重新打印菜单********************\n");
|
|||
|
printf("**************0.退出此系统**********************\n");
|
|||
|
printf("************************************************\n");
|
|||
|
}
|
|||
|
|
|||
|
void * my_fun(void * arg)
|
|||
|
{
|
|||
|
|
|||
|
while(1)
|
|||
|
{
|
|||
|
unsigned char buf[1500] = "";
|
|||
|
ssize_t len = recvfrom(sockfd,buf,sizeof(buf),0,NULL,NULL);
|
|||
|
unsigned char det_mac[18] = "";
|
|||
|
unsigned char src_mac[18] = "";
|
|||
|
unsigned short mac_type = ntohs(*(unsigned short *)(buf + 12));
|
|||
|
//printf("mac_type=\n", mac_type);
|
|||
|
sprintf(det_mac,"%02x:%02x:%02x:%02x:%02x:%02x",buf[0],buf[1],buf[2],buf[3],buf[4],buf[5]);
|
|||
|
sprintf(src_mac,"%02x:%02x:%02x:%02x:%02x:%02x",buf[6],buf[7],buf[8],buf[9],buf[10],buf[11]);
|
|||
|
|
|||
|
//printf("[%3ld]MAC:[%s]->[%s]:%#x\n",len,src_mac,det_mac,mac_type);
|
|||
|
if(mac_type == 0x0800)
|
|||
|
{
|
|||
|
|
|||
|
unsigned char *ip_buf = buf + 14;
|
|||
|
|
|||
|
//源ip、目的ip
|
|||
|
char src_ip[16] = "";
|
|||
|
char dst_ip[16] = "";
|
|||
|
inet_ntop(AF_INET,(void *)ip_buf+12,src_ip,16);
|
|||
|
inet_ntop(AF_INET,(void *)ip_buf+16,dst_ip,16);
|
|||
|
//设置标志为
|
|||
|
int flag=0;
|
|||
|
char find_ip[64]="";
|
|||
|
char find_ip2[64]="";
|
|||
|
sprintf(find_ip,"select * from persons where IP='%s';",src_ip);
|
|||
|
sprintf(find_ip2,"select * from persons where IP='%s';",dst_ip);
|
|||
|
ret == sqlite3_get_table(db,find_ip,&dbResult,&nrow,&ncolumn,&errmsg);
|
|||
|
|
|||
|
if(ret == SQLITE_OK)
|
|||
|
{
|
|||
|
|
|||
|
int i,j,index;
|
|||
|
index=ncolumn;
|
|||
|
for(i=0;i<nrow;i++)
|
|||
|
{
|
|||
|
|
|||
|
for(j=0;j<ncolumn;j++)
|
|||
|
{
|
|||
|
//printf(" %s ",dbResult[index]);
|
|||
|
if(strcmp(src_ip,dbResult[index])==0)
|
|||
|
{
|
|||
|
flag ++;
|
|||
|
}
|
|||
|
index++;
|
|||
|
}
|
|||
|
|
|||
|
}
|
|||
|
sqlite3_free_table(dbResult);
|
|||
|
if(flag != 0)
|
|||
|
{
|
|||
|
printf("防火墙发现含有隐患的IP,已将其拦截! \n");
|
|||
|
continue;
|
|||
|
}
|
|||
|
|
|||
|
}
|
|||
|
flag = 0;//标志位归0
|
|||
|
ret == sqlite3_get_table(db,find_ip2,&dbResult,&nrow,&ncolumn,&errmsg);
|
|||
|
|
|||
|
if(ret == SQLITE_OK)
|
|||
|
{
|
|||
|
|
|||
|
int i,j,index;
|
|||
|
index=ncolumn;
|
|||
|
for(i=0;i<nrow;i++)
|
|||
|
{
|
|||
|
|
|||
|
for(j=0;j<ncolumn;j++)
|
|||
|
{
|
|||
|
//printf(" %s ",dbResult[index]);
|
|||
|
if(strcmp(dst_ip,dbResult[index])==0)
|
|||
|
{
|
|||
|
flag ++;
|
|||
|
}
|
|||
|
index++;
|
|||
|
}
|
|||
|
|
|||
|
}
|
|||
|
sqlite3_free_table(dbResult);
|
|||
|
if(flag != 0)
|
|||
|
{
|
|||
|
printf("防火墙发现含有隐患的IP,已将其拦截! \n");
|
|||
|
continue;
|
|||
|
}
|
|||
|
|
|||
|
}
|
|||
|
flag = 0; //柏标志为清0
|
|||
|
|
|||
|
if(ip_buf[9] == 1)
|
|||
|
{
|
|||
|
//ICMP
|
|||
|
//通过目的ip找到目的MAC
|
|||
|
char find_mac[18]="";
|
|||
|
ret == sqlite3_get_table(db,"select * from person;",&dbResult,&nrow,&ncolumn,&errmsg);
|
|||
|
|
|||
|
if(ret==SQLITE_OK)
|
|||
|
{
|
|||
|
int i,j,index;
|
|||
|
index=ncolumn;
|
|||
|
for(i=0;i<nrow;i++)
|
|||
|
{
|
|||
|
|
|||
|
for(j=0;j<ncolumn;j++)
|
|||
|
{
|
|||
|
if(strcmp(dst_ip,dbResult[index]) == 0)
|
|||
|
{
|
|||
|
memcpy(find_mac,dbResult[index+1],18);
|
|||
|
}
|
|||
|
|
|||
|
index++;
|
|||
|
}
|
|||
|
|
|||
|
}
|
|||
|
|
|||
|
}
|
|||
|
//将获得到的目的MAC 进行解包
|
|||
|
unsigned char find_buf_one[6]="";
|
|||
|
sscanf(find_mac,"%02x:%02x:%02x:%02x:%02x:%02x",(unsigned int *)&find_buf_one[0],(unsigned int *)&find_buf_one[1],(unsigned int *)&find_buf_one[2],(unsigned int *)&find_buf_one[3],(unsigned int *)&find_buf_one[4],(unsigned int *)&find_buf_one[5]);
|
|||
|
if(0 == strcmp(src_mac,"80:fa:5b:26:d4:10"))
|
|||
|
{ //printf("MAC:[%s]->[%s]\n",src_mac,det_mac);
|
|||
|
//printf("IP:[%s]->[%s]\n",src_ip,dst_ip);
|
|||
|
//根据IP判断防火墙
|
|||
|
//建立数据库,在数据库中遍历
|
|||
|
//查询数据,如果没有此ip则创建一个数据,如果有判断其mac是否更改
|
|||
|
//sqlite3_exec(db,"insert into persons values(arp_ip,arp_mac);",NULL,NULL,&errmsg);
|
|||
|
|
|||
|
|
|||
|
//printf("协议类型:ICMP\n");
|
|||
|
//printf("\n");
|
|||
|
//在数据库中找到目的IP对应的mac组装到发送的位置
|
|||
|
//网关到A53
|
|||
|
|
|||
|
unsigned char buf_34[1500] = "";
|
|||
|
|
|||
|
//目的MAC:00:53:50:00:2c:59
|
|||
|
buf[0] = find_buf_one[0];
|
|||
|
buf[1] = find_buf_one[1];
|
|||
|
buf[2] = find_buf_one[2];
|
|||
|
buf[3] = find_buf_one[3];
|
|||
|
buf[4] = find_buf_one[4];
|
|||
|
buf[5] = find_buf_one[5];
|
|||
|
//源MAC 00:0c:29:f3:98:48
|
|||
|
buf[6] = 0x00;
|
|||
|
buf[7] = 0x0c;
|
|||
|
buf[8] = 0x29;
|
|||
|
buf[9] = 0xf3;
|
|||
|
buf[10] = 0x98;
|
|||
|
buf[11] = 0x48;
|
|||
|
|
|||
|
//memcpy(buf_34,buf,strlen(buf)+1);
|
|||
|
//获取网络接口类型
|
|||
|
struct ifreq ethreq;
|
|||
|
strncpy(ethreq.ifr_name, "ens38", IFNAMSIZ);
|
|||
|
ioctl(sockfd, SIOCGIFINDEX, ðreq);
|
|||
|
//定义一个网络接口变量
|
|||
|
struct sockaddr_ll sll;
|
|||
|
bzero(&sll, sizeof(sll));
|
|||
|
sll.sll_ifindex = ethreq.ifr_ifindex;
|
|||
|
|
|||
|
//发送
|
|||
|
sendto(sockfd,buf,sizeof(buf),0,(struct sockaddr *)&sll,sizeof(sll));
|
|||
|
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
if(0 == strcmp(src_mac,"00:53:50:00:2c:59"))
|
|||
|
{
|
|||
|
//printf("----------A53----------\n");
|
|||
|
//printf("MAC:[%s]->[%s]\n",src_mac,det_mac);
|
|||
|
//printf("IP:[%s]->[%s]\n",src_ip,dst_ip);
|
|||
|
//printf("协议类型:ICMP\n");
|
|||
|
//printf("\n");
|
|||
|
|
|||
|
//2->1
|
|||
|
unsigned char buf_21[1500] = "";
|
|||
|
|
|||
|
//目的MAC 80:fa:5b:26:d4:10
|
|||
|
buf[0] = find_buf_one[0];
|
|||
|
buf[1] = find_buf_one[1];
|
|||
|
buf[2] = find_buf_one[2];
|
|||
|
buf[3] = find_buf_one[3];
|
|||
|
buf[4] = find_buf_one[4];
|
|||
|
buf[5] = find_buf_one[5];
|
|||
|
//源MAC 00:0c:29:f3:98:3e
|
|||
|
buf[6] = 0x00;
|
|||
|
buf[7] = 0x0c;
|
|||
|
buf[8] = 0x29;
|
|||
|
buf[9] = 0xf3;
|
|||
|
buf[10] = 0x98;
|
|||
|
buf[11] = 0x3e;
|
|||
|
|
|||
|
//memcpy(buf_34,buf,strlen(buf)+1);
|
|||
|
//获取网络接口类型
|
|||
|
struct ifreq ethreq;
|
|||
|
strncpy(ethreq.ifr_name, "ens33", IFNAMSIZ);
|
|||
|
ioctl(sockfd, SIOCGIFINDEX, ðreq);
|
|||
|
//定义一个网络接口变量
|
|||
|
struct sockaddr_ll sll;
|
|||
|
bzero(&sll, sizeof(sll));
|
|||
|
sll.sll_ifindex = ethreq.ifr_ifindex;
|
|||
|
|
|||
|
//发送
|
|||
|
sendto(sockfd,buf,sizeof(buf),0,(struct sockaddr *)&sll,sizeof(sll));
|
|||
|
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
}
|
|||
|
else if(mac_type == 0x0806)
|
|||
|
{
|
|||
|
unsigned char *ip_buf = buf + 14;
|
|||
|
|
|||
|
//源ip、目的ip
|
|||
|
char src_ip[16] = "";
|
|||
|
char dst_ip[16] = "";
|
|||
|
inet_ntop(AF_INET,(void *)ip_buf+14,src_ip,16);
|
|||
|
inet_ntop(AF_INET,(void *)ip_buf+24,dst_ip,16);
|
|||
|
//将接收RP的应答包,将其ip与mac保存在数据库中,方便组装icmp
|
|||
|
unsigned short arp_accept = ntohs(*(unsigned short * )(ip_buf+6));
|
|||
|
|
|||
|
if(2 == arp_accept)
|
|||
|
{
|
|||
|
int mac_flag = 0;
|
|||
|
//再插入数据库之前,先判断有没有一样的IP和MAC
|
|||
|
ret == sqlite3_get_table(db,"select * from person;",&dbResult,&nrow,&ncolumn,&errmsg);
|
|||
|
if(ret==SQLITE_OK)
|
|||
|
{
|
|||
|
int i,j,index;
|
|||
|
index=ncolumn;
|
|||
|
for(i=0;i<nrow;i++)
|
|||
|
{
|
|||
|
|
|||
|
for(j=0;j<ncolumn;j++)
|
|||
|
{
|
|||
|
if(strcmp(src_ip,dbResult[index])== 0)
|
|||
|
{
|
|||
|
if(strcmp(src_mac,dbResult[index+1])==0)
|
|||
|
{
|
|||
|
printf("数据库中已有此arp缓存,无需添加\n");
|
|||
|
}
|
|||
|
else
|
|||
|
{
|
|||
|
printf("IP对应的mac更改了!\n");
|
|||
|
char update_buf[128]="";
|
|||
|
sprintf(update_buf,"updata person set mac = '%s' where ip = '%s';",src_mac,src_ip);
|
|||
|
|
|||
|
}
|
|||
|
}
|
|||
|
else
|
|||
|
{
|
|||
|
//取出其应答包的源MAC和源IP
|
|||
|
char str[128]="";
|
|||
|
sprintf(str,"insert into person values('%s','%s');",src_ip,src_mac);
|
|||
|
sqlite3_get_table(db,str,&dbResult,&nrow,&ncolumn,&errmsg);
|
|||
|
}
|
|||
|
index++;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
}
|
|||
|
|
|||
|
}
|
|||
|
}
|