取得ping的时间问题,请网络高手看看

xiaopan 2011-09-12 02:43:40
UINT SetSpeedThread(LPVOID pParam)
{
int nConnectTime = 0;
int i;

i = ((St_In_Param *)pParam)->nIndex;
memset(pIp[i], 0, sizeof(pIp[i]));

strcpy(pIp[i], ((St_In_Param *)pParam)->pIp);

nConnectTime = GetPingTime(pIp[i], ((St_In_Param *)pParam)->nIndex);
return 0;
}

主函数:
for (int i = 0; i < m_ServerCount; i++)
{
s_InParam[i].nIndex = i;
memset(s_InParam[i].pIp, 0, sizeof(s_InParam[i].pIp));
strcpy(s_InParam[i].pIp, m_ServerIp[i]);
thRead = AfxBeginThread(SetSpeedThread, &s_InParam[i]);
}

int GetPingTime ( char* lpDestIp, int nIndex )
{
int nTime=1000;

//if (strcmp(lpDestIp, "183.63.2.230") == 0)
//{
// 设置目标地址
//SOCKADDR_IN DestSockAddr ;
DestSockAddr[nIndex].sin_family = AF_INET ;
DestSockAddr[nIndex].sin_addr.s_addr = inet_addr( lpDestIp ) ;
DestSockAddr[nIndex].sin_port = htons ( 0 ) ;
// 创建ICMP回显请求包
memset(ICMPPack[nIndex], 0, sizeof(ICMPPack[nIndex]));
ICMPPack[nIndex][ICMP_PACK_SIZE] = 0 ;
pICMPHeader[nIndex] = (PICMP_HEADER)ICMPPack[nIndex] ;
pICMPHeader[nIndex]->bType = 8 ;
pICMPHeader[nIndex]->bCode = 0 ;
pICMPHeader[nIndex]->nId = (USHORT)::GetCurrentProcessId() ;
pICMPHeader[nIndex]->nCheckSum = 0 ;
pICMPHeader[nIndex]->nTimeStamp = 0 ;
memset ( &(ICMPPack[nIndex][ICMP_HEADER_SIZE]), 'E', ICMP_DATA_SIZE ) ; // 填充数据部分,内容任意
//WaitForSingleObject(eventSet, 1000);
Sleep(1000);
nElapse[nIndex] = 0;
// 初始化WinSock库
//WORD wVersionRequested = MAKEWORD( 2, 2 );
//WSADATA wsaData;
wVersionRequested[nIndex] = MAKEWORD( 2, 2 );
if ( WSAStartup( wVersionRequested[nIndex], &wsaData[nIndex] ) != 0 )
{
nElapse[nIndex] = -1;
SetTimeFormat(nIndex);
return -1 ;
}

// 创建原始套接字
RawSock[nIndex] = socket ( AF_INET, SOCK_RAW, IPPROTO_ICMP ) ;
if ( RawSock[nIndex] == INVALID_SOCKET )
{
printf ( "Create socket error!\n" ) ;
nElapse[nIndex] = -1;
SetTimeFormat(nIndex);
return -1 ;
}

// 设置接收超时为1秒
//int nTime = 1000 ;
int ret = ::setsockopt ( RawSock[nIndex], SOL_SOCKET,SO_RCVTIMEO, (char*)&nTime, sizeof(nTime));

//char szRecvBuf [ DEF_BUF_SIZE] ;
//SOCKADDR_IN SourSockAddr ;
//for ( int i = 0 ; i < 4; i++ )
{

pICMPHeader[nIndex]->nCheckSum = 0 ; // 初始时校验值为0
pICMPHeader[nIndex]->nSequence = 0 ; //=i // 序号
pICMPHeader[nIndex]->nTimeStamp = ::GetTickCount() ;// 当前时间
Sleep(100);
/*char t[20], pIndex[3];
memset(t, 0 , sizeof(t));
memset(pIndex, 0 , sizeof(pIndex));
//itoa(nIndex, pIndex, 10);
itoa(pICMPHeader[nIndex]->nTimeStamp, t, 10);
//strcat(t, pIndex);
AfxMessageBox(t);*/

// 计算校验值,校验值要在ICMP数据报创建完才能计算
pICMPHeader[nIndex]->nCheckSum = GetCheckSum ( (LPBYTE)ICMPPack[nIndex], ICMP_PACK_SIZE ) ;

// 发送ICMP数据包
int nRet = ::sendto ( RawSock[nIndex], ICMPPack[nIndex], ICMP_PACK_SIZE,0,(SOCKADDR*)&DestSockAddr[nIndex], sizeof(DestSockAddr[nIndex]) ) ;
if ( nRet == SOCKET_ERROR )
{
printf ( "sendto error!\n" ) ;
nElapse[nIndex] = -1;
SetTimeFormat(nIndex);
return -1 ;
}

// 接收ICMP响应
int nLen = sizeof(SourSockAddr[nIndex]) ;
nRet = ::recvfrom ( RawSock[nIndex], szRecvBuf[nIndex], DEF_BUF_SIZE,0,(SOCKADDR*)&SourSockAddr[nIndex], &nLen ) ;
if ( nRet == SOCKET_ERROR )
{
if ( ::WSAGetLastError() == WSAETIMEDOUT )
{
printf ( "Request Timeout\n" ) ;
nElapse[nIndex] = -1;
//if (i == 3)
SetTimeFormat(nIndex);
return -1;
//else
//continue ;
}
else
{
printf ( "recvfrom error!\n" ) ;
nElapse[nIndex] = -1;
SetTimeFormat(nIndex);
return -1 ;
}
}

// 计算ICMP数据报的时间差
Sleep(100);
int ttTT = ::GetTickCount();
nElapse[nIndex] = ttTT - pICMPHeader[nIndex]->nTimeStamp ;
SetTimeFormat(nIndex);
::Sleep ( 1000 ) ;
}
SetTimeFormat(nIndex);

closesocket ( RawSock[nIndex] ) ;
WSACleanup () ;

return 0 ;
}
...全文
106 10 打赏 收藏 转发到动态 举报
写回复
用AI写文章
10 条回复
切换为时间正序
请发表友善的回复…
发表回复
xiaopan 2011-09-21
  • 打赏
  • 举报
