Implement handshake on IncomingDuplexSyncConnection

This commit is contained in:
ameba23
2021-04-26 09:59:19 +02:00
parent 6af739e584
commit 4b9c796c1a

View File

@@ -30,6 +30,9 @@ class IncomingDuplexSyncConnection extends DuplexSyncConnection
implements Runnable { implements Runnable {
private final HandshakeManager handshakeManager; private final HandshakeManager handshakeManager;
// FIXME: Exchange timestamp as part of handshake protocol?
private static final long TIMESTAMP = 1617235200; // 1 April 2021 00:00 UTC
IncomingDuplexSyncConnection(KeyManager keyManager, IncomingDuplexSyncConnection(KeyManager keyManager,
ConnectionRegistry connectionRegistry, ConnectionRegistry connectionRegistry,
StreamReaderFactory streamReaderFactory, StreamReaderFactory streamReaderFactory,
@@ -61,41 +64,22 @@ class IncomingDuplexSyncConnection extends DuplexSyncConnection
return; return;
} }
if (ctx.isHandshakeMode()) { if (ctx.isHandshakeMode()) {
if (!performHandshake(ctx, contactId)) {
StreamContext ctxIn = ctx; LOG.warning("Handshake failed");
PendingContactId inPendingContactId = ctxIn.getPendingContactId(); return;
if (inPendingContactId == null) { }
LOG.warning("Expected rendezvous tag, got contact tag"); // Allocate a rotation mode stream context
onReadError(true); ctx = allocateStreamContext(contactId, transportId);
return; if (ctx == null) {
}
// Allocate the outgoing stream context
StreamContext ctxOut =
allocateStreamContext(contactId, transportId);
if (ctxOut == null) {
LOG.warning("Could not allocate stream context"); LOG.warning("Could not allocate stream context");
onReadError(true); onWriteError();
return; return;
} }
try { if (ctx.isHandshakeMode()) {
InputStream in = streamReaderFactory.createStreamReader( LOG.warning("Got handshake mode context after handshaking");
reader.getInputStream(), ctxIn); onWriteError();
// Flush the output stream to send the outgoing stream header
StreamWriter out = streamWriterFactory.createStreamWriter(
writer.getOutputStream(), ctxOut);
out.getOutputStream().flush();
HandshakeManager.HandshakeResult result =
handshakeManager.handshake(contactId, in, out);
return; return;
} catch (IOException | DbException e) {
logException(LOG, WARNING, e);
onReadError(true);
} }
// TODO: Support handshake mode for contacts
// LOG.warning("Received handshake tag, expected rotation mode");
// onReadError(true);
// return;
} }
connectionRegistry.registerIncomingConnection(contactId, transportId, connectionRegistry.registerIncomingConnection(contactId, transportId,
this); this);
@@ -141,5 +125,33 @@ class IncomingDuplexSyncConnection extends DuplexSyncConnection
onWriteError(); onWriteError();
} }
} }
private boolean performHandshake(StreamContext ctxIn, ContactId contactId) {
// Allocate the outgoing stream context
StreamContext ctxOut =
allocateStreamContext(contactId, transportId);
if (ctxOut == null) {
LOG.warning("Could not allocate stream context");
onReadError(true);
return false;
}
try {
InputStream in = streamReaderFactory.createStreamReader(
reader.getInputStream(), ctxIn);
// Flush the output stream to send the outgoing stream header
StreamWriter out = streamWriterFactory.createStreamWriter(
writer.getOutputStream(), ctxOut);
out.getOutputStream().flush();
HandshakeManager.HandshakeResult result =
handshakeManager.handshake(contactId, in, out);
keyManager.addRotationKeys(contactId, result.getMasterKey(),
TIMESTAMP, result.isAlice(), true);
return true;
} catch (IOException | DbException e) {
logException(LOG, WARNING, e);
onReadError(true);
return false;
}
}
} }