diff --git a/src/it/scala/io/iohk/ethereum/sync/RegularSyncItSpec.scala b/src/it/scala/io/iohk/ethereum/sync/RegularSyncItSpec.scala index bda189d94f..0bfee82532 100644 --- a/src/it/scala/io/iohk/ethereum/sync/RegularSyncItSpec.scala +++ b/src/it/scala/io/iohk/ethereum/sync/RegularSyncItSpec.scala @@ -3,7 +3,6 @@ package io.iohk.ethereum.sync import com.typesafe.config.ConfigValueFactory import io.iohk.ethereum.FreeSpecBase import io.iohk.ethereum.metrics.{Metrics, MetricsConfig} -import io.iohk.ethereum.network.PeerId import io.iohk.ethereum.sync.util.RegularSyncItSpecUtils.FakePeer import io.iohk.ethereum.sync.util.SyncCommonItSpec._ import io.iohk.ethereum.utils.Config diff --git a/src/test/scala/io/iohk/ethereum/network/PeerManagerSpec.scala b/src/test/scala/io/iohk/ethereum/network/PeerManagerSpec.scala index 886a34a4c1..c5dfaa90a8 100644 --- a/src/test/scala/io/iohk/ethereum/network/PeerManagerSpec.scala +++ b/src/test/scala/io/iohk/ethereum/network/PeerManagerSpec.scala @@ -13,7 +13,7 @@ import io.iohk.ethereum.network.PeerActor.{ConnectTo, PeerClosedConnection} import io.iohk.ethereum.network.PeerEventBusActor.PeerEvent.PeerDisconnected import io.iohk.ethereum.network.PeerEventBusActor.SubscriptionClassifier.PeerHandshaked import io.iohk.ethereum.network.PeerEventBusActor.{PeerEvent, Publish, Subscribe} -import io.iohk.ethereum.network.PeerManagerActor.{GetPeers, PeerConfiguration, Peers, SendMessage} +import io.iohk.ethereum.network.PeerManagerActor.{GetPeers, PeerAddress, PeerConfiguration, Peers, SendMessage} import io.iohk.ethereum.network.discovery.{DiscoveryConfig, Node, PeerDiscoveryManager} import io.iohk.ethereum.network.p2p.messages.CommonMessages.NewBlock import io.iohk.ethereum.network.p2p.messages.ProtocolVersions @@ -52,6 +52,27 @@ class PeerManagerSpec handleInitialNodesDiscovery() } + it should "blacklist peer that sent a status msg with invalid genesisHash" in new TestSetup { + start() + handleInitialNodesDiscovery() + + val probe: TestProbe = createdPeers(1).probe + + probe.expectMsgClass(classOf[PeerActor.ConnectTo]) + + peerManager ! PeerManagerActor.HandlePeerConnection(incomingConnection1.ref, incomingPeerAddress1) + + val probe2: TestProbe = createdPeers(2).probe + val peer = Peer(PeerId("peerid"), incomingPeerAddress1, probe2.ref, incomingConnection = true) + + peerManager ! PeerClosedConnection(peer.remoteAddress.getHostString, Disconnect.Reasons.DisconnectRequested) + + eventually { + peerManager.underlyingActor.blacklist.keys.size shouldEqual 1 + peerManager.underlyingActor.blacklist.isBlacklisted(PeerAddress(peer.remoteAddress.getHostString)) shouldBe true + } + } + it should "blacklist peer that fail to establish tcp connection" in new TestSetup { start() handleInitialNodesDiscovery() diff --git a/src/test/scala/io/iohk/ethereum/network/p2p/PeerActorSpec.scala b/src/test/scala/io/iohk/ethereum/network/p2p/PeerActorSpec.scala index 3da0b507ec..1162d0024e 100644 --- a/src/test/scala/io/iohk/ethereum/network/p2p/PeerActorSpec.scala +++ b/src/test/scala/io/iohk/ethereum/network/p2p/PeerActorSpec.scala @@ -25,7 +25,7 @@ import io.iohk.ethereum.network.p2p.messages.CommonMessages.Status.StatusEnc import io.iohk.ethereum.network.p2p.messages.PV62.GetBlockHeaders.GetBlockHeadersEnc import io.iohk.ethereum.network.p2p.messages.PV62._ import io.iohk.ethereum.network.p2p.messages.{PV64, ProtocolVersions} -import io.iohk.ethereum.network.p2p.messages.WireProtocol.Disconnect.Reasons +import io.iohk.ethereum.network.p2p.messages.WireProtocol.Disconnect.{DisconnectEnc, Reasons} import io.iohk.ethereum.network.p2p.messages.WireProtocol.Hello.HelloEnc import io.iohk.ethereum.network.p2p.messages.WireProtocol.Pong.PongEnc import io.iohk.ethereum.network.p2p.messages.WireProtocol._ @@ -160,6 +160,35 @@ class PeerActorSpec knownNodesManager.expectNoMessage() } + it should "fail handshake with peer that has a wrong genesis hash" in new TestSetup { + val uri = new URI(s"enode://${Hex.toHexString(remoteNodeId.toArray[Byte])}@localhost:9000") + val completeUri = new URI(s"enode://${Hex.toHexString(remoteNodeId.toArray[Byte])}@127.0.0.1:9000?discport=9000") + peer ! PeerActor.ConnectTo(uri) + peer ! PeerActor.ConnectTo(uri) + + rlpxConnection.expectMsgClass(classOf[RLPxConnectionHandler.ConnectTo]) + rlpxConnection.reply(RLPxConnectionHandler.ConnectionEstablished(remoteNodeId)) + + //Hello exchange + val remoteHello = Hello(4, "test-client", Seq(Eth63Capability), 9000, ByteString("unused")) + rlpxConnection.expectMsgPF() { case RLPxConnectionHandler.SendMessage(_: HelloEnc) => () } + rlpxConnection.send(peer, RLPxConnectionHandler.MessageReceived(remoteHello)) + + val remoteStatus = Status( + protocolVersion = ProtocolVersions.PV63, + networkId = peerConf.networkId, + totalDifficulty = daoForkBlockChainTotalDifficulty + 100000, // remote is after the fork + bestHash = ByteString("blockhash"), + genesisHash = genesisHash.drop(2) + ) + + //Node status exchange + rlpxConnection.expectMsgPF() { case RLPxConnectionHandler.SendMessage(_: StatusEnc) => () } + rlpxConnection.send(peer, RLPxConnectionHandler.MessageReceived(remoteStatus)) + + rlpxConnection.expectMsgPF() { case RLPxConnectionHandler.SendMessage(_: DisconnectEnc) => () } + } + it should "successfully connect to ETC peer with protocol 64" in new TestSetup { override def protocol: Version = ProtocolVersions.PV64 val uri = new URI(s"enode://${Hex.toHexString(remoteNodeId.toArray[Byte])}@localhost:9000")