如何在protobuf.net中反序列化UDPTunnel

3

我正在使用Unity3d(c#脚本)和Mumble制作voip客户端代码,现在我已成功连接到任何公共服务器。但是,当我尝试反序列化UDP隧道时,我会遇到很多异常,包括“无效的wiretype”,“数字溢出”,“无效字段”,“endofstream”,“错误的组结束”等等......全部都出现在特定的一行。

var udpTunnel = Serializer.DeserializeWithLengthPrefix<UDPTunnel> (_ssl, PrefixStyle.Fixed32BigEndian);

其中_ssl是SslStream。

这是我的完整方法:

nternal void ProcessTcpData ()
{
        try {

                var masg = IPAddress.NetworkToHostOrder (_reader.ReadInt16 ());
                MessageType messageType = (MessageType)masg;
                Debug.Log ("Received message type: " + messageType);

                switch (messageType) {
                case MessageType.Version:
                        _mc.RemoteVersion = Serializer.DeserializeWithLengthPrefix<Version> (_ssl,
PrefixStyle.Fixed32BigEndian);
                        break;
                case MessageType.CryptSetup:
                        var cryptSetup = Serializer.DeserializeWithLengthPrefix<CryptSetup> (_ssl,
PrefixStyle.Fixed32BigEndian);
                        ProcessCryptSetup (cryptSetup);
                        break;
                case MessageType.CodecVersion:
                        _mc.CodecVersion = Serializer.DeserializeWithLengthPrefix<CodecVersion> (_ssl,
PrefixStyle.Fixed32BigEndian);
                        break;
                case MessageType.ChannelState:
                        _mc.ChannelState = Serializer.DeserializeWithLengthPrefix<ChannelState> (_ssl,
PrefixStyle.Fixed32BigEndian);
                        break;
                case MessageType.PermissionQuery:
                        _mc.PermissionQuery = Serializer.DeserializeWithLengthPrefix<PermissionQuery> (_ssl,
PrefixStyle.Fixed32BigEndian);
                        break;
                case MessageType.UserState:
                        _mc.UserState = Serializer.DeserializeWithLengthPrefix<UserState> (_ssl,
PrefixStyle.Fixed32BigEndian);
                        break;
                case MessageType.ServerSync:
                        _mc.ServerSync = Serializer.DeserializeWithLengthPrefix<ServerSync> (_ssl,
PrefixStyle.Fixed32BigEndian);
                        _mc.ConnectionSetupFinished = true;
                        break;
                case MessageType.ServerConfig:
                        _mc.ServerConfig = Serializer.DeserializeWithLengthPrefix<ServerConfig> (_ssl,
PrefixStyle.Fixed32BigEndian);
                        _validConnection = true; // handshake complete
                        break;
                case MessageType.TextMessage:
                        var textMessage = Serializer.DeserializeWithLengthPrefix<TextMessage> (_ssl, PrefixStyle.Fixed32BigEndian);
                        break;
                case MessageType.UDPTunnel:
                        if (_validConnection) {
                                var udpTunnel = Serializer.DeserializeWithLengthPrefix<UDPTunnel> (_ssl, PrefixStyle.Fixed32BigEndian);
                        }
                        break;
                case MessageType.Ping:
                        var ping = Serializer.DeserializeWithLengthPrefix<MumbleProto.Ping> (_ssl, PrefixStyle.Fixed32BigEndian);
                        Debug.Log ("Received ping: " + ping.timestamp + ", udp: " + ping.udp_packets + ", tcp:" +
                                ping.tcp_packets);
                        break;
                case MessageType.Reject:
                        var reject = Serializer.DeserializeWithLengthPrefix<Reject> (_ssl,
PrefixStyle.Fixed32BigEndian);
                        _validConnection = false;
                        _errorCallback ("Mumble server reject: " + reject.reason, true);
                        break;
                default:
                        _errorCallback ("Message type " + messageType + " not implemented", true);
                        break;
                }
                if (_validConnection) {
                        Debug.Log ("Handshake Complete:\tconnection is valid");
                }
        } catch (Exception ex) {
                Debug.LogException (ex);
        }
}

_reader是二进制读取器


你是否收到了发送的相同字节?在确定获取正确数据之前,其他一切都是无意义的。 - Marc Gravell
1个回答

4
我通过使用以下方法解决了这个问题:
var size = IPAddress.NetworkToHostOrder (_reader.ReadInt32 ());
var udpTunnel = new UDPTunnel { packet = _reader.ReadBytes(size) };

现在我不知道为什么Deserializewithlengthprefix没有起作用,因为我理解这些行代码在做同样的事情。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接