由于最经做模拟TCP三次握手的实验,需要用到raw socket编程。

运行第一段代码,发送ip数据报,第二段代码接收ip数据报。需要运行第二段代码,否则将无法接收数据报。

#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#include<sys/socket.h>
#include<sys/types.h>
#include<netinet/in.h>struct iphead{   //该结构体模拟IP首部(代码中,控制套接字不添加IP数据包首部,需要自己添加),
     //关于各变量的含义,可对照IP数据报格式,一目了然。unsigned char ip_hl:4, ip_version:4;  //ip_hl,ip_version各占四个bit位。unsigned char ip_tos;unsigned short int ip_len;   unsigned short int ip_id;unsigned short int ip_off;  unsigned char ip_ttl;unsigned char ip_pro;unsigned short int ip_sum;unsigned int ip_src;unsigned int ip_dst;
};struct icmphead{  //该结构体模拟ICMP报文首部
unsigned char icmp_type;unsigned char icmp_code;unsigned short int icmp_sum;unsigned short int icmp_id;unsigned short int icmp_seq;
};unsigned short int cksum(char buffer[], int size){   //计算校验和,具体的算法可自行百度,或查阅资料unsigned long sum = 0;unsigned short int answer;unsigned short int *temp;temp = (short int *)buffer;for( ; temp<buffer+size; temp+=1){sum += *temp;}sum = (sum >> 16) + (sum & 0xffff);sum += (sum >> 16);answer = ~sum;return answer;
}int main(){int sockfd;struct sockaddr_in conn;struct iphead *ip;struct icmphead *icmp;unsigned char package[sizeof(struct iphead) + sizeof(struct icmphead)];  //package存储IP数据报的首部和数据memset(package, 0, sizeof(package));ip = (struct iphead*)package;icmp = (struct icmphead*)(package+sizeof(struct iphead)); //IP数据报数据字段仅仅包含一个ICMP首部sockfd = socket(AF_INET, SOCK_RAW, IPPROTO_ICMP); //创建套接字if(sockfd < 0){printf("Create socket failed\n");return -1;}conn.sin_family = AF_INET;conn.sin_addr.s_addr = inet_addr("192.168.230.135");int one = 1;if(setsockopt(sockfd, IPPROTO_IP, IP_HDRINCL, &one, sizeof(one)) < 0){  //设置套接字行为,此处设置套接字不添加IP首部printf("setsockopt failed!\n");return -1;}/*设置IP首部各个字段的值*/  ip->ip_version = 4; ip->ip_hl = 5;ip->ip_tos = 0;ip->ip_len = htons(sizeof(struct iphead) + sizeof(struct icmphead)); //关于htons()、htonl()的作用,可自行百度 ip->ip_id = htons(1);ip->ip_off = htons(0x4000);ip->ip_ttl = 10;ip->ip_pro = IPPROTO_ICMP;ip->ip_src = htonl(inet_addr("192.168.230.135"));ip->ip_dst = htonl(inet_addr("192.168.230.135"));printf("ipcksum : %d\n", cksum(package, 20)); ip->ip_sum = cksum(package, 20);  // 计算校验和,应当在其他字段之后设置(实验中发现检验和会被自动添加上)/*设置ICMP首部各字段值*/icmp->icmp_type = 8;icmp->icmp_code = 0;icmp->icmp_id = 1;icmp->icmp_seq = 0;icmp->icmp_sum = (cksum(package+20, 8));/*接下来发送IP数据报即可*/if(sendto(sockfd, package, htons(ip->ip_len), 0,(struct sockaddr *)&conn, sizeof(struct sockaddr)) < 0){printf("send failed\n"); return -1;}printf("send successful\n");    return 0;
}
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#include<sys/socket.h>
#include<sys/types.h>
#include<netinet/in.h>
#include<unistd.h>
#include<linux/if_ether.h>unsigned short int cksum(char buffer[], int size){  //校验函数unsigned long sum = 0;unsigned short int answer;unsigned short int *temp;temp = (short int *)buffer;for( ; temp<buffer+size; temp+=1)sum += *temp;sum = (sum >> 16) + (sum & 0xffff);sum += (sum >> 16);answer = ~sum;return answer;
}int main(){unsigned char buffer[1024];//  int sockfd = socket(AF_INET, SOCK_RAW, IPPROTO_ICMP);//不知为啥,无法设置原始套接字在网络层抓IP数据报int sockfd = socket(PF_PACKET, SOCK_RAW, htons(ETH_P_IP)); //此处,利用原始套接字在数据链路层抓取MAC帧,去掉if(sockfd < 0){                                            //14个字节的MAC帧首部即可printf("create sock failed\n");return -1;}    int n = recvfrom(sockfd, buffer, 1024, 0, NULL, NULL); //接收MAC帧printf("receive %d bytes\n", n);for(int i=14; i<n; i++){      //去掉MAC帧首部,直接输出IP数据报每个字节的数据if((i-14) % 16 == 0)printf("\n");printf("%d ",buffer[i]);}printf("\n");printf("ipcksum: %d\n", cksum(buffer+14, 20)); //此处再次校验时,应当输出0return 0;
}

