Split transport identifiers into two: TransportId (globally unique)

and TransportIndex (locally unique).

This is the first step towards forward secrecy. Also removed the
Writable interface and unnecessary user-defined types, moved various
constants to ProtocolConstants and renamed some classes.
This commit is contained in:
akwizgran
2011-11-14 21:40:05 +00:00
parent 7d09102c4d
commit 73aa7d14d7
113 changed files with 1610 additions and 1121 deletions

View File

@@ -15,8 +15,6 @@ import java.util.LinkedHashMap;
import java.util.Map;
import junit.framework.TestCase;
import net.sf.briar.api.TransportId;
import net.sf.briar.api.TransportProperties;
import net.sf.briar.api.crypto.CryptoComponent;
import net.sf.briar.api.protocol.Ack;
import net.sf.briar.api.protocol.Author;
@@ -26,17 +24,20 @@ import net.sf.briar.api.protocol.BatchId;
import net.sf.briar.api.protocol.Group;
import net.sf.briar.api.protocol.GroupFactory;
import net.sf.briar.api.protocol.Message;
import net.sf.briar.api.protocol.MessageEncoder;
import net.sf.briar.api.protocol.MessageId;
import net.sf.briar.api.protocol.Offer;
import net.sf.briar.api.protocol.ProtocolReader;
import net.sf.briar.api.protocol.ProtocolReaderFactory;
import net.sf.briar.api.protocol.Request;
import net.sf.briar.api.protocol.SubscriptionUpdate;
import net.sf.briar.api.protocol.Transport;
import net.sf.briar.api.protocol.TransportId;
import net.sf.briar.api.protocol.TransportIndex;
import net.sf.briar.api.protocol.TransportUpdate;
import net.sf.briar.api.protocol.UniqueId;
import net.sf.briar.api.protocol.writers.AckWriter;
import net.sf.briar.api.protocol.writers.BatchWriter;
import net.sf.briar.api.protocol.writers.MessageEncoder;
import net.sf.briar.api.protocol.writers.OfferWriter;
import net.sf.briar.api.protocol.writers.ProtocolWriterFactory;
import net.sf.briar.api.protocol.writers.RequestWriter;
@@ -52,6 +53,8 @@ import net.sf.briar.protocol.ProtocolModule;
import net.sf.briar.protocol.writers.ProtocolWritersModule;
import net.sf.briar.serial.SerialModule;
import net.sf.briar.transport.TransportModule;
import net.sf.briar.transport.batch.TransportBatchModule;
import net.sf.briar.transport.stream.TransportStreamModule;
import org.junit.Test;
@@ -69,7 +72,7 @@ public class ProtocolIntegrationTest extends TestCase {
private final ProtocolWriterFactory protocolWriterFactory;
private final CryptoComponent crypto;
private final byte[] aliceSecret, bobSecret;
private final TransportId transportId = new TransportId(123);
private final TransportIndex transportIndex = new TransportIndex(13);
private final long connection = 12345L;
private final Author author;
private final Group group, group1;
@@ -77,14 +80,15 @@ public class ProtocolIntegrationTest extends TestCase {
private final String authorName = "Alice";
private final String subject = "Hello";
private final String messageBody = "Hello world";
private final Map<TransportId, TransportProperties> transports;
private final Collection<Transport> transports;
public ProtocolIntegrationTest() throws Exception {
super();
Injector i = Guice.createInjector(new CryptoModule(),
new DatabaseModule(), new ProtocolModule(),
new ProtocolWritersModule(), new SerialModule(),
new TestDatabaseModule(), new TransportModule());
new TestDatabaseModule(), new TransportBatchModule(),
new TransportModule(), new TransportStreamModule());
connectionReaderFactory = i.getInstance(ConnectionReaderFactory.class);
connectionWriterFactory = i.getInstance(ConnectionWriterFactory.class);
protocolReaderFactory = i.getInstance(ProtocolReaderFactory.class);
@@ -120,9 +124,11 @@ public class ProtocolIntegrationTest extends TestCase {
message3 = messageEncoder.encodeMessage(null, group1,
groupKeyPair.getPrivate(), author, authorKeyPair.getPrivate(),
subject, messageBody.getBytes("UTF-8"));
TransportProperties p =
new TransportProperties(Collections.singletonMap("bar", "baz"));
transports = Collections.singletonMap(transportId, p);
// Create some transports
TransportId transportId = new TransportId(TestUtils.getRandomId());
Transport transport = new Transport(transportId, transportIndex,
Collections.singletonMap("bar", "baz"));
transports = Collections.singletonList(transport);
}
@Test
@@ -134,7 +140,7 @@ public class ProtocolIntegrationTest extends TestCase {
ByteArrayOutputStream out = new ByteArrayOutputStream();
// Use Alice's secret for writing
ConnectionWriter w = connectionWriterFactory.createConnectionWriter(out,
Long.MAX_VALUE, transportId, connection, aliceSecret);
Long.MAX_VALUE, transportIndex, connection, aliceSecret);
OutputStream out1 = w.getOutputStream();
AckWriter a = protocolWriterFactory.createAckWriter(out1);
@@ -188,7 +194,7 @@ public class ProtocolIntegrationTest extends TestCase {
assertEquals(16, offset);
// Use Bob's secret for reading
ConnectionReader r = connectionReaderFactory.createConnectionReader(in,
transportId, encryptedIv, bobSecret);
transportIndex, encryptedIv, bobSecret);
in = r.getInputStream();
ProtocolReader protocolReader =
protocolReaderFactory.createProtocolReader(in);

View File

@@ -48,7 +48,7 @@ public class DatabaseComponentImplTest extends DatabaseComponentTest {
oneOf(database).startTransaction();
will(returnValue(txn));
oneOf(database).getOldMessages(txn, BYTES_PER_SWEEP);
will(returnValue(Collections.emptySet()));
will(returnValue(Collections.emptyList()));
oneOf(database).commitTransaction(txn);
// As if by magic, some free space has appeared
oneOf(database).getFreeSpace();

View File

@@ -10,7 +10,6 @@ import junit.framework.TestCase;
import net.sf.briar.TestUtils;
import net.sf.briar.api.ContactId;
import net.sf.briar.api.Rating;
import net.sf.briar.api.TransportId;
import net.sf.briar.api.TransportProperties;
import net.sf.briar.api.db.DatabaseComponent;
import net.sf.briar.api.db.MessageHeader;
@@ -21,7 +20,7 @@ import net.sf.briar.api.db.event.ContactRemovedEvent;
import net.sf.briar.api.db.event.DatabaseListener;
import net.sf.briar.api.db.event.MessagesAddedEvent;
import net.sf.briar.api.db.event.RatingChangedEvent;
import net.sf.briar.api.db.event.TransportsUpdatedEvent;
import net.sf.briar.api.db.event.TransportAddedEvent;
import net.sf.briar.api.protocol.Ack;
import net.sf.briar.api.protocol.AuthorId;
import net.sf.briar.api.protocol.Batch;
@@ -33,6 +32,9 @@ import net.sf.briar.api.protocol.MessageId;
import net.sf.briar.api.protocol.Offer;
import net.sf.briar.api.protocol.ProtocolConstants;
import net.sf.briar.api.protocol.SubscriptionUpdate;
import net.sf.briar.api.protocol.Transport;
import net.sf.briar.api.protocol.TransportId;
import net.sf.briar.api.protocol.TransportIndex;
import net.sf.briar.api.protocol.TransportUpdate;
import net.sf.briar.api.protocol.writers.AckWriter;
import net.sf.briar.api.protocol.writers.BatchWriter;
@@ -61,7 +63,8 @@ public abstract class DatabaseComponentTest extends TestCase {
private final Message message, privateMessage;
private final Group group;
private final TransportId transportId;
private final Map<TransportId, TransportProperties> transports;
private final TransportIndex localIndex, remoteIndex;
private final Collection<Transport> transports;
private final Map<ContactId, TransportProperties> remoteProperties;
private final byte[] secret;
@@ -82,11 +85,15 @@ public abstract class DatabaseComponentTest extends TestCase {
privateMessage = new TestMessage(messageId, null, null, null, subject,
timestamp, raw);
group = new TestGroup(groupId, "The really exciting group", null);
transportId = new TransportId(123);
TransportProperties p =
new TransportProperties(Collections.singletonMap("foo", "bar"));
transports = Collections.singletonMap(transportId, p);
remoteProperties = Collections.singletonMap(contactId, p);
transportId = new TransportId(TestUtils.getRandomId());
localIndex = new TransportIndex(0);
remoteIndex = new TransportIndex(13);
TransportProperties properties = new TransportProperties(
Collections.singletonMap("foo", "bar"));
remoteProperties = Collections.singletonMap(contactId, properties);
Transport transport = new Transport(transportId, localIndex,
properties);
transports = Collections.singletonList(transport);
secret = new byte[123];
}
@@ -124,17 +131,17 @@ public abstract class DatabaseComponentTest extends TestCase {
// setRating(authorId, Rating.GOOD) again
oneOf(database).setRating(txn, authorId, Rating.GOOD);
will(returnValue(Rating.GOOD));
// addContact(transports)
oneOf(database).addContact(txn, transports, secret);
// addContact()
oneOf(database).addContact(txn, secret);
will(returnValue(contactId));
oneOf(listener).eventOccurred(with(any(ContactAddedEvent.class)));
// getContacts()
oneOf(database).getContacts(txn);
will(returnValue(Collections.singletonList(contactId)));
// getConnectionWindow(contactId, 123)
// getConnectionWindow(contactId, 13)
oneOf(database).containsContact(txn, contactId);
will(returnValue(true));
oneOf(database).getConnectionWindow(txn, contactId, transportId);
oneOf(database).getConnectionWindow(txn, contactId, remoteIndex);
will(returnValue(connectionWindow));
// getSharedSecret(contactId)
oneOf(database).containsContact(txn, contactId);
@@ -170,10 +177,10 @@ public abstract class DatabaseComponentTest extends TestCase {
// unsubscribe(groupId) again
oneOf(database).containsSubscription(txn, groupId);
will(returnValue(false));
// setConnectionWindow(contactId, 123, connectionWindow)
// setConnectionWindow(contactId, 13, connectionWindow)
oneOf(database).containsContact(txn, contactId);
will(returnValue(true));
oneOf(database).setConnectionWindow(txn, contactId, transportId,
oneOf(database).setConnectionWindow(txn, contactId, remoteIndex,
connectionWindow);
// removeContact(contactId)
oneOf(database).removeContact(txn, contactId);
@@ -189,10 +196,10 @@ public abstract class DatabaseComponentTest extends TestCase {
assertEquals(Rating.UNRATED, db.getRating(authorId));
db.setRating(authorId, Rating.GOOD); // First time - listeners called
db.setRating(authorId, Rating.GOOD); // Second time - not called
assertEquals(contactId, db.addContact(transports, secret));
assertEquals(contactId, db.addContact(secret));
assertEquals(Collections.singletonList(contactId), db.getContacts());
assertEquals(connectionWindow,
db.getConnectionWindow(contactId, transportId));
db.getConnectionWindow(contactId, remoteIndex));
assertEquals(secret, db.getSharedSecret(contactId));
assertEquals(remoteProperties, db.getRemoteProperties(transportId));
db.subscribe(group); // First time - listeners called
@@ -201,7 +208,7 @@ public abstract class DatabaseComponentTest extends TestCase {
assertEquals(Collections.singletonList(groupId), db.getSubscriptions());
db.unsubscribe(groupId); // First time - listeners called
db.unsubscribe(groupId); // Second time - not called
db.setConnectionWindow(contactId, transportId, connectionWindow);
db.setConnectionWindow(contactId, remoteIndex, connectionWindow);
db.removeContact(contactId);
db.removeListener(listener);
db.close();
@@ -540,7 +547,7 @@ public abstract class DatabaseComponentTest extends TestCase {
} catch(NoSuchContactException expected) {}
try {
db.getConnectionWindow(contactId, transportId);
db.getConnectionWindow(contactId, remoteIndex);
fail();
} catch(NoSuchContactException expected) {}
@@ -580,7 +587,7 @@ public abstract class DatabaseComponentTest extends TestCase {
} catch(NoSuchContactException expected) {}
try {
db.setConnectionWindow(contactId, transportId, null);
db.setConnectionWindow(contactId, remoteIndex, null);
fail();
} catch(NoSuchContactException expected) {}
@@ -1379,7 +1386,7 @@ public abstract class DatabaseComponentTest extends TestCase {
with(any(long.class)));
oneOf(database).commitTransaction(txn);
oneOf(listener).eventOccurred(with(any(
TransportsUpdatedEvent.class)));
TransportAddedEvent.class)));
}});
DatabaseComponent db = createDatabaseComponent(database, cleaner);

View File

@@ -10,7 +10,6 @@ import java.util.Collections;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Random;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.TimeUnit;
@@ -22,7 +21,6 @@ import net.sf.briar.TestUtils;
import net.sf.briar.api.ContactId;
import net.sf.briar.api.Rating;
import net.sf.briar.api.TransportConfig;
import net.sf.briar.api.TransportId;
import net.sf.briar.api.TransportProperties;
import net.sf.briar.api.crypto.Password;
import net.sf.briar.api.db.DbException;
@@ -35,12 +33,18 @@ import net.sf.briar.api.protocol.GroupFactory;
import net.sf.briar.api.protocol.GroupId;
import net.sf.briar.api.protocol.Message;
import net.sf.briar.api.protocol.MessageId;
import net.sf.briar.api.protocol.Transport;
import net.sf.briar.api.protocol.TransportId;
import net.sf.briar.api.protocol.TransportIndex;
import net.sf.briar.api.transport.ConnectionWindow;
import net.sf.briar.api.transport.ConnectionWindowFactory;
import net.sf.briar.crypto.CryptoModule;
import net.sf.briar.protocol.ProtocolModule;
import net.sf.briar.protocol.writers.ProtocolWritersModule;
import net.sf.briar.serial.SerialModule;
import net.sf.briar.transport.TransportModule;
import net.sf.briar.transport.batch.TransportBatchModule;
import net.sf.briar.transport.stream.TransportStreamModule;
import org.apache.commons.io.FileSystemUtils;
import org.junit.After;
@@ -75,17 +79,20 @@ public class H2DatabaseTest extends TestCase {
private final Message message, privateMessage;
private final Group group;
private final TransportId transportId;
private final TransportIndex localIndex, remoteIndex;
private final TransportProperties properties;
private final Map<TransportId, TransportProperties> transports;
private final Map<ContactId, TransportProperties> remoteProperties;
private final Collection<Transport> remoteTransports;
private final Map<Group, Long> subscriptions;
private final byte[] secret;
public H2DatabaseTest() throws Exception {
super();
Injector i = Guice.createInjector(new CryptoModule(),
new DatabaseModule(), new ProtocolModule(), new SerialModule(),
new TransportModule(), new TestDatabaseModule(testDir));
new DatabaseModule(), new ProtocolModule(),
new ProtocolWritersModule(), new SerialModule(),
new TransportBatchModule(), new TransportModule(),
new TransportStreamModule(), new TestDatabaseModule(testDir));
connectionWindowFactory = i.getInstance(ConnectionWindowFactory.class);
groupFactory = i.getInstance(GroupFactory.class);
authorId = new AuthorId(TestUtils.getRandomId());
@@ -104,11 +111,15 @@ public class H2DatabaseTest extends TestCase {
privateMessage = new TestMessage(privateMessageId, null, null, null,
subject, timestamp, raw);
group = groupFactory.createGroup(groupId, "Group name", null);
transportId = new TransportId(0);
transportId = new TransportId(TestUtils.getRandomId());
localIndex = new TransportIndex(1);
remoteIndex = new TransportIndex(13);
properties = new TransportProperties(
Collections.singletonMap("foo", "bar"));
transports = Collections.singletonMap(transportId, properties);
remoteProperties = Collections.singletonMap(contactId, properties);
Transport remoteTransport = new Transport(transportId, remoteIndex,
properties);
remoteTransports = Collections.singletonList(remoteTransport);
subscriptions = Collections.singletonMap(group, 0L);
secret = new byte[123];
}
@@ -124,7 +135,7 @@ public class H2DatabaseTest extends TestCase {
Database<Connection> db = open(false);
Connection txn = db.startTransaction();
assertFalse(db.containsContact(txn, contactId));
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
assertTrue(db.containsContact(txn, contactId));
assertFalse(db.containsSubscription(txn, groupId));
db.addSubscription(txn, group);
@@ -142,8 +153,6 @@ public class H2DatabaseTest extends TestCase {
db = open(true);
txn = db.startTransaction();
assertTrue(db.containsContact(txn, contactId));
assertEquals(remoteProperties,
db.getRemoteProperties(txn, transportId));
assertTrue(db.containsSubscription(txn, groupId));
assertTrue(db.containsMessage(txn, messageId));
byte[] raw1 = db.getMessage(txn, messageId);
@@ -182,20 +191,20 @@ public class H2DatabaseTest extends TestCase {
// Create three contacts
assertFalse(db.containsContact(txn, contactId));
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
assertTrue(db.containsContact(txn, contactId));
assertFalse(db.containsContact(txn, contactId1));
assertEquals(contactId1, db.addContact(txn, transports, secret));
assertEquals(contactId1, db.addContact(txn, secret));
assertTrue(db.containsContact(txn, contactId1));
assertFalse(db.containsContact(txn, contactId2));
assertEquals(contactId2, db.addContact(txn, transports, secret));
assertEquals(contactId2, db.addContact(txn, secret));
assertTrue(db.containsContact(txn, contactId2));
// Delete the contact with the highest ID
db.removeContact(txn, contactId2);
assertFalse(db.containsContact(txn, contactId2));
// Add another contact - a new ID should be created
assertFalse(db.containsContact(txn, contactId3));
assertEquals(contactId3, db.addContact(txn, transports, secret));
assertEquals(contactId3, db.addContact(txn, secret));
assertTrue(db.containsContact(txn, contactId3));
db.commitTransaction(txn);
@@ -242,7 +251,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact and store a private message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addPrivateMessage(txn, privateMessage, contactId);
// Removing the contact should remove the message
@@ -261,7 +270,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact and store a private message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addPrivateMessage(txn, privateMessage, contactId);
// The message has no status yet, so it should not be sendable
@@ -300,7 +309,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact and store a private message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addPrivateMessage(txn, privateMessage, contactId);
db.setStatus(txn, contactId, privateMessageId, Status.NEW);
@@ -328,7 +337,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setVisibility(txn, groupId, Collections.singleton(contactId));
db.setSubscriptions(txn, contactId, subscriptions, 1);
@@ -366,7 +375,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setVisibility(txn, groupId, Collections.singleton(contactId));
db.setSubscriptions(txn, contactId, subscriptions, 1);
@@ -408,7 +417,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setVisibility(txn, groupId, Collections.singleton(contactId));
db.addGroupMessage(txn, message);
@@ -447,7 +456,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setVisibility(txn, groupId, Collections.singleton(contactId));
db.addGroupMessage(txn, message);
@@ -482,7 +491,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setVisibility(txn, groupId, Collections.singleton(contactId));
db.setSubscriptions(txn, contactId, subscriptions, 1);
@@ -513,7 +522,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setSubscriptions(txn, contactId, subscriptions, 1);
db.addGroupMessage(txn, message);
@@ -546,7 +555,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact and some batches to ack
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addBatchToAck(txn, contactId, batchId);
db.addBatchToAck(txn, contactId, batchId1);
@@ -573,7 +582,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact and receive the same batch twice
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addBatchToAck(txn, contactId, batchId);
db.addBatchToAck(txn, contactId, batchId);
@@ -599,7 +608,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.addGroupMessage(txn, message);
@@ -624,8 +633,8 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add two contacts, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
ContactId contactId1 = db.addContact(txn, transports, secret);
assertEquals(contactId, db.addContact(txn, secret));
ContactId contactId1 = db.addContact(txn, secret);
db.addSubscription(txn, group);
db.addGroupMessage(txn, message);
@@ -647,7 +656,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setVisibility(txn, groupId, Collections.singleton(contactId));
db.setSubscriptions(txn, contactId, subscriptions, 1);
@@ -686,7 +695,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setVisibility(txn, groupId, Collections.singleton(contactId));
db.setSubscriptions(txn, contactId, subscriptions, 1);
@@ -731,12 +740,12 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
// Add some outstanding batches, a few ms apart
for(int i = 0; i < ids.length; i++) {
db.addOutstandingBatch(txn, contactId, ids[i],
Collections.<MessageId>emptySet());
Collections.<MessageId>emptyList());
Thread.sleep(5);
}
@@ -771,12 +780,12 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
// Add some outstanding batches, a few ms apart
for(int i = 0; i < ids.length; i++) {
db.addOutstandingBatch(txn, contactId, ids[i],
Collections.<MessageId>emptySet());
Collections.<MessageId>emptyList());
Thread.sleep(5);
}
@@ -991,43 +1000,55 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact with some transport properties
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.setTransports(txn, contactId, remoteTransports, 1);
assertEquals(remoteProperties,
db.getRemoteProperties(txn, transportId));
// Replace the transport properties
TransportProperties properties1 =
new TransportProperties(Collections.singletonMap("baz", "bam"));
Map<TransportId, TransportProperties> transports1 =
Collections.singletonMap(transportId, properties1);
Transport remoteTransport1 =
new Transport(transportId, remoteIndex, properties1);
Collection<Transport> remoteTransports1 =
Collections.singletonList(remoteTransport1);
Map<ContactId, TransportProperties> remoteProperties1 =
Collections.singletonMap(contactId, properties1);
db.setTransports(txn, contactId, transports1, 1);
db.setTransports(txn, contactId, remoteTransports1, 2);
assertEquals(remoteProperties1,
db.getRemoteProperties(txn, transportId));
// Remove the transport properties
db.setTransports(txn, contactId,
Collections.<TransportId, TransportProperties>emptyMap(), 2);
db.setTransports(txn, contactId, Collections.<Transport>emptyList(), 3);
assertEquals(Collections.emptyMap(),
db.getRemoteProperties(txn, transportId));
// Set the local transport properties
for(Entry<TransportId, TransportProperties> e : transports.entrySet()) {
db.setLocalProperties(txn, e.getKey(), e.getValue());
}
assertEquals(transports, db.getLocalTransports(txn));
// Remove the local transport properties
for(TransportId t : transports.keySet()) {
db.setLocalProperties(txn, t, new TransportProperties());
}
assertEquals(Collections.emptyMap(), db.getLocalTransports(txn));
db.commitTransaction(txn);
db.close();
}
@Test
public void testLocalTransports() throws Exception {
Database<Connection> db = open(false);
Connection txn = db.startTransaction();
// Allocate a transport index
assertEquals(localIndex, db.addTransport(txn, transportId));
// Set the local transport properties
db.setLocalProperties(txn, transportId, properties);
assertEquals(Collections.singletonList(properties),
db.getLocalTransports(txn));
// Remove the local transport properties - the transport itself will
// not be removed
db.setLocalProperties(txn, transportId, new TransportProperties());
assertEquals(Collections.singletonList(Collections.emptyMap()),
db.getLocalTransports(txn));
db.commitTransaction(txn);
db.close();
}
@Test
public void testUpdateTransportConfig() throws Exception {
@@ -1039,6 +1060,9 @@ public class H2DatabaseTest extends TestCase {
Database<Connection> db = open(false);
Connection txn = db.startTransaction();
// Allocate a transport index
assertEquals(localIndex, db.addTransport(txn, transportId));
// Set the transport config
db.setConfig(txn, transportId, config);
assertEquals(config, db.getConfig(txn, transportId));
@@ -1049,8 +1073,7 @@ public class H2DatabaseTest extends TestCase {
// Remove the transport config
db.setConfig(txn, transportId, new TransportConfig());
assertEquals(Collections.emptyMap(),
db.getConfig(txn, transportId));
assertEquals(Collections.emptyMap(), db.getConfig(txn, transportId));
db.commitTransaction(txn);
db.close();
@@ -1062,27 +1085,32 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact with some transport properties
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.setTransports(txn, contactId, remoteTransports, 1);
assertEquals(remoteProperties,
db.getRemoteProperties(txn, transportId));
// Replace the transport properties using a timestamp of 2
TransportProperties properties1 =
new TransportProperties(Collections.singletonMap("baz", "bam"));
Map<TransportId, TransportProperties> transports1 =
Collections.singletonMap(transportId, properties1);
Transport remoteTransport1 =
new Transport(transportId, remoteIndex, properties1);
Collection<Transport> remoteTransports1 =
Collections.singletonList(remoteTransport1);
Map<ContactId, TransportProperties> remoteProperties1 =
Collections.singletonMap(contactId, properties1);
db.setTransports(txn, contactId, transports1, 2);
db.setTransports(txn, contactId, remoteTransports1, 2);
assertEquals(remoteProperties1,
db.getRemoteProperties(txn, transportId));
// Try to replace the transport properties using a timestamp of 1
TransportProperties properties2 =
new TransportProperties(Collections.singletonMap("quux", "etc"));
Map<TransportId, TransportProperties> transports2 =
Collections.singletonMap(transportId, properties2);
db.setTransports(txn, contactId, transports2, 1);
Transport remoteTransport2 =
new Transport(transportId, remoteIndex, properties2);
Collection<Transport> remoteTransports2 =
Collections.singletonList(remoteTransport2);
db.setTransports(txn, contactId, remoteTransports2, 1);
// The old properties should still be there
assertEquals(remoteProperties1,
@@ -1100,10 +1128,8 @@ public class H2DatabaseTest extends TestCase {
Database<Connection> db = open(false);
Connection txn = db.startTransaction();
// Add a contact
assertEquals(contactId, db.addContact(txn, transports, secret));
// Add some subscriptions
// Add a contact with some subscriptions
assertEquals(contactId, db.addContact(txn, secret));
db.setSubscriptions(txn, contactId, subscriptions, 1);
assertEquals(Collections.singletonList(group),
db.getSubscriptions(txn, contactId));
@@ -1127,10 +1153,8 @@ public class H2DatabaseTest extends TestCase {
Database<Connection> db = open(false);
Connection txn = db.startTransaction();
// Add a contact
assertEquals(contactId, db.addContact(txn, transports, secret));
// Add some subscriptions
// Add a contact with some subscriptions
assertEquals(contactId, db.addContact(txn, secret));
db.setSubscriptions(txn, contactId, subscriptions, 2);
assertEquals(Collections.singletonList(group),
db.getSubscriptions(txn, contactId));
@@ -1154,7 +1178,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact and subscribe to a group
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setSubscriptions(txn, contactId, subscriptions, 1);
@@ -1172,7 +1196,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setSubscriptions(txn, contactId, subscriptions, 1);
db.addGroupMessage(txn, message);
@@ -1195,7 +1219,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setSubscriptions(txn, contactId, subscriptions, 1);
db.addGroupMessage(txn, message);
@@ -1218,7 +1242,7 @@ public class H2DatabaseTest extends TestCase {
// Add a contact, subscribe to a group and store a message -
// the message is older than the contact's subscription
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setVisibility(txn, groupId, Collections.singleton(contactId));
Map<Group, Long> subs = Collections.singletonMap(group, timestamp + 1);
@@ -1242,7 +1266,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setVisibility(txn, groupId, Collections.singleton(contactId));
db.setSubscriptions(txn, contactId, subscriptions, 1);
@@ -1267,7 +1291,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact and subscribe to a group
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setVisibility(txn, groupId, Collections.singleton(contactId));
db.setSubscriptions(txn, contactId, subscriptions, 1);
@@ -1286,7 +1310,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact with a subscription
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.setSubscriptions(txn, contactId, subscriptions, 1);
// There's no local subscription for the group
@@ -1303,7 +1327,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.addGroupMessage(txn, message);
db.setStatus(txn, contactId, messageId, Status.NEW);
@@ -1322,7 +1346,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.addGroupMessage(txn, message);
db.setSubscriptions(txn, contactId, subscriptions, 1);
@@ -1342,7 +1366,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setVisibility(txn, groupId, Collections.singleton(contactId));
db.setSubscriptions(txn, contactId, subscriptions, 1);
@@ -1364,7 +1388,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact, subscribe to a group and store a message
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
db.setVisibility(txn, groupId, Collections.singleton(contactId));
db.setSubscriptions(txn, contactId, subscriptions, 1);
@@ -1385,7 +1409,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact and subscribe to a group
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
// The group should not be visible to the contact
assertEquals(Collections.emptyList(), db.getVisibility(txn, groupId));
@@ -1394,7 +1418,7 @@ public class H2DatabaseTest extends TestCase {
assertEquals(Collections.singletonList(contactId),
db.getVisibility(txn, groupId));
// Make the group invisible again
db.setVisibility(txn, groupId, Collections.<ContactId>emptySet());
db.setVisibility(txn, groupId, Collections.<ContactId>emptyList());
assertEquals(Collections.emptyList(), db.getVisibility(txn, groupId));
db.commitTransaction(txn);
@@ -1408,10 +1432,10 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact
assertEquals(contactId, db.addContact(txn, transports, secret));
// Get the connection window for a new transport
assertEquals(contactId, db.addContact(txn, secret));
// Get the connection window for a new index
ConnectionWindow w = db.getConnectionWindow(txn, contactId,
transportId);
remoteIndex);
// The connection window should exist and be in the initial state
assertNotNull(w);
assertEquals(0L, w.getCentre());
@@ -1427,19 +1451,19 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact
assertEquals(contactId, db.addContact(txn, transports, secret));
// Get the connection window for a new transport
assertEquals(contactId, db.addContact(txn, secret));
// Get the connection window for a new index
ConnectionWindow w = db.getConnectionWindow(txn, contactId,
transportId);
remoteIndex);
// The connection window should exist and be in the initial state
assertNotNull(w);
assertEquals(0L, w.getCentre());
assertEquals(0, w.getBitmap());
// Update the connection window and store it
w.setSeen(5L);
db.setConnectionWindow(txn, contactId, transportId, w);
db.setConnectionWindow(txn, contactId, remoteIndex, w);
// Check that the connection window was stored
w = db.getConnectionWindow(txn, contactId, transportId);
w = db.getConnectionWindow(txn, contactId, remoteIndex);
assertNotNull(w);
assertEquals(6L, w.getCentre());
assertTrue(w.isSeen(5L));
@@ -1527,7 +1551,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact and subscribe to a group
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
// A message with a private parent should return null
@@ -1576,7 +1600,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
// The subscription and transport timestamps should be initialised to 0
assertEquals(0L, db.getSubscriptionsModified(txn, contactId));
@@ -1606,7 +1630,7 @@ public class H2DatabaseTest extends TestCase {
Connection txn = db.startTransaction();
// Add a contact and subscribe to a group
assertEquals(contactId, db.addContact(txn, transports, secret));
assertEquals(contactId, db.addContact(txn, secret));
db.addSubscription(txn, group);
// Store a couple of messages

View File

@@ -1,10 +1,7 @@
package net.sf.briar.db;
import java.io.IOException;
import net.sf.briar.api.protocol.Group;
import net.sf.briar.api.protocol.GroupId;
import net.sf.briar.api.serial.Writer;
public class TestGroup implements Group {
@@ -29,8 +26,4 @@ public class TestGroup implements Group {
public byte[] getPublicKey() {
return publicKey;
}
public void writeTo(Writer w) throws IOException {
throw new UnsupportedOperationException();
}
}

View File

@@ -4,18 +4,19 @@ import java.io.File;
import java.io.IOException;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import junit.framework.TestCase;
import net.sf.briar.TestUtils;
import net.sf.briar.api.TransportId;
import net.sf.briar.api.TransportProperties;
import net.sf.briar.api.db.DatabaseComponent;
import net.sf.briar.api.db.DbException;
import net.sf.briar.api.invitation.InvitationCallback;
import net.sf.briar.api.invitation.InvitationParameters;
import net.sf.briar.api.protocol.Transport;
import net.sf.briar.api.protocol.TransportId;
import net.sf.briar.api.protocol.TransportIndex;
import net.sf.briar.api.serial.Writer;
import net.sf.briar.api.serial.WriterFactory;
@@ -109,11 +110,12 @@ public class InvitationWorkerTest extends TestCase {
private void testInstallerCreation(final boolean createExe,
final boolean createJar) throws IOException, DbException {
TransportProperties properties =
new TransportProperties(Collections.singletonMap("foo", "bar"));
TransportId transportId = new TransportId(123);
final Map<TransportId, TransportProperties> transports =
Collections.singletonMap(transportId, properties);
TransportId transportId = new TransportId(TestUtils.getRandomId());
TransportIndex transportIndex = new TransportIndex(13);
Transport transport = new Transport(transportId, transportIndex,
Collections.singletonMap("foo", "bar"));
final Collection<Transport> transports =
Collections.singletonList(transport);
final File setup = new File(testDir, "setup.dat");
TestUtils.createFile(setup, "foo bar baz");
final File invitation = new File(testDir, "invitation.dat");
@@ -148,7 +150,7 @@ public class InvitationWorkerTest extends TestCase {
will(returnValue(transports));
oneOf(writerFactory).createWriter(with(any(OutputStream.class)));
will(returnValue(writer));
oneOf(writer).writeMap(transports);
oneOf(writer).writeList(transports);
oneOf(params).shouldCreateExe();
will(returnValue(createExe));
oneOf(params).shouldCreateJar();

View File

@@ -1,11 +1,12 @@
package net.sf.briar.plugins;
import java.util.concurrent.Executor;
import java.util.concurrent.atomic.AtomicInteger;
import junit.framework.TestCase;
import net.sf.briar.api.TransportId;
import net.sf.briar.api.TransportProperties;
import net.sf.briar.api.db.DatabaseComponent;
import net.sf.briar.api.protocol.TransportId;
import net.sf.briar.api.protocol.TransportIndex;
import net.sf.briar.api.transport.ConnectionDispatcher;
import net.sf.briar.api.ui.UiCallback;
@@ -22,7 +23,12 @@ public class PluginManagerImplTest extends TestCase {
final ConnectionDispatcher dispatcher =
context.mock(ConnectionDispatcher.class);
final UiCallback uiCallback = context.mock(UiCallback.class);
final AtomicInteger index = new AtomicInteger(0);
context.checking(new Expectations() {{
allowing(db).getLocalIndex(with(any(TransportId.class)));
will(returnValue(null));
allowing(db).addTransport(with(any(TransportId.class)));
will(returnValue(new TransportIndex(index.getAndIncrement())));
allowing(db).getLocalProperties(with(any(TransportId.class)));
will(returnValue(new TransportProperties()));
allowing(db).getRemoteProperties(with(any(TransportId.class)));
@@ -30,10 +36,9 @@ public class PluginManagerImplTest extends TestCase {
allowing(db).setLocalProperties(with(any(TransportId.class)),
with(any(TransportProperties.class)));
}});
Executor executor = new ImmediateExecutor();
Poller poller = new PollerImpl();
PluginManagerImpl p =
new PluginManagerImpl(executor, db, poller, dispatcher, uiCallback);
PluginManagerImpl p = new PluginManagerImpl(db, poller, dispatcher,
uiCallback);
// The Bluetooth plugin will not start without a Bluetooth device, so
// we expect two plugins to be started
assertEquals(2, p.startPlugins());

View File

@@ -1,5 +1,7 @@
package net.sf.briar.plugins.file;
import static org.junit.Assert.assertArrayEquals;
import java.io.File;
import java.io.FileOutputStream;
import java.io.OutputStream;
@@ -47,8 +49,8 @@ public class RemovableDrivePluginTest extends TestCase {
RemovableDrivePlugin plugin = new RemovableDrivePlugin(executor,
callback, finder, monitor);
assertEquals(RemovableDrivePlugin.TRANSPORT_ID,
plugin.getId().getInt());
assertArrayEquals(RemovableDrivePlugin.TRANSPORT_ID,
plugin.getId().getBytes());
context.assertIsSatisfied();
}

View File

@@ -3,28 +3,30 @@ package net.sf.briar.protocol;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.util.BitSet;
import java.util.Collection;
import java.util.Collections;
import java.util.Map;
import junit.framework.TestCase;
import net.sf.briar.TestUtils;
import net.sf.briar.api.TransportId;
import net.sf.briar.api.TransportProperties;
import net.sf.briar.api.protocol.Ack;
import net.sf.briar.api.protocol.Batch;
import net.sf.briar.api.protocol.BatchId;
import net.sf.briar.api.protocol.Group;
import net.sf.briar.api.protocol.GroupFactory;
import net.sf.briar.api.protocol.Message;
import net.sf.briar.api.protocol.MessageEncoder;
import net.sf.briar.api.protocol.Offer;
import net.sf.briar.api.protocol.ProtocolReader;
import net.sf.briar.api.protocol.ProtocolReaderFactory;
import net.sf.briar.api.protocol.Request;
import net.sf.briar.api.protocol.SubscriptionUpdate;
import net.sf.briar.api.protocol.Transport;
import net.sf.briar.api.protocol.TransportId;
import net.sf.briar.api.protocol.TransportIndex;
import net.sf.briar.api.protocol.TransportUpdate;
import net.sf.briar.api.protocol.writers.AckWriter;
import net.sf.briar.api.protocol.writers.BatchWriter;
import net.sf.briar.api.protocol.writers.MessageEncoder;
import net.sf.briar.api.protocol.writers.OfferWriter;
import net.sf.briar.api.protocol.writers.ProtocolWriterFactory;
import net.sf.briar.api.protocol.writers.RequestWriter;
@@ -50,8 +52,7 @@ public class ProtocolReadWriteTest extends TestCase {
private final String messageBody = "Hello world";
private final BitSet bitSet;
private final Map<Group, Long> subscriptions;
private final TransportId transportId;
private final Map<TransportId, TransportProperties> transports;
private final Collection<Transport> transports;
private final long timestamp = System.currentTimeMillis();
public ProtocolReadWriteTest() throws Exception {
@@ -71,10 +72,11 @@ public class ProtocolReadWriteTest extends TestCase {
bitSet.set(3);
bitSet.set(7);
subscriptions = Collections.singletonMap(group, 123L);
transportId = new TransportId(123);
TransportProperties p =
new TransportProperties(Collections.singletonMap("bar", "baz"));
transports = Collections.singletonMap(transportId, p);
TransportId transportId = new TransportId(TestUtils.getRandomId());
TransportIndex transportIndex = new TransportIndex(13);
Transport transport = new Transport(transportId, transportIndex,
Collections.singletonMap("bar", "baz"));
transports = Collections.singletonList(transport);
}
@Test

View File

@@ -1,14 +1,25 @@
package net.sf.briar.protocol.writers;
import static net.sf.briar.api.protocol.ProtocolConstants.MAX_AUTHOR_NAME_LENGTH;
import static net.sf.briar.api.protocol.ProtocolConstants.MAX_BODY_LENGTH;
import static net.sf.briar.api.protocol.ProtocolConstants.MAX_GROUPS;
import static net.sf.briar.api.protocol.ProtocolConstants.MAX_GROUP_NAME_LENGTH;
import static net.sf.briar.api.protocol.ProtocolConstants.MAX_PACKET_LENGTH;
import static net.sf.briar.api.protocol.ProtocolConstants.MAX_PROPERTIES_PER_TRANSPORT;
import static net.sf.briar.api.protocol.ProtocolConstants.MAX_PROPERTY_LENGTH;
import static net.sf.briar.api.protocol.ProtocolConstants.MAX_PUBLIC_KEY_LENGTH;
import static net.sf.briar.api.protocol.ProtocolConstants.MAX_SUBJECT_LENGTH;
import static net.sf.briar.api.protocol.ProtocolConstants.MAX_TRANSPORTS;
import java.io.ByteArrayOutputStream;
import java.security.PrivateKey;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.Map;
import junit.framework.TestCase;
import net.sf.briar.TestUtils;
import net.sf.briar.api.TransportId;
import net.sf.briar.api.TransportProperties;
import net.sf.briar.api.crypto.CryptoComponent;
import net.sf.briar.api.protocol.Author;
import net.sf.briar.api.protocol.AuthorFactory;
@@ -16,14 +27,14 @@ import net.sf.briar.api.protocol.BatchId;
import net.sf.briar.api.protocol.Group;
import net.sf.briar.api.protocol.GroupFactory;
import net.sf.briar.api.protocol.Message;
import net.sf.briar.api.protocol.MessageEncoder;
import net.sf.briar.api.protocol.MessageId;
import net.sf.briar.api.protocol.ProtocolConstants;
import net.sf.briar.api.protocol.SubscriptionUpdate;
import net.sf.briar.api.protocol.TransportUpdate;
import net.sf.briar.api.protocol.Transport;
import net.sf.briar.api.protocol.TransportId;
import net.sf.briar.api.protocol.TransportIndex;
import net.sf.briar.api.protocol.UniqueId;
import net.sf.briar.api.protocol.writers.AckWriter;
import net.sf.briar.api.protocol.writers.BatchWriter;
import net.sf.briar.api.protocol.writers.MessageEncoder;
import net.sf.briar.api.protocol.writers.OfferWriter;
import net.sf.briar.api.protocol.writers.SubscriptionWriter;
import net.sf.briar.api.protocol.writers.TransportWriter;
@@ -50,7 +61,8 @@ public class ConstantsTest extends TestCase {
public ConstantsTest() throws Exception {
super();
Injector i = Guice.createInjector(new CryptoModule(),
new ProtocolModule(), new SerialModule());
new ProtocolModule(), new ProtocolWritersModule(),
new SerialModule());
writerFactory = i.getInstance(WriterFactory.class);
crypto = i.getInstance(CryptoComponent.class);
serial = i.getInstance(SerialComponent.class);
@@ -61,7 +73,7 @@ public class ConstantsTest extends TestCase {
@Test
public void testBatchesFitIntoLargeAck() throws Exception {
testBatchesFitIntoAck(ProtocolConstants.MAX_PACKET_LENGTH);
testBatchesFitIntoAck(MAX_PACKET_LENGTH);
}
@Test
@@ -94,32 +106,32 @@ public class ConstantsTest extends TestCase {
@Test
public void testMessageFitsIntoBatch() throws Exception {
// Create a maximum-length group
String groupName = createRandomString(Group.MAX_NAME_LENGTH);
byte[] groupPublic = new byte[Group.MAX_PUBLIC_KEY_LENGTH];
String groupName = createRandomString(MAX_GROUP_NAME_LENGTH);
byte[] groupPublic = new byte[MAX_PUBLIC_KEY_LENGTH];
Group group = groupFactory.createGroup(groupName, groupPublic);
// Create a maximum-length author
String authorName = createRandomString(Author.MAX_NAME_LENGTH);
byte[] authorPublic = new byte[Author.MAX_PUBLIC_KEY_LENGTH];
String authorName = createRandomString(MAX_AUTHOR_NAME_LENGTH);
byte[] authorPublic = new byte[MAX_PUBLIC_KEY_LENGTH];
Author author = authorFactory.createAuthor(authorName, authorPublic);
// Create a maximum-length message
PrivateKey groupPrivate = crypto.generateKeyPair().getPrivate();
PrivateKey authorPrivate = crypto.generateKeyPair().getPrivate();
String subject = createRandomString(Message.MAX_SUBJECT_LENGTH);
byte[] body = new byte[Message.MAX_BODY_LENGTH];
String subject = createRandomString(MAX_SUBJECT_LENGTH);
byte[] body = new byte[MAX_BODY_LENGTH];
Message message = messageEncoder.encodeMessage(null, group,
groupPrivate, author, authorPrivate, subject, body);
// Add the message to a batch
ByteArrayOutputStream out = new ByteArrayOutputStream(
ProtocolConstants.MAX_PACKET_LENGTH);
ByteArrayOutputStream out =
new ByteArrayOutputStream(MAX_PACKET_LENGTH);
BatchWriter b = new BatchWriterImpl(out, serial, writerFactory,
crypto.getMessageDigest());
assertTrue(b.writeMessage(message.getSerialised()));
b.finish();
// Check the size of the serialised batch
assertTrue(out.size() > UniqueId.LENGTH + Group.MAX_NAME_LENGTH +
Group.MAX_PUBLIC_KEY_LENGTH + Author.MAX_NAME_LENGTH +
Author.MAX_PUBLIC_KEY_LENGTH + Message.MAX_BODY_LENGTH);
assertTrue(out.size() <= ProtocolConstants.MAX_PACKET_LENGTH);
assertTrue(out.size() > UniqueId.LENGTH + MAX_GROUP_NAME_LENGTH +
MAX_PUBLIC_KEY_LENGTH + MAX_AUTHOR_NAME_LENGTH +
MAX_PUBLIC_KEY_LENGTH + MAX_BODY_LENGTH);
assertTrue(out.size() <= MAX_PACKET_LENGTH);
}
@Test
@@ -136,7 +148,7 @@ public class ConstantsTest extends TestCase {
@Test
public void testMessagesFitIntoLargeOffer() throws Exception {
testMessagesFitIntoOffer(ProtocolConstants.MAX_PACKET_LENGTH);
testMessagesFitIntoOffer(MAX_PACKET_LENGTH);
}
@Test
@@ -169,52 +181,49 @@ public class ConstantsTest extends TestCase {
@Test
public void testSubscriptionsFitIntoUpdate() throws Exception {
// Create the maximum number of maximum-length subscriptions
Map<Group, Long> subs =
new HashMap<Group, Long>(SubscriptionUpdate.MAX_SUBS_PER_UPDATE);
byte[] publicKey = new byte[Group.MAX_PUBLIC_KEY_LENGTH];
for(int i = 0; i < SubscriptionUpdate.MAX_SUBS_PER_UPDATE; i++) {
String name = createRandomString(Group.MAX_NAME_LENGTH);
Map<Group, Long> subs = new HashMap<Group, Long>(MAX_GROUPS);
byte[] publicKey = new byte[MAX_PUBLIC_KEY_LENGTH];
for(int i = 0; i < MAX_GROUPS; i++) {
String name = createRandomString(MAX_GROUP_NAME_LENGTH);
Group group = groupFactory.createGroup(name, publicKey);
subs.put(group, Long.MAX_VALUE);
}
// Add the subscriptions to an update
ByteArrayOutputStream out = new ByteArrayOutputStream(
ProtocolConstants.MAX_PACKET_LENGTH);
ByteArrayOutputStream out =
new ByteArrayOutputStream(MAX_PACKET_LENGTH);
SubscriptionWriter s = new SubscriptionWriterImpl(out, writerFactory);
s.writeSubscriptions(subs, Long.MAX_VALUE);
// Check the size of the serialised update
assertTrue(out.size() > SubscriptionUpdate.MAX_SUBS_PER_UPDATE *
(Group.MAX_NAME_LENGTH + Group.MAX_PUBLIC_KEY_LENGTH + 8) + 8);
assertTrue(out.size() <= ProtocolConstants.MAX_PACKET_LENGTH);
assertTrue(out.size() > MAX_GROUPS *
(MAX_GROUP_NAME_LENGTH + MAX_PUBLIC_KEY_LENGTH + 8) + 8);
assertTrue(out.size() <= MAX_PACKET_LENGTH);
}
@Test
public void testTransportsFitIntoUpdate() throws Exception {
// Create the maximum number of plugins, each with the maximum number
// of maximum-length properties
Map<TransportId, TransportProperties> transports =
new HashMap<TransportId, TransportProperties>();
for(int i = 0; i < TransportUpdate.MAX_PLUGINS_PER_UPDATE; i++) {
TransportProperties p = new TransportProperties();
for(int j = 0; j < TransportUpdate.MAX_PROPERTIES_PER_PLUGIN; j++) {
String key = createRandomString(
TransportUpdate.MAX_KEY_OR_VALUE_LENGTH);
String value = createRandomString(
TransportUpdate.MAX_KEY_OR_VALUE_LENGTH);
p.put(key, value);
Collection<Transport> transports = new ArrayList<Transport>();
for(int i = 0; i < MAX_TRANSPORTS; i++) {
TransportId id = new TransportId(TestUtils.getRandomId());
TransportIndex index = new TransportIndex(i);
Transport t = new Transport(id, index);
for(int j = 0; j < MAX_PROPERTIES_PER_TRANSPORT; j++) {
String key = createRandomString(MAX_PROPERTY_LENGTH);
String value = createRandomString(MAX_PROPERTY_LENGTH);
t.put(key, value);
}
transports.put(new TransportId(i), p);
transports.add(t);
}
// Add the transports to an update
ByteArrayOutputStream out = new ByteArrayOutputStream(
ProtocolConstants.MAX_PACKET_LENGTH);
ByteArrayOutputStream out =
new ByteArrayOutputStream(MAX_PACKET_LENGTH);
TransportWriter t = new TransportWriterImpl(out, writerFactory);
t.writeTransports(transports, Long.MAX_VALUE);
// Check the size of the serialised update
assertTrue(out.size() > TransportUpdate.MAX_PLUGINS_PER_UPDATE *
(4 + TransportUpdate.MAX_PROPERTIES_PER_PLUGIN *
TransportUpdate.MAX_KEY_OR_VALUE_LENGTH * 2) + 8);
assertTrue(out.size() <= ProtocolConstants.MAX_PACKET_LENGTH);
assertTrue(out.size() > MAX_TRANSPORTS * (UniqueId.LENGTH + 4 +
(MAX_PROPERTIES_PER_TRANSPORT * MAX_PROPERTY_LENGTH * 2)) + 8);
assertTrue(out.size() <= MAX_PACKET_LENGTH);
}
private static String createRandomString(int length) throws Exception {

View File

@@ -42,9 +42,9 @@ public class RequestWriterImplTest extends TestCase {
b.set(12);
b.set(15);
r.writeRequest(b, 16);
// Short user tag 10, short bytes with length 2, 0xD959
// Short user tag 8, short bytes with length 2, 0xD959
byte[] output = out.toByteArray();
assertEquals("CA" + "92" + "D959", StringUtils.toHexString(output));
assertEquals("C8" + "92" + "D959", StringUtils.toHexString(output));
}
@Test
@@ -63,8 +63,8 @@ public class RequestWriterImplTest extends TestCase {
b.set(11);
b.set(12);
r.writeRequest(b, 13);
// Short user tag 10, short bytes with length 2, 0x59D8
// Short user tag 8, short bytes with length 2, 0x59D8
byte[] output = out.toByteArray();
assertEquals("CA" + "92" + "59D8", StringUtils.toHexString(output));
assertEquals("C8" + "92" + "59D8", StringUtils.toHexString(output));
}
}

View File

@@ -4,14 +4,11 @@ import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import junit.framework.TestCase;
import net.sf.briar.api.serial.Writable;
import net.sf.briar.api.serial.Writer;
import net.sf.briar.util.StringUtils;
import org.junit.Before;
@@ -284,20 +281,6 @@ public class WriterImplTest extends TestCase {
checkContents("EF" + "20" + "EF" + "FF");
}
@Test
public void testWriteCollectionOfWritables() throws IOException {
Writable writable = new Writable() {
public void writeTo(Writer w) throws IOException {
w.writeUserDefinedId(0);
w.writeString("foo");
}
};
w.writeList(Collections.singleton(writable));
// SHORT_LIST tag, length 1, SHORT_USER tag (3 bits), 0 (5 bits),
// "foo" as short string
checkContents("A" + "1" + "C0" + "83666F6F");
}
private void checkContents(String hex) throws IOException {
out.flush();
out.close();

View File

@@ -11,8 +11,8 @@ import javax.crypto.spec.IvParameterSpec;
import junit.framework.TestCase;
import net.sf.briar.TestUtils;
import net.sf.briar.api.TransportId;
import net.sf.briar.api.crypto.CryptoComponent;
import net.sf.briar.api.protocol.TransportIndex;
import net.sf.briar.crypto.CryptoModule;
import org.apache.commons.io.output.ByteArrayOutputStream;
@@ -27,7 +27,7 @@ public class ConnectionDecrypterImplTest extends TestCase {
private final Cipher ivCipher, frameCipher;
private final SecretKey ivKey, frameKey;
private final TransportId transportId = new TransportId(123);
private final TransportIndex transportIndex = new TransportIndex(13);
private final long connection = 12345L;
public ConnectionDecrypterImplTest() {
@@ -52,7 +52,7 @@ public class ConnectionDecrypterImplTest extends TestCase {
private void testDecryption(boolean initiator) throws Exception {
// Calculate the plaintext and ciphertext for the IV
byte[] iv = IvEncoder.encodeIv(initiator, transportId, connection);
byte[] iv = IvEncoder.encodeIv(initiator, transportIndex, connection);
ivCipher.init(Cipher.ENCRYPT_MODE, ivKey);
byte[] encryptedIv = ivCipher.doFinal(iv);
assertEquals(IV_LENGTH, encryptedIv.length);
@@ -85,7 +85,7 @@ public class ConnectionDecrypterImplTest extends TestCase {
ByteArrayInputStream in = new ByteArrayInputStream(out.toByteArray());
// Use a ConnectionDecrypter to decrypt the ciphertext
ConnectionDecrypter d = new ConnectionDecrypterImpl(in,
IvEncoder.encodeIv(initiator, transportId, connection),
IvEncoder.encodeIv(initiator, transportIndex, connection),
frameCipher, frameKey);
// First frame
byte[] decrypted = new byte[ciphertext.length];

View File

@@ -10,8 +10,8 @@ import javax.crypto.SecretKey;
import javax.crypto.spec.IvParameterSpec;
import junit.framework.TestCase;
import net.sf.briar.api.TransportId;
import net.sf.briar.api.crypto.CryptoComponent;
import net.sf.briar.api.protocol.TransportIndex;
import net.sf.briar.crypto.CryptoModule;
import org.junit.Test;
@@ -25,7 +25,7 @@ public class ConnectionEncrypterImplTest extends TestCase {
private final Cipher ivCipher, frameCipher;
private final SecretKey ivKey, frameKey;
private final TransportId transportId = new TransportId(123);
private final TransportIndex transportIndex = new TransportIndex(13);
private final long connection = 12345L;
public ConnectionEncrypterImplTest() {
@@ -50,7 +50,7 @@ public class ConnectionEncrypterImplTest extends TestCase {
private void testEncryption(boolean initiator) throws Exception {
// Calculate the expected ciphertext for the IV
byte[] iv = IvEncoder.encodeIv(initiator, transportId, connection);
byte[] iv = IvEncoder.encodeIv(initiator, transportIndex, connection);
ivCipher.init(Cipher.ENCRYPT_MODE, ivKey);
byte[] encryptedIv = ivCipher.doFinal(iv);
assertEquals(IV_LENGTH, encryptedIv.length);
@@ -82,7 +82,7 @@ public class ConnectionEncrypterImplTest extends TestCase {
byte[] expected = out.toByteArray();
// Use a ConnectionEncrypter to encrypt the plaintext
out.reset();
iv = IvEncoder.encodeIv(initiator, transportId, connection);
iv = IvEncoder.encodeIv(initiator, transportIndex, connection);
ConnectionEncrypter e = new ConnectionEncrypterImpl(out, Long.MAX_VALUE,
iv, ivCipher, frameCipher, ivKey, frameKey);
e.getOutputStream().write(plaintext);

View File

@@ -9,10 +9,14 @@ import javax.crypto.Cipher;
import javax.crypto.SecretKey;
import junit.framework.TestCase;
import net.sf.briar.TestUtils;
import net.sf.briar.api.ContactId;
import net.sf.briar.api.TransportId;
import net.sf.briar.api.crypto.CryptoComponent;
import net.sf.briar.api.db.DatabaseComponent;
import net.sf.briar.api.protocol.Transport;
import net.sf.briar.api.protocol.TransportId;
import net.sf.briar.api.protocol.TransportIndex;
import net.sf.briar.api.transport.ConnectionContext;
import net.sf.briar.api.transport.ConnectionWindow;
import net.sf.briar.crypto.CryptoModule;
@@ -29,6 +33,8 @@ public class ConnectionRecogniserImplTest extends TestCase {
private final ContactId contactId;
private final byte[] secret;
private final TransportId transportId;
private final TransportIndex localIndex, remoteIndex;
private final Collection<Transport> transports;
private final ConnectionWindow connectionWindow;
public ConnectionRecogniserImplTest() {
@@ -37,7 +43,12 @@ public class ConnectionRecogniserImplTest extends TestCase {
crypto = i.getInstance(CryptoComponent.class);
contactId = new ContactId(1);
secret = new byte[18];
transportId = new TransportId(123);
transportId = new TransportId(TestUtils.getRandomId());
localIndex = new TransportIndex(13);
remoteIndex = new TransportIndex(7);
Transport transport = new Transport(transportId, localIndex,
Collections.singletonMap("foo", "bar"));
transports = Collections.singletonList(transport);
connectionWindow = new ConnectionWindowImpl(0L, 0);
}
@@ -47,15 +58,20 @@ public class ConnectionRecogniserImplTest extends TestCase {
final DatabaseComponent db = context.mock(DatabaseComponent.class);
context.checking(new Expectations() {{
oneOf(db).addListener(with(any(ConnectionRecogniserImpl.class)));
// Initialise
oneOf(db).getLocalTransports();
will(returnValue(transports));
oneOf(db).getContacts();
will(returnValue(Collections.singleton(contactId)));
oneOf(db).getSharedSecret(contactId);
will(returnValue(secret));
oneOf(db).getConnectionWindow(contactId, transportId);
oneOf(db).getRemoteIndex(contactId, transportId);
will(returnValue(remoteIndex));
oneOf(db).getConnectionWindow(contactId, remoteIndex);
will(returnValue(connectionWindow));
}});
final ConnectionRecogniserImpl c =
new ConnectionRecogniserImpl(transportId, crypto, db);
new ConnectionRecogniserImpl(crypto, db);
assertNull(c.acceptConnection(new byte[IV_LENGTH]));
context.assertIsSatisfied();
}
@@ -66,26 +82,41 @@ public class ConnectionRecogniserImplTest extends TestCase {
SecretKey ivKey = crypto.deriveIncomingIvKey(secret);
Cipher ivCipher = crypto.getIvCipher();
ivCipher.init(Cipher.ENCRYPT_MODE, ivKey);
byte[] iv = IvEncoder.encodeIv(true, transportId, 3L);
byte[] iv = IvEncoder.encodeIv(true, remoteIndex, 3L);
byte[] encryptedIv = ivCipher.doFinal(iv);
Mockery context = new Mockery();
final DatabaseComponent db = context.mock(DatabaseComponent.class);
context.checking(new Expectations() {{
oneOf(db).addListener(with(any(ConnectionRecogniserImpl.class)));
// Initialise
oneOf(db).getLocalTransports();
will(returnValue(transports));
oneOf(db).getContacts();
will(returnValue(Collections.singleton(contactId)));
oneOf(db).getSharedSecret(contactId);
will(returnValue(secret));
oneOf(db).getConnectionWindow(contactId, transportId);
oneOf(db).getRemoteIndex(contactId, transportId);
will(returnValue(remoteIndex));
oneOf(db).getConnectionWindow(contactId, remoteIndex);
will(returnValue(connectionWindow));
oneOf(db).setConnectionWindow(contactId, transportId,
// Update the window
oneOf(db).getConnectionWindow(contactId, remoteIndex);
will(returnValue(connectionWindow));
oneOf(db).setConnectionWindow(contactId, remoteIndex,
connectionWindow);
oneOf(db).getSharedSecret(contactId);
will(returnValue(secret));
}});
final ConnectionRecogniserImpl c =
new ConnectionRecogniserImpl(transportId, crypto, db);
new ConnectionRecogniserImpl(crypto, db);
// First time - the IV should be expected
assertEquals(contactId, c.acceptConnection(encryptedIv));
ConnectionContext ctx = c.acceptConnection(encryptedIv);
assertNotNull(ctx);
assertEquals(contactId, ctx.getContactId());
assertEquals(transportId, ctx.getTransportId());
assertEquals(remoteIndex, ctx.getTransportIndex());
assertEquals(3L, ctx.getConnectionNumber());
// Second time - the IV should no longer be expected
assertNull(c.acceptConnection(encryptedIv));
// The window should have advanced

View File

@@ -7,13 +7,16 @@ import java.io.ByteArrayOutputStream;
import junit.framework.TestCase;
import net.sf.briar.TestDatabaseModule;
import net.sf.briar.api.TransportId;
import net.sf.briar.api.protocol.TransportIndex;
import net.sf.briar.api.transport.ConnectionWriter;
import net.sf.briar.api.transport.ConnectionWriterFactory;
import net.sf.briar.crypto.CryptoModule;
import net.sf.briar.db.DatabaseModule;
import net.sf.briar.protocol.ProtocolModule;
import net.sf.briar.protocol.writers.ProtocolWritersModule;
import net.sf.briar.serial.SerialModule;
import net.sf.briar.transport.batch.TransportBatchModule;
import net.sf.briar.transport.stream.TransportStreamModule;
import org.junit.Test;
@@ -24,14 +27,16 @@ public class ConnectionWriterTest extends TestCase {
private final ConnectionWriterFactory connectionWriterFactory;
private final byte[] secret = new byte[100];
private final TransportId transportId = new TransportId(123);
private final TransportIndex transportIndex = new TransportIndex(13);
private final long connection = 12345L;
public ConnectionWriterTest() throws Exception {
super();
Injector i = Guice.createInjector(new CryptoModule(),
new DatabaseModule(), new ProtocolModule(), new SerialModule(),
new TestDatabaseModule(), new TransportModule());
new DatabaseModule(), new ProtocolModule(),
new ProtocolWritersModule(), new SerialModule(),
new TestDatabaseModule(), new TransportBatchModule(),
new TransportModule(), new TransportStreamModule());
connectionWriterFactory = i.getInstance(ConnectionWriterFactory.class);
}
@@ -40,7 +45,7 @@ public class ConnectionWriterTest extends TestCase {
ByteArrayOutputStream out =
new ByteArrayOutputStream(MIN_CONNECTION_LENGTH);
ConnectionWriter w = connectionWriterFactory.createConnectionWriter(out,
MIN_CONNECTION_LENGTH, transportId, connection, secret);
MIN_CONNECTION_LENGTH, transportIndex, connection, secret);
// Check that the connection writer thinks there's room for a packet
long capacity = w.getRemainingCapacity();
assertTrue(capacity >= MAX_PACKET_LENGTH);

View File

@@ -14,8 +14,8 @@ import javax.crypto.Mac;
import javax.crypto.SecretKey;
import junit.framework.TestCase;
import net.sf.briar.api.TransportId;
import net.sf.briar.api.crypto.CryptoComponent;
import net.sf.briar.api.protocol.TransportIndex;
import net.sf.briar.api.transport.ConnectionReader;
import net.sf.briar.api.transport.ConnectionWriter;
import net.sf.briar.crypto.CryptoModule;
@@ -33,7 +33,7 @@ public class FrameReadWriteTest extends TestCase {
private final Mac mac;
private final Random random;
private final byte[] secret = new byte[100];
private final TransportId transportId = new TransportId(123);
private final TransportIndex transportIndex = new TransportIndex(13);
private final long connection = 12345L;
public FrameReadWriteTest() {
@@ -62,7 +62,7 @@ public class FrameReadWriteTest extends TestCase {
private void testWriteAndRead(boolean initiator) throws Exception {
// Create and encrypt the IV
byte[] iv = IvEncoder.encodeIv(initiator, transportId, connection);
byte[] iv = IvEncoder.encodeIv(initiator, transportIndex, connection);
ivCipher.init(Cipher.ENCRYPT_MODE, ivKey);
byte[] encryptedIv = ivCipher.doFinal(iv);
assertEquals(IV_LENGTH, encryptedIv.length);
@@ -90,7 +90,7 @@ public class FrameReadWriteTest extends TestCase {
// Decrypt the IV
ivCipher.init(Cipher.DECRYPT_MODE, ivKey);
byte[] recoveredIv = ivCipher.doFinal(recoveredEncryptedIv);
iv = IvEncoder.encodeIv(initiator, transportId, connection);
iv = IvEncoder.encodeIv(initiator, transportIndex, connection);
assertArrayEquals(iv, recoveredIv);
// Read the frames back
ConnectionDecrypter decrypter = new ConnectionDecrypterImpl(in, iv,

View File

@@ -7,28 +7,30 @@ import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.Collection;
import java.util.Collections;
import java.util.Map;
import junit.framework.TestCase;
import net.sf.briar.TestDatabaseModule;
import net.sf.briar.TestUtils;
import net.sf.briar.api.ContactId;
import net.sf.briar.api.TransportId;
import net.sf.briar.api.TransportProperties;
import net.sf.briar.api.db.DatabaseComponent;
import net.sf.briar.api.db.event.DatabaseEvent;
import net.sf.briar.api.db.event.DatabaseListener;
import net.sf.briar.api.db.event.MessagesAddedEvent;
import net.sf.briar.api.protocol.Message;
import net.sf.briar.api.protocol.MessageEncoder;
import net.sf.briar.api.protocol.ProtocolReaderFactory;
import net.sf.briar.api.protocol.Transport;
import net.sf.briar.api.protocol.TransportId;
import net.sf.briar.api.protocol.TransportIndex;
import net.sf.briar.api.protocol.TransportUpdate;
import net.sf.briar.api.protocol.writers.MessageEncoder;
import net.sf.briar.api.protocol.writers.ProtocolWriterFactory;
import net.sf.briar.api.transport.BatchTransportReader;
import net.sf.briar.api.transport.BatchTransportWriter;
import net.sf.briar.api.transport.ConnectionContext;
import net.sf.briar.api.transport.ConnectionReaderFactory;
import net.sf.briar.api.transport.ConnectionRecogniser;
import net.sf.briar.api.transport.ConnectionRecogniserFactory;
import net.sf.briar.api.transport.ConnectionWriterFactory;
import net.sf.briar.crypto.CryptoModule;
import net.sf.briar.db.DatabaseModule;
@@ -36,6 +38,7 @@ import net.sf.briar.protocol.ProtocolModule;
import net.sf.briar.protocol.writers.ProtocolWritersModule;
import net.sf.briar.serial.SerialModule;
import net.sf.briar.transport.TransportModule;
import net.sf.briar.transport.stream.TransportStreamModule;
import org.junit.After;
import org.junit.Before;
@@ -49,15 +52,16 @@ public class BatchConnectionReadWriteTest extends TestCase {
private final File testDir = TestUtils.getTestDirectory();
private final File aliceDir = new File(testDir, "alice");
private final File bobDir = new File(testDir, "bob");
private final TransportId transportId = new TransportId(123);
private final Map<TransportId, TransportProperties> transports =
Collections.emptyMap();
private final TransportId transportId;
private final TransportIndex transportIndex;
private final byte[] aliceSecret, bobSecret;
private Injector alice, bob;
public BatchConnectionReadWriteTest() throws Exception {
super();
transportId = new TransportId(TestUtils.getRandomId());
transportIndex = new TransportIndex(1);
// Create matching secrets for Alice and Bob
aliceSecret = new byte[100];
aliceSecret[16] = (byte) 1;
@@ -71,12 +75,14 @@ public class BatchConnectionReadWriteTest extends TestCase {
alice = Guice.createInjector(new CryptoModule(), new DatabaseModule(),
new ProtocolModule(), new ProtocolWritersModule(),
new SerialModule(), new TestDatabaseModule(aliceDir),
new TransportModule());
new TransportBatchModule(), new TransportModule(),
new TransportStreamModule());
// Create Bob's injector
bob = Guice.createInjector(new CryptoModule(), new DatabaseModule(),
new ProtocolModule(), new ProtocolWritersModule(),
new SerialModule(), new TestDatabaseModule(bobDir),
new TransportModule());
new TransportBatchModule(), new TransportModule(),
new TransportStreamModule());
}
@Test
@@ -96,7 +102,7 @@ public class BatchConnectionReadWriteTest extends TestCase {
DatabaseComponent db = alice.getInstance(DatabaseComponent.class);
db.open(false);
// Add Bob as a contact and send him a message
ContactId contactId = db.addContact(transports, aliceSecret);
ContactId contactId = db.addContact(aliceSecret);
String subject = "Hello";
byte[] messageBody = "Hi Bob!".getBytes("UTF-8");
MessageEncoder encoder = alice.getInstance(MessageEncoder.class);
@@ -110,7 +116,8 @@ public class BatchConnectionReadWriteTest extends TestCase {
alice.getInstance(ProtocolWriterFactory.class);
BatchTransportWriter writer = new TestBatchTransportWriter(out);
OutgoingBatchConnection batchOut = new OutgoingBatchConnection(
connFactory, db, protoFactory, transportId, contactId, writer);
connFactory, db, protoFactory, transportIndex, contactId,
writer);
// Write whatever needs to be written
batchOut.write();
// Close Alice's database
@@ -127,18 +134,33 @@ public class BatchConnectionReadWriteTest extends TestCase {
MessageListener listener = new MessageListener();
db.addListener(listener);
// Add Alice as a contact
ContactId contactId = db.addContact(transports, bobSecret);
ContactId contactId = db.addContact(bobSecret);
// Add the transport
assertEquals(transportIndex, db.addTransport(transportId));
// Fake a transport update from Alice
TransportUpdate transportUpdate = new TransportUpdate() {
public Collection<Transport> getTransports() {
Transport t = new Transport(transportId, transportIndex);
return Collections.singletonList(t);
}
public long getTimestamp() {
return System.currentTimeMillis();
}
};
db.receiveTransportUpdate(contactId, transportUpdate);
// Create a connection recogniser and recognise the connection
ByteArrayInputStream in = new ByteArrayInputStream(b);
ConnectionRecogniserFactory recFactory =
bob.getInstance(ConnectionRecogniserFactory.class);
ConnectionRecogniser rec =
recFactory.createConnectionRecogniser(transportId);
ConnectionRecogniser rec = bob.getInstance(ConnectionRecogniser.class);
byte[] encryptedIv = new byte[IV_LENGTH];
int read = in.read(encryptedIv);
assertEquals(encryptedIv.length, read);
ContactId accepted = rec.acceptConnection(encryptedIv);
assertEquals(contactId, accepted);
ConnectionContext ctx = rec.acceptConnection(encryptedIv);
assertNotNull(ctx);
assertEquals(contactId, ctx.getContactId());
assertEquals(transportId, ctx.getTransportId());
assertEquals(transportIndex, ctx.getTransportIndex());
// Create an incoming batch connection
ConnectionReaderFactory connFactory =
bob.getInstance(ConnectionReaderFactory.class);
@@ -146,8 +168,8 @@ public class BatchConnectionReadWriteTest extends TestCase {
bob.getInstance(ProtocolReaderFactory.class);
BatchTransportReader reader = new TestBatchTransportReader(in);
IncomingBatchConnection batchIn = new IncomingBatchConnection(
connFactory, db, protoFactory, transportId, contactId, reader,
encryptedIv);
connFactory, db, protoFactory, transportIndex, contactId,
reader, encryptedIv);
// No messages should have been added yet
assertFalse(listener.messagesAdded);
// Read whatever needs to be read