bool FStreamingNetworkPlatformFile::SendReadMessage(uint64 HandleId, uint8* Destination, int64 BytesToRead) { FScopeLock ScopeLock(&SynchronizationObject); // Send the filename over. FStreamingNetworkFileArchive Payload(NFS_Messages::Read); Payload << HandleId; Payload << BytesToRead; // Send the filename over FArrayReader Response; if (SendPayloadAndReceiveResponse(Payload, Response) == false) { return false; } // Get the server number of bytes read. int64 ServerBytesRead = 0; Response << ServerBytesRead; bool bSuccess = (ServerBytesRead == BytesToRead); if (bSuccess) { // Get the data. Response.Serialize(Destination, BytesToRead); } return bSuccess; }
bool FTCPTransport::SendPayloadAndReceiveResponse(TArray<uint8>& In, TArray<uint8>& Out) { bool SendResult = false; #if USE_MCSOCKET_FOR_NFS SendResult = FNFSMessageHeader::WrapAndSendPayload(In, FSimpleAbstractSocket_FMultichannelTCPSocket(MCSocket, NFS_Channels::Main)); #else SendResult = FNFSMessageHeader::WrapAndSendPayload(In, FSimpleAbstractSocket_FSocket(FileSocket)); #endif if (!SendResult) return false; FArrayReader Response; bool RetResult = false; #if USE_MCSOCKET_FOR_NFS RetResult = FNFSMessageHeader::ReceivePayload(Response, FSimpleAbstractSocket_FMultichannelTCPSocket(MCSocket, NFS_Channels::Main)); #else RetResult = FNFSMessageHeader::ReceivePayload(Response, FSimpleAbstractSocket_FSocket(FileSocket)); #endif if (RetResult) { Out.Append( Response.GetData(), Response.Num()); return true; } return false; }
bool FNFSMessageHeader::ReceivePayload(FArrayReader& OutPayload, const FSimpleAbstractSocket& Socket) { // make room to receive a header TArray<uint8> HeaderBytes; int32 Size = sizeof(FNFSMessageHeader); HeaderBytes.AddZeroed(Size); if (!Socket.Receive(HeaderBytes.GetData(), Size)) { UE_LOG(LogSockets, Error, TEXT("Unable to read full header")); return false; } // parse it as a header (doing any byte swapping as needed) FMemoryReader Reader(HeaderBytes); FNFSMessageHeader Header(Socket); Reader << Header; // make sure it's valid if (Header.Magic != Socket.GetMagic()) { UE_LOG(LogSockets, Error, TEXT("Bad network header magic")); return false; } if (!Header.PayloadSize) { UE_LOG(LogSockets, Error, TEXT("Empty payload")); return false; } // was the header byteswapped? If so, make the archive byteswapped OutPayload.SetByteSwapping(Reader.ForceByteSwapping()); // we are going to append to the payload, so note how much data is in it now int32 PayloadOffset = OutPayload.AddUninitialized(Header.PayloadSize); // put the read head at the start of the new data OutPayload.Seek(PayloadOffset); // receive the payload if (!Socket.Receive(OutPayload.GetData() + PayloadOffset, Header.PayloadSize)) { UE_LOG(LogSockets, Error, TEXT("Unable to read full payload")); return false; } // make sure it's valid uint32 ActualPayloadCrc = FCrc::MemCrc_DEPRECATED(OutPayload.GetData() + PayloadOffset, Header.PayloadSize); if (Header.PayloadCrc != ActualPayloadCrc) { UE_LOG(LogSockets, Error, TEXT("Payload Crc failure.")); return false; } // success! return true; }
bool FSocketMessageHeader::ReceivePayload(FArrayReader& OutPayload, FSocket* Socket, bool* unknown_error) { TArray<uint8> HeaderBytes; int32 Size = sizeof(FSocketMessageHeader); HeaderBytes.AddZeroed(Size); if (!SocketReceiveAll(Socket, HeaderBytes.GetData(), Size, unknown_error)) { // false here means socket disconnected. // UE_LOG(LogUnrealCV, Error, TEXT("Unable to read header, Socket disconnected.")); UE_LOG(LogUnrealCV, Log, TEXT("Client disconnected.")); return false; } FMemoryReader Reader(HeaderBytes); uint32 Magic; Reader << Magic; if (Magic != FSocketMessageHeader::DefaultMagic) { UE_LOG(LogUnrealCV, Error, TEXT("Bad network header magic")); return false; } uint32 PayloadSize; Reader << PayloadSize; if (!PayloadSize) { UE_LOG(LogUnrealCV, Error, TEXT("Empty payload")); return false; } int32 PayloadOffset = OutPayload.AddUninitialized(PayloadSize); OutPayload.Seek(PayloadOffset); if (!SocketReceiveAll(Socket, OutPayload.GetData() + PayloadOffset, PayloadSize, unknown_error)) { UE_LOG(LogUnrealCV, Error, TEXT("Unable to read full payload, Socket disconnected.")); return false; } // Skip CRC checking in FNFSMessageHeader return true; }
bool FNetworkPlatformFile::InitializeInternal(IPlatformFile* Inner, const TCHAR* HostIP) { // This platform file requires an inner. check(Inner != NULL); InnerPlatformFile = Inner; if (HostIP == NULL) { UE_LOG(LogNetworkPlatformFile, Error, TEXT("No Host IP specified in the commandline.")); bIsUsable = false; return false; } // Save and Intermediate directories are always local LocalDirectories.Add(FPaths::EngineDir() / TEXT("Binaries")); LocalDirectories.Add(FPaths::EngineIntermediateDir()); LocalDirectories.Add(FPaths::GameDir() / TEXT("Binaries")); LocalDirectories.Add(FPaths::GameIntermediateDir()); LocalDirectories.Add(FPaths::GameSavedDir() / TEXT("Backup")); LocalDirectories.Add(FPaths::GameSavedDir() / TEXT("Config")); LocalDirectories.Add(FPaths::GameSavedDir() / TEXT("Logs")); LocalDirectories.Add(FPaths::GameSavedDir() / TEXT("Sandboxes")); InnerPlatformFile->GetLowerLevel()->AddLocalDirectories(LocalDirectories); FNetworkFileArchive Payload(NFS_Messages::Heartbeat); FArrayReader Out; if (!SendPayloadAndReceiveResponse(Payload,Out)) bIsUsable = true; // lets see we can test whether the server is up. if (Out.Num()) { FCommandLine::AddToSubprocessCommandline( *FString::Printf( TEXT("-FileHostIP=%s"), HostIP ) ); bIsUsable = true; } return bIsUsable; }
bool ImportObjImpl::GetMessage(FString & Result) { // get all data from client and create one long FString from it // return the result when the client is out of pending data. //FString Result; uint32 DataSize = 0; while (Client->HasPendingData(DataSize) && DataSize > 0) { //UE_LOG(LogM2U, Log, TEXT("pending data size %i"), DataSize); // create data array to read from client //FArrayReaderPtr Data = MakeShareable(new FArrayReader(true)); FArrayReader Data; Data.SetNumUninitialized(DataSize); int32 BytesRead = 0; // read pending data into the Data array reader if (Client->Recv(Data.GetData(), Data.Num(), BytesRead)) { //UE_LOG(LogM2U, Log, TEXT("DataNum %i, BytesRead: %i"), Data.Num(), BytesRead); // the data we receive is supposed to be ansi, but we will work with TCHAR, so we have to convert int32 DestLen = TStringConvert<ANSICHAR, TCHAR>::ConvertedLength((char*)(Data.GetData()), Data.Num()); //UE_LOG(LogM2U, Log, TEXT("DestLen will be %i"), DestLen); TCHAR* Dest = new TCHAR[DestLen + 1]; TStringConvert<ANSICHAR, TCHAR>::Convert(Dest, DestLen, (char*)(Data.GetData()), Data.Num()); Dest[DestLen] = '\0'; //FString Text(Dest); // FString from tchar array //UE_LOG(LogM2U, Log, TEXT("server received %s"), *Text); //UE_LOG(LogM2U, Log, TEXT("Server received: %s"), Dest); //FString Result = ExecuteCommand(Dest, this); //SendResponse(Result); // add all the message parts to the Result Result += Dest; delete Dest; } }// while if (!Result.IsEmpty()) return true; else return false; }
bool FTcpMessageTransportConnection::ReceiveMessages() { uint32 PendingDataSize = 0; // check if the socket has closed { int32 BytesRead; uint8 Dummy; if (!Socket->Recv(&Dummy, 1, BytesRead, ESocketReceiveFlags::Peek)) { return false; } } if (!bReceivedHeader) { if (Socket->HasPendingData(PendingDataSize) && PendingDataSize >= sizeof(FTcpMessageHeader)) { FArrayReader HeaderData = FArrayReader(true); HeaderData.SetNumUninitialized(sizeof(FTcpMessageHeader)); int32 BytesRead = 0; if (!Socket->Recv(HeaderData.GetData(), sizeof(FTcpMessageHeader), BytesRead)) { return false; } check(BytesRead == sizeof(FTcpMessageHeader)); TotalBytesReceived += BytesRead; FTcpMessageHeader MessageHeader; HeaderData << MessageHeader; if (!MessageHeader.IsValid()) { return false; } else { RemoteNodeId = MessageHeader.GetNodeId(); RemoteProtocolVersion = MessageHeader.GetVersion(); bReceivedHeader = true; OpenedTime = FDateTime::UtcNow(); UpdateConnectionState(STATE_Connected); } } else { // no header yet return true; } } // keep going until we have no data. for(;;) { int32 BytesRead = 0; // See if we're in the process of receiving a (large) message if (RecvMessageDataRemaining == 0) { // no partial message. Try to receive the size of a message if (!Socket->HasPendingData(PendingDataSize) || (PendingDataSize < sizeof(uint32))) { // no messages return true; } FArrayReader MessagesizeData = FArrayReader(true); MessagesizeData.SetNumUninitialized(sizeof(uint32)); // read message size from the stream BytesRead = 0; if (!Socket->Recv(MessagesizeData.GetData(), sizeof(uint32), BytesRead)) { return false; } check(BytesRead == sizeof(uint32)); TotalBytesReceived += BytesRead; // Setup variables to receive the message MessagesizeData << RecvMessageDataRemaining; RecvMessageData = MakeShareable(new FArrayReader(true)); RecvMessageData->SetNumUninitialized(RecvMessageDataRemaining); check(RecvMessageDataRemaining > 0); } BytesRead = 0; if (!Socket->Recv(RecvMessageData->GetData() + RecvMessageData->Num() - RecvMessageDataRemaining, RecvMessageDataRemaining, BytesRead)) { return false; } if (BytesRead > 0) { check(BytesRead <= RecvMessageDataRemaining); TotalBytesReceived += BytesRead; RecvMessageDataRemaining -= BytesRead; if (RecvMessageDataRemaining == 0) { // @todo gmp: move message deserialization into an async task FTcpDeserializedMessage* DeserializedMessage = new FTcpDeserializedMessage(nullptr); if (DeserializedMessage->Deserialize(RecvMessageData)) { Inbox.Enqueue(MakeShareable(DeserializedMessage)); } RecvMessageData.Reset(); } } else { // no data return true; } } }