Transports: Improve banning of routers from wrong network

This commit is contained in:
zzz
2018-12-21 11:32:17 +00:00
parent 18b7d97584
commit 94fd60db10
5 changed files with 55 additions and 6 deletions

View File

@@ -920,7 +920,7 @@ public abstract class KademliaNetworkDatabaseFacade extends NetworkDatabaseFacad
return "Invalid routerInfo signature";
}
if (routerInfo.getNetworkId() != _networkID){
_context.banlist().banlistRouter(key, "Not in our network");
_context.banlist().banlistRouterForever(key, "Not in our network: " + routerInfo.getNetworkId());
if (_log.shouldLog(Log.WARN))
_log.warn("Bad network: " + routerInfo);
return "Not in our network";

View File

@@ -572,6 +572,38 @@ class InboundEstablishState extends EstablishBase implements NTCP2Payload.Payloa
return true;
}
/**
* Validate network ID, NTCP 2 only.
* Call after receiving Alice's RouterInfo,
* but before storing it in the netdb.
*
* Side effects: When returning false, sets _msg3p2FailReason,
* banlists permanently and blocklists
*
* @return success
* @since 0.9.38
*/
private boolean verifyInboundNetworkID(RouterInfo alice) {
int aliceID = alice.getNetworkId();
boolean rv = aliceID == _context.router().getNetworkID();
if (!rv) {
Hash aliceHash = alice.getHash();
if (_log.shouldLog(Log.WARN))
_log.warn("Dropping inbound connection from wrong network: " + aliceID + ' ' + aliceHash);
// So next time we will not accept the con from this IP,
// rather than doing the whole handshake
InetAddress addr = _con.getChannel().socket().getInetAddress();
if (addr != null) {
byte[] ip = addr.getAddress();
_context.blocklist().add(ip);
}
_context.banlist().banlistRouterForever(aliceHash, "Not in our network: " + aliceID);
_transport.markUnreachable(aliceHash);
_msg3p2FailReason = NTCPConnection.REASON_BANNED;
}
return rv;
}
/**
* We are Bob. Send message #4 to Alice.
*
@@ -988,6 +1020,9 @@ class InboundEstablishState extends EstablishBase implements NTCP2Payload.Payloa
boolean ok = verifyInbound(h);
if (!ok)
throw new DataFormatException("NTCP2 verifyInbound() fail");
ok = verifyInboundNetworkID(ri);
if (!ok)
throw new DataFormatException("NTCP2 network ID mismatch");
try {
RouterInfo old = _context.netDb().store(h, ri);
if (flood && !ri.equals(old)) {

View File

@@ -81,6 +81,7 @@ public class NTCPTransport extends TransportImpl {
private int _ssuPort;
/** synch on this */
private final Set<InetSocketAddress> _endpoints;
private final int _networkID;
/**
* list of NTCPConnection of connections not yet established that we
@@ -229,6 +230,7 @@ public class NTCPTransport extends TransportImpl {
_reader = new Reader(ctx);
_writer = new net.i2p.router.transport.ntcp.Writer(ctx);
_networkID = ctx.router().getNetworkID();
_fastBid = new SharedBid(25); // best
_slowBid = new SharedBid(70); // better than ssu unestablished, but not better than ssu established
_slowCostBid = new SharedBid(85);
@@ -504,6 +506,11 @@ public class NTCPTransport extends TransportImpl {
}
return _fastBid;
}
if (toAddress.getNetworkId() != _networkID) {
_context.banlist().banlistRouterForever(peer, "Not in our network: " + toAddress.getNetworkId());
markUnreachable(peer);
return null;
}
if (dataSize > NTCPConnection.NTCP1_MAX_MSG_SIZE) {
// Not established, too big for NTCP 1, let SSU deal with it
// TODO look at his addresses to see if NTCP2 supported?

View File

@@ -252,7 +252,7 @@ class EstablishmentManager {
RouterIdentity toIdentity = toRouterInfo.getIdentity();
Hash toHash = toIdentity.calculateHash();
if (toRouterInfo.getNetworkId() != _networkID) {
_context.banlist().banlistRouter(toHash);
_context.banlist().banlistRouterForever(toHash, "Not in our network: " + toRouterInfo.getNetworkId());
_transport.markUnreachable(toHash);
_transport.failed(msg, "Remote peer is on the wrong network, cannot establish");
return;

View File

@@ -1416,7 +1416,7 @@ public class UDPTransport extends TransportImpl implements TimedWeightedPriority
_context.simpleTimer2().addEvent(new RemoveDropList(remote), DROPLIST_PERIOD);
}
markUnreachable(peerHash);
_context.banlist().banlistRouter(peerHash, "Part of the wrong network, version = " + ((RouterInfo) entry).getVersion());
_context.banlist().banlistRouterForever(peerHash, "Not in our network: " + ((RouterInfo) entry).getNetworkId());
//_context.banlist().banlistRouter(peerHash, "Part of the wrong network", STYLE);
if (peer != null)
sendDestroy(peer);
@@ -1754,6 +1754,12 @@ public class UDPTransport extends TransportImpl implements TimedWeightedPriority
else
return _cachedBid[FAST_BID];
} else {
if (toAddress.getNetworkId() != _networkID) {
_context.banlist().banlistRouterForever(to, "Not in our network: " + toAddress.getNetworkId());
markUnreachable(to);
return null;
}
// If we don't have a port, all is lost
if ( _reachabilityStatus == Status.HOSED) {
markUnreachable(to);
@@ -1880,15 +1886,16 @@ public class UDPTransport extends TransportImpl implements TimedWeightedPriority
@Override
public void send(OutNetMessage msg) {
if (msg == null) return;
if (msg.getTarget() == null) return;
if (msg.getTarget().getIdentity() == null) return;
RouterInfo tori = msg.getTarget();
if (tori == null) return;
if (tori.getIdentity() == null) return;
if (_establisher == null) {
failed(msg, "UDP not up yet");
return;
}
msg.timestamp("sending on UDP transport");
Hash to = msg.getTarget().getIdentity().calculateHash();
Hash to = tori.getIdentity().calculateHash();
PeerState peer = getPeerState(to);
if (_log.shouldLog(Log.DEBUG))
_log.debug("Sending to " + (to != null ? to.toString() : ""));