回复
最终还是用互诉+全局变量数组解决。谢谢各位
zwfgdlc 2011-09-12
  • 打赏
  • 举报
回复
直接用IcmpSendEcho()呢?
gameslq 2011-09-12
  • 打赏
  • 举报
回复
[Quote=引用 7 楼 xiaopan 的回复:]

引用 5 楼 gameslq 的回复:
// 接收ICMP响应 部份要进行检验是不是自己发出的icmp报
ICMPPack[nIndex] ->nId = ::GetCurrentProcessId()
如果这步步做,很可能会直接返回


刚才试了,还是不行,
主要是多线程运行时,都是gettickcount函数,得到的都是同样的数据,我加了互诉之后,数据就变了,
觉得还是这个问……
[/Quote]
不太了解你的软件架构,多个线程调用一个函数是有问题,
但 ICMPPack[nIndex] ->nId = ::GetCurrentProcessId()
也要加上才合理
xiaopan 2011-09-12
  • 打赏
  • 举报
回复
[Quote=引用 5 楼 gameslq 的回复:]
// 接收ICMP响应 部份要进行检验是不是自己发出的icmp报
ICMPPack[nIndex] ->nId = ::GetCurrentProcessId()
如果这步步做,很可能会直接返回
[/Quote]

刚才试了,还是不行,
主要是多线程运行时,都是gettickcount函数,得到的都是同样的数据,我加了互诉之后,数据就变了,
觉得还是这个问题,线程访问同一函数,返回的是同一的数据,需要互诉才可以。
xiaopan 2011-09-12
  • 打赏
  • 举报
回复
创建了个线程critical_section.Lock(),貌似有用,呵呵
gameslq 2011-09-12
  • 打赏
  • 举报
回复
// 接收ICMP响应 部份要进行检验是不是自己发出的icmp报
ICMPPack[nIndex] ->nId = ::GetCurrentProcessId()
如果这步步做,很可能会直接返回
xiaopan 2011-09-12
  • 打赏
  • 举报
回复
int ttTT = ::GetTickCount();
char t[20]
memset(t, 0 , sizeof(t));
memset(pIndex, 0 , sizeof(pIndex));
itoa(ttTT, t, 10);
AfxMessageBox(t);
另外,在线程函数里面,弹出的ttTT,数据是一样的。我创建了多个线程。
xiaopan 2011-09-12
  • 打赏
  • 举报
回复
[Quote=引用 2 楼 gameslq 的回复:]
修改下:
// 创建ICMP回显请求包
memset(ICMPPack[nIndex], 0, sizeof(ICMPPack[nIndex]));
ICMPPack[nIndex][ICMP_PACK_SIZE] = 0 ;
pICMPHeader[nIndex] = (PICMP_HEADER)ICMPPack[nIndex] ;
pICMPHeader[nIndex]->……
[/Quote]
老大,我那程序里面已经有了:
//for ( int i = 0 ; i < 4; i++ )
{

pICMPHeader[nIndex]->nCheckSum = 0 ; // 初始时校验值为0
pICMPHeader[nIndex]->nSequence = 0 ; //=i // 序号
pICMPHeader[nIndex]->nTimeStamp = ::GetTickCount() ;// 当前时间


我想,可能是多线程调用gettickcount的时候,得到的是同一个地址数据。
gameslq 2011-09-12
  • 打赏
  • 举报
回复
修改下:
// 创建ICMP回显请求包
memset(ICMPPack[nIndex], 0, sizeof(ICMPPack[nIndex]));
ICMPPack[nIndex][ICMP_PACK_SIZE] = 0 ;
pICMPHeader[nIndex] = (PICMP_HEADER)ICMPPack[nIndex] ;
pICMPHeader[nIndex]->bType = 8 ;
pICMPHeader[nIndex]->bCode = 0 ;
pICMPHeader[nIndex]->nId = (USHORT)::GetCurrentProcessId() ;
pICMPHeader[nIndex]->nCheckSum = 0 ;
pICMPHeader[nIndex]->nTimeStamp = 0 ; 改为
pICMPHeader[nIndex]->nTimeStamp = ::GetTickCount();

然后返回ICMP包后
int ttTT = ::GetTickCount();
nElapse[nIndex] = ttTT - pICMPHeader[nIndex]->nTimeStamp ;
即可。

xiaopan 2011-09-12
  • 打赏
  • 举报
回复
现在的问题是:GetPingTime 函数运行时,所有线程得到的时间都是一样的。就是运行到:gettickcount得到的数据全部都是一样的,我用afxmessagebox将数据显示出来,结果所有线程的数据都是一样的,各位有什么方法解决一下。

18,355

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC 网络编程
c++c语言开发语言 技术论坛(原bbs)
社区管理员
  • 网络编程
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