这是之前参考过的一篇文章,写的还可以:http://www.it165.net/pro/html/201208/3450.html

raw socket编程实例相关推荐

  1. linux raw socket 例子,raw socket编程例子

    raw socket编程例子内容安排: 1.原始套接字介绍 1.1 原始套接字工作原理与规则 1.2 简单应用 2 FTP密码窃取器实现(简单的rootkit) 2.1 设计思路 2.2 实现 2.3 ...

  2. C语言 socket编程实例

    C语言 socket编程实例 一. 面向连接的流式套接字 C/S 例子 二. 非阻塞的多人聊天服务器端例子 三. 简单的 IPv6 UDP socket编程 四.使用wireshark抓包分析tcp协 ...

  3. Socket编程实例

    2019独角兽企业重金招聘Python工程师标准>>> Java具有非常强大的网络应用开发能力.学习网络编程,估计都是从编写一个socket通信开始,从中慢慢掌握网络编程的一点点知识 ...

  4. android c++ socket编程,C++ 中 socket编程实例详解

    C++ 中 socket编程实例详解 sockets(套接字)编程有三种,流式套接字(SOCK_STREAM),数据报套接字(SOCK_DGRAM),原始套接字(SOCK_RAW):基于TCP的soc ...

  5. C#下的Raw Socket编程实现网络封包监视

    谈起socket编程,大家也许会想起QQ和IE,没错.还有许多网络工具如P2P.NetMeeting等在应用层实现的应用程序,也是用socket来实现的.Socket是一个网络编程接口,实现于网络应用 ...

  6. 用C#下的Raw Socket编程实现网络封包监视(摘录)

    谈起socket编程,大家也许会想起QQ和IE,没错.还有许多网络工具如P2P.NetMeeting等在应用层实现的应用程序,也是用 socket来实现的.Socket是一个网络编程接口,实现于网络应 ...

  7. NIO Socket编程实例

    1.阻塞模式实例 NIOUtil类,用来通过SOcket获取BufferedReader和PrintWriter. package IO;import java.io.BufferedReader; ...

  8. JAVA socket编程实例 转载

    事实上网络编程简单的理解就是两台计算机相互通讯数据而已.对于程序员而言,去掌握一种编程接口并使用一种编程模型相对就会显得简单的多了.Java SDK提供一些相对简单的Api来完成这些工作.Socket ...

  9. Raw Socket编程

    原始套接字(SOCK_RAW)是一种不同于SOCK_STREAM.SOCK_DGRAM的套接字,它实现于系统核心.然而,原始套接字能做什么呢?首 先来说,普通的套接字无法处理ICMP.IGMP等网络报 ...

  10. JAVA socket编程实例

    2019独角兽企业重金招聘Python工程师标准>>> 事实上网络编程简单的理解就是两台计算机相互通讯数据而已.对于程序员而言,去掌握一种编程接口并使用一种编程模型相对就会显得简单的 ...

最新文章

  1. 一行js_Node.js 一行命令上传本地文件到服务器
  2. 串行通信------字符串发送和十六进制发送
  3. frida hook so层方法大全
  4. 在页面制作过程中需要注意事项
  5. 《现代操作系统》精读与思考笔记 第七章 多媒体
  6. C#数据库事务机制及实践(下)
  7. iOS 应用启动慢的原因找到了!
  8. 模糊数学 计算机智能,吴国平:如果“模糊数学”没有出现,人工智能或许就无从谈起...
  9. python乱码怎么解决方法_python中文乱码的解决方法
  10. python--手柄遥控通讯
  11. 团队管理的一些基本要点
  12. JSON for Modern C++
  13. 判定重大风险有哪几种_重大危险源判定
  14. 《Linux命令速查手册》笔记
  15. 让PcShare2005vip免费
  16. Node.js的卸载
  17. python数据分析大作业-python大作业实验报告
  18. 5种css隐藏元素的方法_在CSS中隐藏元素的10种方法
  19. Word 模板渲染引擎-Poi-tl - 标签(二)
  20. 水仙花数判断 (10 分)

热门文章

  1. 小米电视共享计算机权限,小米电视局域网共享文件 小米盒子局域网共享视频通用方法...
  2. 计算机软考软件设计师2019试题,软考试题及答案【2018计算机软考软件设计师考前练习试题及答案】...
  3. 将图片背景处理为透明的方法步骤
  4. Matlab使用EMD
  5. 注解学习(参考尚硅谷视频)
  6. 介绍一下小规模纳税人如何开具增值税专用发票的流程
  7. 闲谈:渗透测试-红队版
  8. 对抗样本生成算法-FGSM、I-FGSM、ILCM、PGD
  9. Eclipse 9.x 10.0 之破解详细步骤
  10. 《推荐系统实战(一)》基于统计的电影推荐系统(tmdb-5000数据集,数据清洗、特征提取、搭建模型等详细过程)