コード例 #1
0
ファイル: Net.cpp プロジェクト: genxinzou/svn-spring-archive
void CNet::SendRawPacket(int conn, unsigned char* data, int length, int packetNum)
{
    Connection* c=&connections[conn];

    *(int*)&tempbuf[0]=packetNum;
    *(int*)&tempbuf[4]=c->lastInOrder;
    int hsize=9;
    if(!c->waitingPackets.empty() && c->waitingPackets.find(c->lastInOrder+1)==c->waitingPackets.end()) {
        tempbuf[8]=1;
        *(int*)&tempbuf[9]=c->waitingPackets.begin()->first-1;
        hsize=13;
    } else {
        tempbuf[8]=0;
    }

    memcpy(&tempbuf[hsize],data,length);
//	if(rand()&7)
    if(sendto(mySocket,(char*)tempbuf,length+hsize,0,(sockaddr*)&c->addr,sizeof(c->addr))==SOCKET_ERROR) {
        if (IsFakeError())
            return;
        char test[100];
        sprintf(test,"Error sending data. %d",WSAGetLastError());
        handleerror(NULL,test,"SHUTDOWN ERROR", MBF_OK | MBF_INFO);
        exit(0);
    }
}
コード例 #2
0
void CRemoteConnection::SendRawPacket(const unsigned char* data, const unsigned length, const int packetNum)
{
	if (!active)
		return;

	const unsigned hsize = 9;
	unsigned char tempbuf[NETWORK_BUFFER_SIZE];
	*(int*)tempbuf = packetNum;
	*(int*)(tempbuf+4) = lastInOrder;
	if(!waitingPackets.empty() && waitingPackets.find(lastInOrder+1)==waitingPackets.end()){
		int nak = (waitingPackets.begin()->first-1) - lastInOrder;
		assert(nak >= 0);
		if (nak <= 255)
			*(unsigned char*)(tempbuf+8) = (unsigned char)nak;
		else
			*(unsigned char*)(tempbuf+8) = 255;
	}
	else {
		*(unsigned char*)(tempbuf+8) = 0;
	}

	memcpy(&tempbuf[hsize],data,length);

	if(sendto(*mySocket,(char*)tempbuf,length+hsize,0,(sockaddr*)&addr,sizeof(addr))==SOCKET_ERROR){
		if (IsFakeError())
			return;
		throw network_error("Error sending data: "+GetErrorMsg());
	}
	dataSent += length;
	sentOverhead += hsize;
}
コード例 #3
0
ファイル: UDPConnectedSocket.cpp プロジェクト: Gepard/spring
void UDPConnectedSocket::Send(const unsigned char* const buf, const unsigned dataLength) const
{
	int error = send(mySocket, (char*)buf, dataLength, 0);
	if (error == SOCKET_ERROR && !IsFakeError())
	{
		throw network_error(std::string("Error sending data to socket: ") + GetErrorMsg());
	}
}
コード例 #4
0
ファイル: UDPConnectedSocket.cpp プロジェクト: Gepard/spring
unsigned UDPConnectedSocket::Recv(unsigned char* buf, const unsigned bufLength) const
{
	const int data = recv(mySocket,(char*)buf,bufLength,0);
	if (data == SOCKET_ERROR)
	{
		if (IsFakeError())
		{
			return 0;
		}
		else
		{
			throw network_error(std::string("Error receiving data from socket: ") + GetErrorMsg());
		}
	}
	return (unsigned)data;
}
コード例 #5
0
ファイル: Net.cpp プロジェクト: genxinzou/svn-spring-archive
void CNet::Update(void)
{
    Uint64 t;
    t = SDL_GetTicks();
    curTime=float(t)/1000.f;
    if(playbackDemo)
        ReadDemoFile();
    if(onlyLocal) {
        return;
    }
    sockaddr_in from;
    socklen_t fromsize;
    fromsize=sizeof(from);
    int r;
    unsigned char inbuf[16000];
    if(connected)
        while(true) {
            if((r=recvfrom(mySocket,(char*)inbuf,16000,0,(sockaddr*)&from,&fromsize))==SOCKET_ERROR) {
                if (IsFakeError())
                    break;
                char test[500];
                sprintf(test,"Error receiving data. %i %d",(int)imServer,WSAGetLastError());
                handleerror(NULL,test,"SHUTDOWN ERROR",MBF_OK | MBF_INFO);
                exit(0);
            }
            int conn=ResolveConnection(&from);
            if(conn==-1) {
                if(waitOnCon && r>=12 && (*(int*)inbuf)==0 && (*(int*)&inbuf[4])==-1 && inbuf[8]==0 && inbuf[9]==NETMSG_ATTEMPTCONNECT && inbuf[11]==NETWORK_VERSION) {
                    conn=InitNewConn(&from,false,inbuf[10]);
                } else {
                    continue;
                }
            }
            inInitialConnect=false;
            int packetNum=(*(int*)inbuf);
            ProcessRawPacket(inbuf,r,conn);
        }

    for(int a=0; a<gs->activePlayers; ++a) {
        Connection* c=&connections[a];
        if(c->localConnection || !c->active)
            continue;
        std::map<int,Packet*>::iterator wpi;
        while((wpi=c->waitingPackets.find(c->lastInOrder+1))!=c->waitingPackets.end()) {		//process all in order packets that we have waiting
            if(c->readyLength+wpi->second->length>=NETWORK_BUFFER_SIZE) {
                logOutput.Print("Overflow in incoming network buffer");
                break;
            }
            memcpy(&c->readyData[c->readyLength],wpi->second->data,wpi->second->length);
            c->readyLength+=wpi->second->length;
            delete wpi->second;
            c->waitingPackets.erase(wpi);
            c->lastInOrder++;
        }
        if(inInitialConnect && c->lastSendTime<curTime-1) {		//server hasnt responded so try to send the connection attempt again
            SendRawPacket(a,c->unackedPackets[0]->data,c->unackedPackets[0]->length,0);
            c->lastSendTime=curTime;
        }

        if(c->lastSendTime<curTime-5 && !inInitialConnect) {		//we havent sent anything for a while so send something to prevent timeout
            SendData(NETMSG_HELLO);
        }
        if(c->lastSendTime<curTime-0.2f && !c->waitingPackets.empty()) {	//we have at least one missing incomming packet lying around so send a packet to ensure the other side get a nak
            SendData(NETMSG_HELLO);
        }
        if(c->lastReceiveTime < curTime-(inInitialConnect ? 40 : 30)) {		//other side has timed out
            c->active=false;
        }

        if(c->outgoingLength>0 && (c->lastSendTime < (curTime-0.2f+c->outgoingLength*0.01f) || c->lastSendFrame < gs->frameNum-1)) {
            FlushConnection(a);
        }
    }
}