diff --git a/api/net/sf/briar/api/plugins/duplex/DuplexTransportConnection.java b/api/net/sf/briar/api/plugins/duplex/DuplexTransportConnection.java
index f5c40e1e465f9ccdba66b68b0dc29eadc1b86ffc..6fc1d3cd570b7602f0a1375cde124ed50bdc2fce 100644
--- a/api/net/sf/briar/api/plugins/duplex/DuplexTransportConnection.java
+++ b/api/net/sf/briar/api/plugins/duplex/DuplexTransportConnection.java
@@ -28,5 +28,5 @@ public interface DuplexTransportConnection {
 	 * of an exception and the second argument indicates whether the connection
 	 * was recognised, which may affect how resources are disposed of.
 	 */
-	void dispose(boolean exception, boolean recognised);
+	void dispose(boolean exception, boolean recognised) throws IOException;
 }
diff --git a/api/net/sf/briar/api/plugins/simplex/SimplexTransportReader.java b/api/net/sf/briar/api/plugins/simplex/SimplexTransportReader.java
index 5ffc0635c1c9ce871be5b674de5f11de560f0575..b7f0f35ed956fc6ea59cf26c226ccad84fc3e191 100644
--- a/api/net/sf/briar/api/plugins/simplex/SimplexTransportReader.java
+++ b/api/net/sf/briar/api/plugins/simplex/SimplexTransportReader.java
@@ -18,7 +18,6 @@ public interface SimplexTransportReader {
 	 * argument indicates whether the reader is being closed because of an
 	 * exception and the second argument indicates whether the connection was
 	 * recognised, which may affect how resources are disposed of.
-	 * @throws IOException 
 	 */
 	void dispose(boolean exception, boolean recognised) throws IOException;
 }
diff --git a/api/net/sf/briar/api/plugins/simplex/SimplexTransportWriter.java b/api/net/sf/briar/api/plugins/simplex/SimplexTransportWriter.java
index 09e80a5cfa0148924980edd8ee1f830089ba47d9..c48b2795de6be837fd917777884f0d65712198d2 100644
--- a/api/net/sf/briar/api/plugins/simplex/SimplexTransportWriter.java
+++ b/api/net/sf/briar/api/plugins/simplex/SimplexTransportWriter.java
@@ -25,7 +25,6 @@ public interface SimplexTransportWriter {
 	 * Closes the writer and disposes of any associated resources. The
 	 * argument indicates whether the writer is being closed because of an
 	 * exception, which may affect how resources are disposed of.
-	 * @throws IOException 
 	 */
 	void dispose(boolean exception) throws IOException;
 }
diff --git a/components/net/sf/briar/plugins/bluetooth/BluetoothTransportConnection.java b/components/net/sf/briar/plugins/bluetooth/BluetoothTransportConnection.java
index 4a110cf94becf8d4eb05ed197778364c45e80dc7..bc2c1fbd44858ac027a0d29b1fddda567cf9ea35 100644
--- a/components/net/sf/briar/plugins/bluetooth/BluetoothTransportConnection.java
+++ b/components/net/sf/briar/plugins/bluetooth/BluetoothTransportConnection.java
@@ -3,8 +3,6 @@ package net.sf.briar.plugins.bluetooth;
 import java.io.IOException;
 import java.io.InputStream;
 import java.io.OutputStream;
-import java.util.logging.Level;
-import java.util.logging.Logger;
 
 import javax.microedition.io.StreamConnection;
 
