TCPserverSocket编程VC++6.0
研⼆  wifi嗅探项⽬  第⼀阶段 数据提取与分析
#include <stdio.h>
#include <winsock2.h>
#pragma comment(lib,"ws2_32.lib")
int main(int argc, char* argv[])
{
//⼀、WSAStartup函数初始化Winsock
WORD sockVersion = MAKEWORD(2,2);
WSADATA wsaData;
if(WSAStartup(sockVersion, &wsaData)!=0)  //使⽤Winsocket函数之前,必须⾸先调⽤WSAStartup初始化ws2_32.dll
{
return 0;
}
//⼆、socket函数创建套接字
SOCKET slisten = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);  //AF_INET指定协议族为Internet协议;SOCK_STREAM 称为流套接⼝,对应于TCP协议;IPPROTO_TCP指定所⽤的协议为TCP协议
if(slisten == INVALID_SOCKET)  //函数socket有错误返回INVALID_SOCKET
{
printf("socket error !");
return 0;
}
//三、结构体内绑定IP、端⼝;bind函数绑定套接⼝
sockaddr_in sin;              //INET协议族地址结构
sin.sin_family = AF_INET;    //地址族
sin.sin_port = htons(8080);  //16位的IP端⼝  ⾃⼰的应⽤程序的端⼝号需设置为5001-65535之间
sin.sin_addr.s_addr = INADDR_ANY;
//32位的iPv4地址  INADDR_ANY表⽰本地的任意以太⽹接⼝地址
if(bind(slisten, (LPSOCKADDR)&sin, sizeof(sin)) == SOCKET_ERROR)  //bind绑定套接⼝ slisten为socket函数已创建的套接⼝描述字  (LPSOCKADDR)&sin为仅供套接⼝使⽤的本地地址的通⽤地址指针  最后⼀个参数为sin指针长度  bind函数有错返回
SOCKET_ERROR
{
printf("bind error !");
}
//四、listen函数开始监听
if(listen(slisten, SOMAXCONN) == SOCKET_ERROR)  //listen函数⽤于服务器端,connect函数⽤于客户端。listen函数负责通知进程接收连接请求,同时指定排队等待的最⼤连接数,⼀般为5,设置为SOMAXCONN则默认环境中可得的最⼤值。slisten为经socket函数创建,bind函数绑定但未连接的套接⼝描述字
{
printf("listen error !");
return 0;
}
//循环接收数据
SOCKET sClient;
SOCKET sClient;
sockaddr_in remoteAddr;
int nAddrlen = sizeof(remoteAddr);
#define hsize 2550      //缓冲区⼤⼩设置
char revData[hsize];
unsigned char revData1[hsize];
unsigned char lengh[2]={0};
int datalengh=0;        //数据长度
int j=0;                //作为帧⾸标志序号 作为数组序号的基准
int flag=0;            //⽤于判断是否是第⼀个FE,避免将数据包中的FE判断为帧头
while (true)
{
server error啥意思printf("等待连接...\n");
sClient = accept(slisten, (SOCKADDR *)&remoteAddr, &nAddrlen);  //accept函数等待接受连接请求 slisten为处于监听状态的套接⼝描述字 remoteAddr为⽤来接收外来连接的地址信息 nAddrlen为由remoteAddr所指的INET地址结构的长度
if (sClient == INVALID_SOCKET)  //accept函数错误返回INVALID_SOCKET
{
printf("accept error !");
continue;
}
printf("接收到⼀个连接:%s \r\n", inet_ntoa(remoteAddr.sin_addr));  //打印收到的连接信息
//recv函数从套接⼝接收数据
ZeroMemory(revData,hsize);  //清除数据接收缓冲区
int ret = recv(sClient, revData, hsize, 0);  //sClient为套接⼝描述字 revData为⽤于接收数据的缓冲区指针 hsize为应⽤程序提供的缓冲区⼤⼩ 0为标志值
if(ret>0)                                    //没有错误发⽣则返回接收的字节数,否则返回SOCKET_ERROR,返回0时,如果是UDP套接⼝,那么说明读到了⼀个没有应⽤数据的纯UDP头报⽂;如果是TCP连接,意味着对⽅已经关闭了连接
{
for (int i=0;i<ret;i++)
{
revData1[i]=(unsigned char)(revData[i]);
printf("%02X ",(unsigned char)(revData[i]));
if (flag==0)
{
if (revData1[i]==0xFE)
{
j=i;
flag=1;
}
}
}
flag=0;
//解析数据报长度 2 Byte
lengh[0]=revData1[j+1];
lengh[1]=revData1[j+2];
datalengh=(int)lengh[1]<<8|(int)lengh[0];
printf("\n数据长度为:%d  ",datalengh);    //数据长度包含第⼀个状态位 因此⼀定是9的倍数加⼀
//帧类型  1 Byte
//帧类型  1 Byte
printf("  %02X上⾏数据包",revData1[j+3]);
//设备ID  4 Byte
printf("  设备ID:%02X.%02X.%02X.%02X\n",revData1[j+4],revData1[j+5],revData1[j+6],revData1[j+7]);
//数据体
printf("数据体:  设备状态%02X\n",revData1[j+8]);
int q=9;            //数组序号
int timepc=0;        //时间偏差
int k=1;            //循环次数 也是设备个数
while (q < (datalengh+8) )
{
printf("WIFI设备%03d:MAC地址:%02X.%02X.%02X.%02X.%02X.%02X  RSSI:%d dbm
",k,revData1[q],revData1[q+1],revData1[q+2],revData1[q+3],revData1[q+4],revData1[q+5],(char) revData1[q+6]); timepc=(int)revData1[q+8]<<8|(int)revData1[q+7];  //⼩端模式 所以后⾯是⾼位
printf("时间偏差:%ds\n",timepc);
k=k+1;
q=j+9*k;
}
//校验值
printf("校验值%02X\n",revData1[j+8+datalengh]);
}
closesocket(sClient);
}
closesocket(slisten);    //closesocket关闭⼀个存在的套接⼝
WSACleanup();            //应⽤结束后必须调⽤WSACleanup函数终⽌ws2_32.dll的使⽤
return 0;
}
参考书籍:
TCP/IP协议及⽹络编程技术
Windows+Sockets⽹络开发:基于Visual+C++实现
WinSock⽹络编程经络

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。