diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/tcp/LanTcpPlugin.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/tcp/LanTcpPlugin.java
index c1cdb0b35f9f79c46544b8bf5156811ad89b665c..dc07b5686bcab87988c40162eac8db2f9155f57a 100644
--- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/tcp/LanTcpPlugin.java
+++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/tcp/LanTcpPlugin.java
@@ -1,7 +1,6 @@
 package org.briarproject.bramble.plugin.tcp;
 
 import org.briarproject.bramble.api.FormatException;
-import org.briarproject.bramble.api.contact.ContactId;
 import org.briarproject.bramble.api.data.BdfList;
 import org.briarproject.bramble.api.keyagreement.KeyAgreementConnection;
 import org.briarproject.bramble.api.keyagreement.KeyAgreementListener;
@@ -126,9 +125,8 @@ class LanTcpPlugin extends TcpPlugin {
 	}
 
 	@Override
-	protected List<InetSocketAddress> getRemoteSocketAddresses(ContactId c) {
-		TransportProperties p = callback.getRemoteProperties().get(c);
-		if (p == null) return Collections.emptyList();
+	protected List<InetSocketAddress> getRemoteSocketAddresses(
+			TransportProperties p) {
 		return parseSocketAddresses(p.get(PROP_IP_PORTS));
 	}
 
diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/tcp/TcpPlugin.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/tcp/TcpPlugin.java
index 247950ff578ed72b8105a39a5940b03d1d9d4465..47e40f969ddc2d5fc929c6f581a9066fc732f751 100644
--- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/tcp/TcpPlugin.java
+++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/tcp/TcpPlugin.java
@@ -9,6 +9,7 @@ import org.briarproject.bramble.api.plugin.Backoff;
 import org.briarproject.bramble.api.plugin.duplex.DuplexPlugin;
 import org.briarproject.bramble.api.plugin.duplex.DuplexPluginCallback;
 import org.briarproject.bramble.api.plugin.duplex.DuplexTransportConnection;
+import org.briarproject.bramble.api.properties.TransportProperties;
 import org.briarproject.bramble.util.StringUtils;
 
 import java.io.IOException;
@@ -24,6 +25,7 @@ import java.util.ArrayList;
 import java.util.Collection;
 import java.util.Collections;
 import java.util.List;
+import java.util.Map.Entry;
 import java.util.concurrent.Executor;
 import java.util.concurrent.atomic.AtomicBoolean;
 import java.util.logging.Logger;
@@ -66,11 +68,11 @@ abstract class TcpPlugin implements DuplexPlugin {
 	protected abstract void setLocalSocketAddress(InetSocketAddress a);
 
 	/**
-	 * Returns zero or more socket addresses for connecting to the given
-	 * contact.
+	 * Returns zero or more socket addresses for connecting to a contact with
+	 * the given transport properties.
 	 */
 	protected abstract List<InetSocketAddress> getRemoteSocketAddresses(
-			ContactId c);
+			TransportProperties p);
 
 	/**
 	 * Returns true if connections to the given address can be attempted.
@@ -207,16 +209,20 @@ abstract class TcpPlugin implements DuplexPlugin {
 	public void poll(Collection<ContactId> connected) {
 		if (!isRunning()) return;
 		backoff.increment();
-		// TODO: Pass properties to connectAndCallBack()
-		for (ContactId c : callback.getRemoteProperties().keySet())
-			if (!connected.contains(c)) connectAndCallBack(c);
+		for (Entry<ContactId, TransportProperties> e :
+				callback.getRemoteProperties().entrySet()) {
+			ContactId c = e.getKey();
+			if (!connected.contains(c)) connectAndCallBack(c, e.getValue());
+		}
 	}
 
-	private void connectAndCallBack(final ContactId c) {
+	private void connectAndCallBack(final ContactId c,
+			final TransportProperties p) {
 		ioExecutor.execute(new Runnable() {
 			@Override
 			public void run() {
-				DuplexTransportConnection d = createConnection(c);
+				if (!isRunning()) return;
+				DuplexTransportConnection d = createConnection(p);
 				if (d != null) {
 					backoff.reset();
 					callback.outgoingConnectionCreated(c, d);
@@ -228,7 +234,13 @@ abstract class TcpPlugin implements DuplexPlugin {
 	@Override
 	public DuplexTransportConnection createConnection(ContactId c) {
 		if (!isRunning()) return null;
-		for (InetSocketAddress remote : getRemoteSocketAddresses(c)) {
+		TransportProperties p = callback.getRemoteProperties().get(c);
+		return p == null ? null : createConnection(p);
+	}
+
+	@Nullable
+	private DuplexTransportConnection createConnection(TransportProperties p) {
+		for (InetSocketAddress remote : getRemoteSocketAddresses(p)) {
 			if (!isConnectable(remote)) {
 				if (LOG.isLoggable(INFO)) {
 					SocketAddress local = socket.getLocalSocketAddress();
diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/tcp/WanTcpPlugin.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/tcp/WanTcpPlugin.java
index fe3045728528599aa6f1dd6f06284c55e6564fdb..bc30c959713bfcdd3daa167395187698656c1640 100644
--- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/tcp/WanTcpPlugin.java
+++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/tcp/WanTcpPlugin.java
@@ -16,6 +16,8 @@ import java.util.LinkedList;
 import java.util.List;
 import java.util.concurrent.Executor;
 
+import javax.annotation.Nullable;
+
 import static org.briarproject.bramble.api.plugin.WanTcpConstants.ID;
 
 @MethodsNotNullByDefault
@@ -78,9 +80,8 @@ class WanTcpPlugin extends TcpPlugin {
 	}
 
 	@Override
-	protected List<InetSocketAddress> getRemoteSocketAddresses(ContactId c) {
-		TransportProperties p = callback.getRemoteProperties().get(c);
-		if (p == null) return Collections.emptyList();
+	protected List<InetSocketAddress> getRemoteSocketAddresses(
+			TransportProperties p) {
 		InetSocketAddress parsed = parseSocketAddress(p.get(PROP_IP_PORT));
 		if (parsed == null) return Collections.emptyList();
 		return Collections.singletonList(parsed);