+Classes formerly in net.i2p.data but moved here as they are only used by the router. +
+ + diff --git a/router/java/src/net/i2p/router/Blocklist.java b/router/java/src/net/i2p/router/Blocklist.java index 093a6fdc5..a6fe1d209 100644 --- a/router/java/src/net/i2p/router/Blocklist.java +++ b/router/java/src/net/i2p/router/Blocklist.java @@ -28,8 +28,8 @@ import java.util.TreeSet; import net.i2p.data.Base64; import net.i2p.data.DataHelper; import net.i2p.data.Hash; -import net.i2p.data.RouterAddress; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterAddress; +import net.i2p.data.router.RouterInfo; import net.i2p.router.networkdb.kademlia.FloodfillNetworkDatabaseFacade; import net.i2p.util.Addresses; import net.i2p.util.ConcurrentHashSet; diff --git a/router/java/src/net/i2p/router/CommSystemFacade.java b/router/java/src/net/i2p/router/CommSystemFacade.java index 9c7d92338..59a22eb9c 100644 --- a/router/java/src/net/i2p/router/CommSystemFacade.java +++ b/router/java/src/net/i2p/router/CommSystemFacade.java @@ -13,7 +13,7 @@ import java.io.Writer; import java.util.Collections; import java.util.List; import net.i2p.data.Hash; -import net.i2p.data.RouterAddress; +import net.i2p.data.router.RouterAddress; /** * Manages the communication subsystem between peers, including connections, diff --git a/router/java/src/net/i2p/router/HandlerJobBuilder.java b/router/java/src/net/i2p/router/HandlerJobBuilder.java index c1c9832cd..62e2074a5 100644 --- a/router/java/src/net/i2p/router/HandlerJobBuilder.java +++ b/router/java/src/net/i2p/router/HandlerJobBuilder.java @@ -9,7 +9,7 @@ package net.i2p.router; */ import net.i2p.data.Hash; -import net.i2p.data.RouterIdentity; +import net.i2p.data.router.RouterIdentity; import net.i2p.data.i2np.I2NPMessage; /** diff --git a/router/java/src/net/i2p/router/InNetMessagePool.java b/router/java/src/net/i2p/router/InNetMessagePool.java index 28296cebb..fb4c2a632 100644 --- a/router/java/src/net/i2p/router/InNetMessagePool.java +++ b/router/java/src/net/i2p/router/InNetMessagePool.java @@ -14,7 +14,7 @@ import java.util.Date; import java.util.List; import net.i2p.data.Hash; -import net.i2p.data.RouterIdentity; +import net.i2p.data.router.RouterIdentity; import net.i2p.data.i2np.DatabaseLookupMessage; import net.i2p.data.i2np.DatabaseSearchReplyMessage; import net.i2p.data.i2np.DeliveryStatusMessage; diff --git a/router/java/src/net/i2p/router/KeyManager.java b/router/java/src/net/i2p/router/KeyManager.java index ce4992f8b..2807e8fe7 100644 --- a/router/java/src/net/i2p/router/KeyManager.java +++ b/router/java/src/net/i2p/router/KeyManager.java @@ -18,6 +18,7 @@ import java.io.OutputStream; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; +import net.i2p.crypto.SigType; import net.i2p.data.DataFormatException; import net.i2p.data.DataStructure; import net.i2p.data.Destination; @@ -26,6 +27,7 @@ import net.i2p.data.PrivateKey; import net.i2p.data.PublicKey; import net.i2p.data.SigningPrivateKey; import net.i2p.data.SigningPublicKey; +import net.i2p.router.startup.CreateRouterInfoJob; import net.i2p.util.Log; import net.i2p.util.SecureDirectory; import net.i2p.util.SecureFileOutputStream; @@ -47,10 +49,10 @@ public class KeyManager { public final static String PROP_KEYDIR = "router.keyBackupDir"; public final static String DEFAULT_KEYDIR = "keyBackup"; - private final static String KEYFILE_PRIVATE_ENC = "privateEncryption.key"; - private final static String KEYFILE_PUBLIC_ENC = "publicEncryption.key"; - private final static String KEYFILE_PRIVATE_SIGNING = "privateSigning.key"; - private final static String KEYFILE_PUBLIC_SIGNING = "publicSigning.key"; + public final static String KEYFILE_PRIVATE_ENC = "privateEncryption.key"; + public final static String KEYFILE_PUBLIC_ENC = "publicEncryption.key"; + public final static String KEYFILE_PRIVATE_SIGNING = "privateSigning.key"; + public final static String KEYFILE_PUBLIC_SIGNING = "publicSigning.key"; public KeyManager(RouterContext context) { _context = context; @@ -151,8 +153,9 @@ public class KeyManager { private void syncKeys(File keyDir) { syncPrivateKey(keyDir); syncPublicKey(keyDir); - syncSigningKey(keyDir); - syncVerificationKey(keyDir); + SigType type = CreateRouterInfoJob.getSigTypeConfig(getContext()); + syncSigningKey(keyDir, type); + syncVerificationKey(keyDir, type); } private void syncPrivateKey(File keyDir) { @@ -181,27 +184,33 @@ public class KeyManager { _publicKey = (PublicKey) readin; } - private void syncSigningKey(File keyDir) { + /** + * @param type the SigType to expect on read-in, ignored on write + */ + private void syncSigningKey(File keyDir, SigType type) { DataStructure ds; File keyFile = new File(keyDir, KEYFILE_PRIVATE_SIGNING); boolean exists = (_signingPrivateKey != null); if (exists) ds = _signingPrivateKey; else - ds = new SigningPrivateKey(); + ds = new SigningPrivateKey(type); DataStructure readin = syncKey(keyFile, ds, exists); if (readin != null && !exists) _signingPrivateKey = (SigningPrivateKey) readin; } - private void syncVerificationKey(File keyDir) { + /** + * @param type the SigType to expect on read-in, ignored on write + */ + private void syncVerificationKey(File keyDir, SigType type) { DataStructure ds; File keyFile = new File(keyDir, KEYFILE_PUBLIC_SIGNING); boolean exists = (_signingPublicKey != null); if (exists) ds = _signingPublicKey; else - ds = new SigningPublicKey(); + ds = new SigningPublicKey(type); DataStructure readin = syncKey(keyFile, ds, exists); if (readin != null && !exists) _signingPublicKey = (SigningPublicKey) readin; diff --git a/router/java/src/net/i2p/router/MultiRouter.java b/router/java/src/net/i2p/router/MultiRouter.java index 5e8cb4760..abcd32e3d 100644 --- a/router/java/src/net/i2p/router/MultiRouter.java +++ b/router/java/src/net/i2p/router/MultiRouter.java @@ -10,7 +10,7 @@ import java.util.Scanner; import net.i2p.I2PAppContext; import net.i2p.data.DataHelper; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.router.Router; /** diff --git a/router/java/src/net/i2p/router/NetworkDatabaseFacade.java b/router/java/src/net/i2p/router/NetworkDatabaseFacade.java index 7fc3c5082..2e4ee3c15 100644 --- a/router/java/src/net/i2p/router/NetworkDatabaseFacade.java +++ b/router/java/src/net/i2p/router/NetworkDatabaseFacade.java @@ -16,7 +16,7 @@ import java.util.Set; import net.i2p.data.DatabaseEntry; import net.i2p.data.Hash; import net.i2p.data.LeaseSet; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.router.networkdb.reseed.ReseedChecker; /** diff --git a/router/java/src/net/i2p/router/OutNetMessage.java b/router/java/src/net/i2p/router/OutNetMessage.java index 633416640..54434ac4b 100644 --- a/router/java/src/net/i2p/router/OutNetMessage.java +++ b/router/java/src/net/i2p/router/OutNetMessage.java @@ -18,7 +18,7 @@ import java.util.List; import java.util.Map; import java.util.Set; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.i2np.I2NPMessage; import net.i2p.router.util.CDPQEntry; import net.i2p.util.Log; diff --git a/router/java/src/net/i2p/router/Router.java b/router/java/src/net/i2p/router/Router.java index f6eb8a907..c199aca2b 100644 --- a/router/java/src/net/i2p/router/Router.java +++ b/router/java/src/net/i2p/router/Router.java @@ -29,11 +29,12 @@ import net.i2p.data.Certificate; import net.i2p.data.DataFormatException; import net.i2p.data.DataHelper; import net.i2p.data.Destination; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.SigningPrivateKey; import net.i2p.data.i2np.GarlicMessage; import net.i2p.router.message.GarlicMessageHandler; import net.i2p.router.networkdb.kademlia.FloodfillNetworkDatabaseFacade; +import net.i2p.router.startup.CreateRouterInfoJob; import net.i2p.router.startup.StartupJob; import net.i2p.router.startup.WorkingDir; import net.i2p.router.tasks.*; @@ -98,10 +99,6 @@ public class Router implements RouterClock.ClockShiftListener { /** this does not put an 'H' in your routerInfo **/ public final static String PROP_HIDDEN_HIDDEN = "router.isHidden"; public final static String PROP_DYNAMIC_KEYS = "router.dynamicKeys"; - public final static String PROP_INFO_FILENAME = "router.info.location"; - public final static String PROP_INFO_FILENAME_DEFAULT = "router.info"; - public final static String PROP_KEYS_FILENAME = "router.keys.location"; - public final static String PROP_KEYS_FILENAME_DEFAULT = "router.keys"; public final static String PROP_SHUTDOWN_IN_PROGRESS = "__shutdownInProgress"; public final static String DNS_CACHE_TIME = "" + (5*60); private static final String EVENTLOG = "eventlog.txt"; @@ -671,20 +668,6 @@ public class Router implements RouterClock.ClockShiftListener { return Boolean.parseBoolean(h); return _context.commSystem().isInBadCountry(); } - - /** - * Only called at startup via LoadRouterInfoJob and RebuildRouterInfoJob. - * Not called by periodic RepublishLocalRouterInfoJob. - * We don't want to change the cert on the fly as it changes the router hash. - * RouterInfo.isHidden() checks the capability, but RouterIdentity.isHidden() checks the cert. - * There's no reason to ever add a hidden cert? - * @return the certificate for a new RouterInfo - probably a null cert. - */ - public Certificate createCertificate() { - if (_context.getBooleanProperty(PROP_HIDDEN)) - return new Certificate(Certificate.CERTIFICATE_TYPE_HIDDEN, null); - return Certificate.NULL_CERT; - } /** * @since 0.9.3 @@ -697,16 +680,18 @@ public class Router implements RouterClock.ClockShiftListener { * Ugly list of files that we need to kill if we are building a new identity * */ - private static final String _rebuildFiles[] = new String[] { "router.info", - "router.keys", - "netDb/my.info", // no longer used - "connectionTag.keys", // never used? - "keyBackup/privateEncryption.key", - "keyBackup/privateSigning.key", - "keyBackup/publicEncryption.key", - "keyBackup/publicSigning.key", - "sessionKeys.dat" // no longer used - }; + private static final String _rebuildFiles[] = new String[] { + CreateRouterInfoJob.INFO_FILENAME, + CreateRouterInfoJob.KEYS_FILENAME, + CreateRouterInfoJob.KEYS2_FILENAME, + "netDb/my.info", // no longer used + "connectionTag.keys", // never used? + KeyManager.DEFAULT_KEYDIR + '/' + KeyManager.KEYFILE_PRIVATE_ENC, + KeyManager.DEFAULT_KEYDIR + '/' + KeyManager.KEYFILE_PUBLIC_ENC, + KeyManager.DEFAULT_KEYDIR + '/' + KeyManager.KEYFILE_PRIVATE_SIGNING, + KeyManager.DEFAULT_KEYDIR + '/' + KeyManager.KEYFILE_PUBLIC_SIGNING, + "sessionKeys.dat" // no longer used + }; public void killKeys() { //new Exception("Clearing identity files").printStackTrace(); diff --git a/router/java/src/net/i2p/router/RouterContext.java b/router/java/src/net/i2p/router/RouterContext.java index 1f8a38af6..20b2fe9b7 100644 --- a/router/java/src/net/i2p/router/RouterContext.java +++ b/router/java/src/net/i2p/router/RouterContext.java @@ -10,7 +10,7 @@ import java.util.concurrent.CopyOnWriteArrayList; import net.i2p.I2PAppContext; import net.i2p.app.ClientAppManager; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.internal.InternalClientManager; import net.i2p.router.client.ClientManagerFacadeImpl; import net.i2p.router.crypto.TransientSessionKeyManager; diff --git a/router/java/src/net/i2p/router/RouterThrottleImpl.java b/router/java/src/net/i2p/router/RouterThrottleImpl.java index 805e7bbbc..275e4d85a 100644 --- a/router/java/src/net/i2p/router/RouterThrottleImpl.java +++ b/router/java/src/net/i2p/router/RouterThrottleImpl.java @@ -1,7 +1,7 @@ package net.i2p.router; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.router.peermanager.TunnelHistory; import net.i2p.stat.Rate; import net.i2p.stat.RateAverages; diff --git a/router/java/src/net/i2p/router/dummy/DummyNetworkDatabaseFacade.java b/router/java/src/net/i2p/router/dummy/DummyNetworkDatabaseFacade.java index 11b9419f3..6c99bb90b 100644 --- a/router/java/src/net/i2p/router/dummy/DummyNetworkDatabaseFacade.java +++ b/router/java/src/net/i2p/router/dummy/DummyNetworkDatabaseFacade.java @@ -17,7 +17,7 @@ import java.util.Set; import net.i2p.data.DatabaseEntry; import net.i2p.data.Hash; import net.i2p.data.LeaseSet; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.router.Job; import net.i2p.router.NetworkDatabaseFacade; import net.i2p.router.RouterContext; diff --git a/router/java/src/net/i2p/router/message/GarlicConfig.java b/router/java/src/net/i2p/router/message/GarlicConfig.java index 9fe299e0c..4970a589f 100644 --- a/router/java/src/net/i2p/router/message/GarlicConfig.java +++ b/router/java/src/net/i2p/router/message/GarlicConfig.java @@ -14,7 +14,7 @@ import java.util.List; import net.i2p.data.Certificate; import net.i2p.data.PublicKey; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.i2np.DeliveryInstructions; /** diff --git a/router/java/src/net/i2p/router/message/GarlicMessageHandler.java b/router/java/src/net/i2p/router/message/GarlicMessageHandler.java index c44ec2f05..3a762b6fd 100644 --- a/router/java/src/net/i2p/router/message/GarlicMessageHandler.java +++ b/router/java/src/net/i2p/router/message/GarlicMessageHandler.java @@ -9,7 +9,7 @@ package net.i2p.router.message; */ import net.i2p.data.Hash; -import net.i2p.data.RouterIdentity; +import net.i2p.data.router.RouterIdentity; import net.i2p.data.i2np.GarlicMessage; import net.i2p.data.i2np.I2NPMessage; import net.i2p.router.HandlerJobBuilder; diff --git a/router/java/src/net/i2p/router/message/HandleGarlicMessageJob.java b/router/java/src/net/i2p/router/message/HandleGarlicMessageJob.java index 9392526b3..9a22ec6e8 100644 --- a/router/java/src/net/i2p/router/message/HandleGarlicMessageJob.java +++ b/router/java/src/net/i2p/router/message/HandleGarlicMessageJob.java @@ -9,7 +9,7 @@ package net.i2p.router.message; */ import net.i2p.data.Hash; -import net.i2p.data.RouterIdentity; +import net.i2p.data.router.RouterIdentity; import net.i2p.data.i2np.DeliveryInstructions; import net.i2p.data.i2np.GarlicMessage; import net.i2p.data.i2np.I2NPMessage; diff --git a/router/java/src/net/i2p/router/message/OutboundClientMessageOneShotJob.java b/router/java/src/net/i2p/router/message/OutboundClientMessageOneShotJob.java index 5040606e8..7da54172c 100644 --- a/router/java/src/net/i2p/router/message/OutboundClientMessageOneShotJob.java +++ b/router/java/src/net/i2p/router/message/OutboundClientMessageOneShotJob.java @@ -18,7 +18,7 @@ import net.i2p.data.Lease; import net.i2p.data.LeaseSet; import net.i2p.data.Payload; import net.i2p.data.PublicKey; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.SessionKey; import net.i2p.data.SessionTag; import net.i2p.data.i2cp.MessageId; diff --git a/router/java/src/net/i2p/router/message/SendMessageDirectJob.java b/router/java/src/net/i2p/router/message/SendMessageDirectJob.java index 6d0cfdbcf..cc7a337cc 100644 --- a/router/java/src/net/i2p/router/message/SendMessageDirectJob.java +++ b/router/java/src/net/i2p/router/message/SendMessageDirectJob.java @@ -11,7 +11,7 @@ package net.i2p.router.message; import java.util.Date; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.i2np.I2NPMessage; import net.i2p.router.Job; import net.i2p.router.JobImpl; diff --git a/router/java/src/net/i2p/router/networkdb/HandleDatabaseLookupMessageJob.java b/router/java/src/net/i2p/router/networkdb/HandleDatabaseLookupMessageJob.java index 685e18512..9931444aa 100644 --- a/router/java/src/net/i2p/router/networkdb/HandleDatabaseLookupMessageJob.java +++ b/router/java/src/net/i2p/router/networkdb/HandleDatabaseLookupMessageJob.java @@ -14,8 +14,8 @@ import java.util.Set; import net.i2p.data.DatabaseEntry; import net.i2p.data.Hash; import net.i2p.data.LeaseSet; -import net.i2p.data.RouterIdentity; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterIdentity; +import net.i2p.data.router.RouterInfo; import net.i2p.data.SessionKey; import net.i2p.data.TunnelId; import net.i2p.data.i2np.DatabaseLookupMessage; diff --git a/router/java/src/net/i2p/router/networkdb/PublishLocalRouterInfoJob.java b/router/java/src/net/i2p/router/networkdb/PublishLocalRouterInfoJob.java index f6a29355b..8b235260e 100644 --- a/router/java/src/net/i2p/router/networkdb/PublishLocalRouterInfoJob.java +++ b/router/java/src/net/i2p/router/networkdb/PublishLocalRouterInfoJob.java @@ -12,7 +12,7 @@ import java.util.Date; import java.util.Properties; import net.i2p.data.DataFormatException; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.SigningPrivateKey; import net.i2p.router.JobImpl; import net.i2p.router.Router; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/ExpireRoutersJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/ExpireRoutersJob.java index c2ea790a5..b52df8e17 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/ExpireRoutersJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/ExpireRoutersJob.java @@ -12,7 +12,7 @@ import java.util.Set; import net.i2p.data.DatabaseEntry; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.router.CommSystemFacade; import net.i2p.router.JobImpl; import net.i2p.router.RouterContext; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/FloodOnlyLookupMatchJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/FloodOnlyLookupMatchJob.java index 8f3a193a5..0de6c6504 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/FloodOnlyLookupMatchJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/FloodOnlyLookupMatchJob.java @@ -2,7 +2,7 @@ package net.i2p.router.networkdb.kademlia; import net.i2p.data.DatabaseEntry; import net.i2p.data.LeaseSet; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.i2np.DatabaseSearchReplyMessage; import net.i2p.data.i2np.DatabaseStoreMessage; import net.i2p.data.i2np.I2NPMessage; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillDatabaseLookupMessageHandler.java b/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillDatabaseLookupMessageHandler.java index 8ef121d06..a07ac8c70 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillDatabaseLookupMessageHandler.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillDatabaseLookupMessageHandler.java @@ -9,7 +9,7 @@ package net.i2p.router.networkdb.kademlia; */ import net.i2p.data.Hash; -import net.i2p.data.RouterIdentity; +import net.i2p.data.router.RouterIdentity; import net.i2p.data.i2np.DatabaseLookupMessage; import net.i2p.data.i2np.I2NPMessage; import net.i2p.router.HandlerJobBuilder; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillDatabaseStoreMessageHandler.java b/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillDatabaseStoreMessageHandler.java index e4c6ce71a..99d8c6265 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillDatabaseStoreMessageHandler.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillDatabaseStoreMessageHandler.java @@ -9,7 +9,7 @@ package net.i2p.router.networkdb.kademlia; */ import net.i2p.data.Hash; -import net.i2p.data.RouterIdentity; +import net.i2p.data.router.RouterIdentity; import net.i2p.data.i2np.DatabaseStoreMessage; import net.i2p.data.i2np.I2NPMessage; import net.i2p.router.HandlerJobBuilder; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillMonitorJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillMonitorJob.java index 99c4beda2..de634943c 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillMonitorJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillMonitorJob.java @@ -3,8 +3,8 @@ package net.i2p.router.networkdb.kademlia; import java.util.List; import net.i2p.data.Hash; -import net.i2p.data.RouterAddress; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterAddress; +import net.i2p.data.router.RouterInfo; import net.i2p.router.JobImpl; import net.i2p.router.Router; import net.i2p.router.RouterContext; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillNetworkDatabaseFacade.java b/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillNetworkDatabaseFacade.java index 24a7bc40a..22d51249a 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillNetworkDatabaseFacade.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillNetworkDatabaseFacade.java @@ -8,7 +8,7 @@ import java.util.Set; import net.i2p.data.DatabaseEntry; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.TunnelId; import net.i2p.data.i2np.DatabaseLookupMessage; import net.i2p.data.i2np.DatabaseStoreMessage; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillPeerSelector.java b/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillPeerSelector.java index fdf47bf3c..6870edcd5 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillPeerSelector.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillPeerSelector.java @@ -18,8 +18,8 @@ import java.util.Set; import java.util.TreeSet; import net.i2p.data.Hash; -import net.i2p.data.RouterAddress; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterAddress; +import net.i2p.data.router.RouterInfo; import net.i2p.kademlia.KBucketSet; import net.i2p.kademlia.SelectionCollector; import net.i2p.kademlia.XORComparator; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillVerifyStoreJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillVerifyStoreJob.java index f66b50020..85d0bc974 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillVerifyStoreJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/FloodfillVerifyStoreJob.java @@ -8,7 +8,7 @@ import net.i2p.data.Certificate; import net.i2p.data.DatabaseEntry; import net.i2p.data.Hash; import net.i2p.data.LeaseSet; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.i2np.DatabaseLookupMessage; import net.i2p.data.i2np.DatabaseSearchReplyMessage; import net.i2p.data.i2np.DatabaseStoreMessage; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/HandleFloodfillDatabaseLookupMessageJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/HandleFloodfillDatabaseLookupMessageJob.java index 0d03d7d4f..eceb4b576 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/HandleFloodfillDatabaseLookupMessageJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/HandleFloodfillDatabaseLookupMessageJob.java @@ -11,8 +11,8 @@ package net.i2p.router.networkdb.kademlia; import java.util.Set; import net.i2p.data.Hash; -import net.i2p.data.RouterIdentity; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterIdentity; +import net.i2p.data.router.RouterInfo; import net.i2p.data.TunnelId; import net.i2p.data.i2np.DatabaseStoreMessage; import net.i2p.data.i2np.DatabaseLookupMessage; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/HandleFloodfillDatabaseStoreMessageJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/HandleFloodfillDatabaseStoreMessageJob.java index f623022ca..57d1ee57b 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/HandleFloodfillDatabaseStoreMessageJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/HandleFloodfillDatabaseStoreMessageJob.java @@ -14,9 +14,9 @@ import java.util.Date; import net.i2p.data.DatabaseEntry; import net.i2p.data.Hash; import net.i2p.data.LeaseSet; -import net.i2p.data.RouterAddress; -import net.i2p.data.RouterIdentity; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterAddress; +import net.i2p.data.router.RouterIdentity; +import net.i2p.data.router.RouterInfo; import net.i2p.data.i2np.DatabaseStoreMessage; import net.i2p.data.i2np.DeliveryStatusMessage; import net.i2p.router.JobImpl; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/HarvesterJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/HarvesterJob.java index a69a2bc90..6bd687185 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/HarvesterJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/HarvesterJob.java @@ -7,7 +7,7 @@ import java.util.Set; import java.util.TreeMap; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.i2np.DatabaseLookupMessage; import net.i2p.router.JobImpl; import net.i2p.router.OutNetMessage; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/IterativeLookupJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/IterativeLookupJob.java index 13d763688..ac283109c 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/IterativeLookupJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/IterativeLookupJob.java @@ -1,7 +1,7 @@ package net.i2p.router.networkdb.kademlia; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.i2np.DatabaseSearchReplyMessage; import net.i2p.util.Log; import net.i2p.router.JobImpl; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/IterativeSearchJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/IterativeSearchJob.java index 7a2fa7770..023b6a873 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/IterativeSearchJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/IterativeSearchJob.java @@ -13,7 +13,7 @@ import java.util.concurrent.ConcurrentHashMap; import net.i2p.data.Base64; import net.i2p.data.DataHelper; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.i2np.DatabaseLookupMessage; import net.i2p.data.i2np.I2NPMessage; import net.i2p.kademlia.KBucketSet; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/KademliaNetworkDatabaseFacade.java b/router/java/src/net/i2p/router/networkdb/kademlia/KademliaNetworkDatabaseFacade.java index b4d108d02..ba52e5d61 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/KademliaNetworkDatabaseFacade.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/KademliaNetworkDatabaseFacade.java @@ -23,8 +23,8 @@ import net.i2p.data.DatabaseEntry; import net.i2p.data.DataHelper; import net.i2p.data.Hash; import net.i2p.data.LeaseSet; -import net.i2p.data.RouterAddress; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterAddress; +import net.i2p.data.router.RouterInfo; import net.i2p.data.i2np.DatabaseLookupMessage; import net.i2p.data.i2np.DatabaseStoreMessage; import net.i2p.kademlia.KBucketSet; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/MessageWrapper.java b/router/java/src/net/i2p/router/networkdb/kademlia/MessageWrapper.java index 15ae87a8b..ff9d3d501 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/MessageWrapper.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/MessageWrapper.java @@ -8,7 +8,7 @@ import net.i2p.crypto.TagSetHandle; import net.i2p.data.Certificate; import net.i2p.data.Hash; import net.i2p.data.PublicKey; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.SessionKey; import net.i2p.data.SessionTag; import net.i2p.data.i2np.DeliveryInstructions; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/PeerSelector.java b/router/java/src/net/i2p/router/networkdb/kademlia/PeerSelector.java index f73eb00fe..4eb23e13c 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/PeerSelector.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/PeerSelector.java @@ -16,7 +16,7 @@ import java.util.Set; import java.util.TreeMap; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.kademlia.KBucketSet; import net.i2p.kademlia.SelectionCollector; import net.i2p.router.RouterContext; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/PersistentDataStore.java b/router/java/src/net/i2p/router/networkdb/kademlia/PersistentDataStore.java index 27435d5b5..2a7713cff 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/PersistentDataStore.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/PersistentDataStore.java @@ -29,7 +29,7 @@ import net.i2p.data.Base64; import net.i2p.data.DatabaseEntry; import net.i2p.data.DataFormatException; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.router.JobImpl; import net.i2p.router.Router; import net.i2p.router.RouterContext; @@ -524,6 +524,11 @@ class PersistentDataStore extends TransientDataStore { if (_log.shouldLog(Log.INFO)) _log.info("Unable to read the router reference in " + _routerFile.getName(), ioe); corrupt = true; + } catch (Exception e) { + // key certificate problems, etc., don't let one bad RI kill the whole thing + if (_log.shouldLog(Log.INFO)) + _log.info("Unable to read the router reference in " + _routerFile.getName(), e); + corrupt = true; } finally { if (fis != null) try { fis.close(); } catch (IOException ioe) {} } diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/RefreshRoutersJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/RefreshRoutersJob.java index 852a5c792..20dd2a075 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/RefreshRoutersJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/RefreshRoutersJob.java @@ -5,7 +5,7 @@ import java.util.List; import java.util.Set; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.router.JobImpl; import net.i2p.router.RouterContext; import net.i2p.util.Log; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/SearchJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/SearchJob.java index 54a938319..9f2313f8e 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/SearchJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/SearchJob.java @@ -17,7 +17,7 @@ import net.i2p.data.DatabaseEntry; import net.i2p.data.DataHelper; import net.i2p.data.Hash; import net.i2p.data.LeaseSet; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.TunnelId; import net.i2p.data.i2np.DatabaseLookupMessage; import net.i2p.data.i2np.DatabaseSearchReplyMessage; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/SearchMessageSelector.java b/router/java/src/net/i2p/router/networkdb/kademlia/SearchMessageSelector.java index 3d756529d..30e8e4b18 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/SearchMessageSelector.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/SearchMessageSelector.java @@ -3,7 +3,7 @@ package net.i2p.router.networkdb.kademlia; import java.util.concurrent.atomic.AtomicInteger; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.i2np.DatabaseSearchReplyMessage; import net.i2p.data.i2np.DatabaseStoreMessage; import net.i2p.data.i2np.I2NPMessage; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/SearchReplyJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/SearchReplyJob.java index 8d8e5f19d..a8354b096 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/SearchReplyJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/SearchReplyJob.java @@ -2,7 +2,7 @@ package net.i2p.router.networkdb.kademlia; import net.i2p.data.Hash; import net.i2p.data.i2np.DatabaseSearchReplyMessage; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.router.JobImpl; import net.i2p.router.RouterContext; import net.i2p.util.Log; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/SearchUpdateReplyFoundJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/SearchUpdateReplyFoundJob.java index 22602b497..a67ae2fd8 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/SearchUpdateReplyFoundJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/SearchUpdateReplyFoundJob.java @@ -5,7 +5,7 @@ import java.util.Date; import net.i2p.data.DatabaseEntry; import net.i2p.data.Hash; import net.i2p.data.LeaseSet; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.i2np.DatabaseSearchReplyMessage; import net.i2p.data.i2np.DatabaseStoreMessage; import net.i2p.data.i2np.I2NPMessage; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/SingleLookupJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/SingleLookupJob.java index 711510fb4..62a878d6d 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/SingleLookupJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/SingleLookupJob.java @@ -1,7 +1,7 @@ package net.i2p.router.networkdb.kademlia; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.i2np.DatabaseSearchReplyMessage; import net.i2p.router.JobImpl; import net.i2p.router.RouterContext; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/StartExplorersJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/StartExplorersJob.java index cced2f546..7938ab072 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/StartExplorersJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/StartExplorersJob.java @@ -12,7 +12,7 @@ import java.util.HashSet; import java.util.Set; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.router.JobImpl; import net.i2p.router.Router; import net.i2p.router.RouterContext; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/StoreJob.java b/router/java/src/net/i2p/router/networkdb/kademlia/StoreJob.java index 311f2ba8f..81bef6950 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/StoreJob.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/StoreJob.java @@ -18,7 +18,7 @@ import net.i2p.data.DatabaseEntry; import net.i2p.data.DataFormatException; import net.i2p.data.Hash; import net.i2p.data.LeaseSet; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.TunnelId; import net.i2p.data.i2np.DatabaseStoreMessage; import net.i2p.data.i2np.I2NPMessage; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/StoreMessageSelector.java b/router/java/src/net/i2p/router/networkdb/kademlia/StoreMessageSelector.java index 6901f0afa..352c19cd7 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/StoreMessageSelector.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/StoreMessageSelector.java @@ -1,7 +1,7 @@ package net.i2p.router.networkdb.kademlia; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.i2np.DeliveryStatusMessage; import net.i2p.data.i2np.I2NPMessage; import net.i2p.router.MessageSelector; diff --git a/router/java/src/net/i2p/router/networkdb/kademlia/TransientDataStore.java b/router/java/src/net/i2p/router/networkdb/kademlia/TransientDataStore.java index 2a7318d25..11603efb9 100644 --- a/router/java/src/net/i2p/router/networkdb/kademlia/TransientDataStore.java +++ b/router/java/src/net/i2p/router/networkdb/kademlia/TransientDataStore.java @@ -18,7 +18,7 @@ import java.util.Set; import net.i2p.data.DatabaseEntry; import net.i2p.data.Hash; import net.i2p.data.LeaseSet; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.router.RouterContext; import net.i2p.util.Log; diff --git a/router/java/src/net/i2p/router/peermanager/PeerManager.java b/router/java/src/net/i2p/router/peermanager/PeerManager.java index ef7b1de34..d2de16d9b 100644 --- a/router/java/src/net/i2p/router/peermanager/PeerManager.java +++ b/router/java/src/net/i2p/router/peermanager/PeerManager.java @@ -19,7 +19,7 @@ import java.util.Set; import java.util.concurrent.ConcurrentHashMap; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.router.PeerSelectionCriteria; import net.i2p.router.Router; import net.i2p.router.RouterContext; diff --git a/router/java/src/net/i2p/router/peermanager/PeerTestJob.java b/router/java/src/net/i2p/router/peermanager/PeerTestJob.java index 24176a208..466c63ec1 100644 --- a/router/java/src/net/i2p/router/peermanager/PeerTestJob.java +++ b/router/java/src/net/i2p/router/peermanager/PeerTestJob.java @@ -5,7 +5,7 @@ import java.util.List; import java.util.Set; import net.i2p.data.Hash; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterInfo; import net.i2p.data.TunnelId; import net.i2p.data.i2np.DatabaseStoreMessage; import net.i2p.data.i2np.DeliveryStatusMessage; diff --git a/router/java/src/net/i2p/router/peermanager/ProfileOrganizer.java b/router/java/src/net/i2p/router/peermanager/ProfileOrganizer.java index a224f576a..7e89cab25 100644 --- a/router/java/src/net/i2p/router/peermanager/ProfileOrganizer.java +++ b/router/java/src/net/i2p/router/peermanager/ProfileOrganizer.java @@ -19,8 +19,8 @@ import java.util.concurrent.locks.ReentrantReadWriteLock; import net.i2p.crypto.SHA256Generator; import net.i2p.data.Hash; -import net.i2p.data.RouterAddress; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterAddress; +import net.i2p.data.router.RouterInfo; import net.i2p.router.NetworkDatabaseFacade; import net.i2p.router.RouterContext; import net.i2p.router.tunnel.pool.TunnelPeerSelector; diff --git a/router/java/src/net/i2p/router/startup/BootCommSystemJob.java b/router/java/src/net/i2p/router/startup/BootCommSystemJob.java index 3af4164b5..305869bad 100644 --- a/router/java/src/net/i2p/router/startup/BootCommSystemJob.java +++ b/router/java/src/net/i2p/router/startup/BootCommSystemJob.java @@ -16,7 +16,7 @@ import net.i2p.router.tasks.ReadConfigJob; import net.i2p.util.Log; /** This actually boots almost everything */ -public class BootCommSystemJob extends JobImpl { +class BootCommSystemJob extends JobImpl { private Log _log; public static final String PROP_USE_TRUSTED_LINKS = "router.trustedLinks"; diff --git a/router/java/src/net/i2p/router/startup/BootNetworkDbJob.java b/router/java/src/net/i2p/router/startup/BootNetworkDbJob.java index bf8d36a77..e512f9ea3 100644 --- a/router/java/src/net/i2p/router/startup/BootNetworkDbJob.java +++ b/router/java/src/net/i2p/router/startup/BootNetworkDbJob.java @@ -12,7 +12,7 @@ import net.i2p.router.JobImpl; import net.i2p.router.RouterContext; /** start up the network database */ -public class BootNetworkDbJob extends JobImpl { +class BootNetworkDbJob extends JobImpl { public BootNetworkDbJob(RouterContext ctx) { super(ctx); diff --git a/router/java/src/net/i2p/router/startup/BootPeerManagerJob.java b/router/java/src/net/i2p/router/startup/BootPeerManagerJob.java index 7ac5254f0..33f401023 100644 --- a/router/java/src/net/i2p/router/startup/BootPeerManagerJob.java +++ b/router/java/src/net/i2p/router/startup/BootPeerManagerJob.java @@ -12,7 +12,7 @@ import net.i2p.router.JobImpl; import net.i2p.router.RouterContext; /** start up the peer manager */ -public class BootPeerManagerJob extends JobImpl { +class BootPeerManagerJob extends JobImpl { public BootPeerManagerJob(RouterContext ctx) { super(ctx); diff --git a/router/java/src/net/i2p/router/startup/BuildTrustedLinksJob.java b/router/java/src/net/i2p/router/startup/BuildTrustedLinksJob.java index 3b88a2d9c..566204068 100644 --- a/router/java/src/net/i2p/router/startup/BuildTrustedLinksJob.java +++ b/router/java/src/net/i2p/router/startup/BuildTrustedLinksJob.java @@ -15,7 +15,7 @@ import net.i2p.router.RouterContext; /** * For future restricted routes. Does nothing now. */ -public class BuildTrustedLinksJob extends JobImpl { +class BuildTrustedLinksJob extends JobImpl { private final Job _next; public BuildTrustedLinksJob(RouterContext context, Job next) { diff --git a/router/java/src/net/i2p/router/startup/CreateRouterInfoJob.java b/router/java/src/net/i2p/router/startup/CreateRouterInfoJob.java index 498cbe665..a343939f9 100644 --- a/router/java/src/net/i2p/router/startup/CreateRouterInfoJob.java +++ b/router/java/src/net/i2p/router/startup/CreateRouterInfoJob.java @@ -12,16 +12,22 @@ import java.io.BufferedOutputStream; import java.io.File; import java.io.IOException; import java.io.OutputStream; +import java.security.GeneralSecurityException; import java.util.Properties; +import net.i2p.crypto.SigType; import net.i2p.data.Certificate; import net.i2p.data.DataFormatException; +import net.i2p.data.DataHelper; +import net.i2p.data.KeyCertificate; import net.i2p.data.PrivateKey; +import net.i2p.data.PrivateKeyFile; import net.i2p.data.PublicKey; -import net.i2p.data.RouterIdentity; -import net.i2p.data.RouterInfo; +import net.i2p.data.router.RouterIdentity; +import net.i2p.data.router.RouterInfo; import net.i2p.data.SigningPrivateKey; import net.i2p.data.SigningPublicKey; +import net.i2p.data.SimpleDataStructure; import net.i2p.router.Job; import net.i2p.router.JobImpl; import net.i2p.router.Router; @@ -40,7 +46,14 @@ public class CreateRouterInfoJob extends JobImpl { private final Log _log; private final Job _next; - public CreateRouterInfoJob(RouterContext ctx, Job next) { + public static final String INFO_FILENAME = "router.info"; + public static final String KEYS_FILENAME = "router.keys"; + public static final String KEYS2_FILENAME = "router.keys.dat"; + private static final String PROP_ROUTER_SIGTYPE = "router.sigType"; + /** TODO when changing, check isAvailable() and fallback to DSA_SHA1 */ + private static final SigType DEFAULT_SIGTYPE = SigType.DSA_SHA1; + + CreateRouterInfoJob(RouterContext ctx, Job next) { super(ctx); _next = next; _log = ctx.logManager().getLog(CreateRouterInfoJob.class); @@ -59,9 +72,13 @@ public class CreateRouterInfoJob extends JobImpl { /** * Writes 6 files: router.info (standard RI format), - * router,keys, and 4 individual key files under keyBackup/ + * router.keys2, and 4 individual key files under keyBackup/ * - * router.keys file format: Note that this is NOT the + * router.keys2 file format: This is the + * same "eepPriv.dat" format used by the client code, + * as documented in PrivateKeyFile. + * + * Old router.keys file format: Note that this is NOT the * same "eepPriv.dat" format used by the client code. *
* - Private key (256 bytes)
@@ -74,9 +91,9 @@ public class CreateRouterInfoJob extends JobImpl {
* Caller must hold Router.routerInfoFileLock.
*/
RouterInfo createRouterInfo() {
+ SigType type = getSigTypeConfig(getContext());
RouterInfo info = new RouterInfo();
OutputStream fos1 = null;
- OutputStream fos2 = null;
try {
info.setAddresses(getContext().commSystem().createAddresses());
Properties stats = getContext().statPublisher().publishStatistics();
@@ -86,21 +103,26 @@ public class CreateRouterInfoJob extends JobImpl {
// not necessary, in constructor
//info.setPeers(new HashSet());
info.setPublished(getCurrentPublishDate(getContext()));
- RouterIdentity ident = new RouterIdentity();
- Certificate cert = getContext().router().createCertificate();
- ident.setCertificate(cert);
- PublicKey pubkey = null;
- PrivateKey privkey = null;
- SigningPublicKey signingPubKey = null;
- SigningPrivateKey signingPrivKey = null;
Object keypair[] = getContext().keyGenerator().generatePKIKeypair();
- pubkey = (PublicKey)keypair[0];
- privkey = (PrivateKey)keypair[1];
- Object signingKeypair[] = getContext().keyGenerator().generateSigningKeypair();
- signingPubKey = (SigningPublicKey)signingKeypair[0];
- signingPrivKey = (SigningPrivateKey)signingKeypair[1];
+ PublicKey pubkey = (PublicKey)keypair[0];
+ PrivateKey privkey = (PrivateKey)keypair[1];
+ SimpleDataStructure signingKeypair[] = getContext().keyGenerator().generateSigningKeys(type);
+ SigningPublicKey signingPubKey = (SigningPublicKey)signingKeypair[0];
+ SigningPrivateKey signingPrivKey = (SigningPrivateKey)signingKeypair[1];
+ RouterIdentity ident = new RouterIdentity();
+ Certificate cert = createCertificate(getContext(), signingPubKey);
+ ident.setCertificate(cert);
ident.setPublicKey(pubkey);
ident.setSigningPublicKey(signingPubKey);
+ byte[] padding;
+ int padLen = SigningPublicKey.KEYSIZE_BYTES - signingPubKey.length();
+ if (padLen > 0) {
+ padding = new byte[padLen];
+ getContext().random().nextBytes(padding);
+ ident.setPadding(padding);
+ } else {
+ padding = null;
+ }
info.setIdentity(ident);
info.sign(signingPrivKey);
@@ -108,34 +130,51 @@ public class CreateRouterInfoJob extends JobImpl {
if (!info.isValid())
throw new DataFormatException("RouterInfo we just built is invalid: " + info);
- String infoFilename = getContext().getProperty(Router.PROP_INFO_FILENAME, Router.PROP_INFO_FILENAME_DEFAULT);
- File ifile = new File(getContext().getRouterDir(), infoFilename);
+ // remove router.keys
+ (new File(getContext().getRouterDir(), KEYS_FILENAME)).delete();
+
+ // write router.info
+ File ifile = new File(getContext().getRouterDir(), INFO_FILENAME);
fos1 = new BufferedOutputStream(new SecureFileOutputStream(ifile));
info.writeBytes(fos1);
- String keyFilename = getContext().getProperty(Router.PROP_KEYS_FILENAME, Router.PROP_KEYS_FILENAME_DEFAULT);
- File kfile = new File(getContext().getRouterDir(), keyFilename);
- fos2 = new BufferedOutputStream(new SecureFileOutputStream(kfile));
- privkey.writeBytes(fos2);
- signingPrivKey.writeBytes(fos2);
- pubkey.writeBytes(fos2);
- signingPubKey.writeBytes(fos2);
+ // write router.keys.dat
+ File kfile = new File(getContext().getRouterDir(), KEYS2_FILENAME);
+ PrivateKeyFile pkf = new PrivateKeyFile(kfile, pubkey, signingPubKey, cert,
+ privkey, signingPrivKey, padding);
+ pkf.write();
getContext().keyManager().setKeys(pubkey, privkey, signingPubKey, signingPrivKey);
- _log.info("Router info created and stored at " + ifile.getAbsolutePath() + " with private keys stored at " + kfile.getAbsolutePath() + " [" + info + "]");
+ if (_log.shouldLog(Log.INFO))
+ _log.info("Router info created and stored at " + ifile.getAbsolutePath() + " with private keys stored at " + kfile.getAbsolutePath() + " [" + info + "]");
getContext().router().eventLog().addEvent(EventLog.REKEYED, ident.calculateHash().toBase64());
+ } catch (GeneralSecurityException gse) {
+ _log.log(Log.CRIT, "Error building the new router information", gse);
} catch (DataFormatException dfe) {
_log.log(Log.CRIT, "Error building the new router information", dfe);
} catch (IOException ioe) {
_log.log(Log.CRIT, "Error writing out the new router information", ioe);
} finally {
if (fos1 != null) try { fos1.close(); } catch (IOException ioe) {}
- if (fos2 != null) try { fos2.close(); } catch (IOException ioe) {}
}
return info;
}
+ /**
+ * The configured SigType to expect on read-in
+ * @since 0.9.16
+ */
+ public static SigType getSigTypeConfig(RouterContext ctx) {
+ SigType cstype = CreateRouterInfoJob.DEFAULT_SIGTYPE;
+ String sstype = ctx.getProperty(PROP_ROUTER_SIGTYPE);
+ if (sstype != null) {
+ SigType ntype = SigType.parseSigType(sstype);
+ if (ntype != null && ntype.isAvailable())
+ cstype = ntype;
+ }
+ return cstype;
+ }
/**
* We probably don't want to expose the exact time at which a router published its info.
@@ -146,4 +185,22 @@ public class CreateRouterInfoJob extends JobImpl {
//_log.info("Setting published date to /now/");
return context.clock().now();
}
+
+ /**
+ * Only called at startup via LoadRouterInfoJob and RebuildRouterInfoJob.
+ * Not called by periodic RepublishLocalRouterInfoJob.
+ * We don't want to change the cert on the fly as it changes the router hash.
+ * RouterInfo.isHidden() checks the capability, but RouterIdentity.isHidden() checks the cert.
+ * There's no reason to ever add a hidden cert?
+ *
+ * @return the certificate for a new RouterInfo - probably a null cert.
+ * @since 0.9.16 moved from Router
+ */
+ static Certificate createCertificate(RouterContext ctx, SigningPublicKey spk) {
+ if (spk.getType() != SigType.DSA_SHA1)
+ return new KeyCertificate(spk);
+ if (ctx.getBooleanProperty(Router.PROP_HIDDEN))
+ return new Certificate(Certificate.CERTIFICATE_TYPE_HIDDEN, null);
+ return Certificate.NULL_CERT;
+ }
}
diff --git a/router/java/src/net/i2p/router/startup/LoadRouterInfoJob.java b/router/java/src/net/i2p/router/startup/LoadRouterInfoJob.java
index 9a560da5f..51ca135ab 100644
--- a/router/java/src/net/i2p/router/startup/LoadRouterInfoJob.java
+++ b/router/java/src/net/i2p/router/startup/LoadRouterInfoJob.java
@@ -15,18 +15,27 @@ import java.io.InputStream;
import java.io.IOException;
import java.util.concurrent.atomic.AtomicBoolean;
+import net.i2p.crypto.SigType;
+import net.i2p.data.Certificate;
import net.i2p.data.DataFormatException;
+import net.i2p.data.DataHelper;
import net.i2p.data.PrivateKey;
import net.i2p.data.PublicKey;
-import net.i2p.data.RouterInfo;
import net.i2p.data.SigningPrivateKey;
import net.i2p.data.SigningPublicKey;
+import net.i2p.data.router.RouterIdentity;
+import net.i2p.data.router.RouterInfo;
+import net.i2p.data.router.RouterPrivateKeyFile;
import net.i2p.router.JobImpl;
import net.i2p.router.Router;
import net.i2p.router.RouterContext;
import net.i2p.util.Log;
-public class LoadRouterInfoJob extends JobImpl {
+/**
+ * Run once or twice at startup by StartupJob,
+ * and then runs BootCommSystemJob
+ */
+class LoadRouterInfoJob extends JobImpl {
private final Log _log;
private RouterInfo _us;
private static final AtomicBoolean _keyLengthChecked = new AtomicBoolean();
@@ -45,6 +54,7 @@ public class LoadRouterInfoJob extends JobImpl {
if (_us == null) {
RebuildRouterInfoJob r = new RebuildRouterInfoJob(getContext());
r.rebuildRouterInfo(false);
+ // run a second time
getContext().jobQueue().addJob(this);
return;
} else {
@@ -54,18 +64,21 @@ public class LoadRouterInfoJob extends JobImpl {
}
}
+ /**
+ * Loads router.info and router.keys2 or router.keys.
+ *
+ * See CreateRouterInfoJob for file formats
+ */
private void loadRouterInfo() {
- String routerInfoFile = getContext().getProperty(Router.PROP_INFO_FILENAME, Router.PROP_INFO_FILENAME_DEFAULT);
RouterInfo info = null;
- String keyFilename = getContext().getProperty(Router.PROP_KEYS_FILENAME, Router.PROP_KEYS_FILENAME_DEFAULT);
-
- File rif = new File(getContext().getRouterDir(), routerInfoFile);
+ File rif = new File(getContext().getRouterDir(), CreateRouterInfoJob.INFO_FILENAME);
boolean infoExists = rif.exists();
- File rkf = new File(getContext().getRouterDir(), keyFilename);
+ File rkf = new File(getContext().getRouterDir(), CreateRouterInfoJob.KEYS_FILENAME);
boolean keysExist = rkf.exists();
+ File rkf2 = new File(getContext().getRouterDir(), CreateRouterInfoJob.KEYS2_FILENAME);
+ boolean keys2Exist = rkf2.exists();
InputStream fis1 = null;
- InputStream fis2 = null;
try {
// if we have a routerinfo but no keys, things go bad in a hurry:
// CRIT ...rkdb.PublishLocalRouterInfoJob: Internal error - signing private key not known? rescheduling publish for 30s
@@ -73,7 +86,7 @@ public class LoadRouterInfoJob extends JobImpl {
// CRIT ...sport.udp.EstablishmentManager: Error in the establisher java.lang.NullPointerException
// at net.i2p.router.transport.udp.PacketBuilder.buildSessionConfirmedPacket(PacketBuilder.java:574)
// so pretend the RI isn't there if there is no keyfile
- if (infoExists && keysExist) {
+ if (infoExists && (keys2Exist || keysExist)) {
fis1 = new BufferedInputStream(new FileInputStream(rif));
info = new RouterInfo();
info.readBytes(fis1);
@@ -85,29 +98,32 @@ public class LoadRouterInfoJob extends JobImpl {
_us = info;
}
- if (keysExist) {
- fis2 = new BufferedInputStream(new FileInputStream(rkf));
- PrivateKey privkey = new PrivateKey();
- privkey.readBytes(fis2);
- if (shouldRebuild(privkey)) {
+ if (keys2Exist || keysExist) {
+ KeyData kd = readKeyData(rkf, rkf2);
+ PublicKey pubkey = kd.routerIdentity.getPublicKey();
+ SigningPublicKey signingPubKey = kd.routerIdentity.getSigningPublicKey();
+ PrivateKey privkey = kd.privateKey;
+ SigningPrivateKey signingPrivKey = kd.signingPrivateKey;
+ SigType stype = signingPubKey.getType();
+
+ // check if the sigtype config changed
+ SigType cstype = CreateRouterInfoJob.getSigTypeConfig(getContext());
+ boolean sigTypeChanged = stype != cstype;
+
+ if (sigTypeChanged || shouldRebuild(privkey)) {
+ if (sigTypeChanged)
+ _log.logAlways(Log.WARN, "Rebuilding RouterInfo with new signature type " + cstype);
_us = null;
// windows... close before deleting
if (fis1 != null) {
try { fis1.close(); } catch (IOException ioe) {}
fis1 = null;
}
- try { fis2.close(); } catch (IOException ioe) {}
- fis2 = null;
rif.delete();
rkf.delete();
+ rkf2.delete();
return;
}
- SigningPrivateKey signingPrivKey = new SigningPrivateKey();
- signingPrivKey.readBytes(fis2);
- PublicKey pubkey = new PublicKey();
- pubkey.readBytes(fis2);
- SigningPublicKey signingPubKey = new SigningPublicKey();
- signingPubKey.readBytes(fis2);
getContext().keyManager().setKeys(pubkey, privkey, signingPubKey, signingPrivKey);
}
@@ -119,12 +135,9 @@ public class LoadRouterInfoJob extends JobImpl {
try { fis1.close(); } catch (IOException ioe2) {}
fis1 = null;
}
- if (fis2 != null) {
- try { fis2.close(); } catch (IOException ioe2) {}
- fis2 = null;
- }
rif.delete();
rkf.delete();
+ rkf2.delete();
} catch (DataFormatException dfe) {
_log.log(Log.CRIT, "Corrupt router info or keys at " + rif.getAbsolutePath() + " / " + rkf.getAbsolutePath(), dfe);
_us = null;
@@ -133,15 +146,11 @@ public class LoadRouterInfoJob extends JobImpl {
try { fis1.close(); } catch (IOException ioe) {}
fis1 = null;
}
- if (fis2 != null) {
- try { fis2.close(); } catch (IOException ioe) {}
- fis2 = null;
- }
rif.delete();
rkf.delete();
+ rkf2.delete();
} finally {
if (fis1 != null) try { fis1.close(); } catch (IOException ioe) {}
- if (fis2 != null) try { fis2.close(); } catch (IOException ioe) {}
}
}
@@ -174,4 +183,55 @@ public class LoadRouterInfoJob extends JobImpl {
_log.logAlways(Log.WARN, "Rebuilding RouterInfo with faster key");
return uselong != haslong;
}
+
+ /** @since 0.9.16 */
+ public static class KeyData {
+ public final RouterIdentity routerIdentity;
+ public final PrivateKey privateKey;
+ public final SigningPrivateKey signingPrivateKey;
+
+ public KeyData(RouterIdentity ri, PrivateKey pk, SigningPrivateKey spk) {
+ routerIdentity = ri;
+ privateKey = pk;
+ signingPrivateKey = spk;
+ }
+ }
+
+ /**
+ * @param rkf1 in router.keys format, tried second
+ * @param rkf2 in eepPriv.dat format, tried first
+ * @return non-null, throws IOE if neither exisits
+ * @since 0.9.16
+ */
+ public static KeyData readKeyData(File rkf1, File rkf2) throws DataFormatException, IOException {
+ RouterIdentity ri;
+ PrivateKey privkey;
+ SigningPrivateKey signingPrivKey;
+ if (rkf2.exists()) {
+ RouterPrivateKeyFile pkf = new RouterPrivateKeyFile(rkf2);
+ ri = pkf.getRouterIdentity();
+ privkey = pkf.getPrivKey();
+ signingPrivKey = pkf.getSigningPrivKey();
+ } else {
+ InputStream fis = null;
+ try {
+ fis = new BufferedInputStream(new FileInputStream(rkf1));
+ privkey = new PrivateKey();
+ privkey.readBytes(fis);
+ signingPrivKey = new SigningPrivateKey();
+ signingPrivKey.readBytes(fis);
+ PublicKey pubkey = new PublicKey();
+ pubkey.readBytes(fis);
+ SigningPublicKey signingPubKey = new SigningPublicKey();
+ signingPubKey.readBytes(fis);
+ ri = new RouterIdentity();
+ ri.setPublicKey(pubkey);
+ ri.setSigningPublicKey(signingPubKey);
+ ri.setCertificate(Certificate.NULL_CERT);
+ } finally {
+ if (fis != null) try { fis.close(); } catch (IOException ioe) {}
+ }
+ }
+ return new KeyData(ri, privkey, signingPrivKey);
+ }
}
diff --git a/router/java/src/net/i2p/router/startup/RebuildRouterInfoJob.java b/router/java/src/net/i2p/router/startup/RebuildRouterInfoJob.java
index b611114d0..ef0826cf5 100644
--- a/router/java/src/net/i2p/router/startup/RebuildRouterInfoJob.java
+++ b/router/java/src/net/i2p/router/startup/RebuildRouterInfoJob.java
@@ -9,22 +9,24 @@ package net.i2p.router.startup;
*/
import java.io.File;
-import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.Properties;
+import net.i2p.crypto.SigType;
import net.i2p.data.Certificate;
import net.i2p.data.DataFormatException;
+import net.i2p.data.DataHelper;
import net.i2p.data.PrivateKey;
import net.i2p.data.PublicKey;
-import net.i2p.data.RouterIdentity;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterIdentity;
+import net.i2p.data.router.RouterInfo;
import net.i2p.data.SigningPrivateKey;
import net.i2p.data.SigningPublicKey;
import net.i2p.router.JobImpl;
import net.i2p.router.Router;
import net.i2p.router.RouterContext;
+import net.i2p.router.startup.LoadRouterInfoJob.KeyData;
import net.i2p.util.Log;
import net.i2p.util.SecureFileOutputStream;
@@ -44,7 +46,7 @@ import net.i2p.util.SecureFileOutputStream;
* router.info.rebuild file is deleted
*
*/
-public class RebuildRouterInfoJob extends JobImpl {
+class RebuildRouterInfoJob extends JobImpl {
private final Log _log;
private final static long REBUILD_DELAY = 45*1000; // every 30 seconds
@@ -57,11 +59,11 @@ public class RebuildRouterInfoJob extends JobImpl {
public String getName() { return "Rebuild Router Info"; }
public void runJob() {
+ throw new UnsupportedOperationException();
+/****
_log.debug("Testing to rebuild router info");
- String infoFile = getContext().getProperty(Router.PROP_INFO_FILENAME, Router.PROP_INFO_FILENAME_DEFAULT);
- File info = new File(getContext().getRouterDir(), infoFile);
- String keyFilename = getContext().getProperty(Router.PROP_KEYS_FILENAME, Router.PROP_KEYS_FILENAME_DEFAULT);
- File keyFile = new File(getContext().getRouterDir(), keyFilename);
+ File info = new File(getContext().getRouterDir(), CreateRouterInfoJob.INFO_FILENAME);
+ File keyFile = new File(getContext().getRouterDir(), CreateRouterInfoJob.KEYS2_FILENAME);
if (!info.exists() || !keyFile.exists()) {
_log.info("Router info file [" + info.getAbsolutePath() + "] or private key file [" + keyFile.getAbsolutePath() + "] deleted, rebuilding");
@@ -71,51 +73,37 @@ public class RebuildRouterInfoJob extends JobImpl {
}
getTiming().setStartAfter(getContext().clock().now() + REBUILD_DELAY);
getContext().jobQueue().addJob(this);
+****/
}
void rebuildRouterInfo() {
rebuildRouterInfo(true);
}
+ /**
+ * @param alreadyRunning unused
+ */
void rebuildRouterInfo(boolean alreadyRunning) {
_log.debug("Rebuilding the new router info");
RouterInfo info = null;
- String infoFilename = getContext().getProperty(Router.PROP_INFO_FILENAME, Router.PROP_INFO_FILENAME_DEFAULT);
- File infoFile = new File(getContext().getRouterDir(), infoFilename);
- String keyFilename = getContext().getProperty(Router.PROP_KEYS_FILENAME, Router.PROP_KEYS_FILENAME_DEFAULT);
- File keyFile = new File(getContext().getRouterDir(), keyFilename);
+ File infoFile = new File(getContext().getRouterDir(), CreateRouterInfoJob.INFO_FILENAME);
+ File keyFile = new File(getContext().getRouterDir(), CreateRouterInfoJob.KEYS_FILENAME);
+ File keyFile2 = new File(getContext().getRouterDir(), CreateRouterInfoJob.KEYS2_FILENAME);
- if (keyFile.exists()) {
+ if (keyFile2.exists() || keyFile.exists()) {
// ok, no need to rebuild a brand new identity, just update what we can
RouterInfo oldinfo = getContext().router().getRouterInfo();
if (oldinfo == null) {
- info = new RouterInfo();
- FileInputStream fis = null;
try {
- fis = new FileInputStream(keyFile);
- PrivateKey privkey = new PrivateKey();
- privkey.readBytes(fis);
- SigningPrivateKey signingPrivKey = new SigningPrivateKey();
- signingPrivKey.readBytes(fis);
- PublicKey pubkey = new PublicKey();
- pubkey.readBytes(fis);
- SigningPublicKey signingPubKey = new SigningPublicKey();
- signingPubKey.readBytes(fis);
- RouterIdentity ident = new RouterIdentity();
- Certificate cert = getContext().router().createCertificate();
- ident.setCertificate(cert);
- ident.setPublicKey(pubkey);
- ident.setSigningPublicKey(signingPubKey);
- info.setIdentity(ident);
+ KeyData kd = LoadRouterInfoJob.readKeyData(keyFile, keyFile2);
+ info = new RouterInfo();
+ info.setIdentity(kd.routerIdentity);
} catch (Exception e) {
_log.log(Log.CRIT, "Error reading in the key data from " + keyFile.getAbsolutePath(), e);
- if (fis != null) try { fis.close(); } catch (IOException ioe) {}
- fis = null;
keyFile.delete();
+ keyFile2.delete();
rebuildRouterInfo(alreadyRunning);
return;
- } finally {
- if (fis != null) try { fis.close(); } catch (IOException ioe) {}
}
} else {
// Make a new RI from the old identity, or else info.setAddresses() will throw an ISE
@@ -160,12 +148,14 @@ public class RebuildRouterInfoJob extends JobImpl {
_log.warn("Private key file " + keyFile.getAbsolutePath() + " deleted! Rebuilding a brand new router identity!");
// this proc writes the keys and info to the file as well as builds the latest and greatest info
CreateRouterInfoJob j = new CreateRouterInfoJob(getContext(), null);
- info = j.createRouterInfo();
+ synchronized (getContext().router().routerInfoFileLock) {
+ info = j.createRouterInfo();
+ }
}
//MessageHistory.initialize();
getContext().router().setRouterInfo(info);
- _log.info("Router info rebuilt and stored at " + infoFilename + " [" + info + "]");
+ _log.info("Router info rebuilt and stored at " + infoFile + " [" + info + "]");
}
}
diff --git a/router/java/src/net/i2p/router/startup/StartAcceptingClientsJob.java b/router/java/src/net/i2p/router/startup/StartAcceptingClientsJob.java
index 50d840d43..672bf702a 100644
--- a/router/java/src/net/i2p/router/startup/StartAcceptingClientsJob.java
+++ b/router/java/src/net/i2p/router/startup/StartAcceptingClientsJob.java
@@ -12,7 +12,7 @@ import net.i2p.router.JobImpl;
import net.i2p.router.RouterContext;
/** start I2CP interface */
-public class StartAcceptingClientsJob extends JobImpl {
+class StartAcceptingClientsJob extends JobImpl {
public StartAcceptingClientsJob(RouterContext context) {
super(context);
diff --git a/router/java/src/net/i2p/router/startup/WorkingDir.java b/router/java/src/net/i2p/router/startup/WorkingDir.java
index 3763f2e7a..15a3e7fb4 100644
--- a/router/java/src/net/i2p/router/startup/WorkingDir.java
+++ b/router/java/src/net/i2p/router/startup/WorkingDir.java
@@ -147,7 +147,7 @@ public class WorkingDir {
// Check for a router.keys file or logs dir, if either exists it's an old install,
// and only migrate the data files if told to do so
// (router.keys could be deleted later by a killkeys())
- test = new File(oldDirf, "router.keys");
+ test = new File(oldDirf, CreateRouterInfoJob.KEYS_FILENAME);
boolean oldInstall = test.exists();
if (!oldInstall) {
test = new File(oldDirf, "logs");
diff --git a/router/java/src/net/i2p/router/tasks/PersistRouterInfoJob.java b/router/java/src/net/i2p/router/tasks/PersistRouterInfoJob.java
index c29dd2577..6a14a5134 100644
--- a/router/java/src/net/i2p/router/tasks/PersistRouterInfoJob.java
+++ b/router/java/src/net/i2p/router/tasks/PersistRouterInfoJob.java
@@ -13,10 +13,10 @@ import java.io.FileOutputStream;
import java.io.IOException;
import net.i2p.data.DataFormatException;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterInfo;
import net.i2p.router.JobImpl;
-import net.i2p.router.Router;
import net.i2p.router.RouterContext;
+import net.i2p.router.startup.CreateRouterInfoJob;
import net.i2p.util.Log;
import net.i2p.util.SecureFileOutputStream;
@@ -37,8 +37,7 @@ public class PersistRouterInfoJob extends JobImpl {
if (_log.shouldLog(Log.DEBUG))
_log.debug("Persisting updated router info");
- String infoFilename = getContext().getProperty(Router.PROP_INFO_FILENAME, Router.PROP_INFO_FILENAME_DEFAULT);
- File infoFile = new File(getContext().getRouterDir(), infoFilename);
+ File infoFile = new File(getContext().getRouterDir(), CreateRouterInfoJob.INFO_FILENAME);
RouterInfo info = getContext().router().getRouterInfo();
diff --git a/router/java/src/net/i2p/router/transport/CommSystemFacadeImpl.java b/router/java/src/net/i2p/router/transport/CommSystemFacadeImpl.java
index bc3ad9543..b9e38f9da 100644
--- a/router/java/src/net/i2p/router/transport/CommSystemFacadeImpl.java
+++ b/router/java/src/net/i2p/router/transport/CommSystemFacadeImpl.java
@@ -17,8 +17,8 @@ import java.util.Locale;
import java.util.Vector;
import net.i2p.data.Hash;
-import net.i2p.data.RouterAddress;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterAddress;
+import net.i2p.data.router.RouterInfo;
import net.i2p.router.CommSystemFacade;
import net.i2p.router.OutNetMessage;
import net.i2p.router.RouterContext;
diff --git a/router/java/src/net/i2p/router/transport/Transport.java b/router/java/src/net/i2p/router/transport/Transport.java
index e232fa7e4..459c84680 100644
--- a/router/java/src/net/i2p/router/transport/Transport.java
+++ b/router/java/src/net/i2p/router/transport/Transport.java
@@ -14,8 +14,8 @@ import java.util.List;
import java.util.Vector;
import net.i2p.data.Hash;
-import net.i2p.data.RouterAddress;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterAddress;
+import net.i2p.data.router.RouterInfo;
import net.i2p.router.OutNetMessage;
/**
diff --git a/router/java/src/net/i2p/router/transport/TransportEventListener.java b/router/java/src/net/i2p/router/transport/TransportEventListener.java
index 9a6d80d1c..b8437efd1 100644
--- a/router/java/src/net/i2p/router/transport/TransportEventListener.java
+++ b/router/java/src/net/i2p/router/transport/TransportEventListener.java
@@ -9,7 +9,7 @@ package net.i2p.router.transport;
*/
import net.i2p.data.Hash;
-import net.i2p.data.RouterIdentity;
+import net.i2p.data.router.RouterIdentity;
import net.i2p.data.i2np.I2NPMessage;
public interface TransportEventListener {
diff --git a/router/java/src/net/i2p/router/transport/TransportImpl.java b/router/java/src/net/i2p/router/transport/TransportImpl.java
index 194ae3016..6dd93b4c5 100644
--- a/router/java/src/net/i2p/router/transport/TransportImpl.java
+++ b/router/java/src/net/i2p/router/transport/TransportImpl.java
@@ -30,9 +30,9 @@ import java.util.concurrent.CopyOnWriteArrayList;
import net.i2p.data.DataHelper;
import net.i2p.data.Hash;
-import net.i2p.data.RouterAddress;
-import net.i2p.data.RouterIdentity;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterAddress;
+import net.i2p.data.router.RouterIdentity;
+import net.i2p.data.router.RouterInfo;
import net.i2p.data.i2np.I2NPMessage;
import net.i2p.router.CommSystemFacade;
import net.i2p.router.Job;
diff --git a/router/java/src/net/i2p/router/transport/TransportManager.java b/router/java/src/net/i2p/router/transport/TransportManager.java
index d9e0c3798..75e843707 100644
--- a/router/java/src/net/i2p/router/transport/TransportManager.java
+++ b/router/java/src/net/i2p/router/transport/TransportManager.java
@@ -22,8 +22,8 @@ import java.util.Vector;
import java.util.concurrent.ConcurrentHashMap;
import net.i2p.data.Hash;
-import net.i2p.data.RouterAddress;
-import net.i2p.data.RouterIdentity;
+import net.i2p.data.router.RouterAddress;
+import net.i2p.data.router.RouterIdentity;
import net.i2p.data.i2np.I2NPMessage;
import net.i2p.router.CommSystemFacade;
import net.i2p.router.OutNetMessage;
@@ -59,6 +59,7 @@ public class TransportManager implements TransportEventListener {
_context = context;
_log = _context.logManager().getLog(TransportManager.class);
_context.statManager().createRateStat("transport.banlistOnUnreachable", "Add a peer to the banlist since none of the transports can reach them", "Transport", new long[] { 60*1000, 10*60*1000, 60*60*1000 });
+ _context.statManager().createRateStat("transport.banlistOnUsupportedSigType", "Add a peer to the banlist since signature type is unsupported", "Transport", new long[] { 60*1000, 10*60*1000, 60*60*1000 });
_context.statManager().createRateStat("transport.noBidsYetNotAllUnreachable", "Add a peer to the banlist since none of the transports can reach them", "Transport", new long[] { 60*1000, 10*60*1000, 60*60*1000 });
_context.statManager().createRateStat("transport.bidFailBanlisted", "Could not attempt to bid on message, as they were banlisted", "Transport", new long[] { 60*1000, 10*60*1000, 60*60*1000 });
_context.statManager().createRateStat("transport.bidFailSelf", "Could not attempt to bid on message, as it targeted ourselves", "Transport", new long[] { 60*1000, 10*60*1000, 60*60*1000 });
@@ -499,8 +500,11 @@ public class TransportManager implements TransportEventListener {
}
}
if (unreachableTransports >= _transports.size()) {
- // Don't banlist if we aren't talking to anybody, as we may have a network connection issue
- if (unreachableTransports >= _transports.size() && countActivePeers() > 0) {
+ if (msg.getTarget().getIdentity().getSigningPublicKey().getType() == null) {
+ _context.statManager().addRateData("transport.banlistOnUnsupportedSigType", 1);
+ _context.banlist().banlistRouterForever(peer, _x("Unsupported signature type"));
+ } else if (unreachableTransports >= _transports.size() && countActivePeers() > 0) {
+ // Don't banlist if we aren't talking to anybody, as we may have a network connection issue
_context.statManager().addRateData("transport.banlistOnUnreachable", msg.getLifetime(), msg.getLifetime());
_context.banlist().banlistRouter(peer, _x("Unreachable on any transport"));
}
diff --git a/router/java/src/net/i2p/router/transport/TransportUtil.java b/router/java/src/net/i2p/router/transport/TransportUtil.java
index 1682abd91..648119f91 100644
--- a/router/java/src/net/i2p/router/transport/TransportUtil.java
+++ b/router/java/src/net/i2p/router/transport/TransportUtil.java
@@ -13,7 +13,7 @@ import java.net.UnknownHostException;
import java.util.HashMap;
import java.util.Map;
-import net.i2p.data.RouterAddress;
+import net.i2p.data.router.RouterAddress;
import net.i2p.router.RouterContext;
/**
diff --git a/router/java/src/net/i2p/router/transport/ntcp/EstablishState.java b/router/java/src/net/i2p/router/transport/ntcp/EstablishState.java
index bc6e37bc4..b451d6154 100644
--- a/router/java/src/net/i2p/router/transport/ntcp/EstablishState.java
+++ b/router/java/src/net/i2p/router/transport/ntcp/EstablishState.java
@@ -11,7 +11,7 @@ import net.i2p.data.Base64;
import net.i2p.data.DataFormatException;
import net.i2p.data.DataHelper;
import net.i2p.data.Hash;
-import net.i2p.data.RouterIdentity;
+import net.i2p.data.router.RouterIdentity;
import net.i2p.data.Signature;
import net.i2p.router.Router;
import net.i2p.router.RouterContext;
diff --git a/router/java/src/net/i2p/router/transport/ntcp/EventPumper.java b/router/java/src/net/i2p/router/transport/ntcp/EventPumper.java
index d4fd7521a..607234ae7 100644
--- a/router/java/src/net/i2p/router/transport/ntcp/EventPumper.java
+++ b/router/java/src/net/i2p/router/transport/ntcp/EventPumper.java
@@ -20,8 +20,8 @@ import java.util.concurrent.ConcurrentLinkedQueue;
import java.util.concurrent.LinkedBlockingQueue;
import net.i2p.I2PAppContext;
-import net.i2p.data.RouterAddress;
-import net.i2p.data.RouterIdentity;
+import net.i2p.data.router.RouterAddress;
+import net.i2p.data.router.RouterIdentity;
import net.i2p.router.CommSystemFacade;
import net.i2p.router.RouterContext;
import net.i2p.router.transport.FIFOBandwidthLimiter;
diff --git a/router/java/src/net/i2p/router/transport/ntcp/NTCPConnection.java b/router/java/src/net/i2p/router/transport/ntcp/NTCPConnection.java
index 2b2ae6a44..acd5570e3 100644
--- a/router/java/src/net/i2p/router/transport/ntcp/NTCPConnection.java
+++ b/router/java/src/net/i2p/router/transport/ntcp/NTCPConnection.java
@@ -17,9 +17,9 @@ import java.util.zip.Adler32;
import net.i2p.data.Base64;
import net.i2p.data.ByteArray;
import net.i2p.data.DataHelper;
-import net.i2p.data.RouterAddress;
-import net.i2p.data.RouterIdentity;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterAddress;
+import net.i2p.data.router.RouterIdentity;
+import net.i2p.data.router.RouterInfo;
import net.i2p.data.SessionKey;
import net.i2p.data.i2np.DatabaseStoreMessage;
import net.i2p.data.i2np.I2NPMessage;
diff --git a/router/java/src/net/i2p/router/transport/ntcp/NTCPTransport.java b/router/java/src/net/i2p/router/transport/ntcp/NTCPTransport.java
index 0ad8d88a9..c7e4703a4 100644
--- a/router/java/src/net/i2p/router/transport/ntcp/NTCPTransport.java
+++ b/router/java/src/net/i2p/router/transport/ntcp/NTCPTransport.java
@@ -25,9 +25,9 @@ import java.util.concurrent.ConcurrentHashMap;
import net.i2p.data.DataHelper;
import net.i2p.data.Hash;
-import net.i2p.data.RouterAddress;
-import net.i2p.data.RouterIdentity;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterAddress;
+import net.i2p.data.router.RouterIdentity;
+import net.i2p.data.router.RouterInfo;
import net.i2p.data.i2np.DatabaseStoreMessage;
import net.i2p.data.i2np.I2NPMessage;
import net.i2p.router.CommSystemFacade;
@@ -362,6 +362,12 @@ public class NTCPTransport extends TransportImpl {
return null;
}
+ // Check for supported sig type
+ if (toAddress.getIdentity().getSigningPublicKey().getType() == null) {
+ markUnreachable(peer);
+ return null;
+ }
+
if (!allowConnection()) {
if (_log.shouldLog(Log.WARN))
_log.warn("no bid when trying to send to " + peer + ", max connection limit reached");
diff --git a/router/java/src/net/i2p/router/transport/udp/EstablishmentManager.java b/router/java/src/net/i2p/router/transport/udp/EstablishmentManager.java
index 267c4fc2a..92696ff9c 100644
--- a/router/java/src/net/i2p/router/transport/udp/EstablishmentManager.java
+++ b/router/java/src/net/i2p/router/transport/udp/EstablishmentManager.java
@@ -10,9 +10,9 @@ import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import net.i2p.data.Hash;
-import net.i2p.data.RouterAddress;
-import net.i2p.data.RouterIdentity;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterAddress;
+import net.i2p.data.router.RouterIdentity;
+import net.i2p.data.router.RouterInfo;
import net.i2p.data.SessionKey;
import net.i2p.data.i2np.DatabaseStoreMessage;
import net.i2p.data.i2np.DeliveryStatusMessage;
diff --git a/router/java/src/net/i2p/router/transport/udp/InboundEstablishState.java b/router/java/src/net/i2p/router/transport/udp/InboundEstablishState.java
index abdd59e15..6d1f17755 100644
--- a/router/java/src/net/i2p/router/transport/udp/InboundEstablishState.java
+++ b/router/java/src/net/i2p/router/transport/udp/InboundEstablishState.java
@@ -5,11 +5,12 @@ import java.io.IOException;
import java.util.Queue;
import java.util.concurrent.LinkedBlockingQueue;
+import net.i2p.crypto.SigType;
import net.i2p.data.Base64;
import net.i2p.data.ByteArray;
import net.i2p.data.DataFormatException;
import net.i2p.data.DataHelper;
-import net.i2p.data.RouterIdentity;
+import net.i2p.data.router.RouterIdentity;
import net.i2p.data.SessionKey;
import net.i2p.data.Signature;
import net.i2p.router.OutNetMessage;
@@ -47,6 +48,9 @@ class InboundEstablishState {
private long _receivedSignedOnTime;
private byte _receivedSignature[];
private boolean _verificationAttempted;
+ // sig not verified
+ private RouterIdentity _receivedUnconfirmedIdentity;
+ // identical to uncomfirmed, but sig now verified
private RouterIdentity _receivedConfirmedIdentity;
// general status
private final long _establishBegin;
@@ -295,9 +299,28 @@ class InboundEstablishState {
if (cur == _receivedIdentity.length-1) {
_receivedSignedOnTime = conf.readFinalFragmentSignedOnTime();
- if (_receivedSignature == null)
- _receivedSignature = new byte[Signature.SIGNATURE_BYTES];
- conf.readFinalSignature(_receivedSignature, 0);
+ // TODO verify time to prevent replay attacks
+ buildIdentity();
+ if (_receivedUnconfirmedIdentity != null) {
+ SigType type = _receivedUnconfirmedIdentity.getSigningPublicKey().getType();
+ if (type != null) {
+ int sigLen = type.getSigLen();
+ if (_receivedSignature == null)
+ _receivedSignature = new byte[sigLen];
+ conf.readFinalSignature(_receivedSignature, 0, sigLen);
+ } else {
+ if (_log.shouldLog(Log.WARN))
+ _log.warn("Unsupported sig type from: " + toString());
+ // _x() in UDPTransport
+ _context.banlist().banlistRouterForever(_receivedUnconfirmedIdentity.calculateHash(),
+ "Unsupported signature type");
+ fail();
+ }
+ } else {
+ if (_log.shouldLog(Log.WARN))
+ _log.warn("Bad ident from: " + toString());
+ fail();
+ }
}
if ( (_currentState == InboundState.IB_STATE_UNKNOWN) ||
@@ -318,9 +341,10 @@ class InboundEstablishState {
*/
private boolean confirmedFullyReceived() {
if (_receivedIdentity != null) {
- for (int i = 0; i < _receivedIdentity.length; i++)
+ for (int i = 0; i < _receivedIdentity.length; i++) {
if (_receivedIdentity[i] == null)
return false;
+ }
return true;
} else {
return false;
@@ -339,7 +363,51 @@ class InboundEstablishState {
}
return _receivedConfirmedIdentity;
}
-
+
+ /**
+ * Construct Alice's RouterIdentity.
+ * Must have received all fragments.
+ * Sets _receivedUnconfirmedIdentity, unless invalid.
+ *
+ * Caller must synch on this.
+ *
+ * @since 0.9.16 was in verifyIdentity()
+ */
+ private void buildIdentity() {
+ if (_receivedUnconfirmedIdentity != null)
+ return; // dup pkt?
+ int frags = _receivedIdentity.length;
+ byte[] ident;
+ if (frags > 1) {
+ int identSize = 0;
+ for (int i = 0; i < _receivedIdentity.length; i++)
+ identSize += _receivedIdentity[i].length;
+ ident = new byte[identSize];
+ int off = 0;
+ for (int i = 0; i < _receivedIdentity.length; i++) {
+ int len = _receivedIdentity[i].length;
+ System.arraycopy(_receivedIdentity[i], 0, ident, off, len);
+ off += len;
+ }
+ } else {
+ // no need to copy
+ ident = _receivedIdentity[0];
+ }
+ ByteArrayInputStream in = new ByteArrayInputStream(ident);
+ RouterIdentity peer = new RouterIdentity();
+ try {
+ peer.readBytes(in);
+ _receivedUnconfirmedIdentity = peer;
+ } catch (DataFormatException dfe) {
+ if (_log.shouldLog(Log.WARN))
+ _log.warn("Improperly formatted yet fully received ident", dfe);
+ } catch (IOException ioe) {
+ if (_log.shouldLog(Log.WARN))
+ _log.warn("Improperly formatted yet fully received ident", ioe);
+ }
+ }
+
+
/**
* Determine if Alice sent us a valid confirmation packet. The
* identity signs: Alice's IP + Alice's port + Bob's IP + Bob's port
@@ -351,21 +419,11 @@ class InboundEstablishState {
* Caller must synch on this.
*/
private void verifyIdentity() {
- int identSize = 0;
- for (int i = 0; i < _receivedIdentity.length; i++)
- identSize += _receivedIdentity[i].length;
- byte ident[] = new byte[identSize];
- int off = 0;
- for (int i = 0; i < _receivedIdentity.length; i++) {
- int len = _receivedIdentity[i].length;
- System.arraycopy(_receivedIdentity[i], 0, ident, off, len);
- off += len;
- }
- ByteArrayInputStream in = new ByteArrayInputStream(ident);
- RouterIdentity peer = new RouterIdentity();
- try {
- peer.readBytes(in);
-
+ if (_receivedUnconfirmedIdentity == null)
+ return; // either not yet recvd or bad ident
+ if (_receivedSignature == null)
+ return; // either not yet recvd or bad sig
+
byte signed[] = new byte[256+256 // X + Y
+ _aliceIP.length + 2
+ _bobIP.length + 2
@@ -373,7 +431,7 @@ class InboundEstablishState {
+ 4 // signed on time
];
- off = 0;
+ int off = 0;
System.arraycopy(_receivedX, 0, signed, off, _receivedX.length);
off += _receivedX.length;
getSentY();
@@ -391,22 +449,15 @@ class InboundEstablishState {
off += 4;
DataHelper.toLong(signed, off, 4, _receivedSignedOnTime);
Signature sig = new Signature(_receivedSignature);
- boolean ok = _context.dsa().verifySignature(sig, signed, peer.getSigningPublicKey());
+ boolean ok = _context.dsa().verifySignature(sig, signed, _receivedUnconfirmedIdentity.getSigningPublicKey());
if (ok) {
// todo partial spoof detection - get peer.calculateHash(),
// lookup in netdb locally, if not equal, fail?
- _receivedConfirmedIdentity = peer;
+ _receivedConfirmedIdentity = _receivedUnconfirmedIdentity;
} else {
if (_log.shouldLog(Log.WARN))
- _log.warn("Signature failed from " + peer);
+ _log.warn("Signature failed from " + _receivedUnconfirmedIdentity);
}
- } catch (DataFormatException dfe) {
- if (_log.shouldLog(Log.WARN))
- _log.warn("Improperly formatted yet fully received ident", dfe);
- } catch (IOException ioe) {
- if (_log.shouldLog(Log.WARN))
- _log.warn("Improperly formatted yet fully received ident", ioe);
- }
}
private void packetReceived() {
diff --git a/router/java/src/net/i2p/router/transport/udp/IntroductionManager.java b/router/java/src/net/i2p/router/transport/udp/IntroductionManager.java
index 37db45880..7e55cf1ce 100644
--- a/router/java/src/net/i2p/router/transport/udp/IntroductionManager.java
+++ b/router/java/src/net/i2p/router/transport/udp/IntroductionManager.java
@@ -11,8 +11,8 @@ import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import net.i2p.data.Base64;
-import net.i2p.data.RouterAddress;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterAddress;
+import net.i2p.data.router.RouterInfo;
import net.i2p.data.SessionKey;
import net.i2p.router.RouterContext;
import net.i2p.util.Addresses;
diff --git a/router/java/src/net/i2p/router/transport/udp/OutboundEstablishState.java b/router/java/src/net/i2p/router/transport/udp/OutboundEstablishState.java
index ba4375dbd..ff9485255 100644
--- a/router/java/src/net/i2p/router/transport/udp/OutboundEstablishState.java
+++ b/router/java/src/net/i2p/router/transport/udp/OutboundEstablishState.java
@@ -3,10 +3,11 @@ package net.i2p.router.transport.udp;
import java.util.Queue;
import java.util.concurrent.LinkedBlockingQueue;
+import net.i2p.crypto.SigType;
import net.i2p.data.Base64;
import net.i2p.data.ByteArray;
import net.i2p.data.DataHelper;
-import net.i2p.data.RouterIdentity;
+import net.i2p.data.router.RouterIdentity;
import net.i2p.data.SessionKey;
import net.i2p.data.Signature;
import net.i2p.data.i2np.DatabaseStoreMessage;
@@ -41,6 +42,7 @@ class OutboundEstablishState {
private SessionKey _sessionKey;
private SessionKey _macKey;
private Signature _receivedSignature;
+ // includes trailing padding to mod 16
private byte[] _receivedEncryptedSignature;
private byte[] _receivedIV;
// SessionConfirmed messages
@@ -104,6 +106,7 @@ class OutboundEstablishState {
/**
* @param claimedAddress an IP/port based RemoteHostId, or null if unknown
* @param remoteHostId non-null, == claimedAddress if direct, or a hash-based one if indirect
+ * @param remotePeer must have supported sig type
* @param introKey Bob's introduction key, as published in the netdb
* @param addr non-null
*/
@@ -247,8 +250,20 @@ class OutboundEstablishState {
_alicePort = reader.readPort();
_receivedRelayTag = reader.readRelayTag();
_receivedSignedOnTime = reader.readSignedOnTime();
- _receivedEncryptedSignature = new byte[Signature.SIGNATURE_BYTES + 8];
- reader.readEncryptedSignature(_receivedEncryptedSignature, 0);
+ // handle variable signature size
+ SigType type = _remotePeer.getSigningPublicKey().getType();
+ if (type == null) {
+ // shouldn't happen, we only connect to supported peers
+ fail();
+ packetReceived();
+ return;
+ }
+ int sigLen = type.getSigLen();
+ int mod = sigLen % 16;
+ int pad = (mod == 0) ? 0 : (16 - mod);
+ int esigLen = sigLen + pad;
+ _receivedEncryptedSignature = new byte[esigLen];
+ reader.readEncryptedSignature(_receivedEncryptedSignature, 0, esigLen);
_receivedIV = new byte[UDPPacket.IV_SIZE];
reader.readIV(_receivedIV, 0);
@@ -353,7 +368,9 @@ class OutboundEstablishState {
* decrypt the signature (and subsequent pad bytes) with the
* additional layer of encryption using the negotiated key along side
* the packet's IV
+ *
* Caller must synch on this.
+ * Only call this once! Decrypts in-place.
*/
private void decryptSignature() {
if (_receivedEncryptedSignature == null) throw new NullPointerException("encrypted signature is null! this=" + this.toString());
@@ -361,11 +378,20 @@ class OutboundEstablishState {
if (_receivedIV == null) throw new NullPointerException("IV is null!");
_context.aes().decrypt(_receivedEncryptedSignature, 0, _receivedEncryptedSignature, 0,
_sessionKey, _receivedIV, _receivedEncryptedSignature.length);
- byte signatureBytes[] = new byte[Signature.SIGNATURE_BYTES];
- System.arraycopy(_receivedEncryptedSignature, 0, signatureBytes, 0, Signature.SIGNATURE_BYTES);
- _receivedSignature = new Signature(signatureBytes);
+ // handle variable signature size
+ SigType type = _remotePeer.getSigningPublicKey().getType();
+ // if type == null throws NPE
+ int sigLen = type.getSigLen();
+ int mod = sigLen % 16;
+ if (mod != 0) {
+ byte signatureBytes[] = new byte[sigLen];
+ System.arraycopy(_receivedEncryptedSignature, 0, signatureBytes, 0, sigLen);
+ _receivedSignature = new Signature(type, signatureBytes);
+ } else {
+ _receivedSignature = new Signature(type, _receivedEncryptedSignature);
+ }
if (_log.shouldLog(Log.DEBUG))
- _log.debug("Decrypted received signature: " + Base64.encode(signatureBytes));
+ _log.debug("Decrypted received signature: " + Base64.encode(_receivedSignature.getData()));
}
/**
diff --git a/router/java/src/net/i2p/router/transport/udp/OutboundMessageFragments.java b/router/java/src/net/i2p/router/transport/udp/OutboundMessageFragments.java
index 034f3e605..2be555774 100644
--- a/router/java/src/net/i2p/router/transport/udp/OutboundMessageFragments.java
+++ b/router/java/src/net/i2p/router/transport/udp/OutboundMessageFragments.java
@@ -6,7 +6,7 @@ import java.util.List;
import java.util.Set;
import net.i2p.data.Hash;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterInfo;
import net.i2p.router.OutNetMessage;
import net.i2p.router.RouterContext;
import net.i2p.util.ConcurrentHashSet;
diff --git a/router/java/src/net/i2p/router/transport/udp/PacketBuilder.java b/router/java/src/net/i2p/router/transport/udp/PacketBuilder.java
index 053703cb1..d518a0b56 100644
--- a/router/java/src/net/i2p/router/transport/udp/PacketBuilder.java
+++ b/router/java/src/net/i2p/router/transport/udp/PacketBuilder.java
@@ -13,7 +13,7 @@ import net.i2p.I2PAppContext;
import net.i2p.data.Base64;
import net.i2p.data.DataHelper;
import net.i2p.data.Hash;
-import net.i2p.data.RouterIdentity;
+import net.i2p.data.router.RouterIdentity;
import net.i2p.data.SessionKey;
import net.i2p.data.Signature;
import net.i2p.util.Addresses;
@@ -596,14 +596,22 @@ class PacketBuilder {
off += 4;
DataHelper.toLong(data, off, 4, state.getSentSignedOnTime());
off += 4;
- System.arraycopy(state.getSentSignature().getData(), 0, data, off, Signature.SIGNATURE_BYTES);
- off += Signature.SIGNATURE_BYTES;
- // ok, we need another 8 bytes of random padding
- // (ok, this only gives us 63 bits, not 64)
- long l = _context.random().nextLong();
- if (l < 0) l = 0 - l;
- DataHelper.toLong(data, off, 8, l);
- off += 8;
+
+ // handle variable signature size
+ Signature sig = state.getSentSignature();
+ int siglen = sig.length();
+ System.arraycopy(sig.getData(), 0, data, off, siglen);
+ off += siglen;
+ // ok, we need another few bytes of random padding
+ int rem = siglen % 16;
+ int padding;
+ if (rem > 0) {
+ padding = 16 - rem;
+ _context.random().nextBytes(data, off, padding);
+ off += padding;
+ } else {
+ padding = 0;
+ }
if (_log.shouldLog(Log.DEBUG)) {
StringBuilder buf = new StringBuilder(128);
@@ -612,9 +620,9 @@ class PacketBuilder {
buf.append(" Bob: ").append(Addresses.toString(state.getReceivedOurIP(), externalPort));
buf.append(" RelayTag: ").append(state.getSentRelayTag());
buf.append(" SignedOn: ").append(state.getSentSignedOnTime());
- buf.append(" signature: ").append(Base64.encode(state.getSentSignature().getData()));
+ buf.append(" signature: ").append(Base64.encode(sig.getData()));
buf.append("\nRawCreated: ").append(Base64.encode(data, 0, off));
- buf.append("\nsignedTime: ").append(Base64.encode(data, off-8-Signature.SIGNATURE_BYTES-4, 4));
+ buf.append("\nsignedTime: ").append(Base64.encode(data, off - padding - siglen - 4, 4));
_log.debug(buf.toString());
}
@@ -623,7 +631,7 @@ class PacketBuilder {
byte[] iv = SimpleByteCache.acquire(UDPPacket.IV_SIZE);
_context.random().nextBytes(iv);
- int encrWrite = Signature.SIGNATURE_BYTES + 8;
+ int encrWrite = siglen + padding;
int sigBegin = off - encrWrite;
_context.aes().encrypt(data, sigBegin, data, sigBegin, state.getCipherKey(), iv, encrWrite);
@@ -774,8 +782,11 @@ class PacketBuilder {
DataHelper.toLong(data, off, 4, state.getSentSignedOnTime());
off += 4;
+ // handle variable signature size
// we need to pad this so we're at the encryption boundary
- int mod = (off + Signature.SIGNATURE_BYTES) & 0x0f;
+ Signature sig = state.getSentSignature();
+ int siglen = sig.length();
+ int mod = (off + siglen) & 0x0f;
if (mod != 0) {
int paddingRequired = 16 - mod;
// add an arbitrary number of 16byte pad blocks too ???
@@ -787,8 +798,8 @@ class PacketBuilder {
// so trailing non-mod-16 data is ignored. That truncates the sig.
// BUG: NPE here if null signature
- System.arraycopy(state.getSentSignature().getData(), 0, data, off, Signature.SIGNATURE_BYTES);
- off += Signature.SIGNATURE_BYTES;
+ System.arraycopy(sig.getData(), 0, data, off, siglen);
+ off += siglen;
} else {
// We never get here (see above)
diff --git a/router/java/src/net/i2p/router/transport/udp/PeerTestManager.java b/router/java/src/net/i2p/router/transport/udp/PeerTestManager.java
index 48a5e0822..bc47fba87 100644
--- a/router/java/src/net/i2p/router/transport/udp/PeerTestManager.java
+++ b/router/java/src/net/i2p/router/transport/udp/PeerTestManager.java
@@ -9,8 +9,8 @@ import java.util.concurrent.LinkedBlockingQueue;
import net.i2p.data.Base64;
import net.i2p.data.DataHelper;
-import net.i2p.data.RouterAddress;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterAddress;
+import net.i2p.data.router.RouterInfo;
import net.i2p.data.SessionKey;
import net.i2p.router.CommSystemFacade;
import net.i2p.router.RouterContext;
diff --git a/router/java/src/net/i2p/router/transport/udp/UDPAddress.java b/router/java/src/net/i2p/router/transport/udp/UDPAddress.java
index f05205582..88551d588 100644
--- a/router/java/src/net/i2p/router/transport/udp/UDPAddress.java
+++ b/router/java/src/net/i2p/router/transport/udp/UDPAddress.java
@@ -5,7 +5,7 @@ import java.net.UnknownHostException;
import java.util.Map;
import net.i2p.data.Base64;
-import net.i2p.data.RouterAddress;
+import net.i2p.data.router.RouterAddress;
import net.i2p.data.SessionKey;
import net.i2p.util.LHMCache;
import net.i2p.util.SystemVersion;
diff --git a/router/java/src/net/i2p/router/transport/udp/UDPPacketReader.java b/router/java/src/net/i2p/router/transport/udp/UDPPacketReader.java
index affaf09df..f7c89bb89 100644
--- a/router/java/src/net/i2p/router/transport/udp/UDPPacketReader.java
+++ b/router/java/src/net/i2p/router/transport/udp/UDPPacketReader.java
@@ -203,9 +203,10 @@ class UDPPacketReader {
return rv;
}
- public void readEncryptedSignature(byte target[], int targetOffset) {
+ /** @param size the amount to be copied, including padding to mod 16 */
+ public void readEncryptedSignature(byte target[], int targetOffset, int size) {
int offset = readBodyOffset() + Y_LENGTH + 1 + readIPSize() + 2 + 4 + 4;
- System.arraycopy(_message, offset, target, targetOffset, Signature.SIGNATURE_BYTES + 8);
+ System.arraycopy(_message, offset, target, targetOffset, size);
}
public void readIV(byte target[], int targetOffset) {
@@ -239,7 +240,11 @@ class UDPPacketReader {
System.arraycopy(_message, readOffset, target, targetOffset, len);
}
- /** read the time at which the signature was generated */
+ /**
+ * Read the time at which the signature was generated.
+ * TODO must be completely in final fragment.
+ * Time and sig cannot be split across fragments.
+ */
public long readFinalFragmentSignedOnTime() {
if (readCurrentFragmentNum() != readTotalFragmentNum()-1)
throw new IllegalStateException("This is not the final fragment");
@@ -247,12 +252,19 @@ class UDPPacketReader {
return DataHelper.fromLong(_message, readOffset, 4);
}
- /** read the signature from the final sessionConfirmed packet */
- public void readFinalSignature(byte target[], int targetOffset) {
+ /**
+ * Read the signature from the final sessionConfirmed packet.
+ * TODO must be completely in final fragment.
+ * Time and sig cannot be split across fragments.
+ * @param size not including padding
+ */
+ public void readFinalSignature(byte target[], int targetOffset, int size) {
if (readCurrentFragmentNum() != readTotalFragmentNum()-1)
throw new IllegalStateException("This is not the final fragment");
- int readOffset = _payloadBeginOffset + _payloadLength - Signature.SIGNATURE_BYTES;
- System.arraycopy(_message, readOffset, target, targetOffset, Signature.SIGNATURE_BYTES);
+ int readOffset = _payloadBeginOffset + _payloadLength - size;
+ if (readOffset < readBodyOffset() + (1 + 2 + 4))
+ throw new IllegalStateException("Sig split across fragments");
+ System.arraycopy(_message, readOffset, target, targetOffset, size);
}
}
diff --git a/router/java/src/net/i2p/router/transport/udp/UDPTransport.java b/router/java/src/net/i2p/router/transport/udp/UDPTransport.java
index b9c2ad802..63fc95760 100644
--- a/router/java/src/net/i2p/router/transport/udp/UDPTransport.java
+++ b/router/java/src/net/i2p/router/transport/udp/UDPTransport.java
@@ -25,9 +25,9 @@ import java.util.concurrent.CopyOnWriteArrayList;
import net.i2p.data.DatabaseEntry;
import net.i2p.data.DataHelper;
import net.i2p.data.Hash;
-import net.i2p.data.RouterAddress;
-import net.i2p.data.RouterIdentity;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterAddress;
+import net.i2p.data.router.RouterIdentity;
+import net.i2p.data.router.RouterInfo;
import net.i2p.data.SessionKey;
import net.i2p.data.i2np.DatabaseStoreMessage;
import net.i2p.data.i2np.I2NPMessage;
@@ -1550,6 +1550,12 @@ public class UDPTransport extends TransportImpl implements TimedWeightedPriority
return null;
}
+ // Check for supported sig type
+ if (toAddress.getIdentity().getSigningPublicKey().getType() == null) {
+ markUnreachable(to);
+ return null;
+ }
+
if (!allowConnection())
return _cachedBid[TRANSIENT_FAIL_BID];
diff --git a/router/java/src/net/i2p/router/tunnel/InboundGatewayReceiver.java b/router/java/src/net/i2p/router/tunnel/InboundGatewayReceiver.java
index 3fa40c984..bb18c44b2 100644
--- a/router/java/src/net/i2p/router/tunnel/InboundGatewayReceiver.java
+++ b/router/java/src/net/i2p/router/tunnel/InboundGatewayReceiver.java
@@ -1,7 +1,7 @@
package net.i2p.router.tunnel;
import net.i2p.data.Hash;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterInfo;
import net.i2p.data.i2np.TunnelDataMessage;
import net.i2p.router.JobImpl;
import net.i2p.router.OutNetMessage;
diff --git a/router/java/src/net/i2p/router/tunnel/InboundMessageDistributor.java b/router/java/src/net/i2p/router/tunnel/InboundMessageDistributor.java
index ec3529b48..660aedab8 100644
--- a/router/java/src/net/i2p/router/tunnel/InboundMessageDistributor.java
+++ b/router/java/src/net/i2p/router/tunnel/InboundMessageDistributor.java
@@ -4,7 +4,7 @@ import net.i2p.data.DatabaseEntry;
import net.i2p.data.Hash;
import net.i2p.data.LeaseSet;
import net.i2p.data.Payload;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterInfo;
import net.i2p.data.TunnelId;
import net.i2p.data.i2np.DataMessage;
import net.i2p.data.i2np.DatabaseSearchReplyMessage;
diff --git a/router/java/src/net/i2p/router/tunnel/OutboundMessageDistributor.java b/router/java/src/net/i2p/router/tunnel/OutboundMessageDistributor.java
index 364c5970a..3961af80f 100644
--- a/router/java/src/net/i2p/router/tunnel/OutboundMessageDistributor.java
+++ b/router/java/src/net/i2p/router/tunnel/OutboundMessageDistributor.java
@@ -4,7 +4,7 @@ import java.util.HashSet;
import java.util.Set;
import net.i2p.data.Hash;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterInfo;
import net.i2p.data.TunnelId;
import net.i2p.data.i2np.I2NPMessage;
import net.i2p.data.i2np.TunnelGatewayMessage;
diff --git a/router/java/src/net/i2p/router/tunnel/OutboundReceiver.java b/router/java/src/net/i2p/router/tunnel/OutboundReceiver.java
index 03923ecfe..4aef14902 100644
--- a/router/java/src/net/i2p/router/tunnel/OutboundReceiver.java
+++ b/router/java/src/net/i2p/router/tunnel/OutboundReceiver.java
@@ -1,7 +1,7 @@
package net.i2p.router.tunnel;
import net.i2p.data.Hash;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterInfo;
import net.i2p.data.i2np.TunnelDataMessage;
import net.i2p.router.JobImpl;
import net.i2p.router.OutNetMessage;
diff --git a/router/java/src/net/i2p/router/tunnel/TunnelParticipant.java b/router/java/src/net/i2p/router/tunnel/TunnelParticipant.java
index b53d8a643..d58060279 100644
--- a/router/java/src/net/i2p/router/tunnel/TunnelParticipant.java
+++ b/router/java/src/net/i2p/router/tunnel/TunnelParticipant.java
@@ -1,7 +1,7 @@
package net.i2p.router.tunnel;
import net.i2p.data.Hash;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterInfo;
import net.i2p.data.TunnelId;
import net.i2p.data.i2np.I2NPMessage;
import net.i2p.data.i2np.TunnelDataMessage;
diff --git a/router/java/src/net/i2p/router/tunnel/pool/BuildExecutor.java b/router/java/src/net/i2p/router/tunnel/pool/BuildExecutor.java
index b771589a1..42cff28c7 100644
--- a/router/java/src/net/i2p/router/tunnel/pool/BuildExecutor.java
+++ b/router/java/src/net/i2p/router/tunnel/pool/BuildExecutor.java
@@ -10,7 +10,7 @@ import java.util.concurrent.ConcurrentHashMap;
import net.i2p.data.Hash;
import net.i2p.data.i2np.I2NPMessage;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterInfo;
import net.i2p.router.CommSystemFacade;
import net.i2p.router.RouterContext;
import net.i2p.router.TunnelManagerFacade;
diff --git a/router/java/src/net/i2p/router/tunnel/pool/BuildHandler.java b/router/java/src/net/i2p/router/tunnel/pool/BuildHandler.java
index afe3940bf..3522e5c4e 100644
--- a/router/java/src/net/i2p/router/tunnel/pool/BuildHandler.java
+++ b/router/java/src/net/i2p/router/tunnel/pool/BuildHandler.java
@@ -9,8 +9,8 @@ import net.i2p.data.Base64;
import net.i2p.data.ByteArray;
import net.i2p.data.DataHelper;
import net.i2p.data.Hash;
-import net.i2p.data.RouterIdentity;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterIdentity;
+import net.i2p.data.router.RouterInfo;
import net.i2p.data.TunnelId;
import net.i2p.data.i2np.BuildRequestRecord;
import net.i2p.data.i2np.BuildResponseRecord;
diff --git a/router/java/src/net/i2p/router/tunnel/pool/BuildRequestor.java b/router/java/src/net/i2p/router/tunnel/pool/BuildRequestor.java
index fbfca2bcc..31aaa8665 100644
--- a/router/java/src/net/i2p/router/tunnel/pool/BuildRequestor.java
+++ b/router/java/src/net/i2p/router/tunnel/pool/BuildRequestor.java
@@ -8,7 +8,7 @@ import net.i2p.data.ByteArray;
import net.i2p.data.DataHelper;
import net.i2p.data.Hash;
import net.i2p.data.PublicKey;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterInfo;
import net.i2p.data.TunnelId;
import net.i2p.data.i2np.TunnelBuildMessage;
import net.i2p.data.i2np.VariableTunnelBuildMessage;
diff --git a/router/java/src/net/i2p/router/tunnel/pool/TunnelPeerSelector.java b/router/java/src/net/i2p/router/tunnel/pool/TunnelPeerSelector.java
index 14eab47e2..8bb657831 100644
--- a/router/java/src/net/i2p/router/tunnel/pool/TunnelPeerSelector.java
+++ b/router/java/src/net/i2p/router/tunnel/pool/TunnelPeerSelector.java
@@ -16,7 +16,7 @@ import net.i2p.I2PAppContext;
import net.i2p.crypto.SHA256Generator;
import net.i2p.data.DataFormatException;
import net.i2p.data.Hash;
-import net.i2p.data.RouterInfo;
+import net.i2p.data.router.RouterInfo;
import net.i2p.router.Router;
import net.i2p.router.RouterContext;
import net.i2p.router.TunnelPoolSettings;