#include #include #include #include #include #include //recvfrom #include //ETH_P_ALL #include //inet_ntop #include //ifreq #include //ioctl #include //sockaddr_ll #include #include #include 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= 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= 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[%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[%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