C++ Win 32 使用原始套接字获取所有ip数据包并分析(包括ping包)
/*页面编码:GBK 开发环境 VS2019 */
#define _WINSOCK_DEPRECATED_NO_WARNINGS
#include <iostream>
#include<WinSock2.h>
#pragma comment(lib,"ws2_32.lib")
#define SIO_RCVALL _WSAIOW(IOC_VENDOR,1)
std::string Utf8ToGbk(const char* src_str)
{
int len = MultiByteToWideChar(CP_UTF8, 0, src_str, -1, NULL, 0);
wchar_t* wszGBK = new wchar_t[len + 1];
memset(wszGBK, 0, len * 2 + 2);
MultiByteToWideChar(CP_UTF8, 0, src_str, -1, wszGBK, len);
len = WideCharToMultiByte(CP_ACP, 0, wszGBK, -1, NULL, 0, NULL, NULL);
char* szGBK = new char[len + 1];
memset(szGBK, 0, len + 1);
WideCharToMultiByte(CP_ACP, 0, wszGBK, -1, szGBK, len, NULL, NULL);
std::string strTemp(szGBK);
if (wszGBK) delete[] wszGBK;
if (szGBK) delete[] szGBK;
return strTemp;
}
typedef struct _IP_HEADER
{
char m_cVersionAndHanderLen; //版本信息(前4位),头长度(后4位)
char m_cTypeOfService; //服务类型8位
short m_sTotalLenOfPacket; //数据包长度
short m_sPacketID; //数据包标识
short m_sSliceinfo; //分片使用
char m_cTTL; //存活时间
char m_cTypeOfProtocol; //协议类型
short m_sChechSum; //校验和
unsigned int m_uiSourIp; //源IP地址
unsigned int m_uiDestIp; //目的IP地址
}IP_HEADER, * PIP_HEADER;
typedef struct _UDP_HEADER
{
unsigned short m_usSourPort; //源端口号16bit
unsigned short m_usDestPort; //目的端口号16bit
unsigned short m_usLength; //数据包长度16bit
unsigned short m_usCheckSum; //校验和16bit
}UDP_HEADER, * PUDP_HEADER;
int main()
{
WSADATA wsadata;
int ret = WSAStartup(MAKEWORD(2, 2), &wsadata); if (ret != 0) { printf("初始化winsock2失败!"); return -1; } //if (LOBYTE(wsadata.wVersion) != 2 || HIBYTE(wsadata.wVersion) != 2) { puts("版本号错误!"); return -1; }
SOCKADDR_IN saddr;
memset(&saddr, 0, sizeof(SOCKADDR_IN));
saddr.sin_family = AF_INET;
saddr.sin_port = htons(8080);
saddr.sin_addr.s_addr = inet_addr("192.168.125.9");
SOCKET sockfd = socket(AF_INET, SOCK_RAW, IPPROTO_IP); if (sockfd < 0) { puts("创建套接字失败!"); return system("pause"); }
int on = 1;
setsockopt(sockfd, SOL_SOCKET, SO_REUSEADDR, (char*)&on, sizeof(on));
ret = bind(sockfd, (SOCKADDR*)&saddr, sizeof(SOCKADDR)); if (ret != 0) { puts("绑定失败!"); return system("pause"); }
DWORD dwlen[10], dwlenrtned = 0, optval = 1;
WSAIoctl(sockfd, SIO_RCVALL, &optval, sizeof(optval), &dwlen, sizeof(dwlen), &dwlenrtned, NULL, NULL); //允许套接字接收所有经过本机的网络数据包
char buf[500] = "";
int len = sizeof(SOCKADDR);
IP_HEADER iph;
UDP_HEADER udph;
while (1)
{
puts("等待接收数据......");
ret = recvfrom(sockfd, buf, 200, 0, (SOCKADDR*)&saddr, &len); if (ret < 0) { puts("接收错误!"); }
memcpy(&iph, buf, 20);
memcpy(&udph, buf + 20, 8);
in_addr ias, iad;
ias.S_un.S_addr = iph.m_uiSourIp;
iad.S_un.S_addr = iph.m_uiDestIp;
printf("协议类型:%d\n", iph.m_cTypeOfProtocol);
switch (iph.m_cTypeOfProtocol)
{
case IPPROTO_ICMP:
puts("收到ICMP包");
break;
case IPPROTO_IGMP:
puts("收到IGMP包");
break;
case IPPROTO_UDP:
puts("收到UDP包");
break;
case IPPROTO_TCP:
puts("收到TCP包");
break;
default:
puts("未指定协议类型");
break;
}
char str1[20];
char str2[20];
strcpy_s(str1, inet_ntoa(ias));
strcpy_s(str2, inet_ntoa(iad));
printf("源地址IP:%s 源地址端口:%d \n目标地址IP:%s 目标地址端口:%d \n", str1, ntohs(udph.m_usSourPort), str2, ntohs(udph.m_usDestPort));
std::string str = "0";
str= Utf8ToGbk(buf+28);
std::cout << "接收到的数据段:" << str << std::endl;
puts("");
}
closesocket(sockfd);
WSACleanup();
return system("pause");
}
注意:使用管理员模式运行,因为原始套接字的使用是需要管理员权限的。
C++ Win 32 使用原始套接字获取所有ip数据包并分析(包括ping包)的更多相关文章
- Linux系统编程(37)—— socket编程之原始套接字
原始套接字的特点 原始套接字(SOCK_RAW)可以用来自行组装IP数据包,然后将数据包发送到其他终端.也就是说原始套接字是基于IP数据包的编程(SOCK_PACKET是基于数据链路层的编程).另外, ...
- Linux网络编程——原始套接字能干什么?
通常情况下程序员接所接触到的套接字(Socket)为两类: (1)流式套接字(SOCK_STREAM):一种面向连接的 Socket,针对于面向连接的TCP 服务应用: (2)数据报式套接字(SOCK ...
- Linux网络编程:原始套接字简介
Linux网络编程:原始套接字编程 一.原始套接字用途 通常情况下程序员接所接触到的套接字(Socket)为两类: 流式套接字(SOCK_STREAM):一种面向连接的Socket,针对于面向连接的T ...
- UNIX网络编程——原始套接字的魔力【续】
如何从链路层直接发送数据帧 上一篇里面提到的是从链路层"收发"数据,该篇是从链路层发送数据帧. 上一节我们主要研究了如何从链路层直接接收数据帧,可以通过bind函数来将原始套接字绑 ...
- Linux原始套接字实现分析---转
http://blog.chinaunix.net/uid-27074062-id-3388166.html 本文从IPV4协议栈原始套接字的分类入手,详细介绍了链路层和网络层原始套接字的特点及其内核 ...
- Linux网络编程——原始套接字编程
原始套接字编程和之前的 UDP 编程差不多,无非就是创建一个套接字后,通过这个套接字接收数据或者发送数据.区别在于,原始套接字可以自行组装数据包(伪装本地 IP,本地 MAC),可以接收本机网卡上所有 ...
- Linux基础(11)原始套接字
一边接收函数返回一边判断返回值时一定要把接收的优先级加()提高再去判断 例 if((sockfd = socket()) < 0) 问题: 如何实现SYN扫描器扫描端口 , 比如AB两个设备要进 ...
- UNP——原始套接字
1.原始套接字的用处 使用原始套接字可以构造或读取网际层及其以上报文. 具体来说,可以构造 ICMP, IGMP 协议报文,通过开启 IP_HDRINCL 套接字选项,进而自定义 IPv4首部. 2. ...
- 005.TCP--拼接TCP头部IP头部,实现TCP三次握手的第一步(Linux,原始套接字)
一.目的: 自己拼接IP头,TCP头,计算效验和,将生成的报文用原始套接字发送出去. 若使用tcpdump能监听有对方服务器的包回应,则证明TCP报文是正确的! 二.数据结构: TCP首部结构图: s ...
随机推荐
- Cloudera Manager和CDH安装部署
本次安装采用离线安装的方式,需要提前下载好需要的包. 1. 准备工作 1.1 环境说明 操作系统:RedHat企业级Linux6.5 64-bit Cloudera Manager:5.8.4 CDH ...
- Ajax每隔2秒自动请求服务端刷新页面
1. window.onload = function () {automatic(); } 2. function automatic(){ //每隔两秒刷新一次页面setTimeout(autom ...
- StringBuilder 比 String 快?空嘴白牙的,证据呢!
作者:小傅哥 博客:https://bugstack.cn 沉淀.分享.成长,让自己和他人都能有所收获! 一.前言 聊的是八股的文,干的是搬砖的活! 面我的题开发都用不到,你为什么要问?可能这是大部分 ...
- 分布式系统监视zabbix-安装
zabbix概述 Zabbix是什么 Zabbix 是由Alexei Vladishev创建,目前由Zabbix SIA在持续开发和支持. Zabbix 是一个企业级的分布式开源监控方案. Zabbi ...
- Golang的Context介绍及其源码分析
简介 在Go服务中,对于每个请求,都会起一个协程去处理.在处理协程中,也会起很多协程去访问资源,比如数据库,比如RPC,这些协程还需要访问请求维度的一些信息比如说请求方的身份,授权信息等等.当一个请求 ...
- Nginx【常见知识点速查】
文章更新时间:2020/04/10 一.简介 定义:Nginx是一个高性能的HTTP和反向代理web服务器 作用: 反向代理 正向代理 负载均衡 HTTP静态资源服务器(动静分离) 二.正向代理与反向 ...
- Java高级开发必会的50个性能优化的细节(珍藏版)
在JAVA程序中,性能问题的大部分原因并不在于JAVA语言,而是程序本身.养成良好的编码习惯非常重要,能够显著地提升程序性能. ● 1. 尽量在合适的场合使用单例 使用单例可以减轻加载的负担,缩短 ...
- 结合 Shell 对 Koa 应用运行环境检查
在开发环境中,启动一个koa 应用服务,通常还需要同时启动数据库.比如.Mongodb.mysql 等 如果一直开着数据库服务,在不使用的话,电脑会占一定的性能.然而如果每次手动去启动服务,效率又不高 ...
- spring+springmvc+mybatis+shiro
创建maven框架https://blog.csdn.net/Ajax_mt/article/details/78549119 具体下边 https://blog.csdn.net/w2222288/ ...
- 创建Maven项目中的几个问题
一.用eclipse创建maven的web项目,需手动添加WEB-INF文件夹及其web.xml配置文件 二.设置编译版本1.8 在pom.xml中设置 1 <build> 2 <! ...