From 2ecccc66d10de7003d6bbeddef6faa9120fd156b Mon Sep 17 00:00:00 2001 From: akwizgran <akwizgran@users.sourceforge.net> Date: Thu, 5 May 2016 18:05:53 +0100 Subject: [PATCH] Ensure that Plugin instances aren't reused. --- .../AndroidNotificationManagerImpl.java | 3 +- .../plugins/droidtooth/DroidtoothPlugin.java | 44 +++++++++++++------ .../plugins/tcp/AndroidLanTcpPlugin.java | 1 + .../briarproject/plugins/tor/TorPlugin.java | 33 +++++++++++++- .../briarproject/plugins/file/FilePlugin.java | 8 ++++ .../plugins/tcp/LanTcpPlugin.java | 1 + .../briarproject/plugins/tcp/TcpPlugin.java | 22 +++++++++- .../plugins/tcp/WanTcpPlugin.java | 1 + .../plugins/bluetooth/BluetoothPlugin.java | 39 +++++++++++----- .../plugins/file/RemovableDrivePlugin.java | 14 ++++-- .../plugins/modem/ModemPlugin.java | 22 +++++++++- 11 files changed, 153 insertions(+), 35 deletions(-) diff --git a/briar-android/src/org/briarproject/android/AndroidNotificationManagerImpl.java b/briar-android/src/org/briarproject/android/AndroidNotificationManagerImpl.java index ee487ebc1c..669722b1d5 100644 --- a/briar-android/src/org/briarproject/android/AndroidNotificationManagerImpl.java +++ b/briar-android/src/org/briarproject/android/AndroidNotificationManagerImpl.java @@ -282,8 +282,7 @@ class AndroidNotificationManagerImpl implements AndroidNotificationManager, public void showForumPostNotification(final GroupId g) { androidExecutor.execute(new Runnable() { @Override - public void - run() { + public void run() { Integer count = forumCounts.get(g); if (count == null) forumCounts.put(g, 1); else forumCounts.put(g, count + 1); diff --git a/briar-android/src/org/briarproject/plugins/droidtooth/DroidtoothPlugin.java b/briar-android/src/org/briarproject/plugins/droidtooth/DroidtoothPlugin.java index 40a8a04106..a89216505b 100644 --- a/briar-android/src/org/briarproject/plugins/droidtooth/DroidtoothPlugin.java +++ b/briar-android/src/org/briarproject/plugins/droidtooth/DroidtoothPlugin.java @@ -9,9 +9,9 @@ import android.content.Context; import android.content.Intent; import android.content.IntentFilter; +import org.briarproject.android.api.AndroidExecutor; import org.briarproject.android.util.AndroidUtils; import org.briarproject.api.TransportId; -import org.briarproject.android.api.AndroidExecutor; import org.briarproject.api.contact.ContactId; import org.briarproject.api.crypto.PseudoRandom; import org.briarproject.api.keyagreement.KeyAgreementConnection; @@ -41,6 +41,7 @@ import java.util.concurrent.ExecutionException; import java.util.concurrent.Executor; import java.util.concurrent.ExecutorCompletionService; import java.util.concurrent.Future; +import java.util.concurrent.atomic.AtomicBoolean; import java.util.logging.Logger; import static android.bluetooth.BluetoothAdapter.ACTION_SCAN_MODE_CHANGED; @@ -80,6 +81,7 @@ class DroidtoothPlugin implements DuplexPlugin { private final Backoff backoff; private final DuplexPluginCallback callback; private final int maxLatency; + private final AtomicBoolean used = new AtomicBoolean(false); private volatile boolean running = false; private volatile boolean wasEnabledByUs = false; @@ -101,24 +103,30 @@ class DroidtoothPlugin implements DuplexPlugin { this.maxLatency = maxLatency; } + @Override public TransportId getId() { return ID; } + @Override public int getMaxLatency() { return maxLatency; } + @Override public int getMaxIdleTime() { // Bluetooth detects dead connections so we don't need keepalives return Integer.MAX_VALUE; } + @Override public boolean start() throws IOException { + if (used.getAndSet(true)) throw new IllegalStateException(); // BluetoothAdapter.getDefaultAdapter() must be called on a thread // with a message queue, so submit it to the AndroidExecutor try { adapter = androidExecutor.submit(new Callable<BluetoothAdapter>() { + @Override public BluetoothAdapter call() throws Exception { return BluetoothAdapter.getDefaultAdapter(); } @@ -158,6 +166,7 @@ class DroidtoothPlugin implements DuplexPlugin { private void bind() { ioExecutor.execute(new Runnable() { + @Override public void run() { if (!isRunning()) return; String address = AndroidUtils.getBluetoothAddress(appContext, @@ -238,6 +247,7 @@ class DroidtoothPlugin implements DuplexPlugin { return new DroidtoothTransportConnection(this, s); } + @Override public void stop() { running = false; if (receiver != null) appContext.unregisterReceiver(receiver); @@ -249,18 +259,22 @@ class DroidtoothPlugin implements DuplexPlugin { } } + @Override public boolean isRunning() { return running && adapter.isEnabled(); } + @Override public boolean shouldPoll() { return true; } + @Override public int getPollingInterval() { return backoff.getPollingInterval(); } + @Override public void poll(Collection<ContactId> connected) { if (!isRunning()) return; backoff.increment(); @@ -275,6 +289,7 @@ class DroidtoothPlugin implements DuplexPlugin { final String uuid = e.getValue().get(PROP_UUID); if (StringUtils.isNullOrEmpty(uuid)) continue; ioExecutor.execute(new Runnable() { + @Override public void run() { if (!running) return; BluetoothSocket s = connect(address, uuid); @@ -327,6 +342,7 @@ class DroidtoothPlugin implements DuplexPlugin { } } + @Override public DuplexTransportConnection createConnection(ContactId c) { if (!isRunning()) return null; TransportProperties p = callback.getRemoteProperties().get(c); @@ -340,10 +356,12 @@ class DroidtoothPlugin implements DuplexPlugin { return new DroidtoothTransportConnection(this, s); } + @Override public boolean supportsInvitations() { return true; } + @Override public DuplexTransportConnection createInvitationConnection(PseudoRandom r, long timeout, boolean alice) { if (!isRunning()) return null; @@ -361,9 +379,8 @@ class DroidtoothPlugin implements DuplexPlugin { } // Create the background tasks CompletionService<BluetoothSocket> complete = - new ExecutorCompletionService<BluetoothSocket>(ioExecutor); - List<Future<BluetoothSocket>> futures = - new ArrayList<Future<BluetoothSocket>>(); + new ExecutorCompletionService<>(ioExecutor); + List<Future<BluetoothSocket>> futures = new ArrayList<>(); if (alice) { // Return the first connected socket futures.add(complete.submit(new ListeningTask(ss))); @@ -398,6 +415,7 @@ class DroidtoothPlugin implements DuplexPlugin { private void closeSockets(final List<Future<BluetoothSocket>> futures, final BluetoothSocket chosen) { ioExecutor.execute(new Runnable() { + @Override public void run() { for (Future<BluetoothSocket> f : futures) { try { @@ -413,9 +431,7 @@ class DroidtoothPlugin implements DuplexPlugin { } catch (InterruptedException e) { LOG.info("Interrupted while closing sockets"); return; - } catch (ExecutionException e) { - if (LOG.isLoggable(INFO)) LOG.info(e.toString()); - } catch (IOException e) { + } catch (ExecutionException | IOException e) { if (LOG.isLoggable(INFO)) LOG.info(e.toString()); } } @@ -423,14 +439,15 @@ class DroidtoothPlugin implements DuplexPlugin { }); } + @Override public boolean supportsKeyAgreement() { return true; } - public KeyAgreementListener createKeyAgreementListener( - byte[] localCommitment) { + @Override + public KeyAgreementListener createKeyAgreementListener(byte[] commitment) { // No truncation necessary because COMMIT_LENGTH = 16 - UUID uuid = UUID.nameUUIDFromBytes(localCommitment); + UUID uuid = UUID.nameUUIDFromBytes(commitment); if (LOG.isLoggable(INFO)) LOG.info("Key agreement UUID " + uuid); // Bind a server socket for receiving invitation connections BluetoothServerSocket ss; @@ -448,8 +465,9 @@ class DroidtoothPlugin implements DuplexPlugin { return new BluetoothKeyAgreementListener(d, ss); } + @Override public DuplexTransportConnection createKeyAgreementConnection( - byte[] remoteCommitment, TransportDescriptor d, long timeout) { + byte[] commitment, TransportDescriptor d, long timeout) { if (!isRunning()) return null; if (!ID.equals(d.getIdentifier())) return null; TransportProperties p = d.getProperties(); @@ -457,7 +475,7 @@ class DroidtoothPlugin implements DuplexPlugin { String address = p.get(PROP_ADDRESS); if (StringUtils.isNullOrEmpty(address)) return null; // No truncation necessary because COMMIT_LENGTH = 16 - UUID uuid = UUID.nameUUIDFromBytes(remoteCommitment); + UUID uuid = UUID.nameUUIDFromBytes(commitment); if (LOG.isLoggable(INFO)) LOG.info("Connecting to key agreement UUID " + uuid); BluetoothSocket s = connect(address, uuid.toString()); @@ -533,7 +551,7 @@ class DroidtoothPlugin implements DuplexPlugin { private static class DiscoveryReceiver extends BroadcastReceiver { private final CountDownLatch finished = new CountDownLatch(1); - private final List<String> addresses = new ArrayList<String>(); + private final List<String> addresses = new ArrayList<>(); @Override public void onReceive(Context ctx, Intent intent) { diff --git a/briar-android/src/org/briarproject/plugins/tcp/AndroidLanTcpPlugin.java b/briar-android/src/org/briarproject/plugins/tcp/AndroidLanTcpPlugin.java index e04e2f4fcb..598e914b6d 100644 --- a/briar-android/src/org/briarproject/plugins/tcp/AndroidLanTcpPlugin.java +++ b/briar-android/src/org/briarproject/plugins/tcp/AndroidLanTcpPlugin.java @@ -35,6 +35,7 @@ class AndroidLanTcpPlugin extends LanTcpPlugin { @Override public boolean start() { + if (used.getAndSet(true)) throw new IllegalStateException(); running = true; // Register to receive network status events networkStateReceiver = new NetworkStateReceiver(); diff --git a/briar-android/src/org/briarproject/plugins/tor/TorPlugin.java b/briar-android/src/org/briarproject/plugins/tor/TorPlugin.java index 19499171b2..cd460d344b 100644 --- a/briar-android/src/org/briarproject/plugins/tor/TorPlugin.java +++ b/briar-android/src/org/briarproject/plugins/tor/TorPlugin.java @@ -51,6 +51,7 @@ import java.util.Map; import java.util.Scanner; import java.util.concurrent.CountDownLatch; import java.util.concurrent.Executor; +import java.util.concurrent.atomic.AtomicBoolean; import java.util.logging.Logger; import java.util.regex.Pattern; import java.util.zip.ZipInputStream; @@ -94,6 +95,7 @@ class TorPlugin implements DuplexPlugin, EventHandler, EventListener { private final File torDirectory, torFile, geoIpFile, configFile; private final File doneFile, cookieFile; private final PowerManager.WakeLock wakeLock; + private final AtomicBoolean used = new AtomicBoolean(false); private volatile boolean running = false; private volatile ServerSocket socket = null; @@ -130,19 +132,24 @@ class TorPlugin implements DuplexPlugin, EventHandler, EventListener { wakeLock.setReferenceCounted(false); } + @Override public TransportId getId() { return ID; } + @Override public int getMaxLatency() { return maxLatency; } + @Override public int getMaxIdleTime() { return maxIdleTime; } + @Override public boolean start() throws IOException { + if (used.getAndSet(true)) throw new IllegalStateException(); // Try to connect to an existing Tor process if there is one boolean startProcess = false; try { @@ -369,6 +376,7 @@ class TorPlugin implements DuplexPlugin, EventHandler, EventListener { private void bind() { ioExecutor.execute(new Runnable() { + @Override public void run() { // If there's already a port number stored in config, reuse it String portString = callback.getSettings().get("port"); @@ -398,6 +406,7 @@ class TorPlugin implements DuplexPlugin, EventHandler, EventListener { callback.mergeSettings(s); // Create a hidden service if necessary ioExecutor.execute(new Runnable() { + @Override public void run() { publishHiddenService(localPort); } @@ -486,6 +495,7 @@ class TorPlugin implements DuplexPlugin, EventHandler, EventListener { } } + @Override public void stop() throws IOException { running = false; tryToClose(socket); @@ -508,18 +518,22 @@ class TorPlugin implements DuplexPlugin, EventHandler, EventListener { wakeLock.release(); } + @Override public boolean isRunning() { return running && connectionStatus.isConnected(); } + @Override public boolean shouldPoll() { return true; } + @Override public int getPollingInterval() { return backoff.getPollingInterval(); } + @Override public void poll(Collection<ContactId> connected) { if (!isRunning()) return; backoff.increment(); @@ -530,6 +544,7 @@ class TorPlugin implements DuplexPlugin, EventHandler, EventListener { private void connectAndCallBack(final ContactId c) { ioExecutor.execute(new Runnable() { + @Override public void run() { DuplexTransportConnection d = createConnection(c); if (d != null) { @@ -540,6 +555,7 @@ class TorPlugin implements DuplexPlugin, EventHandler, EventListener { }); } + @Override public DuplexTransportConnection createConnection(ContactId c) { if (!isRunning()) return null; TransportProperties p = callback.getRemoteProperties().get(c); @@ -566,29 +582,34 @@ class TorPlugin implements DuplexPlugin, EventHandler, EventListener { } } + @Override public boolean supportsInvitations() { return false; } + @Override public DuplexTransportConnection createInvitationConnection(PseudoRandom r, long timeout, boolean alice) { throw new UnsupportedOperationException(); } + @Override public boolean supportsKeyAgreement() { return false; } - public KeyAgreementListener createKeyAgreementListener( - byte[] commitment) { + @Override + public KeyAgreementListener createKeyAgreementListener(byte[] commitment) { throw new UnsupportedOperationException(); } + @Override public DuplexTransportConnection createKeyAgreementConnection( byte[] commitment, TransportDescriptor d, long timeout) { throw new UnsupportedOperationException(); } + @Override public void circuitStatus(String status, String id, String path) { if (status.equals("BUILT") && connectionStatus.getAndSetCircuitBuilt()) { @@ -598,19 +619,24 @@ class TorPlugin implements DuplexPlugin, EventHandler, EventListener { } } + @Override public void streamStatus(String status, String id, String target) { } + @Override public void orConnStatus(String status, String orName) { if (LOG.isLoggable(INFO)) LOG.info("OR connection " + status); } + @Override public void bandwidthUsed(long read, long written) { } + @Override public void newDescriptors(List<String> orList) { } + @Override public void message(String severity, String msg) { if (LOG.isLoggable(INFO)) LOG.info(severity + " " + msg); if (severity.equals("NOTICE") && msg.startsWith("Bootstrapped 100%")) { @@ -621,6 +647,7 @@ class TorPlugin implements DuplexPlugin, EventHandler, EventListener { } } + @Override public void unrecognized(String type, String msg) { if (type.equals("HS_DESC") && msg.startsWith("UPLOADED")) LOG.info("Descriptor uploaded"); @@ -642,6 +669,7 @@ class TorPlugin implements DuplexPlugin, EventHandler, EventListener { } } + @Override public void eventOccurred(Event e) { if (e instanceof SettingsUpdatedEvent) { if (((SettingsUpdatedEvent) e).getNamespace().equals("tor")) { @@ -653,6 +681,7 @@ class TorPlugin implements DuplexPlugin, EventHandler, EventListener { private void updateConnectionStatus() { ioExecutor.execute(new Runnable() { + @Override public void run() { if (!running) return; diff --git a/briar-core/src/org/briarproject/plugins/file/FilePlugin.java b/briar-core/src/org/briarproject/plugins/file/FilePlugin.java index 3394995cfd..9819235539 100644 --- a/briar-core/src/org/briarproject/plugins/file/FilePlugin.java +++ b/briar-core/src/org/briarproject/plugins/file/FilePlugin.java @@ -14,6 +14,7 @@ import java.io.OutputStream; import java.util.Collection; import java.util.Locale; import java.util.concurrent.Executor; +import java.util.concurrent.atomic.AtomicBoolean; import java.util.logging.Logger; import static java.util.logging.Level.WARNING; @@ -27,6 +28,7 @@ public abstract class FilePlugin implements SimplexPlugin { protected final Executor ioExecutor; protected final SimplexPluginCallback callback; protected final int maxLatency; + protected final AtomicBoolean used = new AtomicBoolean(false); protected volatile boolean running = false; @@ -42,22 +44,27 @@ public abstract class FilePlugin implements SimplexPlugin { this.maxLatency = maxLatency; } + @Override public int getMaxLatency() { return maxLatency; } + @Override public int getMaxIdleTime() { return Integer.MAX_VALUE; // We don't need keepalives } + @Override public boolean isRunning() { return running; } + @Override public TransportConnectionReader createReader(ContactId c) { return null; } + @Override public TransportConnectionWriter createWriter(ContactId c) { if (!running) return null; return createWriter(createConnectionFilename()); @@ -105,6 +112,7 @@ public abstract class FilePlugin implements SimplexPlugin { this.file = file; } + @Override public void run() { if (isPossibleConnectionFilename(file.getName())) { try { diff --git a/briar-core/src/org/briarproject/plugins/tcp/LanTcpPlugin.java b/briar-core/src/org/briarproject/plugins/tcp/LanTcpPlugin.java index 8a75a971e6..f50e967945 100644 --- a/briar-core/src/org/briarproject/plugins/tcp/LanTcpPlugin.java +++ b/briar-core/src/org/briarproject/plugins/tcp/LanTcpPlugin.java @@ -22,6 +22,7 @@ class LanTcpPlugin extends TcpPlugin { super(ioExecutor, backoff, callback, maxLatency, maxIdleTime); } + @Override public TransportId getId() { return ID; } diff --git a/briar-core/src/org/briarproject/plugins/tcp/TcpPlugin.java b/briar-core/src/org/briarproject/plugins/tcp/TcpPlugin.java index d6effe2a72..fa3bd311ab 100644 --- a/briar-core/src/org/briarproject/plugins/tcp/TcpPlugin.java +++ b/briar-core/src/org/briarproject/plugins/tcp/TcpPlugin.java @@ -25,6 +25,7 @@ import java.util.Collection; import java.util.Collections; import java.util.List; import java.util.concurrent.Executor; +import java.util.concurrent.atomic.AtomicBoolean; import java.util.logging.Logger; import java.util.regex.Pattern; @@ -42,6 +43,7 @@ abstract class TcpPlugin implements DuplexPlugin { protected final Backoff backoff; protected final DuplexPluginCallback callback; protected final int maxLatency, maxIdleTime, socketTimeout; + protected final AtomicBoolean used = new AtomicBoolean(false); protected volatile boolean running = false; protected volatile ServerSocket socket = null; @@ -67,15 +69,19 @@ abstract class TcpPlugin implements DuplexPlugin { else socketTimeout = maxIdleTime * 2; } + @Override public int getMaxLatency() { return maxLatency; } + @Override public int getMaxIdleTime() { return maxIdleTime; } + @Override public boolean start() { + if (used.getAndSet(true)) throw new IllegalStateException(); running = true; bind(); return true; @@ -83,6 +89,7 @@ abstract class TcpPlugin implements DuplexPlugin { protected void bind() { ioExecutor.execute(new Runnable() { + @Override public void run() { if (!running) return; ServerSocket ss = null; @@ -158,23 +165,28 @@ abstract class TcpPlugin implements DuplexPlugin { } } + @Override public void stop() { running = false; tryToClose(socket); } + @Override public boolean isRunning() { return running && socket != null && !socket.isClosed(); } + @Override public boolean shouldPoll() { return true; } + @Override public int getPollingInterval() { return backoff.getPollingInterval(); } + @Override public void poll(Collection<ContactId> connected) { if (!isRunning()) return; backoff.increment(); @@ -185,6 +197,7 @@ abstract class TcpPlugin implements DuplexPlugin { private void connectAndCallBack(final ContactId c) { ioExecutor.execute(new Runnable() { + @Override public void run() { DuplexTransportConnection d = createConnection(c); if (d != null) { @@ -195,6 +208,7 @@ abstract class TcpPlugin implements DuplexPlugin { }); } + @Override public DuplexTransportConnection createConnection(ContactId c) { if (!isRunning()) return null; InetSocketAddress remote = getRemoteSocketAddress(c); @@ -243,24 +257,28 @@ abstract class TcpPlugin implements DuplexPlugin { } } + @Override public boolean supportsInvitations() { return false; } + @Override public DuplexTransportConnection createInvitationConnection(PseudoRandom r, long timeout, boolean alice) { throw new UnsupportedOperationException(); } + @Override public boolean supportsKeyAgreement() { return false; } - public KeyAgreementListener createKeyAgreementListener( - byte[] commitment) { + @Override + public KeyAgreementListener createKeyAgreementListener(byte[] commitment) { throw new UnsupportedOperationException(); } + @Override public DuplexTransportConnection createKeyAgreementConnection( byte[] commitment, TransportDescriptor d, long timeout) { throw new UnsupportedOperationException(); diff --git a/briar-core/src/org/briarproject/plugins/tcp/WanTcpPlugin.java b/briar-core/src/org/briarproject/plugins/tcp/WanTcpPlugin.java index beabc8bec5..cee16ac254 100644 --- a/briar-core/src/org/briarproject/plugins/tcp/WanTcpPlugin.java +++ b/briar-core/src/org/briarproject/plugins/tcp/WanTcpPlugin.java @@ -27,6 +27,7 @@ class WanTcpPlugin extends TcpPlugin { this.portMapper = portMapper; } + @Override public TransportId getId() { return ID; } diff --git a/briar-desktop/src/org/briarproject/plugins/bluetooth/BluetoothPlugin.java b/briar-desktop/src/org/briarproject/plugins/bluetooth/BluetoothPlugin.java index 875112c5e8..b8a0418c07 100644 --- a/briar-desktop/src/org/briarproject/plugins/bluetooth/BluetoothPlugin.java +++ b/briar-desktop/src/org/briarproject/plugins/bluetooth/BluetoothPlugin.java @@ -30,6 +30,7 @@ import java.util.concurrent.Executor; import java.util.concurrent.ExecutorCompletionService; import java.util.concurrent.Future; import java.util.concurrent.Semaphore; +import java.util.concurrent.atomic.AtomicBoolean; import java.util.logging.Logger; import javax.bluetooth.BluetoothStateException; @@ -62,6 +63,7 @@ class BluetoothPlugin implements DuplexPlugin { private final DuplexPluginCallback callback; private final int maxLatency; private final Semaphore discoverySemaphore = new Semaphore(1); + private final AtomicBoolean used = new AtomicBoolean(false); private volatile boolean running = false; private volatile StreamConnectionNotifier socket = null; @@ -76,20 +78,25 @@ class BluetoothPlugin implements DuplexPlugin { this.maxLatency = maxLatency; } + @Override public TransportId getId() { return ID; } + @Override public int getMaxLatency() { return maxLatency; } + @Override public int getMaxIdleTime() { // Bluetooth detects dead connections so we don't need keepalives return Integer.MAX_VALUE; } + @Override public boolean start() throws IOException { + if (used.getAndSet(true)) throw new IllegalStateException(); // Initialise the Bluetooth stack try { localDevice = LocalDevice.getLocalDevice(); @@ -108,6 +115,7 @@ class BluetoothPlugin implements DuplexPlugin { private void bind() { ioExecutor.execute(new Runnable() { + @Override public void run() { if (!running) return; // Advertise the Bluetooth address to contacts @@ -183,23 +191,28 @@ class BluetoothPlugin implements DuplexPlugin { return new BluetoothTransportConnection(this, s); } + @Override public void stop() { running = false; tryToClose(socket); } + @Override public boolean isRunning() { return running; } + @Override public boolean shouldPoll() { return true; } + @Override public int getPollingInterval() { return backoff.getPollingInterval(); } + @Override public void poll(final Collection<ContactId> connected) { if (!running) return; backoff.increment(); @@ -214,6 +227,7 @@ class BluetoothPlugin implements DuplexPlugin { final String uuid = e.getValue().get(PROP_UUID); if (StringUtils.isNullOrEmpty(uuid)) continue; ioExecutor.execute(new Runnable() { + @Override public void run() { if (!running) return; StreamConnection s = connect(makeUrl(address, uuid)); @@ -238,6 +252,7 @@ class BluetoothPlugin implements DuplexPlugin { } } + @Override public DuplexTransportConnection createConnection(ContactId c) { if (!running) return null; TransportProperties p = callback.getRemoteProperties().get(c); @@ -252,10 +267,12 @@ class BluetoothPlugin implements DuplexPlugin { return new BluetoothTransportConnection(this, s); } + @Override public boolean supportsInvitations() { return true; } + @Override public DuplexTransportConnection createInvitationConnection(PseudoRandom r, long timeout, boolean alice) { if (!running) return null; @@ -279,9 +296,8 @@ class BluetoothPlugin implements DuplexPlugin { } // Create the background tasks CompletionService<StreamConnection> complete = - new ExecutorCompletionService<StreamConnection>(ioExecutor); - List<Future<StreamConnection>> futures = - new ArrayList<Future<StreamConnection>>(); + new ExecutorCompletionService<>(ioExecutor); + List<Future<StreamConnection>> futures = new ArrayList<>(); if (alice) { // Return the first connected socket futures.add(complete.submit(new ListeningTask(ss))); @@ -316,6 +332,7 @@ class BluetoothPlugin implements DuplexPlugin { private void closeSockets(final List<Future<StreamConnection>> futures, final StreamConnection chosen) { ioExecutor.execute(new Runnable() { + @Override public void run() { for (Future<StreamConnection> f : futures) { try { @@ -331,9 +348,7 @@ class BluetoothPlugin implements DuplexPlugin { } catch (InterruptedException e) { LOG.info("Interrupted while closing sockets"); return; - } catch (ExecutionException e) { - if (LOG.isLoggable(INFO)) LOG.info(e.toString()); - } catch (IOException e) { + } catch (ExecutionException | IOException e) { if (LOG.isLoggable(INFO)) LOG.info(e.toString()); } } @@ -341,14 +356,15 @@ class BluetoothPlugin implements DuplexPlugin { }); } + @Override public boolean supportsKeyAgreement() { return true; } - public KeyAgreementListener createKeyAgreementListener( - byte[] localCommitment) { + @Override + public KeyAgreementListener createKeyAgreementListener(byte[] commitment) { // No truncation necessary because COMMIT_LENGTH = 16 - String uuid = UUID.nameUUIDFromBytes(localCommitment).toString(); + String uuid = UUID.nameUUIDFromBytes(commitment).toString(); if (LOG.isLoggable(INFO)) LOG.info("Key agreement UUID " + uuid); String url = makeUrl("localhost", uuid); // Make the device discoverable if possible @@ -371,8 +387,9 @@ class BluetoothPlugin implements DuplexPlugin { return new BluetoothKeyAgreementListener(d, ss); } + @Override public DuplexTransportConnection createKeyAgreementConnection( - byte[] remoteCommitment, TransportDescriptor d, long timeout) { + byte[] commitment, TransportDescriptor d, long timeout) { if (!isRunning()) return null; if (!ID.equals(d.getIdentifier())) return null; TransportProperties p = d.getProperties(); @@ -380,7 +397,7 @@ class BluetoothPlugin implements DuplexPlugin { String address = p.get(PROP_ADDRESS); if (StringUtils.isNullOrEmpty(address)) return null; // No truncation necessary because COMMIT_LENGTH = 16 - String uuid = UUID.nameUUIDFromBytes(remoteCommitment).toString(); + String uuid = UUID.nameUUIDFromBytes(commitment).toString(); if (LOG.isLoggable(INFO)) LOG.info("Connecting to key agreement UUID " + uuid); String url = makeUrl(address, uuid); diff --git a/briar-desktop/src/org/briarproject/plugins/file/RemovableDrivePlugin.java b/briar-desktop/src/org/briarproject/plugins/file/RemovableDrivePlugin.java index 116143225f..926f8d3148 100644 --- a/briar-desktop/src/org/briarproject/plugins/file/RemovableDrivePlugin.java +++ b/briar-desktop/src/org/briarproject/plugins/file/RemovableDrivePlugin.java @@ -34,29 +34,36 @@ implements RemovableDriveMonitor.Callback { this.monitor = monitor; } + @Override public TransportId getId() { return ID; } + @Override public boolean start() throws IOException { + if (used.getAndSet(true)) throw new IllegalStateException(); running = true; monitor.start(this); return true; } + @Override public void stop() throws IOException { running = false; monitor.stop(); } + @Override public boolean shouldPoll() { return false; } + @Override public int getPollingInterval() { throw new UnsupportedOperationException(); } + @Override public void poll(Collection<ContactId> connected) { throw new UnsupportedOperationException(); } @@ -64,8 +71,7 @@ implements RemovableDriveMonitor.Callback { @Override protected File chooseOutputDirectory() { try { - List<File> drives = - new ArrayList<File>(finder.findRemovableDrives()); + List<File> drives = new ArrayList<>(finder.findRemovableDrives()); if (drives.isEmpty()) return null; String[] paths = new String[drives.size()]; for (int i = 0; i < paths.length; i++) { @@ -92,7 +98,7 @@ implements RemovableDriveMonitor.Callback { @Override protected Collection<File> findFilesByName(String filename) { - List<File> matches = new ArrayList<File>(); + List<File> matches = new ArrayList<>(); try { for (File drive : finder.findRemovableDrives()) { File[] files = drive.listFiles(); @@ -109,6 +115,7 @@ implements RemovableDriveMonitor.Callback { return Collections.unmodifiableList(matches); } + @Override public void driveInserted(File root) { File[] files = root.listFiles(); if (files != null) { @@ -116,6 +123,7 @@ implements RemovableDriveMonitor.Callback { } } + @Override public void exceptionThrown(IOException e) { if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); } diff --git a/briar-desktop/src/org/briarproject/plugins/modem/ModemPlugin.java b/briar-desktop/src/org/briarproject/plugins/modem/ModemPlugin.java index 10a68aa56f..ce2d2d57e7 100644 --- a/briar-desktop/src/org/briarproject/plugins/modem/ModemPlugin.java +++ b/briar-desktop/src/org/briarproject/plugins/modem/ModemPlugin.java @@ -16,6 +16,7 @@ import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.util.Collection; +import java.util.concurrent.atomic.AtomicBoolean; import java.util.logging.Logger; import static java.util.logging.Level.INFO; @@ -32,6 +33,7 @@ class ModemPlugin implements DuplexPlugin, Modem.Callback { private final SerialPortList serialPortList; private final DuplexPluginCallback callback; private final int maxLatency; + private final AtomicBoolean used = new AtomicBoolean(false); private volatile boolean running = false; private volatile Modem modem = null; @@ -44,20 +46,25 @@ class ModemPlugin implements DuplexPlugin, Modem.Callback { this.maxLatency = maxLatency; } + @Override public TransportId getId() { return ID; } + @Override public int getMaxLatency() { return maxLatency; } + @Override public int getMaxIdleTime() { // FIXME: Do we need keepalives for this transport? return Integer.MAX_VALUE; } + @Override public boolean start() { + if (used.getAndSet(true)) throw new IllegalStateException(); for (String portName : serialPortList.getPortNames()) { if (LOG.isLoggable(INFO)) LOG.info("Trying to initialise modem on " + portName); @@ -75,6 +82,7 @@ class ModemPlugin implements DuplexPlugin, Modem.Callback { return false; } + @Override public void stop() { running = false; if (modem != null) { @@ -86,18 +94,22 @@ class ModemPlugin implements DuplexPlugin, Modem.Callback { } } + @Override public boolean isRunning() { return running; } + @Override public boolean shouldPoll() { return false; } + @Override public int getPollingInterval() { throw new UnsupportedOperationException(); } + @Override public void poll(Collection<ContactId> connected) { throw new UnsupportedOperationException(); } @@ -121,6 +133,7 @@ class ModemPlugin implements DuplexPlugin, Modem.Callback { return false; } + @Override public DuplexTransportConnection createConnection(ContactId c) { if (!running) return null; // Get the ISO 3166 code for the caller's country @@ -148,29 +161,34 @@ class ModemPlugin implements DuplexPlugin, Modem.Callback { return new ModemTransportConnection(); } + @Override public boolean supportsInvitations() { return false; } + @Override public DuplexTransportConnection createInvitationConnection(PseudoRandom r, long timeout, boolean alice) { throw new UnsupportedOperationException(); } + @Override public boolean supportsKeyAgreement() { return false; } - public KeyAgreementListener createKeyAgreementListener( - byte[] commitment) { + @Override + public KeyAgreementListener createKeyAgreementListener(byte[] commitment) { throw new UnsupportedOperationException(); } + @Override public DuplexTransportConnection createKeyAgreementConnection( byte[] commitment, TransportDescriptor d, long timeout) { throw new UnsupportedOperationException(); } + @Override public void incomingCallConnected() { LOG.info("Incoming call connected"); callback.incomingConnectionCreated(new ModemTransportConnection()); -- GitLab