Compare commits

...

14 Commits

Author SHA1 Message Date
ameba23
d564fc8713 Add logging on replacing outgoing transport keys 2021-10-04 13:55:03 +02:00
ameba23
41443db817 Bug with checking contactId, improve logging 2021-09-30 15:54:32 +02:00
ameba23
274722d695 Log keys in hex on handshake 2021-09-29 10:15:41 +02:00
ameba23
275c7d261f Fix bug when finding handshake mode keys 2021-09-28 14:45:01 +02:00
ameba23
667f8db4f0 Log keys in hex when failing to recognise tags 2021-09-28 12:47:44 +02:00
ameba23
8398ecdeae Merge branch 'social-backup-poc' into social-backup-handshake-after-recover
* social-backup-poc:
  Rm test which was not present in this branch before cherry pick
  Resolve conflict on cherry pick commit to use ByteBuddyClassImposteriser
  Tell animal sniffer gradle plugin to ignore java.util.Objects
  Improve lost password and setup password dialog for social backup
  When creating social backup, only allow selecting contacts when there are at least 2 contacts in contact list
  Disable help recover account option by default
2021-09-28 08:15:28 +02:00
ameba23
8437aa1b10 If current keys are not in handshake mode, look for handshake mode keys 2021-08-27 10:04:50 +02:00
ameba23
9cf00efa9c Comment out additional logging when restoring account 2021-08-27 10:00:27 +02:00
ameba23
2a45fd3c91 Use new method to get stream context in handshake mode on incoming duplex sync connection 2021-08-27 09:58:08 +02:00
ameba23
f1f16f8474 Additional logging for outgoing duplex sync connection 2021-08-27 09:56:05 +02:00
ameba23
873675d68f Additional logging when reading tag 2021-08-27 09:55:28 +02:00
ameba23
1ffa8ee024 Add a method to get stream context in handshake mode 2021-08-27 09:54:50 +02:00
ameba23
a425a33209 Add a method to get stream context in handshake mode 2021-08-27 09:54:24 +02:00
ameba23
5adbf18851 Add and retrieve Onion private key to/from Tor transport propeties 2021-08-27 09:52:04 +02:00
9 changed files with 110 additions and 9 deletions

View File

@@ -116,4 +116,8 @@ public interface KeyManager {
@Nullable
StreamContext getStreamContext(TransportId t, byte[] tag)
throws DbException;
@Nullable
StreamContext getStreamContextInHandshakeMode(ContactId c, TransportId t)
throws DbException;
}

View File

