• 软件测试技术
  • 软件测试博客
  • 软件测试视频
  • 开源软件测试技术
  • 软件测试论坛
  • 软件测试沙龙
  • 软件测试资料下载
  • 软件测试杂志
  • 软件测试人才招聘
    暂时没有公告

字号: | 推荐给好友 上一篇 | 下一篇

利用SNIFFER PRO学习TCP/IP(一)

发布: 2007-7-01 20:40 | 作者: admin | 来源: | 查看: 16次 | 进入软件测试论坛讨论

领测软件测试网

 利用SNIFFER PRO学习TCP/IP(一)

2003/10/28

ydzqw 

注:Sniffer Pro应该大家都知道,不知道的到GOOGLE搜索J

最好手头有本<<TCP/IP详解卷1:协议>> 

这两天在看<<TCP/IP详解>>,总觉得有些地方理解的不够深。于是写了个小程序,再加上Sniffer,慢慢咀嚼。

程序如下:

 

---------------------Server-----------------------------

#include<iostream>

#include<winsock2.h>

#include<windows.h>

using namespace std;

 

void main()

{

       WORD wVer;

       WSADATA wsaData;

       //WSAStartup

       wVer = MAKEWORD(1, 1);

       if ( WSAStartup(wVer, &wsaData) )

       {

              cout << "WSAStaup error!";

              return;

       }

       //SOCKET init

       SOCKET sock;

       if ( (sock = socket(AF_INET, SOCK_STREAM, 0)) < 0 )

       {

              cout << "socket error!";

              return;

       }

       //bind, listen and accept

       sockaddr_in sockadr;

       sockadr.sin_family = AF_INET;

       sockadr.sin_addr.S_un.S_addr = htonl(INADDR_ANY);

       sockadr.sin_port = htons(6666);

       if ( bind(sock, (sockaddr*)&sockadr, sizeof(sockadr)) )

       {

              cout << "bind error!";

              return;

       }

       if ( listen(sock, 5) )

       {

              cout << "listen error!";

              return;

       }

       SOCKET sock_svr;

       sockaddr_in sockadr_svr;

       int iLen = sizeof(sockadr_svr);

       //accept时blocking了,如果这时要退出程序,那该如何?

       sock_svr = accept(sock, (sockaddr*)&sockadr_svr, &iLen);

       if ( sock_svr == INVALID_SOCKET )

       {

              cout << "accetp error!";

              return;

       }

 

       //select and recv

       fd_set rdfs;

       timeval tv;

       char buf[1024 * 2];

       int retval;

       int recv_err;

       tv.tv_sec = 5;

       tv.tv_usec = 0;

       for(; ;)

       {

              FD_ZERO(&rdfs);

              FD_SET(sock_svr, &rdfs);

              retval = select(0, &rdfs, NULL, NULL, &tv);

             memset(buf, 0, sizeof(buf));

              if ( retval > 0 )

              {

                     recv_err = recv(sock_svr, buf, sizeof(buf), 0);

                     if (recv_err == 0)

                     {

                            closesocket(sock_svr);

                            break;

                     }

                     else

                     {

                            cout << buf;

                     }

              }

       }

       closesocket(sock);

       WSACleanup();

}

-------------------------------------Client-------------------------------------

#include<iostream>

#include<winsock2.h>

#include<windows.h>

using namespace std;

 

void main()

{

       WORD wVer;

       WSADATA wsaData;

       //WSAStartup

       wVer = MAKEWORD(1, 1);

       if ( WSAStartup(wVer, &wsaData) )

       {

              cout << "WSAStaup error!";

              return;

       }

       //SOCKET init

       SOCKET sock;

       if ( (sock = socket(AF_INET, SOCK_STREAM, 0)) < 0 )

       {

              cout << "socket error!";

              return;

       }

       //connect and send

       sockaddr_in sockadr;

       sockadr.sin_family = AF_INET;

       //Server在本机时启用环回接口,按理说可以捕捉到数据

       //用sniffer却捕捉不到数据,这应该是Windows在底层做了相应处理

       sockadr.sin_addr.S_un.S_addr = .net_addr("192.168.1.81");

       sockadr.sin_port = htons(6666);

       if ( connect(sock, (sockaddr*)&sockadr, sizeof(sockadr)) == SOCKET_ERROR )

       {

              cout << "connect error!";

              return;

       }

 

       //分片会在哪里进行?IP层?TCP层?

       char Test[2000];

       memset(Test, 65, sizeof(Test));

       Test[sizeof(Test) - 1] = ´B´;//这样才可看出是否全部传过去了

       if ( send(sock, Test, sizeof(Test), 0) == SOCKET_ERROR )

       {

              cout << "send error!";

              return;

       }

       //Sleep(1000);//等待Server的响应包再关闭

       //close and WSACleanup

       if ( closesocket(sock) )

       {

              cout << "closesocket error!";

              return;

       }

       if ( WSACleanup() )

       {

              cout << "WSACleanup error!";

              return;

       }

}

------------------------------------------------------------------------------------

 

把Client端的192.168.1.81改成运行Server端所在机器的IP地址。Client和Server不能在同一台机器(这一点我也很困惑),不然Sniffer捕捉不到数据。

Start SnifferPro(Capture->Start),接着运行Server,Client,程序一闪而过就结束了,Stop and Display SnifferPro(Capture->Stop and Display)。程序虽然一闪就结束了,没关系,我们要的东西都被Sniffer Capture了。

在面板中点击Decode,可以开始了。

注意上图,从NO.12到NO.21(当然,在你的机器执行时不见得是12-21)就是此次发送的全过程。12,13,14是建立连接的三次握手(DDoS攻击就有利用三次握手的漏洞),参见<<详解>>P176。15,16是数据传送(这里有个数据分片问题,下面会详细说明),17,19,20,21是终止连接的四次握手,18是响应包,响应15,16的数据传送。因为在我程序中send之后马上就进行closesocket,所以响应包反而到终止连接请求后面了,当然,只要在send之后Sleep(1000),就不会发生这种情况。开始我也疑惑怎么会有五次握手,在这里我没更正回来,就是为了启示大家,要小心分析。

下面开始分析数据包的结构:


延伸阅读

文章来源于领测软件测试网 https://www.ltesting.net/


关于领测软件测试网 | 领测软件测试网合作伙伴 | 广告服务 | 投稿指南 | 联系我们 | 网站地图 | 友情链接
版权所有(C) 2003-2010 TestAge(领测软件测试网)|领测国际科技(北京)有限公司|软件测试工程师培训网 All Rights Reserved
北京市海淀区中关村南大街9号北京理工科技大厦1402室 京ICP备10010545号-5
技术支持和业务联系:info@testage.com.cn 电话:010-51297073

软件测试 | 领测国际ISTQBISTQB官网TMMiTMMi认证国际软件测试工程师认证领测软件测试网