Пример #1
0
    Client(bool server = false)
    {
        peer = RakNet::RakPeerInterface::GetInstance();

        if(!server)
        {
            RakNet::SocketDescriptor sd;
            peer->Startup(1, &sd, 1);

            Connect("127.0.0.1");

            printf("Starting client. Enter ~ to close.\n");

            std::thread broadcastThread(&Client::Broadcast, this);
            broadcastThread.detach();
        }
        else
        {
            RakNet::SocketDescriptor sd(SERVER_PORT, 0);
            peer->Startup(MAX_CLIENTS, &sd, 1);

            peer->SetMaximumIncomingConnections(MAX_CLIENTS);

            printf("Starting server. Enter ~ to close.\n");

            //std::thread waitThread(&Client::Wait, this);
            //waitThread.detach();
            std::thread broadcastThread(&Client::Broadcast, this);
            broadcastThread.detach();
        }

        std::thread listenThread(&Client::Listen, this);
        listenThread.join();
    }
Пример #2
0
int main(void)
{
	RakNet::RakPeerInterface *peer = RakNet::RakPeerInterface::GetInstance();
	bool isServer;
	RakNet::Packet *packet;

	RakNet::SocketDescriptor sd( SERVER_PORT,0 );
	peer->Startup( MAX_CLIENTS, &sd, 1 );
	isServer = true;

	printf( "Starting the server.\n" );
	// We need to let the server accept incoming connections from the clients
	peer->SetMaximumIncomingConnections( MAX_CLIENTS );

	while (1)
	{
		for( packet=peer->Receive(); packet; peer->DeallocatePacket(packet), packet=peer->Receive() )
		{
			handlePacket( packet, peer );
		}
	}

	RakNet::RakPeerInterface::DestroyInstance( peer );

	return 0;
}
Пример #3
0
int main(void)
{
 	RakNet::RakPeerInterface *rakPeer = RakNet::RakPeerInterface::GetInstance();
 	RakNet::SocketDescriptor sd(60000,0);
 	rakPeer->Startup(128,&sd,1);
 	rakPeer->SetMaximumIncomingConnections(128);

	RakNet::TelnetTransport tt;
	TestCommandServer(&tt, 23, rakPeer); // Uncomment to use Telnet as a client.  Telnet uses port 23 by default.

// 	RakNet::RakNetTransport2 rt2;
// 	rakPeer->AttachPlugin(&rt2);
// 	TestCommandServer(&rt2, 60000,rakPeer); // Uncomment to use RakNet as a client

	return 1;
}
Пример #4
0
unsigned int PingRakNetServer(const char *addr, unsigned short port)
{
    RakNet::Packet *packet;
    bool done = false;
    RakNet::TimeMS time = PING_UNREACHABLE;

    RakNet::SocketDescriptor socketDescriptor{0, ""};
    RakNet::RakPeerInterface *peer = RakNet::RakPeerInterface::GetInstance();
    peer->Startup(1, &socketDescriptor, 1);
    if (!peer->Ping(addr, port, false))
        return time;
    RakNet::TimeMS start = RakNet::GetTimeMS();
    while (!done)
    {
        RakNet::TimeMS now = RakNet::GetTimeMS();
        if (now - start >= PING_UNREACHABLE)
            break;

        packet = peer->Receive();
        if (!packet)
            continue;

        switch (packet->data[0])
        {
            case ID_DISCONNECTION_NOTIFICATION:
            case ID_CONNECTION_LOST:
                done = true;
                break;
            case ID_CONNECTED_PING:
            case ID_UNCONNECTED_PONG:
            {
                RakNet::BitStream bsIn(&packet->data[1], packet->length, false);
                bsIn.Read(time);
                time = now - time;
                done = true;
                break;
            }
            default:
                break;
        }
        peer->DeallocatePacket(packet);
    }

    peer->Shutdown(0);
    RakNet::RakPeerInterface::DestroyInstance(peer);
    return time > PING_UNREACHABLE ? PING_UNREACHABLE : time;
}
Пример #5
0
void* Client::startNetworkTrd(void* data)
{
	
	client_data* clnt_data = (struct client_data *)data;

	Client* clnt = clnt_data->instance;
	const char* h = clnt_data->address;
	int port = clnt_data->port;

	RakNet::RakPeerInterface* inst = RakNet::RakPeerInterface::GetInstance();
	inst->AllowConnectionResponseIPMigration(false);

	RakNet::Packet *packet;
	RakNet::SocketDescriptor sd(port + 100, 0);
	inst->Startup(1, &sd, 1);
	inst->Connect(h, port, 0, 0);
	clnt->setPeer(inst);

	//LOG(INFO) << "[Client]SOcket was configured...";

	struct timespec req;
	req.tv_sec = 0;
	req.tv_nsec = 25000L;
	
	RakNet::RPC4 rpc;
	inst->AttachPlugin(&rpc);
	clnt->setRPC(&rpc);
	clnt->setRunning(true);
		
	while (clnt->getRunning())
	{
		nanosleep(&req, NULL);
		for (packet = clnt->getPeer()->Receive(); packet; clnt->getPeer()->DeallocatePacket(packet), packet = clnt->getPeer()->Receive())
		{
			clnt->getListener()->handle(packet);
		}
	}
	
	clnt->getPeer()->CloseConnection(*clnt->getServerAddr(), true);
	clnt->getPeer()->Shutdown(10.0);
	RakNet::RakPeerInterface::DestroyInstance(clnt->getPeer());
}
Пример #6
0
bool
CProxy::start(const std::string&                  sListenIP,
              ushort                              uListenPort,
              const std::string&                  sLoginSrvIP,
              ushort                              uLoginSrvPort,
              const std::vector<s_serverInfos>&   vecAreas,
              ushort                              uMaxConnections)
{
  // Check if listen address is correctly formated
  if (!m_listenAddress.FromStringExplicitPort(sListenIP.c_str(), uListenPort))
  {
    log_ERROR("Invalid listen address. Aborting.");
    return false;
  }


  // Start listen interface
  RakNet::SocketDescriptor listenSocket(uListenPort, sListenIP.c_str());
  m_pListenInterface = RakNet::RakPeerInterface::GetInstance();

  if (m_pListenInterface->Startup(uMaxConnections, &listenSocket, 1) != RakNet::RAKNET_STARTED)
  {
    log_ERROR("Failed to startup Raknet interface. Aborting.");
    stop();
    return false;
  }

  m_pListenInterface->SetMaximumIncomingConnections(uMaxConnections);
  ff::write(pan::notice, "Started listening on ", sListenIP, ":", uListenPort, ".");
  ff::write(pan::notice, "Accepting max ", uMaxConnections, " connections.");

  ushort uTmpPort = 49777;

  // Start login server interface
  {
    // Check if login server address is correctly formated
    if (!m_loginSrvAddress.FromStringExplicitPort(sLoginSrvIP.c_str(), uLoginSrvPort))
    {
      log_ERROR("Invalid login server address. Aborting.");
      stop();
      return false;
    }

    RakNet::SocketDescriptor loginSocketDesc(++uTmpPort, NULL);

	  while (RakNet::SocketLayer::IsPortInUse(loginSocketDesc.port, loginSocketDesc.hostAddress, loginSocketDesc.socketFamily))
      loginSocketDesc.port = uTmpPort++;
      
    // Create and startup login server interface
    m_pLoginSrvInterface = RakNet::RakPeerInterface::GetInstance();

	  if (m_pLoginSrvInterface->Startup(1, &loginSocketDesc, 1) != RakNet::RAKNET_STARTED)
    {
      log_ERROR("Failed to startup login server interface.");
      stop();
      return false;
    }

    int latency = ping(m_pLoginSrvInterface, sLoginSrvIP, uLoginSrvPort);
    
    if (latency < 0)
      ff::write(pan::warning, "Failed to ping login server (", sLoginSrvIP, ":", uLoginSrvPort, ").");
    else
      ff::write(pan::notice, "Pinged login server (", sLoginSrvIP, ":", uLoginSrvPort, ") - ", latency, "ms.");

    // Attempt connection
    if (m_pLoginSrvInterface->Connect(sLoginSrvIP.c_str(), uLoginSrvPort, NULL, 0) != RakNet::CONNECTION_ATTEMPT_STARTED)
    {
      ff::write(pan::error, "Connection to login server (", sLoginSrvIP, ":", uLoginSrvPort, ") failed.");
      stop();
      return false;
    }

    m_pLoginSrvInterface->SetOccasionalPing(true);
  }

  // Connect to area servers
  for (std::vector<s_serverInfos>::const_iterator it = vecAreas.begin();
       it != vecAreas.end();
       it++)
  {
    RakNet::SocketDescriptor areaSocketDesc(uTmpPort++, NULL);

	  while (RakNet::SocketLayer::IsPortInUse(areaSocketDesc.port, areaSocketDesc.hostAddress, areaSocketDesc.socketFamily))
      areaSocketDesc.port = uTmpPort++;

    RakNet::RakPeerInterface* pAreaItf = RakNet::RakPeerInterface::GetInstance();

	  if (pAreaItf->Startup(1, &areaSocketDesc, 1) != RakNet::RAKNET_STARTED)
    {
      log_ERROR("Failed to startup an area server interface.");
      continue;
    }

    if (pAreaItf->Connect((*it).m_srvIP.c_str(), (*it).m_srvPort, NULL, 0) != RakNet::CONNECTION_ATTEMPT_STARTED)
    {
      ff::write(pan::error, "Connection attempt to area server (", (*it).m_srvIP, ":", (*it).m_srvPort, ") failed.");
      continue;
    }

    pAreaItf->SetOccasionalPing(true);

    // TODO: Do something here with this connection
  }


  // Proxy server started successfuly
  m_pListenInterface->AttachPlugin(this);
  m_bStarted = true;

  m_bQuit = false;
  m_pUpdateThread = new boost::thread(FastDelegate0<>(this, &CProxy::updateThread));

  return m_bStarted;
}
Пример #7
0
int main(int argc, char **argv)
{
    const char *DEFAULT_SERVER_ADDRESS="test.dnsalias.net";
    const unsigned short DEFAULT_SERVER_PORT=60000;

    const char *serverAddress;
    unsigned short serverPort;


#ifndef _DEBUG
    // Only use DEFAULT_SERVER_ADDRESS for debugging
    if (argc<2)
    {
        PrintHelp();
        return false;
    }
#endif

    if (argc<2) serverAddress=DEFAULT_SERVER_ADDRESS;
    else serverAddress=argv[1];

    if (argc<3) serverPort=DEFAULT_SERVER_PORT;
    else serverPort=atoi(argv[2]);

    // ---- RAKPEER -----
    RakNet::RakPeerInterface *rakPeer;
    rakPeer=RakNet::RakPeerInterface::GetInstance();
    static const unsigned short clientLocalPort=0;
    RakNet::SocketDescriptor sd(clientLocalPort,0); // Change this if you want
    RakNet::StartupResult sr = rakPeer->Startup(1,&sd,1); // Change this if you want
    rakPeer->SetMaximumIncomingConnections(0); // Change this if you want
    if (sr!=RakNet::RAKNET_STARTED)
    {
        printf("Startup failed. Reason=%i\n", (int) sr);
        return 1;
    }

    RakNet::CloudClient cloudClient;
    rakPeer->AttachPlugin(&cloudClient);

    RakNet::ConnectionAttemptResult car = rakPeer->Connect(serverAddress, serverPort, 0, 0);
    if (car==RakNet::CANNOT_RESOLVE_DOMAIN_NAME)
    {
        printf("Cannot resolve domain name\n");
        return 1;
    }

    printf("Connecting to %s...\n", serverAddress);
    bool didRebalance=false; // So we only reconnect to a lower load server once, for load balancing
    RakNet::Packet *packet;
    while (1)
    {
        for (packet=rakPeer->Receive(); packet; rakPeer->DeallocatePacket(packet), packet=rakPeer->Receive())
        {
            switch (packet->data[0])
            {
            case ID_CONNECTION_LOST:
                printf("Lost connection to server.\n");
                return 1;
            case ID_CONNECTION_ATTEMPT_FAILED:
                printf("Failed to connect to server at %s.\n", packet->systemAddress.ToString(true));
                return 1;
            case ID_REMOTE_SYSTEM_REQUIRES_PUBLIC_KEY:
            case ID_OUR_SYSTEM_REQUIRES_SECURITY:
            case ID_PUBLIC_KEY_MISMATCH:
            case ID_INVALID_PASSWORD:
            case ID_CONNECTION_BANNED:
                // You won't see these unless you modified CloudServer
                printf("Server rejected the connection.\n");
                return 1;
            case ID_INCOMPATIBLE_PROTOCOL_VERSION:
                printf("Server is running an incompatible RakNet version.\n");
                return 1;
            case ID_NO_FREE_INCOMING_CONNECTIONS:
                printf("Server has no free connections\n");
                return 1;
            case ID_IP_RECENTLY_CONNECTED:
                printf("Recently connected. Retrying.");
                rakPeer->Connect(serverAddress, serverPort, 0, 0);
                break;
            case ID_CONNECTION_REQUEST_ACCEPTED:
                printf("Connected to server.\n");
                UploadInstanceToCloud(&cloudClient, packet->guid);
                GetClientSubscription(&cloudClient, packet->guid);
                GetServers(&cloudClient, packet->guid);
                break;
            case ID_CLOUD_GET_RESPONSE:
            {
                RakNet::CloudQueryResult cloudQueryResult;
                cloudClient.OnGetReponse(&cloudQueryResult, packet);
                unsigned int rowIndex;
                const bool wasCallToGetServers=cloudQueryResult.cloudQuery.keys[0].primaryKey=="CloudConnCount";
                printf("\n");
                if (wasCallToGetServers)
                    printf("Downloaded server list. %i servers.\n", cloudQueryResult.rowsReturned.Size());
                else
                    printf("Downloaded client list. %i clients.\n", cloudQueryResult.rowsReturned.Size());

                unsigned short connectionsOnOurServer=65535;
                unsigned short lowestConnectionsServer=65535;
                RakNet::SystemAddress lowestConnectionAddress;

                for (rowIndex=0; rowIndex < cloudQueryResult.rowsReturned.Size(); rowIndex++)
                {
                    RakNet::CloudQueryRow *row = cloudQueryResult.rowsReturned[rowIndex];
                    if (wasCallToGetServers)
                    {
                        unsigned short connCount;
                        RakNet::BitStream bsIn(row->data, row->length, false);
                        bsIn.Read(connCount);
                        printf("%i. Server found at %s with %i connections\n", rowIndex+1, row->serverSystemAddress.ToString(true), connCount);

                        unsigned short connectionsExcludingOurselves;
                        if (row->serverGUID==packet->guid)
                            connectionsExcludingOurselves=connCount-1;
                        else
                            connectionsExcludingOurselves=connCount;


                        // Find the lowest load server (optional)
                        if (packet->guid==row->serverGUID)
                        {
                            connectionsOnOurServer=connectionsExcludingOurselves;
                        }
                        else if (connectionsExcludingOurselves < lowestConnectionsServer)
                        {
                            lowestConnectionsServer=connectionsExcludingOurselves;
                            lowestConnectionAddress=row->serverSystemAddress;
                        }
                    }
                    else
                    {
                        printf("%i. Client found at %s", rowIndex+1, row->clientSystemAddress.ToString(true));
                        if (row->clientGUID==rakPeer->GetMyGUID())
                            printf(" (Ourselves)");
                        RakNet::BitStream bsIn(row->data, row->length, false);
                        RakNet::RakString clientData;
                        bsIn.Read(clientData);
                        printf(" Data: %s", clientData.C_String());
                        printf("\n");
                    }
                }


                // Do load balancing by reconnecting to lowest load server (optional)
                if (didRebalance==false && wasCallToGetServers && cloudQueryResult.rowsReturned.Size()>0 && connectionsOnOurServer>lowestConnectionsServer)
                {
                    printf("Reconnecting to lower load server %s\n", lowestConnectionAddress.ToString(false));

                    rakPeer->CloseConnection(packet->guid, true);
                    // Wait for the thread to close, otherwise will immediately get back ID_CONNECTION_ATTEMPT_FAILED because no free outgoing connection slots
                    // Alternatively, just call Startup() with 2 slots instead of 1
                    RakSleep(500);

                    rakPeer->Connect(lowestConnectionAddress.ToString(false), lowestConnectionAddress.GetPort(), 0, 0);
                    didRebalance=true;
                }

                cloudClient.DeallocateWithDefaultAllocator(&cloudQueryResult);
            }

            break;
            case ID_CLOUD_SUBSCRIPTION_NOTIFICATION:
            {
                bool wasUpdated;
                RakNet::CloudQueryRow cloudQueryRow;
                cloudClient.OnSubscriptionNotification(&wasUpdated, &cloudQueryRow, packet, 0 );
                if (wasUpdated)
                    printf("New client at %s\n", cloudQueryRow.clientSystemAddress.ToString(true));
                else
                    printf("Lost client at %s\n", cloudQueryRow.clientSystemAddress.ToString(true));
                cloudClient.DeallocateWithDefaultAllocator(&cloudQueryRow);
            }

            break;
            }
        }

        // Any additional client processing can go here
        RakSleep(30);
    }

    RakNet::RakPeerInterface::DestroyInstance(rakPeer);
    return 0;
}
Пример #8
0
int main(void)
{
	// Pointers to the interfaces of our server and client.
	// Note we can easily have both in the same program
	RakNet::RakPeerInterface *client;
	RakNet::RakPeerInterface *server;
	bool b;
	char str[256];
	char serverPort[30], clientPort[30];
	RakNet::TimeMS quitTime;
	// Holds packets
	RakNet::Packet* p;	

	printf("A client / server sample showing how clients can broadcast offline packets\n");
	printf("to find active servers.\n");
	printf("Difficulty: Beginner\n\n");

	printf("Instructions:\nRun one or more servers on the same port.\nRun a client and it will get pongs from those servers.\n");
	printf("Run as (s)erver or (c)lient?\n");
	Gets(str, sizeof(str));

	if (str[0]=='s' || str[0]=='S')
	{
		client=0;
		server=RakNet::RakPeerInterface::GetInstance();
		// A server
		printf("Enter the server port\n");
		Gets(serverPort,sizeof(serverPort));
		if (serverPort[0]==0)
			strcpy(serverPort, "60001");

		printf("Starting server.\n");
		// The server has to be started to respond to pings.
		RakNet::SocketDescriptor socketDescriptor(atoi(serverPort),0);
		socketDescriptor.socketFamily=AF_INET; // Only IPV4 supports broadcast on 255.255.255.255
		b = server->Startup(2, &socketDescriptor, 1)==RakNet::RAKNET_STARTED;
		server->SetMaximumIncomingConnections(2);
		if (b)
			printf("Server started, waiting for connections.\n");
		else
		{ 
			printf("Server failed to start.  Terminating.\n");
			exit(1);
		}
	}
	else
	{
		client=RakNet::RakPeerInterface::GetInstance();
		server=0;

		// Get our input
		printf("Enter the client port to listen on, or 0\n");
		Gets(clientPort,sizeof(clientPort));
		if (clientPort[0]==0)
			strcpy(clientPort, "60000");
		printf("Enter the port to ping\n");
		Gets(serverPort,sizeof(serverPort));
		if (serverPort[0]==0)
			strcpy(serverPort, "60001");
		RakNet::SocketDescriptor socketDescriptor(atoi(clientPort),0);
		socketDescriptor.socketFamily=AF_INET; // Only IPV4 supports broadcast on 255.255.255.255
		client->Startup(1, &socketDescriptor, 1);

		// Connecting the client is very simple.  0 means we don't care about
		// a connectionValidationInteger, and false for low priority threads
		// All 255's mean broadcast
		client->Ping("255.255.255.255", atoi(serverPort), false);

		printf("Pinging\n");
	}

	printf("How many seconds to run this sample for?\n");
	Gets(str, sizeof(str));
	if (str[0]==0)
	{
		printf("Defaulting to 5 seconds\n");
		quitTime = RakNet::GetTimeMS() + 5000;
	}
	else
		quitTime = RakNet::GetTimeMS() + atoi(str) * 1000;

	// Loop for input
	while (RakNet::GetTimeMS() < quitTime)
	{
		if (server)
			p = server->Receive();
		else 
			p = client->Receive();

		if (p==0)
		{
			RakSleep(30);
			continue;
		}
		if (server)
			server->DeallocatePacket(p);
		else
		{
			if (p->data[0]==ID_UNCONNECTED_PONG)
			{
				RakNet::TimeMS time;
				RakNet::BitStream bsIn(p->data,p->length,false);
				bsIn.IgnoreBytes(1);
				bsIn.Read(time);
				printf("Got pong from %s with time %i\n", p->systemAddress.ToString(), RakNet::GetTimeMS() - time);
			}
			else if (p->data[0]==ID_UNCONNECTED_PING)
			{
				printf("ID_UNCONNECTED_PING from %s\n",p->guid.ToString());
			}
			else if (p->data[0]==ID_UNCONNECTED_PING_OPEN_CONNECTIONS)
			{
				printf("ID_UNCONNECTED_PING_OPEN_CONNECTIONS from %s\n",p->guid.ToString());
			}
			client->DeallocatePacket(p);
		}

		RakSleep(30);
	}

	// We're done with the network
	if (server)
		RakNet::RakPeerInterface::DestroyInstance(server);
	if (client)
		RakNet::RakPeerInterface::DestroyInstance(client);

	return 0;
}
Пример #9
0
int main()
{
	char str[512];
	RakNet::RakPeerInterface *peer = RakNet::RakPeerInterface::GetInstance();
	bool isServer;
	RakNet::Packet *packet;

	printf("(C)lient or (S)erver?\n");
	gets(str);

	if ((str[0] == 'c') || (str[0] == 'C'))
	{
		RakNet::SocketDescriptor sd;
		peer->Startup(1, &sd, 1);
		isServer = false;
	}

	else
	{
		RakNet::SocketDescriptor sd(SERVER_PORT, 0);
		peer->Startup(MAX_CLIENTS, &sd, 1);
		isServer = true;
	}

	if (isServer)
	{
		printf("Starting the server.\n");
		peer->SetMaximumIncomingConnections(MAX_CLIENTS);
	}
	else
	{
		printf("Enter server IP or hit enter for default: 127.0.0.1\n");
		gets(str);
		if (str[0] == 0)
		{
			strcpy(str, "127.0.0.1");
		}

		printf("Starting the client.\n");
		peer->Connect(str, SERVER_PORT, 0, 0);
	}

	while (1)
	{
		for (packet = peer->Receive(); packet; peer->DeallocatePacket(packet), packet = peer->Receive())
		{
			switch (packet->data[0])
			{
			case ID_REMOTE_DISCONNECTION_NOTIFICATION:
				printf("Another client has dosconnected\n");
				break;

			case ID_REMOTE_CONNECTION_LOST:
				printf("Another client has lost the connection\n");
				break;

			case ID_REMOTE_NEW_INCOMING_CONNECTION:
				printf("Another client has connected\n");
				break;

			case ID_CONNECTION_REQUEST_ACCEPTED:
				printf("Our connection request has been accepted.\n");
				{
					RakNet::BitStream bsOut;
					bsOut.Write((RakNet::MessageID)ID_GAME_MESSAGE_1);
					bsOut.Write("Hello World");
					peer->Send(&bsOut, HIGH_PRIORITY, RELIABLE_ORDERED, 0, packet->systemAddress, false);
				}
				break;

			case ID_NEW_INCOMING_CONNECTION:
				printf("A connection is incoming.\n");
				break;

			case ID_NO_FREE_INCOMING_CONNECTIONS:
				printf("The server is full.\n");
				break;

			case ID_DISCONNECTION_NOTIFICATION:
				{
					if (isServer)
					{
						printf("A client has disconnected.\n");
					}
					else
					{
						printf("We have been disconnected.\n");
					}
				}
				break;

			case ID_GAME_MESSAGE_1:
				{
					RakNet::RakString rs;
					RakNet::BitStream bsIn(packet->data, packet->length, false);
					bsIn.IgnoreBytes(sizeof(RakNet::MessageID));
					bsIn.Read(rs);
					printf("%s\n", rs.C_String());
				}
				break;

			default:
				printf("Message with identifier %i has arrived.\n", packet->data[0]);
				break;
			}
		}
	}

	RakNet::RakPeerInterface::DestroyInstance(peer);

	return 0;
}
Пример #10
0
int main(int argc, char **argv)
{
	if (argc<8)
	{
		printf("Arguments: serverIP, pathToGame, gameName, patchImmediately, localPort, serverPort, fullScan");
		return 0;
	}

	RakNet::SystemAddress TCPServerAddress=RakNet::UNASSIGNED_SYSTEM_ADDRESS;
	RakNet::AutopatcherClient autopatcherClient;
	RakNet::FileListTransfer fileListTransfer;
	RakNet::CloudClient cloudClient;
	autopatcherClient.SetFileListTransferPlugin(&fileListTransfer);
	bool didRebalance=false; // So we only reconnect to a lower load server once, for load balancing

	bool fullScan = argv[7][0]=='1';

	unsigned short localPort;
	localPort=atoi(argv[5]);

	unsigned short serverPort=atoi(argv[6]);

	RakNet::PacketizedTCP packetizedTCP;
	if (packetizedTCP.Start(localPort,1)==false)
	{
		printf("Failed to start TCP. Is the port already in use?");
		return 1;
	}
	packetizedTCP.AttachPlugin(&autopatcherClient);
	packetizedTCP.AttachPlugin(&fileListTransfer);

	RakNet::RakPeerInterface *rakPeer;
	rakPeer = RakNet::RakPeerInterface::GetInstance();
	RakNet::SocketDescriptor socketDescriptor(localPort,0);
	rakPeer->Startup(1,&socketDescriptor, 1);
	rakPeer->AttachPlugin(&cloudClient);
	DataStructures::List<RakNet::RakNetSocket2* > sockets;
	rakPeer->GetSockets(sockets);
	printf("Started on port %i\n", sockets[0]->GetBoundAddress().GetPort());


	char buff[512];
	strcpy(buff, argv[1]);

	rakPeer->Connect(buff, serverPort, 0, 0);

	printf("Connecting...\n");
	char appDir[512];
	strcpy(appDir, argv[2]);
	char appName[512];
	strcpy(appName, argv[3]);

	bool patchImmediately=argc>=5 && argv[4][0]=='1';

	RakNet::Packet *p;
	while (1)
	{
		RakNet::SystemAddress notificationAddress;
		notificationAddress=packetizedTCP.HasCompletedConnectionAttempt();
		if (notificationAddress!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
		{
			printf("ID_CONNECTION_REQUEST_ACCEPTED\n");
			TCPServerAddress=notificationAddress;
		}
		notificationAddress=packetizedTCP.HasNewIncomingConnection();
		if (notificationAddress!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
			printf("ID_NEW_INCOMING_CONNECTION\n");
		notificationAddress=packetizedTCP.HasLostConnection();
		if (notificationAddress!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
			printf("ID_CONNECTION_LOST\n");
		notificationAddress=packetizedTCP.HasFailedConnectionAttempt();
		if (notificationAddress!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
		{
			printf("ID_CONNECTION_ATTEMPT_FAILED TCP\n");
			autopatcherClient.SetFileListTransferPlugin(0);
			autopatcherClient.Clear();
			packetizedTCP.Stop();
			rakPeer->Shutdown(500,0);
			RakNet::RakPeerInterface::DestroyInstance(rakPeer);
			return 0;
		}


		p=packetizedTCP.Receive();
		while (p)
		{
			if (p->data[0]==ID_AUTOPATCHER_REPOSITORY_FATAL_ERROR)
			{
				char buff[256];
				RakNet::BitStream temp(p->data, p->length, false);
				temp.IgnoreBits(8);
				RakNet::StringCompressor::Instance()->DecodeString(buff, 256, &temp);
				printf("ID_AUTOPATCHER_REPOSITORY_FATAL_ERROR\n");
				printf("%s\n", buff);
				autopatcherClient.SetFileListTransferPlugin(0);
				autopatcherClient.Clear();
				packetizedTCP.Stop();
				rakPeer->Shutdown(500,0);
				RakNet::RakPeerInterface::DestroyInstance(rakPeer);
				return 0;
			}
			else if (p->data[0]==ID_AUTOPATCHER_CANNOT_DOWNLOAD_ORIGINAL_UNMODIFIED_FILES)
			{
				printf("ID_AUTOPATCHER_CANNOT_DOWNLOAD_ORIGINAL_UNMODIFIED_FILES\n");
				autopatcherClient.SetFileListTransferPlugin(0);
				autopatcherClient.Clear();
				packetizedTCP.Stop();
				rakPeer->Shutdown(500,0);
				RakNet::RakPeerInterface::DestroyInstance(rakPeer);
				return 0;
			}			
			else if (p->data[0]==ID_AUTOPATCHER_FINISHED)
			{
				printf("ID_AUTOPATCHER_FINISHED with server time %f\n", autopatcherClient.GetServerDate());
				double srvDate=autopatcherClient.GetServerDate();
				FILE *fp = fopen("srvDate", "wb");
				fwrite(&srvDate,sizeof(double),1,fp);
				fclose(fp);
				autopatcherClient.SetFileListTransferPlugin(0);
				autopatcherClient.Clear();
				packetizedTCP.Stop();
				rakPeer->Shutdown(500,0);
				RakNet::RakPeerInterface::DestroyInstance(rakPeer);
				return 0;
			}
			else if (p->data[0]==ID_AUTOPATCHER_RESTART_APPLICATION)
			{
				printf("ID_AUTOPATCHER_RESTART_APPLICATION");
				autopatcherClient.SetFileListTransferPlugin(0);
				autopatcherClient.Clear();
				packetizedTCP.Stop();
				rakPeer->Shutdown(500,0);
				RakNet::RakPeerInterface::DestroyInstance(rakPeer);
				return 0;
			}
			// Launch \"AutopatcherClientRestarter.exe autopatcherRestart.txt\"\nQuit this application immediately after to unlock files.\n");

			packetizedTCP.DeallocatePacket(p);
			p=packetizedTCP.Receive();
		}

		p=rakPeer->Receive();
		while (p)
		{
			if (p->data[0]==ID_CONNECTION_REQUEST_ACCEPTED)
			{
				// UploadInstanceToCloud(&cloudClient, p->guid);
				// GetClientSubscription(&cloudClient, p->guid);
				GetServers(&cloudClient, p->guid);
				break;
			}
			else if (p->data[0]==ID_CONNECTION_ATTEMPT_FAILED)
			{
				printf("ID_CONNECTION_ATTEMPT_FAILED UDP\n");
				autopatcherClient.SetFileListTransferPlugin(0);
				autopatcherClient.Clear();
				packetizedTCP.Stop();
				rakPeer->Shutdown(500,0);
				RakNet::RakPeerInterface::DestroyInstance(rakPeer);
				return 0;
			}
			else if (p->data[0]==ID_CLOUD_GET_RESPONSE)
			{
				RakNet::CloudQueryResult cloudQueryResult;
				cloudClient.OnGetReponse(&cloudQueryResult, p);
				unsigned int rowIndex;
				const bool wasCallToGetServers=cloudQueryResult.cloudQuery.keys[0].primaryKey=="CloudConnCount";
				printf("\n");
				if (wasCallToGetServers)
					printf("Downloaded server list. %i servers.\n", cloudQueryResult.rowsReturned.Size());

				unsigned short connectionsOnOurServer=65535;
				unsigned short lowestConnectionsServer=65535;
				RakNet::SystemAddress lowestConnectionAddress;

				for (rowIndex=0; rowIndex < cloudQueryResult.rowsReturned.Size(); rowIndex++)
				{
					RakNet::CloudQueryRow *row = cloudQueryResult.rowsReturned[rowIndex];
					if (wasCallToGetServers)
					{
						unsigned short connCount;
						RakNet::BitStream bsIn(row->data, row->length, false);
						bsIn.Read(connCount);
						printf("%i. Server found at %s with %i connections\n", rowIndex+1, row->serverSystemAddress.ToString(true), connCount);

						unsigned short connectionsExcludingOurselves;
						if (row->serverGUID==p->guid)
							connectionsExcludingOurselves=connCount-1;
						else
							connectionsExcludingOurselves=connCount;

						// Find the lowest load server (optional)
						if (p->guid==row->serverGUID)
						{
							connectionsOnOurServer=connectionsExcludingOurselves;
						}
						else if (connectionsExcludingOurselves < lowestConnectionsServer)
						{
							lowestConnectionsServer=connectionsExcludingOurselves;
							lowestConnectionAddress=row->serverSystemAddress;
						}
					}
				}


				// Do load balancing by reconnecting to lowest load server (optional)
				if (didRebalance==false && wasCallToGetServers)
				{
					if (cloudQueryResult.rowsReturned.Size()>0 && connectionsOnOurServer>lowestConnectionsServer)
					{
						printf("Reconnecting to lower load server %s\n", lowestConnectionAddress.ToString(false));

						rakPeer->CloseConnection(p->guid, true);
						// Wait for the thread to close, otherwise will immediately get back ID_CONNECTION_ATTEMPT_FAILED because no free outgoing connection slots
						// Alternatively, just call Startup() with 2 slots instead of 1
						RakSleep(500);

						rakPeer->Connect(lowestConnectionAddress.ToString(false), lowestConnectionAddress.GetPort(), 0, 0);

						// TCP Connect to new IP address
						packetizedTCP.Connect(lowestConnectionAddress.ToString(false),serverPort,false);
					}
					else
					{
						// TCP Connect to original IP address
						packetizedTCP.Connect(buff,serverPort,false);
					}

					didRebalance=true;
				}

				cloudClient.DeallocateWithDefaultAllocator(&cloudQueryResult);
			}

			rakPeer->DeallocatePacket(p);
			p=rakPeer->Receive();
		}

		if (TCPServerAddress!=RakNet::UNASSIGNED_SYSTEM_ADDRESS && patchImmediately==true)
		{
			patchImmediately=false;
			char restartFile[512];
			strcpy(restartFile, appDir);
			strcat(restartFile, "/autopatcherRestart.txt");

			double lastUpdateDate;

			if (fullScan==false)
			{
				FILE *fp = fopen("srvDate", "rb");
				if (fp)
				{
					fread(&lastUpdateDate, sizeof(lastUpdateDate), 1, fp);
					fclose(fp);
				}
				else
					lastUpdateDate=0;
			}
			else
				lastUpdateDate=0;

			if (autopatcherClient.PatchApplication(appName, appDir, lastUpdateDate, TCPServerAddress, &transferCallback, restartFile, argv[0]))
			{
				printf("Patching process starting.\n");
			}
			else
			{
				printf("Failed to start patching.\n");
				autopatcherClient.SetFileListTransferPlugin(0);
				autopatcherClient.Clear();
				packetizedTCP.Stop();
				rakPeer->Shutdown(500,0);
				RakNet::RakPeerInterface::DestroyInstance(rakPeer);
				return 0;
			}
		}
		RakSleep(30);
	}

	// Dereference so the destructor doesn't crash
	autopatcherClient.SetFileListTransferPlugin(0);

	autopatcherClient.Clear();
	packetizedTCP.Stop();
	rakPeer->Shutdown(500,0);
	RakNet::RakPeerInterface::DestroyInstance(rakPeer);
	return 1;
}
int main(int argc, char **argv)
{
	// Avoids the Error: Got a packet bigger than 'max_allowed_packet' bytes
	printf("Important: Requires that you first set the DB schema and the max packet size on the server.\n");
	printf("See DependentExtensions/AutopatcherMySQLRepository/readme.txt\n");
	// // MySQL is extremely slow in AutopatcherMySQLRepository::GetFilePart
	printf("WARNING: MySQL is an order of magnitude slower than PostgreSQL.\nRecommended you use AutopatcherServer_PostgreSQL instead.");

	printf("Server starting... ");
	RakNet::AutopatcherServer autopatcherServer;
	// RakNet::FLP_Printf progressIndicator;
	RakNet::FileListTransfer fileListTransfer;
	// So only one thread runs per connection, we create an array of connection objects, and tell the autopatcher server to use one thread per item
	static const int workerThreadCount=4; // Used for checking patches only
	static const int sqlConnectionObjectCount=32; // Used for both checking patches and downloading
	RakNet::AutopatcherMySQLRepository connectionObject[sqlConnectionObjectCount];
	RakNet::AutopatcherRepositoryInterface *connectionObjectAddresses[sqlConnectionObjectCount];
	for (int i=0; i < sqlConnectionObjectCount; i++)
		connectionObjectAddresses[i]=&connectionObject[i];
	// fileListTransfer.AddCallback(&progressIndicator);
	autopatcherServer.SetFileListTransferPlugin(&fileListTransfer);
	// MySQL is extremely slow in AutopatcherMySQLRepository::GetFilePart so running tho incremental reads in a thread allows multiple concurrent users to read
	// Without this, only one user would be sent files at a time basically
	fileListTransfer.StartIncrementalReadThreads(sqlConnectionObjectCount);
	autopatcherServer.SetMaxConurrentUsers(MAX_INCOMING_CONNECTIONS); // More users than this get queued up
	RakNet::AutopatcherServerLoadNotifier_Printf loadNotifier;
	autopatcherServer.SetLoadManagementCallback(&loadNotifier);
#ifdef USE_TCP
	RakNet::PacketizedTCP packetizedTCP;
	if (packetizedTCP.Start(LISTEN_PORT,MAX_INCOMING_CONNECTIONS)==false)
	{
		printf("Failed to start TCP. Is the port already in use?");
		return 1;
	}
	packetizedTCP.AttachPlugin(&autopatcherServer);
	packetizedTCP.AttachPlugin(&fileListTransfer);
#else
	RakNet::RakPeerInterface *rakPeer;
	rakPeer = RakNet::RakPeerInterface::GetInstance();
	RakNet::SocketDescriptor socketDescriptor(LISTEN_PORT,0);
	rakPeer->Startup(MAX_INCOMING_CONNECTIONS,&socketDescriptor, 1);
	rakPeer->SetMaximumIncomingConnections(MAX_INCOMING_CONNECTIONS);
	rakPeer->AttachPlugin(&autopatcherServer);
	rakPeer->AttachPlugin(&fileListTransfer);
#endif
	printf("started.\n");

	printf("Enter database password:\n");
	char password[128];
	char username[256];
	strcpy(username, "root");
	Gets(password,sizeof(password));
	if (password[0]==0)
		strcpy(password,"aaaa");
	char db[256];
	printf("Enter DB schema: ");
	// To create the schema, go to the command line client and type create schema autopatcher;
	// You also have to add 
	// max_allowed_packet=128M
	// Where 128 is the maximum size file in megabytes you'll ever add
	// to MySQL\MySQL Server 5.1\my.ini in the [mysqld] section
	// Be sure to restart the service after doing so
	Gets(db,sizeof(db));
	if (db[0]==0)
		strcpy(db,"autopatcher");
	for (int conIdx=0; conIdx < sqlConnectionObjectCount; conIdx++)
	{
		if (!connectionObject[conIdx].Connect("localhost", username, password, db, 0, NULL, 0))
		{
			printf("Database connection failed.\n");
			return 1;
		}
	}
	printf("Database connection suceeded.\n");


	printf("Starting threads\n");
	autopatcherServer.StartThreads(workerThreadCount, sqlConnectionObjectCount, connectionObjectAddresses);
	printf("System ready for connections\n");

	printf("(D)rop database\n(C)reate database.\n(A)dd application\n(U)pdate revision.\n(R)emove application\n(Q)uit\n");

	char ch;
	RakNet::Packet *p;
	while (1)
	{
#ifdef USE_TCP
		RakNet::SystemAddress notificationAddress;
		notificationAddress=packetizedTCP.HasCompletedConnectionAttempt();
		if (notificationAddress!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
			printf("ID_CONNECTION_REQUEST_ACCEPTED\n");
		notificationAddress=packetizedTCP.HasNewIncomingConnection();
		if (notificationAddress!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
			printf("ID_NEW_INCOMING_CONNECTION\n");
		notificationAddress=packetizedTCP.HasLostConnection();
		if (notificationAddress!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
			printf("ID_CONNECTION_LOST\n");

		p=packetizedTCP.Receive();
		while (p)
		{
			packetizedTCP.DeallocatePacket(p);
			p=packetizedTCP.Receive();
		}
#else
		p=rakPeer->Receive();
		while (p)
		{
			if (p->data[0]==ID_NEW_INCOMING_CONNECTION)
				printf("ID_NEW_INCOMING_CONNECTION\n");
			else if (p->data[0]==ID_DISCONNECTION_NOTIFICATION)
				printf("ID_DISCONNECTION_NOTIFICATION\n");
			else if (p->data[0]==ID_CONNECTION_LOST)
				printf("ID_CONNECTION_LOST\n");

			rakPeer->DeallocatePacket(p);
			p=rakPeer->Receive();
		}
#endif
		if (kbhit())
		{
			ch=getch();
			if (ch=='q')
				break;
			else if (ch=='c')
			{
				if (connectionObject[0].CreateAutopatcherTables()==false)
					printf("Error: %s\n", connectionObject[0].GetLastError());
				else
					printf("Created\n");
			}
			else if (ch=='d')
			{
				if (connectionObject[0].DestroyAutopatcherTables()==false)
					printf("Error: %s\n", connectionObject[0].GetLastError());
				else
					printf("Destroyed\n");
			}
			else if (ch=='a')
			{
				printf("Enter application name to add: ");
				char appName[512];
				Gets(appName,sizeof(appName));
				if (appName[0]==0)
					strcpy(appName, "TestApp");

				if (connectionObject[0].AddApplication(appName, username)==false)
					printf("Error: %s\n", connectionObject[0].GetLastError());
				else
					printf("Done\n");
			}
			else if (ch=='r')
			{
				printf("Enter application name to remove: ");
				char appName[512];
				Gets(appName,sizeof(appName));
				if (appName[0]==0)
					strcpy(appName, "TestApp");

				if (connectionObject[0].RemoveApplication(appName)==false)
					printf("Error: %s\n", connectionObject[0].GetLastError());
				else
					printf("Done\n");
			}
			else if (ch=='u')
			{
				printf("Enter application name: ");
				char appName[512];
				Gets(appName,sizeof(appName));
				if (appName[0]==0)
					strcpy(appName, "TestApp");

				printf("Enter application directory: ");
				char appDir[512];
				Gets(appDir,sizeof(appName));
				if (appDir[0]==0)
					strcpy(appDir, "C:/temp");

				if (connectionObject[0].UpdateApplicationFiles(appName, appDir, username, 0)==false)
				{
					printf("Error: %s\n", connectionObject[0].GetLastError());
				}
				else
				{
					printf("Update success.\n");
				}
			}
		}

		RakSleep(30);


	}

#ifdef USE_TCP
	packetizedTCP.Stop();
#else
	RakNet::RakPeerInterface::DestroyInstance(rakPeer);
#endif
}
Пример #12
0
// Handles all networking events
DWORD WINAPI HandleNetworking( LPVOID )
{
    // Create RakNet interfaces
    RakNet::RakPeerInterface *peer;
    RakNet::Packet *packet;

    // Initialize networking
    peer = RakNet::RakPeerInterface::GetInstance();

    // Rev up your engines
    RakNet::SocketDescriptor sd( 0, "127.0.0.1" );
    peer->Startup( 1, &sd, 1 );

    // GO GO GO
    RakNet::ConnectionAttemptResult attempt = peer->Connect( "127.0.0.1", 5187, NULL, 0 );

    // Success?
    if( attempt != RakNet::CONNECTION_ATTEMPT_STARTED )
    {
        // Nope
        switch( attempt )
        {
        // None of these should happen, EVER.
        case RakNet::ALREADY_CONNECTED_TO_ENDPOINT:
            MessageBoxA
            (
                NULL,
                "A connection attempt was made to a server we're already connected to.\nPlease contact a developer.",
                "SC4Multi -- Network Error",
                MB_OK | MB_ICONERROR
            );
            break;
        case RakNet::CANNOT_RESOLVE_DOMAIN_NAME:
            MessageBoxA
            (
                NULL,
                "The given domain name could not be resolved.",
                "SC4Multi -- Network Error",
                MB_OK | MB_ICONERROR
            );
            break;
        case RakNet::CONNECTION_ATTEMPT_ALREADY_IN_PROGRESS:
            MessageBoxA
            (
                NULL,
                "Two connection attempts were being made at once by SC4Multi.\nPlease contact a developer.",
                "SC4Multi -- Network Error",
                MB_OK | MB_ICONERROR
            );
            break;
        case RakNet::INVALID_PARAMETER:
            MessageBoxA
            (
                NULL,
                "An invalid parameter was passed by SC4Multi. Please contact a developer.",
                "SC4Multi -- Network Error",
                MB_OK | MB_ICONERROR
            );
            break;
        case RakNet::SECURITY_INITIALIZATION_FAILED:
            MessageBoxA
            (
                NULL,
                "Security initialization failed. Something is terribly wrong,\nplease contact a developer.",
                "SC4Multi -- Network Error",
                MB_OK | MB_ICONERROR
            );
            break;
        default:
            MessageBoxA
            (
                NULL,
                "Something went wrong during network initialization,\nand we don't know what.",
                "SC4Multi -- Network Error",
                MB_OK | MB_ICONERROR
            );
            break;
        }

        // Terminate via ugly hacks
        exit( 1 );
    }

    // Forever and ever and ever and ever and ever and...
    while( isRunning )
    {
        // If there are any packets, read it
        for( packet = peer->Receive(); packet; peer->DeallocatePacket( packet ), packet = peer->Receive() )
        {
            // Get the packet type ID
            switch( packet->data[0] )
            {
            case ID_REMOTE_DISCONNECTION_NOTIFICATION:
                MessageBoxA( NULL, "Other client quit", "SC4Multi", MB_OK | MB_ICONINFORMATION );
                break;
            case ID_REMOTE_CONNECTION_LOST:
                MessageBoxA( NULL, "Other client timeout", "SC4Multi", MB_OK | MB_ICONINFORMATION );
                break;
            case ID_REMOTE_NEW_INCOMING_CONNECTION:
                MessageBoxA( NULL, "Other client connection", "SC4Multi", MB_OK | MB_ICONINFORMATION );
                break;
            case ID_CONNECTION_REQUEST_ACCEPTED:
            {
                MessageBoxA( NULL, "Our connection succeeded", "SC4Multi", MB_OK | MB_ICONINFORMATION );

                // Read the machine GUID generated by Windows
                char guid_net[255];
                bool isGuidNull = false;
                {
                    // Create a wide-char GUID buffer
                    wchar_t guid[255];

                    // Registry stuff
                    HKEY hKey    = 0;
                    DWORD dwType = 0;

                    // Get the size of our buffer
                    DWORD dwBufSize = sizeof( guid );

                    // Define the subkey
                    const wchar_t* subkey = L"Software\\Microsoft\\Cryptography";

                    // Open the registry
                    if( RegOpenKey( HKEY_LOCAL_MACHINE, subkey, &hKey ) == ERROR_SUCCESS )
                    {
                        // We're looking for a string
                        dwType = REG_SZ;

                        // Read to our buffer
                        if( !RegQueryValueEx( hKey, L"MachineGuid", 0, &dwType, (BYTE *)guid, &dwBufSize ) == ERROR_SUCCESS )
                        {
                            // Fall back to a null GUID
                            isGuidNull = true;
                        }
                        else
                        {
                            // Convert the wide char buffer into a char buffer
                            wcstombs( guid_net, guid, 255 );
                        }
                    }
                    else
                    {
                        // Fall back to a null GUID
                        isGuidNull = true;
                    }
                }

                // Initialize a bitstream
                RakNet::BitStream bsOut;

                // Send our user data to the server
                {
                    // Packet ID
                    bsOut.Write( (RakNet::MessageID)ID_SC4_CONNECTION_DATA );

                    // Nickname
                    bsOut.Write( "Stormeus" );

                    // Unique GUID, or a null one
                    if( isGuidNull )
                        bsOut.Write( 0 );
                    else
                    {
#ifdef DEBUG
                        MessageBoxA( NULL, guid_net, "SC4Multi -- GUID", MB_ICONINFORMATION | MB_OK );
#endif

                        bsOut.Write( guid_net );
                    }

                    // City taken
                    bsOut.Write( "Unknown City" );
                }

                // Priority shipping to the server
                peer->Send
                (
                    &bsOut,
                    HIGH_PRIORITY,
                    RELIABLE_ORDERED,
                    0,
                    packet->systemAddress,
                    false
                );

                break;
            }
            case ID_NEW_INCOMING_CONNECTION:
                MessageBoxA( NULL, "Incoming connection", "SC4Multi", MB_OK | MB_ICONINFORMATION );
                break;
            case ID_NO_FREE_INCOMING_CONNECTIONS:
                MessageBoxA( NULL, "Server is full", "SC4Multi", MB_OK | MB_ICONINFORMATION );
                break;
            case ID_DISCONNECTION_NOTIFICATION:
                MessageBoxA( NULL, "We disconnected", "SC4Multi", MB_OK | MB_ICONINFORMATION );
                break;
            case ID_CONNECTION_LOST:
                MessageBoxA( NULL, "We lost connection", "SC4Multi", MB_OK | MB_ICONINFORMATION );
                break;
            }
        }
    }

    // Destroy this instance
    RakNet::RakPeerInterface::DestroyInstance( peer );

    // And we're done here.
    MessageBoxA( NULL, "Destroyed RakNet instance.", "SC4Multi -- Networking Debug", MB_OK | MB_ICONEXCLAMATION );

    return 1;
}
Пример #13
0
int main(int argc, char** argv) {
	RakNet::RakPeerInterface *server = RakNet::RakPeerInterface::GetInstance();
	RakNet::Packet* p;
	unsigned char packetIdentifier;
	RakNet::SystemAddress clientID = RakNet::UNASSIGNED_SYSTEM_ADDRESS;
	RakNet::RakNetStatistics *rss;
	RakNet::SocketDescriptor socketDescriptors[2];
	char portstring[30];

	socketDescriptors[0].port = SERVER_PORT;
	socketDescriptors[0].socketFamily = AF_INET; // Test out IPV4
	socketDescriptors[1].port = SERVER_PORT;
	socketDescriptors[1].socketFamily = AF_INET6; // Test out IPV6
	if (server->Startup(4, socketDescriptors, 2) != RakNet::RAKNET_STARTED) {
		std::cout << "IPV6 not supported, starting with IPV4-only interface..." << std::endl;
		if (server->Startup(4, socketDescriptors, 1) != RakNet::RAKNET_STARTED) {
			std::cerr << "Error creating server, exiting..." << std::endl;
			exit(-1);
		}
	}
	std::cout << "Server started successfully. Listening on port " << SERVER_PORT << std::endl;
	server->SetMaximumIncomingConnections(20);
	server->SetOccasionalPing(true);
	server->SetUnreliableTimeout(1000);

	DataStructures::List<RakNet::RakNetSocket2*> sockets;
	server->GetSockets(sockets);
	std::cout << "Socket addresses used by RakNet:" << std::endl;
	for (unsigned int i = 0; i < sockets.Size(); i++) {
		printf("%i. %s\n", i + 1, sockets[i]->GetBoundAddress().ToString(true));
	}
	char message[2048];

	// Loop for input
	while (1)
	{

		// This sleep keeps RakNet responsive
		RakSleep(30);

		if (kbhit())
		{
			// Notice what is not here: something to keep our network running.  It's
			// fine to block on gets or anything we want
			// Because the network engine was painstakingly written using threads.
			Gets(message, sizeof(message));

			if (strcmp(message, "quit") == 0)
			{
				puts("Quitting.");
				break;
			}

			if (strcmp(message, "stat") == 0)
			{
				rss = server->GetStatistics(server->GetSystemAddressFromIndex(0));
				StatisticsToString(rss, message, 2);
				printf("%s", message);
				printf("Ping %i\n", server->GetAveragePing(server->GetSystemAddressFromIndex(0)));

				continue;
			}

			if (strcmp(message, "ping") == 0)
			{
				server->Ping(clientID);

				continue;
			}

			if (strcmp(message, "pingip") == 0)
			{
				printf("Enter IP: ");
				Gets(message, sizeof(message));
				printf("Enter port: ");
				Gets(portstring, sizeof(portstring));
				if (portstring[0] == 0)
					strcpy(portstring, "1234");
				server->Ping(message, atoi(portstring), false);

				continue;
			}

			if (strcmp(message, "kick") == 0)
			{
				server->CloseConnection(clientID, true, 0);

				continue;
			}

			if (strcmp(message, "getconnectionlist") == 0)
			{
				printf("Connections:\n");
				RakNet::SystemAddress systems[10];
				unsigned short numConnections = 10;
				server->GetConnectionList((RakNet::SystemAddress*) &systems, &numConnections);
				for (int i = 0; i < numConnections; i++)
				{
					printf("%i. %s\n", i + 1, systems[i].ToString(true));
				}
				continue;
			}

			if (strcmp(message, "ban") == 0)
			{
				printf("Enter IP to ban.  You can use * as a wildcard\n");
				Gets(message, sizeof(message));
				server->AddToBanList(message);
				printf("IP %s added to ban list.\n", message);

				continue;
			}


			// Message now holds what we want to broadcast
			char message2[2048];
			// Append Server: to the message so clients know that it ORIGINATED from the server
			// All messages to all clients come from the server either directly or by being
			// relayed from other clients
			message2[0] = 0;
			const static char prefix[] = "Server: ";
			strncpy(message2, prefix, sizeof(message2));
			strncat(message2, message, sizeof(message2) - strlen(prefix) - 1);

			// message2 is the data to send
			// strlen(message2)+1 is to send the null terminator
			// HIGH_PRIORITY doesn't actually matter here because we don't use any other priority
			// RELIABLE_ORDERED means make sure the message arrives in the right order
			// We arbitrarily pick 0 for the ordering stream
			// RakNet::UNASSIGNED_SYSTEM_ADDRESS means don't exclude anyone from the broadcast
			// true means broadcast the message to everyone connected
			server->Send(message2, (const int)strlen(message2) + 1, HIGH_PRIORITY, RELIABLE_ORDERED, 0, RakNet::UNASSIGNED_SYSTEM_ADDRESS, true);
		}

		// Get a packet from either the server or the client

		for (p = server->Receive(); p; server->DeallocatePacket(p), p = server->Receive())
		{
			// We got a packet, get the identifier with our handy function
			packetIdentifier = GetPacketIdentifier(p);

			// Check if this is a network message packet
			switch (packetIdentifier)
			{
			case ID_DISCONNECTION_NOTIFICATION:
				// Connection lost normally
				printf("ID_DISCONNECTION_NOTIFICATION from %s\n", p->systemAddress.ToString(true));;
				break;


			case ID_NEW_INCOMING_CONNECTION:
				// Somebody connected.  We have their IP now
				printf("ID_NEW_INCOMING_CONNECTION from %s with GUID %s\n", p->systemAddress.ToString(true), p->guid.ToString());
				clientID = p->systemAddress; // Record the player ID of the client

				printf("Remote internal IDs:\n");
				for (int index = 0; index < MAXIMUM_NUMBER_OF_INTERNAL_IDS; index++)
				{
					RakNet::SystemAddress internalId = server->GetInternalID(p->systemAddress, index);
					if (internalId != RakNet::UNASSIGNED_SYSTEM_ADDRESS)
					{
						printf("%i. %s\n", index + 1, internalId.ToString(true));
					}
				}

				break;

			case ID_INCOMPATIBLE_PROTOCOL_VERSION:
				printf("ID_INCOMPATIBLE_PROTOCOL_VERSION\n");
				break;

			case ID_CONNECTED_PING:
			case ID_UNCONNECTED_PING:
				printf("Ping from %s\n", p->systemAddress.ToString(true));
				break;

			case ID_CONNECTION_LOST:
				// Couldn't deliver a reliable packet - i.e. the other system was abnormally
				// terminated
				printf("ID_CONNECTION_LOST from %s\n", p->systemAddress.ToString(true));;
				break;

			default:
				// The server knows the static data of all clients, so we can prefix the message
				// With the name data
				printf("%s\n", p->data);

				// Relay the message.  We prefix the name for other clients.  This demonstrates
				// That messages can be changed on the server before being broadcast
				// Sending is the same as before
				sprintf(message, "%s", p->data);
				server->Send(message, (const int)strlen(message) + 1, HIGH_PRIORITY, RELIABLE_ORDERED, 0, p->systemAddress, true);

				break;
			}

		}
	}

	server->Shutdown(300);
	// We're done with the network
	RakNet::RakPeerInterface::DestroyInstance(server);


}
Пример #14
0
int _tmain(int argc, _TCHAR* argv[])
{
	// Create networking interfaces
	RakNet::RakPeerInterface *peer = RakNet::RakPeerInterface::GetInstance();
	RakNet::Packet *packet;

	// Initialize a socket descriptor
	RakNet::SocketDescriptor sd( 5187, 0 );

	// Start a server with max. 5 clients
	peer->Startup( 5, &sd, 1 );
	printf( "Starting the server...\n" );

	// Set the maximum number of clients
	peer->SetMaximumIncomingConnections( 5 );

	// Listen
	printf( "Listening...\n" );
	while( 1 )
	{
		for( packet = peer->Receive(); packet; peer->DeallocatePacket( packet ), packet = peer->Receive() )
		{
			switch( packet->data[0] )
			{
				case ID_NEW_INCOMING_CONNECTION:
					printf("A connection is incoming.\n");
					break;
				case ID_NO_FREE_INCOMING_CONNECTIONS:
					printf("The server is full.\n");
					break;
				case ID_DISCONNECTION_NOTIFICATION:
					printf("A client has disconnected.\n");
					break;
				case ID_CONNECTION_LOST:
					printf("A client lost the connection.\n");
					break;
				case ID_SC4_CONNECTION_DATA:
				{
					printf( "An SC4Multi connection was made:\n" );

					// Create several RakNet strings for reading the bistream
					RakNet::RakString username, guid, city;

					// Read the packet into the bitstream
					RakNet::BitStream bsIn(packet->data,packet->length,false);

					// Ignore the packet ID, which we already know
					bsIn.IgnoreBytes(sizeof(RakNet::MessageID));

					// Read the bitstream into our variables
					bsIn.Read( username );
					bsIn.Read( guid );
					bsIn.Read( city );

					// Print the data
					printf
					(
						"\tUsername | %s\n"
						"\tGUID     | %s\n"
						"\tCity     | %s\n",

						username.C_String(),
						guid.C_String(),
						city.C_String()
					);
					
					break;
				}
			
				default:
					printf("Message with identifier %i has arrived.\n", packet->data[0]);
					break;
			}
		}
	}

	// Shut down
	RakNet::RakPeerInterface::DestroyInstance( peer );

	return 0;
}
Пример #15
0
// Called from main()/WindMain() after settings are initialized to execute
// most of the program logic. Responsible for setting up the window,
// loading movies and containing the playback/message loop.
int FxPlayerTiny::Run()
{    
    if (!SetupWindow(GString(FXPLAYER_APP_TITLE " ") + FileName))
        return 1;

    // Show the window.
    ShowWindow(hWnd, SW_SHOWDEFAULT);
    UpdateWindow(hWnd);

   
    // Create and Configure GFxLoader.   
    GFxLoader loader;

    // Developers set states on the loader to modify loading and playback behavior.
    // If you need to load files from a custom package, for example, you can 
    // create a GFxFileOpener derived class that loads files in a custom way.
    // Here GFxFileOpener and GFxFSCommandHandler are set for sample purposes.    
    GPtr<GFxFileOpener> pfileOpener = *new GFxFileOpener;
    loader.SetFileOpener(pfileOpener); 
    GPtr<GFxFSCommandHandler> pcommandHandler = *new FxPlayerFSCommandHandler;
    loader.SetFSCommandHandler(pcommandHandler);

    // For D3D, it is good to override image creator to keep image data,
    // so that it can be restored in case of a lost device.
    GPtr<GFxImageCreator> pimageCreator = *new GFxImageCreator(1);
    loader.SetImageCreator(pimageCreator);

    
    // Load the movie file and create its instance.
    if (!(pMovieDef = *loader.CreateMovie(FileName)))
    {
        GString errorString = "Unable to load file: ";
        errorString += FileName;
        MessageBox(NULL, errorString.ToCStr(), "Error", MB_OK | MB_ICONEXCLAMATION);
        return 1;
    }

    if (!(pMovie = *pMovieDef->CreateInstance()))
        return 1;

    // Create renderer.
    if (!(pRenderer = *GRendererD3D9::CreateRenderer()))
        return 1;

    // Configure renderer in "Dependent mode", honoring externally
    // configured device settings.
    if (!pRenderer->SetDependentVideoMode(pDevice, &PresentParams, 0, hWnd))
        return 1;

    // Set renderer on loader so that it is also applied to all children.
    pRenderConfig = *new GFxRenderConfig(pRenderer, GFxRenderConfig::RF_EdgeAA | GFxRenderConfig::RF_StrokeNormal);
    loader.SetRenderConfig(pRenderConfig);

    // Set playback view to span the entire window.
    pMovie->SetViewport(Width, Height, 0,0, Width, Height);

    // If you wanted to use the movie as a transparent HUD overlay, you would
    // set Background Alpha to 0. We don't need to do this for player sample.
    // pMovie->SetBackgroundAlpha(0.0f);

    // Store initial timing, so that we can determine
    // how much to advance Flash playback.
    MovieLastTime = timeGetTime();

    // Application / Player message loop.
    MSG msg;
    ZeroMemory(&msg, sizeof(msg));

	// KevinJ: 1/3 functions, Init()
	// Path to current exe is used to the patcher can restart itself if needed
	RakNet::Lobby2ClientGFx3Impl sampleImpl;
	GPtr<FxDelegate> pDelegate = *new FxDelegate; 
	pMovie->SetExternalInterface(pDelegate); 
	RakNet::Lobby2Client lobby2Client;
	RakNet::Lobby2MessageFactory messageFactory;
	RakNet::RakPeerInterface *rakPeer = RakNet::RakPeerInterface::GetInstance();
	RakNet::SocketDescriptor sd;
	rakPeer->Startup(1,&sd, 1);
	rakPeer->AttachPlugin(&lobby2Client);
	rakPeer->AttachPlugin(&sampleImpl);
	lobby2Client.SetMessageFactory(&messageFactory);
	lobby2Client.SetCallbackInterface(&sampleImpl);
	sampleImpl.Init(&lobby2Client, &messageFactory, rakPeer, pDelegate, pMovie);

    while(msg.message != WM_QUIT)
    {
        if (PeekMessage(&msg, NULL, 0U, 0U, PM_REMOVE))
        {
            TranslateMessage(&msg);
            DispatchMessage(&msg);
        }
        else
        {
            // Check for lost D3D Devices.
            if (pRenderer)
            {                       
                GRendererD3D9::DisplayStatus status = pRenderer->CheckDisplayStatus();
                if (status == GRendererD3D9::DisplayStatus_Unavailable)
                { ::Sleep(10); continue; }
                if (status == GRendererD3D9::DisplayStatus_NeedsReset)
                {           
                    if (!SUCCEEDED(ResetD3D()))
                        continue;
                }
            }

            // Advance movie animation and render it to screen.
            AdvanceAndDisplay();
        }

		// KevinJ: 2/3 functions, periodic update
		RakNet::Packet *p;
		for (p=rakPeer->Receive(); p; rakPeer->DeallocatePacket(p), p=rakPeer->Receive())
		{
		}
    }

	// KevinJ: 3/3 functions, Shutdown()
	sampleImpl.Shutdown();
	RakNet::RakPeerInterface::DestroyInstance(rakPeer);

    return 0;
}
Пример #16
0
int main(void)
{
	char ch;
	RakNet::SocketDescriptor sd;
	sd.socketFamily=AF_INET; // Only IPV4 supports broadcast on 255.255.255.255
	char ip[128];
	static const int SERVER_PORT=12345;


	// ReplicaManager3 requires NetworkIDManager to lookup pointers from numbers.
	NetworkIDManager networkIdManager;
	// Each application has one instance of RakPeerInterface
	RakNet::RakPeerInterface *rakPeer;
	// The system that performs most of our functionality for this demo
	ReplicaManager3Sample replicaManager;

	printf("Demonstration of ReplicaManager3.\n");
	printf("1. Demonstrates creating objects created by the server and client.\n");
	printf("2. Demonstrates automatic serialization data members\n");
	printf("Difficulty: Intermediate\n\n");

	printf("Start as (c)lient, (s)erver, (p)eer? ");
	ch=getche();

	rakPeer = RakNet::RakPeerInterface::GetInstance();
	if (ch=='c' || ch=='C')
	{
		topology=CLIENT;
		sd.port=0;
	}
	else if (ch=='s' || ch=='S')
	{
		topology=SERVER;
		sd.port=SERVER_PORT;
	}
	else
	{
		topology=P2P;
		sd.port=SERVER_PORT;
		while (IRNS2_Berkley::IsPortInUse(sd.port,sd.hostAddress,sd.socketFamily, SOCK_DGRAM)==true)
			sd.port++;
	}

	// Start RakNet, up to 32 connections if the server
	rakPeer->Startup(32,&sd,1);
	rakPeer->AttachPlugin(&replicaManager);
	replicaManager.SetNetworkIDManager(&networkIdManager);
	rakPeer->SetMaximumIncomingConnections(32);
	printf("\nMy GUID is %s\n", rakPeer->GetMyGUID().ToString());

	printf("\n");
	if (topology==CLIENT)
	{
		printf("Enter server IP: ");
		Gets(ip, sizeof(ip));
		if (ip[0]==0)
			strcpy(ip, "127.0.0.1");
		rakPeer->Connect(ip,SERVER_PORT,0,0,0);
		printf("Connecting...\n");
	}

	printf("Commands:\n(Q)uit\n'C'reate objects\n'R'andomly change variables in my objects\n'D'estroy my objects\n");

	// Enter infinite loop to run the system
	RakNet::Packet *packet;
	bool quit=false;
	while (!quit)
	{
		for (packet = rakPeer->Receive(); packet; rakPeer->DeallocatePacket(packet), packet = rakPeer->Receive())
		{
			switch (packet->data[0])
			{
			case ID_CONNECTION_ATTEMPT_FAILED:
				printf("ID_CONNECTION_ATTEMPT_FAILED\n");
				quit=true;
				break;
			case ID_NO_FREE_INCOMING_CONNECTIONS:
				printf("ID_NO_FREE_INCOMING_CONNECTIONS\n");
				quit=true;
				break;
			case ID_CONNECTION_REQUEST_ACCEPTED:
				printf("ID_CONNECTION_REQUEST_ACCEPTED\n");
				break;
			case ID_NEW_INCOMING_CONNECTION:
				printf("ID_NEW_INCOMING_CONNECTION from %s\n", packet->systemAddress.ToString());
				break;
			case ID_DISCONNECTION_NOTIFICATION:
				printf("ID_DISCONNECTION_NOTIFICATION\n");
				break;
			case ID_CONNECTION_LOST:
				printf("ID_CONNECTION_LOST\n");
				break;
			case ID_ADVERTISE_SYSTEM:
				// The first conditional is needed because ID_ADVERTISE_SYSTEM may be from a system we are connected to, but replying on a different address.
				// The second conditional is because AdvertiseSystem also sends to the loopback
				if (rakPeer->GetSystemAddressFromGuid(packet->guid)==RakNet::UNASSIGNED_SYSTEM_ADDRESS &&
					rakPeer->GetMyGUID()!=packet->guid)
				{
					printf("Connecting to %s\n", packet->systemAddress.ToString(true));
					rakPeer->Connect(packet->systemAddress.ToString(false), packet->systemAddress.GetPort(),0,0);
				}
				break;
			case ID_SND_RECEIPT_LOSS:
			case ID_SND_RECEIPT_ACKED:
				{
					uint32_t msgNumber;
					memcpy(&msgNumber, packet->data+1, 4);

					DataStructures::List<Replica3*> replicaListOut;
					replicaManager.GetReplicasCreatedByMe(replicaListOut);
					unsigned int idx;
					for (idx=0; idx < replicaListOut.Size(); idx++)
					{
						((SampleReplica*)replicaListOut[idx])->NotifyReplicaOfMessageDeliveryStatus(packet->guid,msgNumber, packet->data[0]==ID_SND_RECEIPT_ACKED);
					}
				}
				break;
			}
		}

		if (kbhit())
		{
			ch=getch();
			if (ch=='q' || ch=='Q')
			{
				printf("Quitting.\n");
				quit=true;
			}
			if (ch=='c' || ch=='C')
			{
				printf("Objects created.\n");
				if (topology==SERVER||topology==CLIENT)
				{
					replicaManager.Reference(new ClientCreatible_ClientSerialized);
					replicaManager.Reference(new ServerCreated_ClientSerialized);
					replicaManager.Reference(new ClientCreatible_ServerSerialized);
					replicaManager.Reference(new ServerCreated_ServerSerialized);
				}
				else
				{
				//	for (int i=0; i < 20; i++)
						replicaManager.Reference(new P2PReplica);
				}
			}
			if (ch=='r' || ch=='R')
			{
				DataStructures::List<Replica3*> replicaListOut;
				replicaManager.GetReplicasCreatedByMe(replicaListOut);
				unsigned int idx;
				for (idx=0; idx < replicaListOut.Size(); idx++)
				{
					((SampleReplica*)replicaListOut[idx])->RandomizeVariables();
				}
			}
			if (ch=='d' || ch=='D')
			{
				printf("My objects destroyed.\n");
				DataStructures::List<Replica3*> replicaListOut;
				// The reason for ClearPointers is that in the sample, I don't track which objects have and have not been allocated at the application level. So ClearPointers will call delete on every object in the returned list, which is every object that the application has created. Another way to put it is
				// 	A. Send a packet to tell other systems to delete these objects
				// 	B. Delete these objects on my own system
				replicaManager.GetReplicasCreatedByMe(replicaListOut);
				replicaManager.BroadcastDestructionList(replicaListOut, RakNet::UNASSIGNED_SYSTEM_ADDRESS);
				for (unsigned int i=0; i < replicaListOut.Size(); i++)
					RakNet::OP_DELETE(replicaListOut[i], _FILE_AND_LINE_);
			}

		}

		RakSleep(30);
		for (int i=0; i < 4; i++)
		{
			if (rakPeer->GetInternalID(RakNet::UNASSIGNED_SYSTEM_ADDRESS,0).GetPort()!=SERVER_PORT+i)
				rakPeer->AdvertiseSystem("255.255.255.255", SERVER_PORT+i, 0,0,0);
		}
	}

	rakPeer->Shutdown(100,0);
	RakNet::RakPeerInterface::DestroyInstance(rakPeer);
}
Пример #17
0
ServerExtendedData getExtendedData(const char *addr, unsigned short port)
{
    ServerExtendedData data;
    RakNet::SocketDescriptor socketDescriptor = {0, ""};
    RakNet::RakPeerInterface *peer = RakNet::RakPeerInterface::GetInstance();
    peer->Startup(1, &socketDescriptor, 1);

    stringstream sstr;
    sstr << TES3MP_VERSION;
    sstr << TES3MP_PROTO_VERSION;

    std::string msg;

    if (peer->Connect(addr, port, sstr.str().c_str(), (int)(sstr.str().size()), nullptr, 0, 3, 500, 0) != RakNet::CONNECTION_ATTEMPT_STARTED)
        msg = "Connection attempt failed.\n";


    int queue = 0;
    while (queue == 0)
    {
        for (RakNet::Packet *packet = peer->Receive(); packet; peer->DeallocatePacket(
                packet), packet = peer->Receive())
        {
            switch (packet->data[0])
            {
                case ID_CONNECTION_ATTEMPT_FAILED:
                {
                    msg = "Connection failed.\n"
                            "Either the IP address is wrong or a firewall on either system is blocking\n"
                            "UDP packets on the port you have chosen.";
                    queue = -1;
                    break;
                }
                case ID_INVALID_PASSWORD:
                {
                    msg = "Connection failed.\n"
                            "The client or server is outdated.\n";
                    queue = -1;
                    break;
                }
                case ID_CONNECTION_REQUEST_ACCEPTED:
                {
                    msg = "Connection accepted.\n";
                    queue = 1;
                    break;
                }
                case ID_DISCONNECTION_NOTIFICATION:
                    throw runtime_error("ID_DISCONNECTION_NOTIFICATION.\n");
                case ID_CONNECTION_BANNED:
                    throw runtime_error("ID_CONNECTION_BANNED.\n");
                case ID_CONNECTION_LOST:
                    throw runtime_error("ID_CONNECTION_LOST.\n");
                default:
                    printf("Connection message with identifier %i has arrived in initialization.\n", packet->data[0]);
            }
        }
    }
    puts(msg.c_str());

    if (queue == -1) // connection is failed
        return data;

    {
        RakNet::BitStream bs;
        bs.Write((unsigned char) (ID_USER_PACKET_ENUM + 1));
        peer->Send(&bs, HIGH_PRIORITY, RELIABLE_ORDERED, 0, RakNet::UNASSIGNED_SYSTEM_ADDRESS, true);
    }

    RakNet::Packet *packet;
    bool done = false;
    while (!done)
    {
        for (packet = peer->Receive(); packet; peer->DeallocatePacket(packet), packet = peer->Receive())
        {
            if (packet->data[0] == (ID_USER_PACKET_ENUM + 1))
            {
                RakNet::BitStream bs(packet->data, packet->length, false);
                bs.IgnoreBytes(1);
                size_t length = 0;
                bs.Read(length);
                for (size_t i = 0; i < length; i++)
                {
                    RakNet::RakString str;
                    bs.Read(str);
                    data.players.emplace_back(str.C_String());
                }
                bs.Read(length);
                for (size_t i = 0; i < length; i++)
                {
                    RakNet::RakString str;
                    bs.Read(str);
                    data.plugins.emplace_back(str.C_String());
                }
                done = true;
            }
        }
    }

    peer->Shutdown(0);
    RakSleep(10);
    RakNet::RakPeerInterface::DestroyInstance(peer);
    return data;
}
Пример #18
0
int main(int argc, char **argv)
{
	printf("Server starting... ");
	RakNet::AutopatcherServer autopatcherServer;
	// RakNet::FLP_Printf progressIndicator;
	RakNet::FileListTransfer fileListTransfer;
	static const int workerThreadCount=4; // Used for checking patches only
	static const int sqlConnectionObjectCount=32; // Used for both checking patches and downloading
	AutopatcherPostgreRepository2_WithXDelta connectionObject[sqlConnectionObjectCount];
	RakNet::AutopatcherRepositoryInterface *connectionObjectAddresses[sqlConnectionObjectCount];
	for (int i=0; i < sqlConnectionObjectCount; i++)
		connectionObjectAddresses[i]=&connectionObject[i];
//	fileListTransfer.AddCallback(&progressIndicator);
	autopatcherServer.SetFileListTransferPlugin(&fileListTransfer);
	// PostgreSQL is fast, so this may not be necessary, or could use fewer threads
	// This is used to read increments of large files concurrently, thereby serving users downloads as other users read from the DB
	fileListTransfer.StartIncrementalReadThreads(sqlConnectionObjectCount);
	autopatcherServer.SetMaxConurrentUsers(MAX_INCOMING_CONNECTIONS); // More users than this get queued up
	RakNet::AutopatcherServerLoadNotifier_Printf loadNotifier;
	autopatcherServer.SetLoadManagementCallback(&loadNotifier);
#ifdef USE_TCP
	RakNet::PacketizedTCP packetizedTCP;
	if (packetizedTCP.Start(LISTEN_PORT,MAX_INCOMING_CONNECTIONS)==false)
	{
		printf("Failed to start TCP. Is the port already in use?");
		return 1;
	}
	packetizedTCP.AttachPlugin(&autopatcherServer);
	packetizedTCP.AttachPlugin(&fileListTransfer);
#else
	RakNet::RakPeerInterface *rakPeer;
	rakPeer = RakNet::RakPeerInterface::GetInstance();
	RakNet::SocketDescriptor socketDescriptor(LISTEN_PORT,0);
	rakPeer->Startup(MAX_INCOMING_CONNECTIONS,&socketDescriptor, 1);
	rakPeer->SetMaximumIncomingConnections(MAX_INCOMING_CONNECTIONS);
	rakPeer->AttachPlugin(&autopatcherServer);
	rakPeer->AttachPlugin(&fileListTransfer);
#endif
	printf("started.\n");

	printf("Enter database password:\n");
	char connectionString[256],password[128];
	char username[256];
	strcpy(username, "postgres");
	gets(password);
	if (password[0]==0) strcpy(password, "aaaa");
	strcpy(connectionString, "user="******" password="******"Database connection failed.\n");
			return 1;
		}
	}

	printf("Database connection suceeded.\n");
	printf("Starting threads\n");
	// 4 Worker threads, which is CPU intensive
	// A greater number of SQL connections, which read files incrementally for large downloads
	autopatcherServer.StartThreads(workerThreadCount,sqlConnectionObjectCount, connectionObjectAddresses);
	autopatcherServer.CacheMostRecentPatch(0);
	// autopatcherServer.SetAllowDownloadOfOriginalUnmodifiedFiles(false);
	printf("System ready for connections\n");

	// https://code.google.com/p/xdelta/downloads/list
	printf("Optional: Enter path to xdelta.exe: ");
	Gets(PATH_TO_XDELTA_EXE, sizeof(PATH_TO_XDELTA_EXE));
	if (PATH_TO_XDELTA_EXE[0]==0)
		strcpy(PATH_TO_XDELTA_EXE, "c:/xdelta3-3.0.6-win32.exe");

	if (PATH_TO_XDELTA_EXE[0])
	{
		printf("Enter working directory to store temporary files: ");
		Gets(WORKING_DIRECTORY, sizeof(WORKING_DIRECTORY));
		if (WORKING_DIRECTORY[0]==0)
			GetTempPath(MAX_PATH, WORKING_DIRECTORY);
		if (WORKING_DIRECTORY[strlen(WORKING_DIRECTORY)-1]=='\\' || WORKING_DIRECTORY[strlen(WORKING_DIRECTORY)-1]=='/')
			WORKING_DIRECTORY[strlen(WORKING_DIRECTORY)-1]=0;
	}

	printf("(D)rop database\n(C)reate database.\n(A)dd application\n(U)pdate revision.\n(R)emove application\n(Q)uit\n");

	char ch;
	RakNet::Packet *p;
	while (1)
	{
#ifdef USE_TCP
		RakNet::SystemAddress notificationAddress;
		notificationAddress=packetizedTCP.HasCompletedConnectionAttempt();
		if (notificationAddress!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
			printf("ID_CONNECTION_REQUEST_ACCEPTED\n");
		notificationAddress=packetizedTCP.HasNewIncomingConnection();
		if (notificationAddress!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
			printf("ID_NEW_INCOMING_CONNECTION\n");
		notificationAddress=packetizedTCP.HasLostConnection();
		if (notificationAddress!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
			printf("ID_CONNECTION_LOST\n");

		p=packetizedTCP.Receive();
		while (p)
		{
			packetizedTCP.DeallocatePacket(p);
			p=packetizedTCP.Receive();
		}
#else
		p=rakPeer->Receive();
		while (p)
		{
			if (p->data[0]==ID_NEW_INCOMING_CONNECTION)
				printf("ID_NEW_INCOMING_CONNECTION\n");
			else if (p->data[0]==ID_DISCONNECTION_NOTIFICATION)
				printf("ID_DISCONNECTION_NOTIFICATION\n");
			else if (p->data[0]==ID_CONNECTION_LOST)
				printf("ID_CONNECTION_LOST\n");

			rakPeer->DeallocatePacket(p);
			p=rakPeer->Receive();
		}
#endif

		if (kbhit())
		{
			ch=getch();
			if (ch=='q')
				break;
			else if (ch=='c')
			{
				if (connectionObject[0].CreateAutopatcherTables()==false)
					printf("%s", connectionObject[0].GetLastError());
			}
			else if (ch=='d')
			{
                if (connectionObject[0].DestroyAutopatcherTables()==false)
					printf("%s", connectionObject[0].GetLastError());
			}
			else if (ch=='a')
			{
				printf("Enter application name to add: ");
				char appName[512];
				Gets(appName,sizeof(appName));
				if (appName[0]==0)
					strcpy(appName, "TestApp");

				if (connectionObject[0].AddApplication(appName, username)==false)
					printf("%s", connectionObject[0].GetLastError());
				else
					printf("Done\n");
			}
			else if (ch=='r')
			{
				printf("Enter application name to remove: ");
				char appName[512];
				Gets(appName,sizeof(appName));
				if (appName[0]==0)
					strcpy(appName, "TestApp");

				if (connectionObject[0].RemoveApplication(appName)==false)
					printf("%s", connectionObject[0].GetLastError());
				else
					printf("Done\n");
			}
			else if (ch=='u')
			{
				printf("Enter application name: ");
				char appName[512];
				Gets(appName,sizeof(appName));
				if (appName[0]==0)
					strcpy(appName, "TestApp");

				printf("Enter application directory: ");
				char appDir[512];
				Gets(appDir,sizeof(appDir));
				if (appDir[0]==0)
					strcpy(appDir, "D:\\temp");
				
				if (connectionObject[0].UpdateApplicationFiles(appName, appDir, username, 0)==false)
				{
					printf("%s", connectionObject[0].GetLastError());
				}
				else
				{
					printf("Update success.\n");
					autopatcherServer.CacheMostRecentPatch(appName);
				}
			}
		}

		RakSleep(30);
	}


#ifdef USE_TCP
	packetizedTCP.Stop();
#else
	RakNet::RakPeerInterface::DestroyInstance(rakPeer);
#endif


return 0;
}
Пример #19
0
int main(void)
{
	char str[512];
	
	RakNet::RakPeerInterface *peer = RakNet::RakPeerInterface::GetInstance();
	bool isServer;
	RakNet::Packet *packet;


	printf("(C) or (S)erver?\n");

	Gets(str, sizeof(str));
	if ((str[0]=='c')||(str[0]=='C'))
	{
		RakNet::SocketDescriptor sd;
		peer->Startup(1,&sd, 1);
		isServer = false;
	} else {
		RakNet::SocketDescriptor sd(SERVER_PORT,0);
		peer->Startup(MAX_CLIENTS, &sd, 1);
		isServer = true;
	}


	if (isServer)
	{
		printf("Starting the server.\n");
		// We need to let the server accept incoming connections from the clients
		peer->SetMaximumIncomingConnections(MAX_CLIENTS);
	} else {
		printf("Enter server IP or hit enter for 127.0.0.1\n");
		Gets(str, sizeof(str));
		if (str[0]==0){
			strcpy(str, "127.0.0.1");
		}
		printf("Starting the client.\n");
		peer->Connect(str, SERVER_PORT, 0,0);

	}

	while (1)
	{
		for (packet=peer->Receive(); packet; peer->DeallocatePacket(packet), packet=peer->Receive())
		{
			switch (packet->data[0])
			{
				case ID_REMOTE_DISCONNECTION_NOTIFICATION:
					printf("Another client has disconnected.\n");
					break;
				case ID_REMOTE_CONNECTION_LOST:
					printf("Another client has lost the connection.\n");
					break;
				case ID_REMOTE_NEW_INCOMING_CONNECTION:
					printf("Another client has connected.\n");
					break;
				case ID_CONNECTION_REQUEST_ACCEPTED:
					printf("Our connection request has been accepted.\n");
					break;					
				case ID_NEW_INCOMING_CONNECTION:
					printf("A connection is incoming.\n");
					break;
				case ID_NO_FREE_INCOMING_CONNECTIONS:
					printf("The server is full.\n");
					break;
				case ID_DISCONNECTION_NOTIFICATION:
					if (isServer){
						printf("A client has disconnected.\n");
					} else {
						printf("We have been disconnected.\n");
					}
					break;
				case ID_CONNECTION_LOST:
					if (isServer){
						printf("A client lost the connection.\n");
					} else {
						printf("Connection lost.\n");
					}
					break;
				default:
					printf("Message with identifier %i has arrived.\n", packet->data[0]);
					break;
			}
		}
	}


	RakNet::RakPeerInterface::DestroyInstance(peer);

	return 0;
}
Пример #20
0
int main(int argc, char **argv)
{
	printf("A simple client interface for the advanced autopatcher.\n");
	printf("Use DirectoryDeltaTransfer for a simpler version of an autopatcher.\n");
	printf("Difficulty: Intermediate\n\n");

	printf("Client starting...");
	RakNet::SystemAddress serverAddress=RakNet::UNASSIGNED_SYSTEM_ADDRESS;
	RakNet::AutopatcherClient autopatcherClient;
	RakNet::FileListTransfer fileListTransfer;
	autopatcherClient.SetFileListTransferPlugin(&fileListTransfer);
	unsigned short localPort=0;
	if (argc>=6)
	{
		localPort=atoi(argv[5]);
	}
#ifdef USE_TCP
	RakNet::PacketizedTCP packetizedTCP;
	if (packetizedTCP.Start(localPort,1)==false)
	{
		printf("Failed to start TCP. Is the port already in use?");
		return 1;
	}
	packetizedTCP.AttachPlugin(&autopatcherClient);
	packetizedTCP.AttachPlugin(&fileListTransfer);
#else
	RakNet::RakPeerInterface *rakPeer;
	rakPeer = RakNet::RakPeerInterface::GetInstance();
	RakNet::SocketDescriptor socketDescriptor(localPort,0);
	rakPeer->Startup(1,&socketDescriptor, 1);
	// Plugin will send us downloading progress notifications if a file is split to fit under the MTU 10 or more times
	rakPeer->SetSplitMessageProgressInterval(10);
	rakPeer->AttachPlugin(&autopatcherClient);
	rakPeer->AttachPlugin(&fileListTransfer);
#endif
	printf("started\n");
	char buff[512];
	if (argc<2)
	{
		printf("Enter server IP: ");
		Gets(buff,sizeof(buff));
		if (buff[0]==0)
			//strcpy(buff, "94.198.81.195");
			strcpy(buff, "127.0.0.1");
	}
	else
		strcpy(buff, argv[1]);

#ifdef USE_TCP
	packetizedTCP.Connect(buff,60000,false);
#else
	rakPeer->Connect(buff, 60000, 0, 0);
#endif

	printf("Connecting...\n");
	char appDir[512];
	if (argc<3)
	{
		printf("Enter application directory: ");
		Gets(appDir,sizeof(appDir));
		if (appDir[0]==0)
		{
			strcpy(appDir, "D:/temp2");
		}
	}
	else
		strcpy(appDir, argv[2]);
	char appName[512];
	if (argc<4)
	{
		printf("Enter application name: ");
		Gets(appName,sizeof(appName));
		if (appName[0]==0)
			strcpy(appName, "TestApp");
	}
	else
		strcpy(appName, argv[3]);

	bool patchImmediately=argc>=5 && argv[4][0]=='1';

	if (patchImmediately==false)
		printf("Hit 'q' to quit, 'p' to patch, 'c' to cancel the patch. 'r' to reconnect. 'd' to disconnect.\n");
	else
		printf("Hit 'q' to quit, 'c' to cancel the patch.\n");

	char ch;
	RakNet::Packet *p;
	while (1)
	{
#ifdef USE_TCP
		RakNet::SystemAddress notificationAddress;
		notificationAddress=packetizedTCP.HasCompletedConnectionAttempt();
		if (notificationAddress!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
		{
			printf("ID_CONNECTION_REQUEST_ACCEPTED\n");
			serverAddress=notificationAddress;
		}
		notificationAddress=packetizedTCP.HasNewIncomingConnection();
		if (notificationAddress!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
			printf("ID_NEW_INCOMING_CONNECTION\n");
		notificationAddress=packetizedTCP.HasLostConnection();
		if (notificationAddress!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
			printf("ID_CONNECTION_LOST\n");


		p=packetizedTCP.Receive();
		while (p)
		{
			if (p->data[0]==ID_AUTOPATCHER_REPOSITORY_FATAL_ERROR)
			{
				char buff[256];
				RakNet::BitStream temp(p->data, p->length, false);
				temp.IgnoreBits(8);
				RakNet::StringCompressor::Instance()->DecodeString(buff, 256, &temp);
				printf("ID_AUTOPATCHER_REPOSITORY_FATAL_ERROR\n");
				printf("%s\n", buff);
			}
			else if (p->data[0]==ID_AUTOPATCHER_FINISHED)
			{
				printf("ID_AUTOPATCHER_FINISHED with server time %f\n", autopatcherClient.GetServerDate());
				double srvDate=autopatcherClient.GetServerDate();
				FILE *fp = fopen("srvDate", "wb");
				fwrite(&srvDate,sizeof(double),1,fp);
				fclose(fp);
			}
			else if (p->data[0]==ID_AUTOPATCHER_RESTART_APPLICATION)
				printf("Launch \"AutopatcherClientRestarter.exe autopatcherRestart.txt\"\nQuit this application immediately after to unlock files.\n");

			packetizedTCP.DeallocatePacket(p);
			p=packetizedTCP.Receive();
		}
#else
		p=rakPeer->Receive();
		while (p)
		{
			if (p->data[0]==ID_DISCONNECTION_NOTIFICATION)
				printf("ID_DISCONNECTION_NOTIFICATION\n");
			else if (p->data[0]==ID_CONNECTION_LOST)
				printf("ID_CONNECTION_LOST\n");
			else if (p->data[0]==ID_CONNECTION_REQUEST_ACCEPTED)
			{
				printf("ID_CONNECTION_REQUEST_ACCEPTED\n");
				serverAddress=p->systemAddress;
			}
			else if (p->data[0]==ID_CONNECTION_ATTEMPT_FAILED)
				printf("ID_CONNECTION_ATTEMPT_FAILED\n");
			else if (p->data[0]==ID_NO_FREE_INCOMING_CONNECTIONS)
				printf("ID_NO_FREE_INCOMING_CONNECTIONS\n");
			else if (p->data[0]==ID_AUTOPATCHER_REPOSITORY_FATAL_ERROR)
			{
				char buff[256];
				RakNet::BitStream temp(p->data, p->length, false);
				temp.IgnoreBits(8);
				RakNet::StringCompressor::Instance()->DecodeString(buff, 256, &temp);
				printf("ID_AUTOPATCHER_REPOSITORY_FATAL_ERROR\n");
				printf("%s\n", buff);
			}
			else if (p->data[0]==ID_AUTOPATCHER_FINISHED)
			{
				printf("ID_AUTOPATCHER_FINISHED with server time %f\n", autopatcherClient.GetServerDate());
				double srvDate=autopatcherClient.GetServerDate();
				FILE *fp = fopen("srvDate", "wb");
				fwrite(&srvDate,sizeof(double),1,fp);
				fclose(fp);
			}
			else if (p->data[0]==ID_AUTOPATCHER_RESTART_APPLICATION)
				printf("Launch \"AutopatcherClientRestarter.exe autopatcherRestart.txt\"\nQuit this application immediately after to unlock files.\n");

			rakPeer->DeallocatePacket(p);
			p=rakPeer->Receive();
		}
#endif

		if (kbhit())
			ch=getch();
		else
			ch=0;

		if (ch=='q')
			break;
		else if (ch=='r')
		{
#ifdef USE_TCP
			packetizedTCP.Connect(buff,60000,false);
#else
			rakPeer->Connect(buff, 60000, 0, 0);
#endif
		}
		else if (ch=='d')
		{
#ifdef USE_TCP
			packetizedTCP.CloseConnection(serverAddress);
#else
			rakPeer->CloseConnection(serverAddress, true);
#endif
		}
		else if (ch=='p' || (serverAddress!=RakNet::UNASSIGNED_SYSTEM_ADDRESS && patchImmediately==true))
		{
			patchImmediately=false;
			char restartFile[512];
			strcpy(restartFile, appDir);
			strcat(restartFile, "/autopatcherRestart.txt");

			double lastUpdateDate;
			FILE *fp = fopen("srvDate", "rb");
			if (fp)
			{
				fread(&lastUpdateDate, sizeof(lastUpdateDate), 1, fp);
				fclose(fp);
			}
			else
				lastUpdateDate=0;

			if (autopatcherClient.PatchApplication(appName, appDir, lastUpdateDate, serverAddress, &transferCallback, restartFile, argv[0]))
			{
				printf("Patching process starting.\n");
			}
			else
			{
				printf("Failed to start patching.\n");
			}
		}
		else if (ch=='c')
		{
			autopatcherClient.Clear();
			printf("Autopatcher cleared.\n");
		}

		RakSleep(30);
	}

	// Dereference so the destructor doesn't crash
	autopatcherClient.SetFileListTransferPlugin(0);

#ifdef USE_TCP
	packetizedTCP.Stop();
#else
	rakPeer->Shutdown(500,0);
	RakNet::RakPeerInterface::DestroyInstance(rakPeer);
#endif
	return 1;
}
Пример #21
0
int main()
{
	RakNet::Packet *packet;
	RakNet::RakPeerInterface *rakPeer;
	bool isConnected=false;
	rakPeer=RakNet::RakPeerInterface::GetInstance();
	char command[512];
	printf("This sample demonstrates connecting to the command console.\n");
	printf("using the RakNet transport protocol\n");
	printf("It's the equivalent of a secure telnet client\n");
	printf("See the 'CommandConsoleServer' project.\n");
	printf("Difficulty: Intermediate\n\n");

	printf("RakNet secure command console.\n");
	printf("Commands:\n");
	printf("/Connect\n");
	printf("/Disconnect\n");
	printf("/Quit\n");
	printf("Any other command goes to the remote console\n");
	while (1)
	{
		if (kbhit())
		{
			Gets(command,sizeof(command));

			if (stricmp(command, "/quit")==0)
			{
				printf("Goodbye.\n");
				rakPeer->Shutdown(500, 0);
				return 0;
			}
			else if (stricmp(command, "/disconnect")==0)
			{
				if (isConnected)
				{
					rakPeer->Shutdown(500, 0);
					isConnected=false;
					printf("Disconnecting.\n");
				}
				else
				{
					printf("Not currently connected.\n");
				}
			}
			else if (stricmp(command, "/connect")==0)
			{
				if (isConnected)
				{
					printf("Disconnect first.\n");
				}
				else
				{
					char ip[128];
					char remotePort[64];
					char password[512];
					char localPort[64];
					printf("Enter remote IP: ");
					do {
						Gets(ip, sizeof(ip));
					} while(ip[0]==0);
					printf("Enter remote port: ");
					do {
						Gets(remotePort,sizeof(remotePort));
					} while(remotePort[0]==0);
					printf("Enter local port (enter for 0): ");
					Gets(localPort,sizeof(localPort));
					if (localPort[0]==0)
					{
						strcpy(localPort, "0");
					}
					printf("Enter console password (enter for none): ");
					Gets(password,sizeof(password));
					RakNet::SocketDescriptor socketDescriptor((int) atoi(localPort),0);
					if (rakPeer->Startup(1, &socketDescriptor, 1)==RakNet::RAKNET_STARTED)
					{
						int passwordLen;
						if (password[0])
							passwordLen=(int) strlen(password)+1;
						else
							passwordLen=0;
						if (rakPeer->Connect(ip, (int) atoi(remotePort), password, passwordLen)==RakNet::CONNECTION_ATTEMPT_STARTED)
							printf("Connecting...\nNote: if the password is wrong the other system will ignore us.\n");
						else
						{
							printf("Connect call failed.\n");
							rakPeer->Shutdown(0, 0);
						}
					}
					else
						printf("Initialize call failed.\n");					
					
				}				
			}
			else
			{
				if (isConnected)
				{
					RakNet::BitStream str;
					str.Write((unsigned char) ID_TRANSPORT_STRING);
					str.Write(command, (int) strlen(command)+1);
					rakPeer->Send(&str, MEDIUM_PRIORITY, RELIABLE_ORDERED, 0, RakNet::UNASSIGNED_SYSTEM_ADDRESS, true);
				}
				else
				{
					printf("You must be connected to send commands.\n");
				}
			}
		}

		packet = rakPeer->Receive();
		if (packet)
		{
			switch (packet->data[0])
			{
			case ID_DISCONNECTION_NOTIFICATION:
				printf("The server disconnected us.\n");
				isConnected=false;
				break;
			case ID_CONNECTION_BANNED:
				printf("We are banned from this server.\n");
				isConnected=false;
				break;
			case ID_CONNECTION_ATTEMPT_FAILED:
				printf("Connection attempt failed.\nThe password was wrong or there is no responsive machine at that IP/port.\n");
				isConnected=false;
				break;
			case ID_NO_FREE_INCOMING_CONNECTIONS:
				printf("Server is full.\n");
				isConnected=false;
				break;
			case ID_CONNECTION_LOST:
				printf("We lost the connection.\n");
				isConnected=false;
				break;
			case ID_CONNECTION_REQUEST_ACCEPTED:
				printf("Connection accepted.\n");
				isConnected=true;
				break;
			case ID_TRANSPORT_STRING:
				printf("%s", packet->data+1);
				break;
			}

			rakPeer->DeallocatePacket(packet);
		}

		// This sleep keeps RakNet responsive
#ifdef _WIN32
		Sleep(30);
#else
		usleep(30 * 1000);
#endif
	}

	return 0;
}
Пример #22
0
//This static method is called when the client wants to connect to the server
void Session::StartClient(void * pVoid){
	//A parameter list is given with needed variables
	ArgumentList* pArgumentList = (ArgumentList*)pVoid;
	RakNet::RakPeerInterface* pClient;
	pClient = pArgumentList->inter;
	SessionType type = pArgumentList->type;
	RakNet::RPC3* rpc3Inst = pArgumentList->rpc3;
	SystemAddress clientID=UNASSIGNED_SYSTEM_ADDRESS;

	//Register the RPC3 functions we want to call upon
	RPC3_REGISTER_FUNCTION(rpc3Inst, ReceiveInformation);
	RPC3_REGISTER_FUNCTION(rpc3Inst, UpdateCharacter);
	RPC3_REGISTER_FUNCTION(rpc3Inst, UpdateCharacterVelocity);
	RPC3_REGISTER_FUNCTION(rpc3Inst, SyncClients);
	RPC3_REGISTER_FUNCTION(rpc3Inst, ReceiveID);
	RPC3_REGISTER_FUNCTION(rpc3Inst, RemoveCharacter);
	
	//Create the basic connection with help of RakNet
	SocketDescriptor socketDescriptor(0,0);
	socketDescriptor.socketFamily=AF_INET;
	pClient->Startup(1,&socketDescriptor, 1);
	pClient->Ping( "255.255.255.255", 50000, true, 0 );

	// Holds packets
	Packet* p;

	//Make sure the RPC3 is attached as a plugin, else it won't work
	pClient->AttachPlugin(rpc3Inst);

	char message[2048];
	// Loop for input
	while (Session::threading)
	{
		// This sleep keeps RakNet responsive
		RakSleep(30);
		#ifdef _WIN32
			Sleep(30);
		#else
			usleep(30 * 1000);
		#endif

		// Get a packet from either the server or the client
		for (p=pClient->Receive(); p; pClient->DeallocatePacket(p), p=pClient->Receive())
		{
			switch (p->data[0])
			{
			case ID_DISCONNECTION_NOTIFICATION:
				printf("ID_DISCONNECTION_NOTIFICATION\n");
				break;
			case ID_ALREADY_CONNECTED:
				printf("ID_ALREADY_CONNECTED\n");
				break;
			case ID_CONNECTION_ATTEMPT_FAILED:
				printf("Connection attempt failed\n");
				break;
			case ID_NO_FREE_INCOMING_CONNECTIONS:
				printf("ID_NO_FREE_INCOMING_CONNECTIONS\n");
				break;
			case ID_UNCONNECTED_PONG:
				// Found the server
				pClient->Connect(p->systemAddress.ToString(false),p->systemAddress.GetPort(),0,0,0);
				break;
			case ID_CONNECTION_REQUEST_ACCEPTED:
				// This tells the client they have connected
				printf("ID_CONNECTION_REQUEST_ACCEPTED\n");
				Game::getSingletonPtr()->CreateCharacter("PlayerHost");
				//Game::getSingletonPtr()->SetPlayer(
				break;
			case ID_NEW_INCOMING_CONNECTION:
			{
				printf("New incoming connection");
				break;
			}
			case ID_RPC_REMOTE_ERROR:
				{
					// Recipient system returned an error
					switch (p->data[1])
					{
					case RakNet::RPC_ERROR_NETWORK_ID_MANAGER_UNAVAILABLE:
						printf("RPC_ERROR_NETWORK_ID_MANAGER_UNAVAILABLE\n");
						break;
					case RakNet::RPC_ERROR_OBJECT_DOES_NOT_EXIST:
						printf("RPC_ERROR_OBJECT_DOES_NOT_EXIST\n");
						break;
					case RakNet::RPC_ERROR_FUNCTION_INDEX_OUT_OF_RANGE:
						printf("RPC_ERROR_FUNCTION_INDEX_OUT_OF_RANGE\n");
						break;
					case RakNet::RPC_ERROR_FUNCTION_NOT_REGISTERED:
						printf("RPC_ERROR_FUNCTION_NOT_REGISTERED\n");
						break;
					case RakNet::RPC_ERROR_FUNCTION_NO_LONGER_REGISTERED:
						printf("RPC_ERROR_FUNCTION_NO_LONGER_REGISTERED\n");
						break;
					case RakNet::RPC_ERROR_CALLING_CPP_AS_C:
						printf("RPC_ERROR_CALLING_CPP_AS_C\n");
						break;
					case RakNet::RPC_ERROR_CALLING_C_AS_CPP:
						printf("RPC_ERROR_CALLING_C_AS_CPP\n");
						break;
					}
					printf("Function: %s", p->data+2);
				}
			}
		}
	}
	//When we are done as a client, close everything and delete RPC3
	Session::threading = false;
	pClient->Shutdown(20,0);
	RakNet::RakPeerInterface::DestroyInstance(pClient);
	delete rpc3Inst;
}
int main(void)
{
	char ch;

#ifdef USE_TCP
	RakNet::PacketizedTCP tcp1;
#else
	RakNet::RakPeerInterface *rakPeer;
#endif

	// directoryDeltaTransfer is the main plugin that does the work for this sample.
	RakNet::DirectoryDeltaTransfer directoryDeltaTransfer;
	// The fileListTransfer plugin is used by the DirectoryDeltaTransfer plugin and must also be registered (you could use this yourself too if you wanted, of course).
	RakNet::FileListTransfer fileListTransfer;
	// Read files in parts, rather than the whole file from disk at once
	RakNet::IncrementalReadInterface iri;
	directoryDeltaTransfer.SetDownloadRequestIncrementalReadInterface(&iri, 1000000);

#ifdef USE_TCP
	tcp1.AttachPlugin(&directoryDeltaTransfer);
	tcp1.AttachPlugin(&fileListTransfer);
#else
	rakPeer = RakNet::RakPeerInterface::GetInstance();
	rakPeer->AttachPlugin(&directoryDeltaTransfer);
	rakPeer->AttachPlugin(&fileListTransfer);
	// Get download progress notifications.  Handled by the plugin.
	rakPeer->SetSplitMessageProgressInterval(100);
#endif
	directoryDeltaTransfer.SetFileListTransferPlugin(&fileListTransfer);

	printf("This sample demonstrates the plugin to incrementally transfer compressed\n");
	printf("deltas of directories.  In essence, it's a simple autopatcher.\n");
	printf("Unlike the full autopatcher, it has no dependencies.  It is suitable for\n");
	printf("patching from non-dedicated servers at runtime.\n");
	printf("Difficulty: Intermediate\n\n");

	printf("Enter listen port. Enter for default. If running two instances on the\nsame computer, use 0 for the client.\n");
	unsigned short localPort;
	char str[256];
	Gets(str, sizeof(str));
	if (str[0]==0)
		localPort=60000;
	else
		localPort=atoi(str);
	RakNet::SocketDescriptor socketDescriptor(localPort,0);
#ifdef USE_TCP
	bool b=tcp1.Start(localPort,8);
	RakAssert(b);
#else
	if (rakPeer->Startup(8,&socketDescriptor, 1)!=RakNet::RAKNET_STARTED)
	{
		RakNet::RakPeerInterface::DestroyInstance(rakPeer);
		printf("RakNet initialize failed.  Possibly duplicate port.\n");
		return 1;
	}
	rakPeer->SetMaximumIncomingConnections(8);
#endif

	printf("Commands:\n");
	printf("(S)et application directory.\n");
	printf("(A)dd allowed uploads from subdirectory.\n");
	printf("(D)ownload from subdirectory.\n");
	printf("(C)lear allowed uploads.\n");
	printf("C(o)nnect to another system.\n");
	printf("(Q)uit.\n");

	RakNet::SystemAddress sysAddrZero=RakNet::UNASSIGNED_SYSTEM_ADDRESS;
	RakNet::TimeMS nextStatTime = RakNet::GetTimeMS() + 1000;

	RakNet::Packet *p;
	while (1)
	{
		/*
		if (//directoryDeltaTransfer.GetNumberOfFilesForUpload()>0 &&
			RakNet::GetTimeMS() > nextStatTime)
		{
			// If sending, periodically show connection stats
			char statData[2048];
			RakNetStatistics *statistics = rakPeer->GetStatistics(rakPeer->GetSystemAddressFromIndex(0));
		//	if (statistics->messagesOnResendQueue>0 || statistics->internalOutputQueueSize>0)
			if (rakPeer->GetSystemAddressFromIndex(0)!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
			{
				StatisticsToString(statistics, statData, 2);
				printf("%s\n", statData);
			}
			
			nextStatTime=RakNet::GetTimeMS()+5000;
		}
		*/

		// Process packets
#ifdef USE_TCP
		p=tcp1.Receive();
#else
		p=rakPeer->Receive();
#endif

#ifdef USE_TCP
		RakNet::SystemAddress sa;
		sa=tcp1.HasNewIncomingConnection();
		if (sa!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
		{
			printf("ID_NEW_INCOMING_CONNECTION\n");
			sysAddrZero=sa;
		}
		if (tcp1.HasLostConnection()!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
			printf("ID_DISCONNECTION_NOTIFICATION\n");
		if (tcp1.HasFailedConnectionAttempt()!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
			printf("ID_CONNECTION_ATTEMPT_FAILED\n");
		sa=tcp1.HasCompletedConnectionAttempt();
		if (sa!=RakNet::UNASSIGNED_SYSTEM_ADDRESS)
		{
			printf("ID_CONNECTION_REQUEST_ACCEPTED\n");
			sysAddrZero=sa;
		}
#endif

		while (p)
		{

#ifdef USE_TCP
			tcp1.DeallocatePacket(p);
			tcp1.Receive();
#else

			if (p->data[0]==ID_NEW_INCOMING_CONNECTION)
			{
				printf("ID_NEW_INCOMING_CONNECTION\n");
				sysAddrZero=p->systemAddress;
			}
			else if (p->data[0]==ID_CONNECTION_REQUEST_ACCEPTED)
			{
				printf("ID_CONNECTION_REQUEST_ACCEPTED\n");
				sysAddrZero=p->systemAddress;
			}
			else if (p->data[0]==ID_DISCONNECTION_NOTIFICATION)
				printf("ID_DISCONNECTION_NOTIFICATION\n");
			else if (p->data[0]==ID_CONNECTION_LOST)
				printf("ID_CONNECTION_LOST\n");
			else if (p->data[0]==ID_CONNECTION_ATTEMPT_FAILED)
				printf("ID_CONNECTION_ATTEMPT_FAILED\n");
			rakPeer->DeallocatePacket(p);
			p=rakPeer->Receive();
#endif
		}

		if (kbhit())
		{
			ch=getch();
			if (ch=='s')
			{
				printf("Enter application directory\n");
				Gets(str, sizeof(str));
				if (str[0]==0)
					strcpy(str, "C:/Temp");
				directoryDeltaTransfer.SetApplicationDirectory(str);
				printf("This directory will be prefixed to upload and download subdirectories.\n");
			}
			else if (ch=='a')
			{
				printf("Enter uploads subdirectory\n");
				Gets(str, sizeof(str));
				directoryDeltaTransfer.AddUploadsFromSubdirectory(str);
				printf("%i files for upload.\n", directoryDeltaTransfer.GetNumberOfFilesForUpload());
			}
			else if (ch=='d')
			{
				char subdir[256];
				char outputSubdir[256];
				printf("Enter remote subdirectory to download from.\n");
				printf("This directory may be any uploaded directory, or a subdir therein.\n");
				Gets(subdir,sizeof(subdir));
				printf("Enter subdirectory to output to.\n");
				Gets(outputSubdir,sizeof(outputSubdir));
                
				unsigned short setId;

				setId=directoryDeltaTransfer.DownloadFromSubdirectory(subdir, outputSubdir, true, sysAddrZero, &transferCallback, HIGH_PRIORITY, 0, 0);
				if (setId==(unsigned short)-1)
					printf("Download failed.  Host unreachable.\n");
				else
					printf("Downloading set %i\n", setId);
			}
			else if (ch=='c')
			{
				directoryDeltaTransfer.ClearUploads();
				printf("Uploads cleared.\n");
			}
			else if (ch=='o')
			{
				char host[256];
				printf("Enter host IP: ");
				Gets(host,sizeof(host));
				if (host[0]==0)
					strcpy(host, "127.0.0.1");
				unsigned short remotePort;
				printf("Enter host port: ");
				Gets(str, sizeof(str));
				if (str[0]==0)
					remotePort=60000;
				else
					remotePort=atoi(str);
#ifdef USE_TCP
				tcp1.Connect(host,remotePort,false);
#else
				rakPeer->Connect(host, remotePort, 0, 0);
#endif
				printf("Connecting.\n");
			}
			else if (ch=='q')
			{
				printf("Bye!\n");
#ifdef USE_TCP
				tcp1.Stop();
#else
				rakPeer->Shutdown(1000,0);
#endif
				break;
			}
		}

		// Keeps the threads responsive
		RakSleep(0);
	}

#ifdef USE_TCP
#else
	RakNet::RakPeerInterface::DestroyInstance(rakPeer);
#endif

	return 0;
}
Пример #24
0
void Video::run(const char* ip) {
	unsigned int maxConnectionsAllowed = 1;
	unsigned int maxPlayersPerServer = 1;
	unsigned short serverPort = 7000;

	RakNet::RakPeerInterface *rakPeer = RakNet::RakPeerInterface::GetInstance();
	RakNet::SocketDescriptor socketDescriptor(serverPort, 0);

	if (rakPeer->Startup(maxConnectionsAllowed, &socketDescriptor, 1) != RakNet::RAKNET_STARTED) {
		std::cerr << "Startup fail:" << std::endl;
		RakNet::RakPeerInterface::DestroyInstance(rakPeer);
		return;
	}

	rakPeer->SetMaximumIncomingConnections(maxPlayersPerServer);

	RakNet::Packet *packet;
	unsigned char typeId;
	bool connected = false;
	char key;

	RakNet::SystemAddress address;

	if (ip) {
		std::cout << "Connect: " << ip << std::endl;
		rakPeer->Connect(ip, serverPort, 0, 0);
	}

	cv::namedWindow("MyVideo", CV_WINDOW_AUTOSIZE | CV_GUI_NORMAL);
	cv::createTrackbar("AlphaTrackbar", "MyVideo", &alpha_slider, 100);

	capture.open(0);
	if (!capture.isOpened()) {
		std::cout << "Capture open fail" << std::endl;
		return;
	}
	capture.set(CV_CAP_PROP_FRAME_WIDTH, 320);
	capture.set(CV_CAP_PROP_FRAME_HEIGHT, 240);
	capture.set(CV_CAP_PROP_FOURCC, CV_FOURCC('X', '2', '6', '4'));

	cv::namedWindow("RemoteVideo", 1);

	while (1) {
		const time_t t = time(NULL);
		struct tm* current_time = localtime(&t);
		std::cout << "current time is " << current_time->tm_sec << std::endl;

		cv::Mat frame;
		capture.read(frame);
		cv::imshow("MyVideo", frame);

		packet = rakPeer->Receive();
		if (packet) {
			RakNet::BitStream bitStream(packet->data, packet->length, false);

			bitStream.Read(typeId);
			switch (typeId) {
				case ID_CONNECTION_REQUEST_ACCEPTED:
				{
					std::cout << "ID_CONNECTION_REQUEST_ACCEPTED" << ip << std::endl;
					address = packet->systemAddress;
					connected = true;
					break;
				}
				case ID_NEW_INCOMING_CONNECTION:
				{
					std::cout << "ID_NEW_INCOMING_CONNECTION" << ip << std::endl;
					address = packet->systemAddress;
					connected = true;
					break;
				}
				case ID_DISCONNECTION_NOTIFICATION:
				{
					connected = false;
					break;
				}
				case ID_CONNECTION_LOST:
				{
					connected = false;
					break;
				}
				case ID_USER_PACKET_ENUM:
				{					
					int cols, rows, type, channels, size;
					
					bitStream.Read(cols);
					bitStream.Read(rows);
					bitStream.Read(type);
					bitStream.Read(channels);
					bitStream.Read(size);
					
					char* data = new char[size];
					bitStream.Read(data, size);
					
					cv::Mat mat(cols, rows, type, (uchar*)data);
							
					cv::imshow("RemoteVideo", mat.reshape(channels, rows));
					
					delete data;
					break;
				}
				default:
					break;
			}
			rakPeer->DeallocatePacket(packet);
		}

		if (connected) {
			int size = frame.total()*frame.elemSize();

			RakNet::BitStream sendStream;
			sendStream.Write((RakNet::MessageID)ID_USER_PACKET_ENUM);
			sendStream.Write(frame.cols);
			sendStream.Write(frame.rows);
			sendStream.Write((int)frame.type());
			sendStream.Write(frame.channels());
			sendStream.Write(size);
			sendStream.Write((const char *)frame.data, size);

			rakPeer->Send(&sendStream, LOW_PRIORITY, UNRELIABLE_SEQUENCED, 0, address, false);
			//rakPeer->Send(&sendStream, IMMEDIATE_PRIORITY, UNRELIABLE_SEQUENCED, 0, RakNet::UNASSIGNED_SYSTEM_ADDRESS, true);
		}
		key = cvWaitKey(10);
		if (char(key) == 27) {
			break;
		}
	}

	rakPeer->Shutdown(300);
	RakNet::RakPeerInterface::DestroyInstance(rakPeer);

	cv::destroyAllWindows();
}