@@ -47,7 +47,9 @@ abstract class Connection {
TransportId transportId) {
StreamContext ctx;
try {
LOG.info("Reading tag...");
byte[] tag = readTag(reader.getInputStream());
LOG.info("Read tag!");
return keyManager.getStreamContext(transportId, tag);
} catch (IOException | DbException e) {
logException(LOG, WARNING, e);

View File

@@ -130,13 +130,17 @@ class IncomingDuplexSyncConnection extends DuplexSyncConnection
private boolean performHandshake(StreamContext ctxIn, ContactId contactId) {
LOG.info("Performing handshake (Incoming)");
// Allocate the outgoing stream context
StreamContext ctxOut =
allocateStreamContext(contactId, transportId);
if (ctxOut == null) {
StreamContext ctxOut;
try {
ctxOut = keyManager.getStreamContextInHandshakeMode(contactId, transportId);
} catch (DbException e) {
logException(LOG, WARNING, e);
LOG.warning("Could not allocate stream context");
onReadError(true);
return false;
}
try {
InputStream in = streamReaderFactory.createStreamReader(
reader.getInputStream(), ctxIn);
@@ -148,7 +152,7 @@ class IncomingDuplexSyncConnection extends DuplexSyncConnection
handshakeManager.handshake(contactId, in, out);
keyManager.addRotationKeys(contactId, result.getMasterKey(),
TIMESTAMP, result.isAlice(), true);
LOG.info("Rotation keys added");
LOG.info("Rotation keys added - IncomingDuplexSyncConnection");
return true;
} catch (IOException | DbException e) {
logException(LOG, WARNING, e);

View File

@@ -64,6 +64,7 @@ class OutgoingDuplexSyncConnection extends DuplexSyncConnection
LOG.info("Running OutgoingDuplexSyncConnection on transport " +
transportId.getString());
// Allocate a stream context
StreamContext ctx = allocateStreamContext(contactId, transportId);
if (ctx == null) {
LOG.warning("Could not allocate stream context");
@@ -71,6 +72,7 @@ class OutgoingDuplexSyncConnection extends DuplexSyncConnection
return;
}
if (ctx.isHandshakeMode()) {
LOG.info("OutgoingDuplexSyncConnection - context is in handshake mode, performing handshake");
if (!performHandshake(ctx)) {
LOG.warning("Handshake failed");
return;
@@ -155,7 +157,8 @@ class OutgoingDuplexSyncConnection extends DuplexSyncConnection
}
private boolean performHandshake(StreamContext ctxOut) {
LOG.info("Performing handshake (Outgoing)");
LOG.info("Performing handshake (Outgoing) for transport " +
ctxOut.getTransportId().getString());
// Flush the output stream to send the outgoing stream header
StreamWriter out;
try {
@@ -177,7 +180,7 @@ class OutgoingDuplexSyncConnection extends DuplexSyncConnection
}
// Check that the stream comes from the expected contact
ContactId inContactId = ctxIn.getContactId();
if (contactId == null) {
if (inContactId == null) {
LOG.warning("Expected contact tag, got rendezvous tag");
onReadError();
return false;
@@ -196,7 +199,7 @@ class OutgoingDuplexSyncConnection extends DuplexSyncConnection
handshakeManager.handshake(contactId, in, out);
keyManager.addRotationKeys(contactId, result.getMasterKey(),
TIMESTAMP, result.isAlice(), true);
LOG.info("Rotation keys added");
LOG.info("Rotation keys added - OutgoingDuplexSyncConnection");
return true;
} catch (IOException | DbException e) {
logException(LOG, WARNING, e);

View File

@@ -470,6 +470,10 @@ abstract class TorPlugin implements DuplexPlugin, EventHandler, EventListener {
if (now - then >= V3_MIGRATION_PERIOD_MS) retireV2HiddenService();
else publishV2HiddenService(port, privKey2);
}
if (isNullOrEmpty(privKey3)) {
TransportProperties p = callback.getLocalProperties();
privKey3 = p.get(HS_PRIVATE_KEY_V3);
}
publishV3HiddenService(port, privKey3);
}
@@ -511,9 +515,11 @@ abstract class TorPlugin implements DuplexPlugin, EventHandler, EventListener {
try {
// Use the control connection to set up the hidden service
if (privKey == null) {
LOG.info("Private key is null");
response = controlConnection.addOnion("NEW:ED25519-V3",
portLines, null);
} else {
LOG.info("Private key is not null");
response = controlConnection.addOnion(privKey, portLines);
}
} catch (IOException e) {
@@ -535,12 +541,15 @@ abstract class TorPlugin implements DuplexPlugin, EventHandler, EventListener {
if (privKey == null) {
// Publish the hidden service's onion hostname in transport props
TransportProperties p = new TransportProperties();
String now = String.valueOf(clock.currentTimeMillis());
p.put(PROP_ONION_V3, onion3);
p.put(HS_PRIVATE_KEY_V3, response.get(HS_PRIVKEY));
p.put(HS_V3_CREATED, now);
callback.mergeLocalProperties(p);
// Save the hidden service's private key for next time
Settings s = new Settings();
s.put(HS_PRIVATE_KEY_V3, response.get(HS_PRIVKEY));
s.put(HS_V3_CREATED, String.valueOf(clock.currentTimeMillis()));
s.put(HS_V3_CREATED, now);
callback.mergeSettings(s);
}
}

View File

@@ -128,6 +128,7 @@ class KeyManagerImpl implements KeyManager, Service, EventListener {
throws DbException, GeneralSecurityException {
SecretKey staticMasterKey = transportCrypto
.deriveStaticMasterKey(theirPublicKey, ourKeyPair);
LOG.info("Deriving root handshake key " + c.toString() + " " + ourKeyPair.getPublic().toString() + " them: " + theirPublicKey.toString());
SecretKey rootKey =
transportCrypto.deriveHandshakeRootKey(staticMasterKey, false);
boolean alice = transportCrypto.isAlice(theirPublicKey, ourKeyPair);
@@ -135,6 +136,7 @@ class KeyManagerImpl implements KeyManager, Service, EventListener {
for (Entry<TransportId, TransportKeyManager> e : managers.entrySet()) {
TransportId t = e.getKey();
TransportKeyManager m = e.getValue();
LOG.info("Adding handshake keys for transport " + t.getString());
ids.put(t, m.addHandshakeKeys(txn, c, rootKey, alice));
}
return ids;
@@ -205,6 +207,14 @@ class KeyManagerImpl implements KeyManager, Service, EventListener {
m.getStreamContext(txn, tag)));
}
@Override
public StreamContext getStreamContextInHandshakeMode(ContactId c, TransportId t)
throws DbException {
return withManager(t, m ->
db.transactionWithNullableResult(false, txn ->
m.getStreamContextInHandshakeMode(txn, c)));
}
@Override
public void eventOccurred(Event e) {
if (e instanceof ContactRemovedEvent) {

View File

@@ -48,4 +48,7 @@ interface TransportKeyManager {
StreamContext getStreamContext(Transaction txn, byte[] tag)
throws DbException;
@Nullable
StreamContext getStreamContextInHandshakeMode(Transaction txn, ContactId c)
throws DbException;
}

View File

@@ -19,6 +19,7 @@ import org.briarproject.bramble.api.transport.StreamContext;
import org.briarproject.bramble.api.transport.TransportKeySet;
import org.briarproject.bramble.api.transport.TransportKeys;
import org.briarproject.bramble.transport.ReorderingWindow.Change;
import org.briarproject.bramble.util.StringUtils;
import java.util.ArrayList;
import java.util.Collection;
@@ -182,9 +183,12 @@ class TransportKeyManagerImpl implements TransportKeyManager {
if (old == null || (old.getKeys().isHandshakeMode() &&
!ks.getKeys().isHandshakeMode()) ||
old.getKeySetId().getInt() < ks.getKeySetId().getInt()) {
LOG.info("Replacing Outgoing keys!");
if (ks.getContactId() == null)
pendingContactOutContexts.put(ks.getPendingContactId(), ks);
else contactOutContexts.put(ks.getContactId(), ks);
} else {
LOG.info("Not replacing Outgoing keys!");
}
}
}
@@ -372,6 +376,9 @@ class TransportKeyManagerImpl implements TransportKeyManager {
MutableTransportKeySet ks = getOutgoingKeySet(c, p);
if (ks == null) return null;
MutableTransportKeys keys = ks.getKeys();
LOG.info("Using keys for outgoing connection - handshake mode: " +
keys.isHandshakeMode());
MutableOutgoingKeys outKeys = keys.getCurrentOutgoingKeys();
if (!outKeys.isActive()) throw new AssertionError();
if (outKeys.getStreamCounter() > MAX_32_BIT_UNSIGNED) return null;
@@ -395,7 +402,18 @@ class TransportKeyManagerImpl implements TransportKeyManager {
try {
// Look up the incoming keys for the tag
TagContext tagCtx = inContexts.remove(new Bytes(tag));
if (tagCtx == null) return null;
if (tagCtx == null) {
LOG.info("Cannot find tag!");
for (MutableTransportKeySet t : keys.values()) {
LOG.info("Header key: " + StringUtils
.toHexString(t.getKeys().getCurrentIncomingKeys()
.getHeaderKey().getBytes()));
LOG.info("Tag key: " + StringUtils.toHexString(
t.getKeys().getCurrentIncomingKeys().getTagKey()
.getBytes()));
}
return null;
}
MutableIncomingKeys inKeys = tagCtx.inKeys;
// Create a stream context
StreamContext ctx = new StreamContext(tagCtx.contactId,
@@ -443,6 +461,51 @@ class TransportKeyManagerImpl implements TransportKeyManager {
}
}
@Override
public StreamContext getStreamContextInHandshakeMode(Transaction txn,
ContactId c)
throws DbException {
lock.lock();
try {
MutableTransportKeySet ks = getOutgoingKeySet(c, null);
if (ks == null) return null;
MutableTransportKeys currentKeys = ks.getKeys();
LOG.info("Current keys handshake mode? " +
currentKeys.isHandshakeMode());
if (currentKeys.isHandshakeMode())
return getStreamContext(txn, c, null);
for (MutableTransportKeySet keySet : this.keys.values()) {
MutableTransportKeys keys = keySet.getKeys();
if (!keys.isHandshakeMode()) continue;
LOG.info("Found handshake mode keys");
MutableOutgoingKeys outKeys = keys.getCurrentOutgoingKeys();
// if (!outKeys.isActive()) throw new AssertionError();
if (outKeys.getStreamCounter() > MAX_32_BIT_UNSIGNED)
return null;
// Create a stream context
LOG.info("Creating handshake mode stream context");
StreamContext ctx = new StreamContext(c, null, transportId,
outKeys.getTagKey(), outKeys.getHeaderKey(),
outKeys.getStreamCounter(), keys.isHandshakeMode());
LOG.info("Tag key: " +
StringUtils.toHexString(outKeys.getTagKey().getBytes()));
LOG.info("Header key: " +
StringUtils.toHexString(outKeys.getHeaderKey().getBytes()));
// Increment the stream counter and write it back to the DB
outKeys.incrementStreamCounter();
db.incrementStreamCounter(txn, transportId,
keySet.getKeySetId());
LOG.info("Returning");
return ctx;
}
LOG.info("Cannot find handshake mode keys");
return null;
} finally {
lock.unlock();
}
}
@DatabaseExecutor
@Wakeful
private void updateKeys(Transaction txn) throws DbException {

View File

@@ -201,6 +201,9 @@ public class RestoreAccountImpl implements RestoreAccount {
transportPropertyManager
.mergeLocalProperties(propertiesEntry.getKey(),
propertiesEntry.getValue());
// for (Map.Entry<String, String> entry : propertiesEntry.getValue().entrySet()) {
// LOG.info(String.format("%s : %s", entry.getKey(), entry.getValue()));
// }
}
}