@@ -12,9 +10,6 @@ import net.sf.briar.api.plugins.duplex.DuplexTransportConnection;
 
 class BluetoothTransportConnection implements DuplexTransportConnection {
 
-	private static final Logger LOG =
-		Logger.getLogger(BluetoothTransportConnection.class.getName());
-
 	private final StreamConnection stream;
 
 	BluetoothTransportConnection(StreamConnection stream) {
@@ -33,11 +28,8 @@ class BluetoothTransportConnection implements DuplexTransportConnection {
 		return true;
 	}
 
-	public void dispose(boolean exception, boolean recognised) {
-		try {
-			stream.close();
-		} catch(IOException e) {
-			if(LOG.isLoggable(Level.WARNING)) LOG.warning(e.toString());
-		}
+	public void dispose(boolean exception, boolean recognised)
+			throws IOException {
+		stream.close();
 	}
 }
diff --git a/components/net/sf/briar/plugins/socket/SocketTransportConnection.java b/components/net/sf/briar/plugins/socket/SocketTransportConnection.java
index a9e147faf89d0a75ab4bd5851cf6a650c2a26613..953f74f6d7d32602f31ea33afd5306b8cbbb6b7c 100644
--- a/components/net/sf/briar/plugins/socket/SocketTransportConnection.java
+++ b/components/net/sf/briar/plugins/socket/SocketTransportConnection.java
@@ -4,16 +4,11 @@ import java.io.IOException;
 import java.io.InputStream;
 import java.io.OutputStream;
 import java.net.Socket;
-import java.util.logging.Level;
-import java.util.logging.Logger;
 
 import net.sf.briar.api.plugins.duplex.DuplexTransportConnection;
 
 class SocketTransportConnection implements DuplexTransportConnection {
 
-	private static final Logger LOG =
-		Logger.getLogger(SocketTransportConnection.class.getName());
-
 	private final Socket socket;
 
 	SocketTransportConnection(Socket socket) {
@@ -32,11 +27,8 @@ class SocketTransportConnection implements DuplexTransportConnection {
 		return true;
 	}
 
-	public void dispose(boolean exception, boolean recognised) {
-		try {
-			socket.close();
-		} catch(IOException e) {
-			if(LOG.isLoggable(Level.WARNING)) LOG.warning(e.toString());
-		}
+	public void dispose(boolean exception, boolean recognised)
+			throws IOException {
+		socket.close();
 	}
 }
diff --git a/components/net/sf/briar/plugins/tor/TorTransportConnection.java b/components/net/sf/briar/plugins/tor/TorTransportConnection.java
index 4a8d74256fae07c349346a2dd5326909d756ec8e..c258e0dbe7f5e8c76519ee5b10a3c01e6a085691 100644
--- a/components/net/sf/briar/plugins/tor/TorTransportConnection.java
+++ b/components/net/sf/briar/plugins/tor/TorTransportConnection.java
@@ -3,8 +3,6 @@ package net.sf.briar.plugins.tor;
 import java.io.IOException;
 import java.io.InputStream;
 import java.io.OutputStream;
-import java.util.logging.Level;
-import java.util.logging.Logger;
 
 import net.sf.briar.api.plugins.duplex.DuplexTransportConnection;
 
@@ -12,9 +10,6 @@ import org.silvertunnel.netlib.api.NetSocket;
 
 class TorTransportConnection implements DuplexTransportConnection {
 
-	private static final Logger LOG =
-		Logger.getLogger(TorTransportConnection.class.getName());
-
 	private final NetSocket socket;
 
 	TorTransportConnection(NetSocket socket) {
@@ -33,11 +28,8 @@ class TorTransportConnection implements DuplexTransportConnection {
 		return true;
 	}
 
-	public void dispose(boolean exception, boolean recognised) {
-		try {
-			socket.close();
-		} catch(IOException e) {
-			if(LOG.isLoggable(Level.WARNING)) LOG.warning(e.toString());
-		}
+	public void dispose(boolean exception, boolean recognised)
+			throws IOException {
+		socket.close();
 	}
 }
diff --git a/components/net/sf/briar/protocol/duplex/DuplexConnection.java b/components/net/sf/briar/protocol/duplex/DuplexConnection.java
index 02da9b9e431c559541beb49ae362156c1bba10f2..37f6c6bb52aba089d7cb305a40a3582aed3f803e 100644
--- a/components/net/sf/briar/protocol/duplex/DuplexConnection.java
+++ b/components/net/sf/briar/protocol/duplex/DuplexConnection.java
@@ -232,7 +232,11 @@ abstract class DuplexConnection implements DatabaseListener {
 	private void dispose(boolean exception, boolean recognised) {
 		if(disposed.getAndSet(true)) return;
 		ByteUtils.erase(ctx.getSecret());
-		transport.dispose(exception, recognised);
+		try {
+			transport.dispose(exception, recognised);
+		} catch(IOException e) {
+			if(LOG.isLoggable(Level.WARNING)) LOG.warning(e.toString());
+		}
 	}
 
 	// This task runs on a database thread
diff --git a/components/net/sf/briar/transport/ConnectionDispatcherImpl.java b/components/net/sf/briar/transport/ConnectionDispatcherImpl.java
index f6954abcc464cca18e62dba253b21f181cf28640..3a17968e39402208ff82dab55780cff54354c982 100644
--- a/components/net/sf/briar/transport/ConnectionDispatcherImpl.java
+++ b/components/net/sf/briar/transport/ConnectionDispatcherImpl.java
@@ -127,21 +127,31 @@ class ConnectionDispatcherImpl implements ConnectionDispatcher {
 		}
 
 		public void run() {
+			byte[] tag;
 			try {
-				byte[] tag = readTag(transport.getInputStream());
-				ConnectionContext ctx = recogniser.acceptConnection(transportId,
-						tag);
-				if(ctx == null) {
-					transport.dispose(false, false);
-				} else {
-					duplexConnFactory.createIncomingConnection(ctx, transport);
-				}
+				tag = readTag(transport.getInputStream());
+			} catch(IOException e) {
+				if(LOG.isLoggable(Level.WARNING)) LOG.warning(e.toString());
+				dispose(true, false);
+				return;
+			}
+			ConnectionContext ctx = null;
+			try {
+				ctx = recogniser.acceptConnection(transportId, tag);
 			} catch(DbException e) {
 				if(LOG.isLoggable(Level.WARNING)) LOG.warning(e.toString());
-				transport.dispose(true, false);
+				dispose(true, false);
+				return;
+			}
+			if(ctx == null) dispose(false, false);
+			else duplexConnFactory.createIncomingConnection(ctx, transport);
+		}
+
+		private void dispose(boolean exception, boolean recognised) {
+			try {
+				transport.dispose(exception, recognised);
 			} catch(IOException e) {
 				if(LOG.isLoggable(Level.WARNING)) LOG.warning(e.toString());
-				transport.dispose(true, false);
 			}
 		}
 	}
diff --git a/test/net/sf/briar/plugins/DuplexTest.java b/test/net/sf/briar/plugins/DuplexTest.java
index cd87fca94b049c2e427f465bf6b551c1192b940c..80eee278f0c05acd481197c8fde43e62c57e04de 100644
--- a/test/net/sf/briar/plugins/DuplexTest.java
+++ b/test/net/sf/briar/plugins/DuplexTest.java
@@ -41,7 +41,11 @@ abstract class DuplexTest {
 			d.dispose(false, true);
 		} catch(IOException e) {
 			e.printStackTrace();
-			d.dispose(true, true);
+			try {
+				d.dispose(true, true);
+			} catch(IOException e1) {
+				e1.printStackTrace();
+			}
 		}
 	}
 
@@ -65,7 +69,11 @@ abstract class DuplexTest {
 			d.dispose(false, true);
 		} catch(IOException e) {
 			e.printStackTrace();
-			d.dispose(true, true);
+			try {
+				d.dispose(true, true);
+			} catch(IOException e1) {
+				e1.printStackTrace();
+			}
 		}
 	}