#include "Player/Player.h" #include "../../Base/Utility.h" #include void SynchTime::StartFirstSynch() { #ifdef _DEBUG D_DEBUG("开始第一轮测试\n"); #endif mFirstSynchEle.SynchStart( 0 ); SendMsgToSync( 0 ); ACE_Time_Value currentTime = ACE_OS::gettimeofday(); msynchstarttime = currentTime.msec(); } bool SynchTime::EndSynch(unsigned int synchID ) { if ( synchID >= MAX_SYNCHARR_COUNT ) return false; //如果已经同步了,则不需要在进行同步时间的操作 if ( mSynchSuccess == true ) return false; do { if ( synchID == 0 ) { mFirstSynchEle.SynchEnd(); #ifdef _DEBUG D_DEBUG("接到客户端反馈 %s 反馈编号:%d 延迟:%d\n",pAttachPlayer->GetAccount(), synchID ,mFirstSynchEle.GetPassTime() ); #endif //如果第一轮同步不在合法的延迟范围内, if ( !mFirstSynchEle.IsValidScope() ) { StartSecondSynch(); } else { mdelayTime = mFirstSynchEle.GetPassTime(); mSynchSuccess = true;//同步成功 break; } } else { if ( synchID >= ARRAY_SIZE(mSynchEleArr) ) { D_ERROR( "SynchTime::EndSynch, synchID(%d) >= ARRAY_SIZE(mSynchEelArr)\n", synchID ); mSynchSuccess = false;//同步失败 return false; } SynchElement& SynEle = mSynchEleArr[synchID]; if ( !SynEle.IsSynchEnded() ) { //该同步元素同步结束 SynEle.SynchEnd(); #ifdef _DEBUG D_DEBUG("接到客户端反馈 %s 反馈编号:%d 延迟:%d\n",pAttachPlayer->GetAccount(), synchID ,mFirstSynchEle.GetPassTime() ); #endif unsigned int passTime = SynEle.GetPassTime(); //如果接到的返回消息在25ms以下,合法的范围,则同步时间完成 if ( SynEle.IsValidScope() ) { mSynchSuccess = true; mdelayTime = passTime; break; } //如果第二轮同步50次完成,则找出其中最小延迟作为客户端和服务器的延迟标准 if ( synchID == MAX_SYNCH_COUNT ) { for ( unsigned int i=1; i< MAX_SYNCHARR_COUNT; ++i ) { if ( i >= ARRAY_SIZE(mSynchEleArr) ) { D_ERROR( "SynchTime::EndSynch, i(%d) >= ARRAY_SIZE(mSynchEelArr)\n", i ); mSynchSuccess = false;//同步失败 return false; } SynchElement& tmpSynchEle = mSynchEleArr[i]; unsigned int passTime = tmpSynchEle.GetPassTime(); mdelayTime = mdelayTime>passTime ? passTime:mdelayTime; } mSynchSuccess = true; break; } } } } while( false ); if ( mSynchSuccess ) SynchClientTime(); return mSynchSuccess; } void SynchTime::StartSecondSynch() { for ( unsigned int i = 1; i< MAX_SYNCHARR_COUNT; ++i ) { if ( i >= ARRAY_SIZE(mSynchEleArr) ) { D_ERROR( "SynchTime::StartSecondSynch, i(%d) >= ARRAY_SIZE(mSynchEelArr)\n", i ); return; } SynchElement& mSynEle = mSynchEleArr[i]; mSynEle.SynchStart( i ); SendMsgToSync( i ); } ACE_Time_Value currentTime = ACE_OS::gettimeofday(); msynchstarttime = currentTime.msec(); } void SynchTime::SendMsgToSync(unsigned int synID ) { if ( !pAttachPlayer ) return; GCSrvSynchTime synchMsg; synchMsg.timeSynchID = synID; NewSendPlayerPkg( GCSrvSynchTime, pAttachPlayer, synchMsg ); //MsgToPut* pNewMsg = CreatePlayerPkg( GCSrvSynchTime, pAttachPlayer, synchMsg ); //pAttachPlayer->SendPkgToPlayer( pNewMsg ); } void SynchTime::SynchClientTime() { if ( !pAttachPlayer ) return; GCSynchClientTime synchMsg; StructMemSet( synchMsg, 0x0, sizeof(synchMsg) ); synchMsg.delayTime = mdelayTime; time_t now = ACE_OS::time(); tm nowTM; ACE_OS::localtime_r(&now, &nowTM); synchMsg.srvTimeSize = (unsigned int)strftime(synchMsg.srvTime, sizeof(synchMsg.srvTime),"%x/%X", &nowTM ); NewSendPlayerPkg( GCSynchClientTime, pAttachPlayer, synchMsg ); //MsgToPut* pNewMsg = CreatePlayerPkg( GCSynchClientTime, pAttachPlayer, synchMsg ); //pAttachPlayer->SendPkgToPlayer( pNewMsg ); #ifdef _DEBUG D_DEBUG("同步客户端的时间 delay:%d date:%s Time:%d\n",synchMsg.delayTime,synchMsg.srvTime,time(NULL) ); #endif }