public void RawInput(byte[] buffer, int msgLength) { int input = kcp.Input(buffer, msgLength); if (input != 0) { Debug.LogWarning($"Input failed with error={input} for buffer with length={msgLength}"); } }
public void RawInput(byte[] buffer, int msgLength) { // parse channel if (msgLength > 0) { byte channel = buffer[0]; switch (channel) { case (byte)KcpChannel.Reliable: { // input into kcp, but skip channel byte int input = kcp.Input(buffer, 1, msgLength - 1); if (input != 0) { Log.Warning($"Input failed with error={input} for buffer with length={msgLength - 1}"); } break; } case (byte)KcpChannel.Unreliable: { // ideally we would queue all unreliable messages and // then process them in ReceiveNext() together with the // reliable messages, but: // -> queues/allocations/pools are slow and complex. // -> DOTSNET 10k is actually slower if we use pooled // unreliable messages for transform messages. // // DOTSNET 10k benchmark: // reliable-only: 170 FPS // unreliable queued: 130-150 FPS // unreliable direct: 183 FPS(!) // // DOTSNET 50k benchmark: // reliable-only: FAILS (queues keep growing) // unreliable direct: 18-22 FPS(!) // // -> all unreliable messages are DATA messages anyway. // -> let's skip the magic and call OnData directly if // the current state allows it. if (state == KcpState.Authenticated) { // only process messages while not paused for Mirror // scene switching etc. // -> if an unreliable message comes in while // paused, simply drop it. it's unreliable! if (!paused) { ArraySegment <byte> message = new ArraySegment <byte>(buffer, 1, msgLength - 1); OnData?.Invoke(message); } // set last receive time to avoid timeout. // -> we do this in ANY case even if not enabled. // a message is a message. // -> we set last receive time for both reliable and // unreliable messages. both count. // otherwise a connection might time out even // though unreliable were received, but no // reliable was received. lastReceiveTime = (uint)refTime.ElapsedMilliseconds; } else { // should never Log.Warning($"KCP: received unreliable message in state {state}. Disconnecting the connection."); Disconnect(); } break; } default: { // not a valid channel. random data or attacks. Log.Info($"Disconnecting connection because of invalid channel header: {channel}"); Disconnect(); break; } } } }
public void RawInput(byte[] buffer, int msgLength) { kcp.Input(buffer, 0, msgLength, true, false); lastReceived = kcp.CurrentMS; }