forked from I2P_Developers/i2p.i2p
* Router:
- Add a lock for reading/writing the router.info file - Check our RouterInfo validity after reading and before saving, to catch fatal errors sooner
This commit is contained in:
12
history.txt
12
history.txt
@@ -1,3 +1,15 @@
|
|||||||
|
2011-06-04 zzz
|
||||||
|
* NBigI: Recognize Android
|
||||||
|
* KeyGenerator: Restore old return type to not break ABI (thx kytv)
|
||||||
|
* Router:
|
||||||
|
- Add a lock for reading/writing the router.info file
|
||||||
|
- Check our RouterInfo validity after reading and before saving,
|
||||||
|
to catch fatal errors sooner
|
||||||
|
|
||||||
|
2011-06-03 zzz
|
||||||
|
* Android: More build updates, start working on JNI for GMP
|
||||||
|
* Build: Fix dependency issue cause by misspelled file name
|
||||||
|
|
||||||
2011-06-02 zzz
|
2011-06-02 zzz
|
||||||
* Android: Build fixes
|
* Android: Build fixes
|
||||||
* Crypto:
|
* Crypto:
|
||||||
|
@@ -63,6 +63,7 @@ public class Router {
|
|||||||
/** full path */
|
/** full path */
|
||||||
private String _configFilename;
|
private String _configFilename;
|
||||||
private RouterInfo _routerInfo;
|
private RouterInfo _routerInfo;
|
||||||
|
public final Object routerInfoFileLock = new Object();
|
||||||
private long _started;
|
private long _started;
|
||||||
private boolean _higherVersionSeen;
|
private boolean _higherVersionSeen;
|
||||||
//private SessionKeyPersistenceHelper _sessionKeyPersistenceHelper;
|
//private SessionKeyPersistenceHelper _sessionKeyPersistenceHelper;
|
||||||
@@ -312,6 +313,9 @@ public class Router {
|
|||||||
|
|
||||||
public RouterInfo getRouterInfo() { return _routerInfo; }
|
public RouterInfo getRouterInfo() { return _routerInfo; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Caller must ensure info is valid - no validation done here
|
||||||
|
*/
|
||||||
public void setRouterInfo(RouterInfo info) {
|
public void setRouterInfo(RouterInfo info) {
|
||||||
_routerInfo = info;
|
_routerInfo = info;
|
||||||
if (_log.shouldLog(Log.INFO))
|
if (_log.shouldLog(Log.INFO))
|
||||||
@@ -452,6 +456,8 @@ public class Router {
|
|||||||
}
|
}
|
||||||
ri.sign(key);
|
ri.sign(key);
|
||||||
setRouterInfo(ri);
|
setRouterInfo(ri);
|
||||||
|
if (!ri.isValid())
|
||||||
|
throw new DataFormatException("Our RouterInfo has a bad signature");
|
||||||
Republish r = new Republish();
|
Republish r = new Republish();
|
||||||
if (blockingRebuild)
|
if (blockingRebuild)
|
||||||
r.timeReached();
|
r.timeReached();
|
||||||
@@ -1582,13 +1588,14 @@ private static class ShutdownHook extends Thread {
|
|||||||
|
|
||||||
/** update the router.info file whenever its, er, updated */
|
/** update the router.info file whenever its, er, updated */
|
||||||
private static class PersistRouterInfoJob extends JobImpl {
|
private static class PersistRouterInfoJob extends JobImpl {
|
||||||
private Log _log;
|
|
||||||
public PersistRouterInfoJob(RouterContext ctx) {
|
public PersistRouterInfoJob(RouterContext ctx) {
|
||||||
super(ctx);
|
super(ctx);
|
||||||
}
|
}
|
||||||
|
|
||||||
public String getName() { return "Persist Updated Router Information"; }
|
public String getName() { return "Persist Updated Router Information"; }
|
||||||
|
|
||||||
public void runJob() {
|
public void runJob() {
|
||||||
_log = getContext().logManager().getLog(PersistRouterInfoJob.class);
|
Log _log = getContext().logManager().getLog(PersistRouterInfoJob.class);
|
||||||
if (_log.shouldLog(Log.DEBUG))
|
if (_log.shouldLog(Log.DEBUG))
|
||||||
_log.debug("Persisting updated router info");
|
_log.debug("Persisting updated router info");
|
||||||
|
|
||||||
@@ -1598,15 +1605,17 @@ private static class PersistRouterInfoJob extends JobImpl {
|
|||||||
RouterInfo info = getContext().router().getRouterInfo();
|
RouterInfo info = getContext().router().getRouterInfo();
|
||||||
|
|
||||||
FileOutputStream fos = null;
|
FileOutputStream fos = null;
|
||||||
try {
|
synchronized (getContext().router().routerInfoFileLock) {
|
||||||
fos = new SecureFileOutputStream(infoFile);
|
try {
|
||||||
info.writeBytes(fos);
|
fos = new SecureFileOutputStream(infoFile);
|
||||||
} catch (DataFormatException dfe) {
|
info.writeBytes(fos);
|
||||||
_log.error("Error rebuilding the router information", dfe);
|
} catch (DataFormatException dfe) {
|
||||||
} catch (IOException ioe) {
|
_log.error("Error rebuilding the router information", dfe);
|
||||||
_log.error("Error writing out the rebuilt router information", ioe);
|
} catch (IOException ioe) {
|
||||||
} finally {
|
_log.error("Error writing out the rebuilt router information", ioe);
|
||||||
if (fos != null) try { fos.close(); } catch (IOException ioe) {}
|
} finally {
|
||||||
|
if (fos != null) try { fos.close(); } catch (IOException ioe) {}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -18,7 +18,7 @@ public class RouterVersion {
|
|||||||
/** deprecated */
|
/** deprecated */
|
||||||
public final static String ID = "Monotone";
|
public final static String ID = "Monotone";
|
||||||
public final static String VERSION = CoreVersion.VERSION;
|
public final static String VERSION = CoreVersion.VERSION;
|
||||||
public final static long BUILD = 16;
|
public final static long BUILD = 17;
|
||||||
|
|
||||||
/** for example "-test" */
|
/** for example "-test" */
|
||||||
public final static String EXTRA = "";
|
public final static String EXTRA = "";
|
||||||
|
@@ -31,7 +31,7 @@ import net.i2p.util.SecureFileOutputStream;
|
|||||||
|
|
||||||
public class CreateRouterInfoJob extends JobImpl {
|
public class CreateRouterInfoJob extends JobImpl {
|
||||||
private static Log _log = new Log(CreateRouterInfoJob.class);
|
private static Log _log = new Log(CreateRouterInfoJob.class);
|
||||||
private Job _next;
|
private final Job _next;
|
||||||
|
|
||||||
public CreateRouterInfoJob(RouterContext ctx, Job next) {
|
public CreateRouterInfoJob(RouterContext ctx, Job next) {
|
||||||
super(ctx);
|
super(ctx);
|
||||||
@@ -43,10 +43,15 @@ public class CreateRouterInfoJob extends JobImpl {
|
|||||||
public void runJob() {
|
public void runJob() {
|
||||||
_log.debug("Creating the new router info");
|
_log.debug("Creating the new router info");
|
||||||
// create a new router info and store it where LoadRouterInfoJob looks
|
// create a new router info and store it where LoadRouterInfoJob looks
|
||||||
createRouterInfo();
|
synchronized (getContext().router().routerInfoFileLock) {
|
||||||
|
createRouterInfo();
|
||||||
|
}
|
||||||
getContext().jobQueue().addJob(_next);
|
getContext().jobQueue().addJob(_next);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Caller must hold Router.routerInfoFileLock
|
||||||
|
*/
|
||||||
RouterInfo createRouterInfo() {
|
RouterInfo createRouterInfo() {
|
||||||
RouterInfo info = new RouterInfo();
|
RouterInfo info = new RouterInfo();
|
||||||
FileOutputStream fos1 = null;
|
FileOutputStream fos1 = null;
|
||||||
@@ -79,6 +84,9 @@ public class CreateRouterInfoJob extends JobImpl {
|
|||||||
|
|
||||||
info.sign(signingPrivKey);
|
info.sign(signingPrivKey);
|
||||||
|
|
||||||
|
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);
|
String infoFilename = getContext().getProperty(Router.PROP_INFO_FILENAME, Router.PROP_INFO_FILENAME_DEFAULT);
|
||||||
File ifile = new File(getContext().getRouterDir(), infoFilename);
|
File ifile = new File(getContext().getRouterDir(), infoFilename);
|
||||||
fos1 = new SecureFileOutputStream(ifile);
|
fos1 = new SecureFileOutputStream(ifile);
|
||||||
|
@@ -24,7 +24,7 @@ import net.i2p.router.RouterContext;
|
|||||||
import net.i2p.util.Log;
|
import net.i2p.util.Log;
|
||||||
|
|
||||||
public class LoadRouterInfoJob extends JobImpl {
|
public class LoadRouterInfoJob extends JobImpl {
|
||||||
private Log _log;
|
private final Log _log;
|
||||||
private boolean _keysExist;
|
private boolean _keysExist;
|
||||||
private boolean _infoExists;
|
private boolean _infoExists;
|
||||||
private RouterInfo _us;
|
private RouterInfo _us;
|
||||||
@@ -37,7 +37,9 @@ public class LoadRouterInfoJob extends JobImpl {
|
|||||||
public String getName() { return "Load Router Info"; }
|
public String getName() { return "Load Router Info"; }
|
||||||
|
|
||||||
public void runJob() {
|
public void runJob() {
|
||||||
loadRouterInfo();
|
synchronized (getContext().router().routerInfoFileLock) {
|
||||||
|
loadRouterInfo();
|
||||||
|
}
|
||||||
if (_us == null) {
|
if (_us == null) {
|
||||||
RebuildRouterInfoJob r = new RebuildRouterInfoJob(getContext());
|
RebuildRouterInfoJob r = new RebuildRouterInfoJob(getContext());
|
||||||
r.rebuildRouterInfo(false);
|
r.rebuildRouterInfo(false);
|
||||||
@@ -78,7 +80,11 @@ public class LoadRouterInfoJob extends JobImpl {
|
|||||||
fis1 = new FileInputStream(rif);
|
fis1 = new FileInputStream(rif);
|
||||||
info = new RouterInfo();
|
info = new RouterInfo();
|
||||||
info.readBytes(fis1);
|
info.readBytes(fis1);
|
||||||
_log.debug("Reading in routerInfo from " + rif.getAbsolutePath() + " and it has " + info.getAddresses().size() + " addresses");
|
// Catch this here before it all gets worse
|
||||||
|
if (!info.isValid())
|
||||||
|
throw new DataFormatException("Our RouterInfo has a bad signature");
|
||||||
|
if (_log.shouldLog(Log.DEBUG))
|
||||||
|
_log.debug("Reading in routerInfo from " + rif.getAbsolutePath() + " and it has " + info.getAddresses().size() + " addresses");
|
||||||
_us = info;
|
_us = info;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -45,7 +45,7 @@ import net.i2p.util.SecureFileOutputStream;
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public class RebuildRouterInfoJob extends JobImpl {
|
public class RebuildRouterInfoJob extends JobImpl {
|
||||||
private Log _log;
|
private final Log _log;
|
||||||
|
|
||||||
private final static long REBUILD_DELAY = 45*1000; // every 30 seconds
|
private final static long REBUILD_DELAY = 45*1000; // every 30 seconds
|
||||||
|
|
||||||
@@ -134,16 +134,23 @@ public class RebuildRouterInfoJob extends JobImpl {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!info.isValid()) {
|
||||||
|
_log.log(Log.CRIT, "RouterInfo we just built is invalid: " + info, new Exception());
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
FileOutputStream fos = null;
|
FileOutputStream fos = null;
|
||||||
try {
|
synchronized (getContext().router().routerInfoFileLock) {
|
||||||
fos = new SecureFileOutputStream(infoFile);
|
try {
|
||||||
info.writeBytes(fos);
|
fos = new SecureFileOutputStream(infoFile);
|
||||||
} catch (DataFormatException dfe) {
|
info.writeBytes(fos);
|
||||||
_log.log(Log.CRIT, "Error rebuilding the router information", dfe);
|
} catch (DataFormatException dfe) {
|
||||||
} catch (IOException ioe) {
|
_log.log(Log.CRIT, "Error rebuilding the router information", dfe);
|
||||||
_log.log(Log.CRIT, "Error writing out the rebuilt router information", ioe);
|
} catch (IOException ioe) {
|
||||||
} finally {
|
_log.log(Log.CRIT, "Error writing out the rebuilt router information", ioe);
|
||||||
if (fos != null) try { fos.close(); } catch (IOException ioe) {}
|
} finally {
|
||||||
|
if (fos != null) try { fos.close(); } catch (IOException ioe) {}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
|
Reference in New Issue
Block a user