diff --git a/briar-api/src/net/sf/briar/api/db/DatabaseComponent.java b/briar-api/src/net/sf/briar/api/db/DatabaseComponent.java index 993af1b6e9dd13c815d95f2ef2e6006543631165..1ea9c17b575e08147e7de120c6190a5d5be9c50f 100644 --- a/briar-api/src/net/sf/briar/api/db/DatabaseComponent.java +++ b/briar-api/src/net/sf/briar/api/db/DatabaseComponent.java @@ -69,8 +69,11 @@ public interface DatabaseComponent { */ void addSecrets(Collection<TemporarySecret> secrets) throws DbException; - /** Adds a transport to the database. */ - void addTransport(TransportId t) throws DbException; + /** + * Adds a transport to the database and returns true if the transport was + * not previously in the database. + */ + boolean addTransport(TransportId t) throws DbException; /** * Generates an acknowledgement for the given contact. Returns null if diff --git a/briar-core/src/net/sf/briar/db/Database.java b/briar-core/src/net/sf/briar/db/Database.java index dfc9d00d7809f6d4ff85c63b1c6a04ced20c7c89..209c40722df549242a0872766212f7d22b0db66d 100644 --- a/briar-core/src/net/sf/briar/db/Database.java +++ b/briar-core/src/net/sf/briar/db/Database.java @@ -140,11 +140,12 @@ interface Database<T> { boolean addSubscription(T txn, Group g) throws DbException; /** - * Adds a new transport to the database. + * Adds a new transport to the database and returns true if the transport + * was not previously in the database. * <p> * Locking: transport write. */ - void addTransport(T txn, TransportId t) throws DbException; + boolean addTransport(T txn, TransportId t) throws DbException; /** * Makes the given group visible to the given contact. diff --git a/briar-core/src/net/sf/briar/db/DatabaseComponentImpl.java b/briar-core/src/net/sf/briar/db/DatabaseComponentImpl.java index e18601d06d3fc1f223c17a61e0ee7feb5d290edc..b27f8acc754a3fe97cefa533992995c08af246f7 100644 --- a/briar-core/src/net/sf/briar/db/DatabaseComponentImpl.java +++ b/briar-core/src/net/sf/briar/db/DatabaseComponentImpl.java @@ -349,7 +349,7 @@ DatabaseCleaner.Callback { public void addLocalPrivateMessage(Message m, ContactId c) throws DbException { - boolean added = false; + boolean added; contactLock.readLock().lock(); try { messageLock.writeLock().lock(); @@ -409,12 +409,13 @@ DatabaseCleaner.Callback { } } - public void addTransport(TransportId t) throws DbException { + public boolean addTransport(TransportId t) throws DbException { + boolean added; transportLock.writeLock().lock(); try { T txn = db.startTransaction(); try { - db.addTransport(txn, t); + added = db.addTransport(txn, t); db.commitTransaction(txn); } catch(DbException e) { db.abortTransaction(txn); @@ -423,7 +424,8 @@ DatabaseCleaner.Callback { } finally { transportLock.writeLock().unlock(); } - callListeners(new TransportAddedEvent(t)); + if(added) callListeners(new TransportAddedEvent(t)); + return added; } /** @@ -1845,8 +1847,4 @@ DatabaseCleaner.Callback { } return false; } - - public void rotateKeys() throws DbException { - - } } diff --git a/briar-core/src/net/sf/briar/db/JdbcDatabase.java b/briar-core/src/net/sf/briar/db/JdbcDatabase.java index 78d5adfe279c869986854a4edacbafb8e1795d9c..550b20e4406d818a1ee45fc1b36706a7a9171c4c 100644 --- a/briar-core/src/net/sf/briar/db/JdbcDatabase.java +++ b/briar-core/src/net/sf/briar/db/JdbcDatabase.java @@ -788,12 +788,23 @@ abstract class JdbcDatabase implements Database<Connection> { } } - public void addTransport(Connection txn, TransportId t) throws DbException { + public boolean addTransport(Connection txn, TransportId t) + throws DbException { PreparedStatement ps = null; ResultSet rs = null; try { + // Return false if the transport is already in the database + String sql = "SELECT NULL FROM transports WHERE transportId = ?"; + ps = txn.prepareStatement(sql); + ps.setBytes(1, t.getBytes()); + rs = ps.executeQuery(); + boolean found = rs.next(); + if(rs.next()) throw new DbStateException(); + rs.close(); + ps.close(); + if(found) return false; // Create a transport row - String sql = "INSERT INTO transports (transportId) VALUES (?)"; + sql = "INSERT INTO transports (transportId) VALUES (?)"; ps = txn.prepareStatement(sql); ps.setBytes(1, t.getBytes()); int affected = ps.executeUpdate(); @@ -807,7 +818,7 @@ abstract class JdbcDatabase implements Database<Connection> { while(rs.next()) contacts.add(rs.getInt(1)); rs.close(); ps.close(); - if(contacts.isEmpty()) return; + if(contacts.isEmpty()) return true; sql = "INSERT INTO transportVersions (contactId, transportId," + " localVersion, localAcked, expiry, txCount)" + " VALUES (?, ?, ?, ZERO(), ZERO(), ZERO())"; @@ -824,6 +835,7 @@ abstract class JdbcDatabase implements Database<Connection> { for(int i = 0; i < batchAffected.length; i++) { if(batchAffected[i] != 1) throw new DbStateException(); } + return true; } catch(SQLException e) { tryToClose(ps); tryToClose(rs); diff --git a/briar-core/src/net/sf/briar/plugins/PluginManagerImpl.java b/briar-core/src/net/sf/briar/plugins/PluginManagerImpl.java index c11c4fcd6e13ec323c21bf4f3fe4575c869c13f2..902fbbd9c63db2b814133ae8f8fb4feba8bdc233 100644 --- a/briar-core/src/net/sf/briar/plugins/PluginManagerImpl.java +++ b/briar-core/src/net/sf/briar/plugins/PluginManagerImpl.java @@ -88,6 +88,12 @@ class PluginManagerImpl implements PluginManager { LOG.warning("Duplicate transport ID: " + id); continue; } + try { + db.addTransport(id); + } catch(DbException e) { + if(LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); + continue; + } SimplexCallback callback = new SimplexCallback(id); SimplexPlugin plugin = factory.createPlugin(callback); if(plugin == null) { @@ -118,6 +124,12 @@ class PluginManagerImpl implements PluginManager { LOG.warning("Duplicate transport ID: " + id); continue; } + try { + db.addTransport(id); + } catch(DbException e) { + if(LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); + continue; + } DuplexCallback callback = new DuplexCallback(id); DuplexPlugin plugin = factory.createPlugin(callback); if(plugin == null) { diff --git a/briar-tests/src/net/sf/briar/plugins/PluginManagerImplTest.java b/briar-tests/src/net/sf/briar/plugins/PluginManagerImplTest.java index a080b890d6f300d95cf8eca1561e2a561eb8ca65..cd610cb1e6c3bfbee06cc287dbe270fd2ed1fac3 100644 --- a/briar-tests/src/net/sf/briar/plugins/PluginManagerImplTest.java +++ b/briar-tests/src/net/sf/briar/plugins/PluginManagerImplTest.java @@ -54,6 +54,8 @@ public class PluginManagerImplTest extends BriarTestCase { will(returnValue(Arrays.asList(removableDrive))); oneOf(duplexPluginConfig).getFactories(); will(returnValue(Arrays.asList(lanTcp))); + exactly(2).of(db).addTransport(with(any(TransportId.class))); + will(returnValue(true)); oneOf(poller).start(with(any(Collection.class))); allowing(db).getConfig(with(any(TransportId.class))); will(returnValue(new TransportConfig()));