public void TryDeserializeTest() { var pl = new VersionPayload(); byte[] data = Helper.HexToBytes("721101000100000000000000bc8f5e5400000000010000000000000000000000000000000000ffffc61b6409208d010000000000000000000000000000000000ffffcb0071c0208d128035cbc97953f80f2f5361746f7368693a302e392e332fcf05050001"); bool b = pl.TryDeserialize(new FastStreamReader(data), out string error); Assert.True(b, error); Assert.Null(error); }
private Message[] CheckVersion(Message msg) { var version = new VersionPayload(); if (!version.TryDeserialize(new FastStreamReader(msg.PayloadData), out _)) { nodeStatus.AddSmallViolation(); return(null); } Message[] result = null; switch (nodeStatus.HandShake) { case HandShakeState.None: nodeStatus.HandShake = HandShakeState.ReceivedAndReplied; result = new Message[2] { new Message(new VerackPayload(), settings.Network), GetVersionMsg(version.TransmittingNodeNetworkAddress) }; break; case HandShakeState.Sent: nodeStatus.HandShake = HandShakeState.SentAndReceived; result = new Message[1] { new Message(new VerackPayload(), settings.Network) }; break; case HandShakeState.SentAndConfirmed: nodeStatus.HandShake = HandShakeState.Finished; result = new Message[1] { new Message(new VerackPayload(), settings.Network) }; break; case HandShakeState.ReceivedAndReplied: case HandShakeState.SentAndReceived: case HandShakeState.Finished: nodeStatus.AddMediumViolation(); break; default: break; } return(result); }
public static IEnumerable <object[]> GetVersionCases() { var cs = new MockClientSettings() { _protoVer = 123, _services = NodeServiceFlags.All, _time = 456, _port = 789, _ua = "foo", _relay = true, _netType = NetworkType.MainNet }; var bc = new MockBlockchain() { _height = 12345 }; var verPl = new VersionPayload(); Assert.True(verPl.TryDeserialize(new FastStreamReader(Helper.HexToBytes("721101000100000000000000bc8f5e5400000000010000000000000000000000000000000000ffffc61b6409208d010000000000000000000000000000000000ffffcb0071c0208d128035cbc97953f80f2f5361746f7368693a302e392e332fcf05050001")), out string error), error); var msg = new Message(verPl, NetworkType.MainNet); var rcv = new NetworkAddress(NodeServiceFlags.NodeNetwork, IPAddress.Parse("203.0.113.192"), 8333); var trs = new NetworkAddress(NodeServiceFlags.All, IPAddress.Loopback, 789); var verak = new Message(new VerackPayload(), NetworkType.MainNet); var ver = new Message(new VersionPayload(123, 456, rcv, trs, 0x0158a8e8ba5f3ed3, "foo", 12345, true), NetworkType.MainNet); yield return(new object[] { new MockNodeStatus() { _handShakeToReturn = HandShakeState.None, _handShakeToSet = HandShakeState.ReceivedAndReplied, updateTime = true }, cs, bc, msg, new Message[] { verak, ver } }); yield return(new object[] { new MockNodeStatus() { _handShakeToReturn = HandShakeState.ReceivedAndReplied, mediumViolation = true, updateTime = true }, cs, bc, msg, null }); yield return(new object[] { new MockNodeStatus() { _handShakeToReturn = HandShakeState.Sent, _handShakeToSet = HandShakeState.SentAndReceived, updateTime = true }, cs, bc, msg, new Message[] { verak } }); yield return(new object[] { new MockNodeStatus() { _handShakeToReturn = HandShakeState.SentAndConfirmed, _handShakeToSet = HandShakeState.Finished, updateTime = true }, cs, bc, msg, new Message[] { verak } }); yield return(new object[] { new MockNodeStatus() { _handShakeToReturn = HandShakeState.SentAndReceived, mediumViolation = true, updateTime = true }, cs, bc, msg, null }); yield return(new object[] { new MockNodeStatus() { _handShakeToReturn = HandShakeState.Finished, mediumViolation = true, updateTime = true }, cs, bc, msg, null }); }
/// <inheritdoc/> public Message[] GetReply(Message msg) { if (!Enum.TryParse(Encoding.ASCII.GetString(msg.PayloadName.TrimEnd()), ignoreCase: true, out PayloadType plt)) { // Undefined payload type nodeStatus.AddSmallViolation(); } else { if (nodeStatus.HandShake != HandShakeState.Finished) { if (plt == PayloadType.Verack) { var verack = new VerackPayload(); if (!verack.TryDeserialize(new FastStreamReader(msg.PayloadData), out _)) { nodeStatus.AddSmallViolation(); } else if (nodeStatus.HandShake == HandShakeState.None || nodeStatus.HandShake == HandShakeState.Finished || nodeStatus.HandShake == HandShakeState.SentAndConfirmed) { nodeStatus.AddMediumViolation(); } else if (nodeStatus.HandShake == HandShakeState.ReceivedAndReplied || nodeStatus.HandShake == HandShakeState.SentAndReceived) { nodeStatus.HandShake = HandShakeState.Finished; } else if (nodeStatus.HandShake == HandShakeState.Sent) { nodeStatus.HandShake = HandShakeState.SentAndConfirmed; } } else if (plt == PayloadType.Version) { var version = new VersionPayload(); if (!version.TryDeserialize(new FastStreamReader(msg.PayloadData), out _)) { nodeStatus.AddSmallViolation(); } else if (nodeStatus.HandShake == HandShakeState.None) { nodeStatus.HandShake = HandShakeState.ReceivedAndReplied; return(new Message[2] { new Message(new VerackPayload(), settings.Network), GetVersionMsg(version.TransmittingNodeNetworkAddress) }); } else if (nodeStatus.HandShake == HandShakeState.Sent) { nodeStatus.HandShake = HandShakeState.SentAndReceived; return(new Message[1] { new Message(new VerackPayload(), settings.Network) }); } else if (nodeStatus.HandShake == HandShakeState.SentAndConfirmed) { nodeStatus.HandShake = HandShakeState.Finished; return(new Message[1] { new Message(new VerackPayload(), settings.Network) }); } else if (nodeStatus.HandShake == HandShakeState.ReceivedAndReplied || nodeStatus.HandShake == HandShakeState.SentAndReceived || nodeStatus.HandShake == HandShakeState.Finished) { nodeStatus.AddMediumViolation(); } } else { // HandShake is not complete but the other node is sending other types of messages nodeStatus.AddMediumViolation(); } } else { switch (plt) { case PayloadType.Addr: break; case PayloadType.Alert: // Alert messages are ignored break; case PayloadType.Block: break; case PayloadType.BlockTxn: break; case PayloadType.CmpctBlock: break; case PayloadType.FeeFilter: break; case PayloadType.FilterAdd: break; case PayloadType.FilterClear: break; case PayloadType.FilterLoad: break; case PayloadType.GetAddr: break; case PayloadType.GetBlocks: break; case PayloadType.GetBlockTxn: break; case PayloadType.GetData: break; case PayloadType.GetHeaders: break; case PayloadType.Headers: break; case PayloadType.Inv: break; case PayloadType.MemPool: break; case PayloadType.MerkleBlock: break; case PayloadType.NotFound: break; case PayloadType.Ping: var ping = new PingPayload(); if (!ping.TryDeserialize(new FastStreamReader(msg.PayloadData), out _)) { nodeStatus.AddSmallViolation(); break; } return(new Message[1] { new Message(new PongPayload(ping.Nonce), settings.Network) }); case PayloadType.Pong: var pong = new PongPayload(); if (!pong.TryDeserialize(new FastStreamReader(msg.PayloadData), out _)) { nodeStatus.AddSmallViolation(); break; } break; case PayloadType.Reject: // Reject messages are ignored break; case PayloadType.SendCmpct: break; case PayloadType.SendHeaders: break; case PayloadType.Tx: break; case PayloadType.Verack: case PayloadType.Version: nodeStatus.AddMediumViolation(); break; default: break; } } } nodeStatus.UpdateTime(); return(null); }
private Message[] CheckVersion(Message msg) { var version = new VersionPayload(); if (!version.TryDeserialize(new FastStreamReader(msg.PayloadData), out _)) { nodeStatus.AddSmallViolation(); return(null); } if (version.Version < Constants.P2PMinProtoVer) { nodeStatus.SignalDisconnect(); return(null); } nodeStatus.ProtocolVersion = version.Version; nodeStatus.Services = version.Services; nodeStatus.Nonce = version.Nonce; nodeStatus.UserAgent = version.UserAgent; nodeStatus.StartHeight = version.StartHeight; nodeStatus.Relay = version.Relay; settings.UpdateMyIP(version.ReceivingNodeNetworkAddress.NodeIP); settings.Time.UpdateTime(version.Timestamp); Message[] result = null; switch (nodeStatus.HandShake) { case HandShakeState.None: nodeStatus.HandShake = HandShakeState.ReceivedAndReplied; result = new Message[2] { new Message(new VerackPayload(), settings.Network), GetVersionMsg() }; break; case HandShakeState.Sent: nodeStatus.HandShake = HandShakeState.SentAndReceived; result = new Message[1] { new Message(new VerackPayload(), settings.Network) }; break; case HandShakeState.SentAndConfirmed: nodeStatus.HandShake = HandShakeState.Finished; result = GetSettingsMessages(new Message(new VerackPayload(), settings.Network)); break; case HandShakeState.ReceivedAndReplied: case HandShakeState.SentAndReceived: case HandShakeState.Finished: nodeStatus.AddMediumViolation(); break; default: break; } return(result); }