Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(8261)

Unified Diff: components/proximity_auth/bluetooth_connection_finder.cc

Issue 656963002: Revert of Revert of [Easy Unlock] Port the BluetoothConnectionFinder class to native code. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 6 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: components/proximity_auth/bluetooth_connection_finder.cc
diff --git a/components/proximity_auth/bluetooth_connection_finder.cc b/components/proximity_auth/bluetooth_connection_finder.cc
new file mode 100644
index 0000000000000000000000000000000000000000..3fe6567c174a0e76dc338ba8c5da75c20d4e7808
--- /dev/null
+++ b/components/proximity_auth/bluetooth_connection_finder.cc
@@ -0,0 +1,145 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "components/proximity_auth/bluetooth_connection_finder.h"
+
+#include "base/bind.h"
+#include "base/location.h"
+#include "base/logging.h"
+#include "base/message_loop/message_loop_proxy.h"
+#include "components/proximity_auth/bluetooth_connection.h"
+#include "device/bluetooth/bluetooth_adapter_factory.h"
+
+using device::BluetoothAdapter;
+
+namespace proximity_auth {
+
+BluetoothConnectionFinder::BluetoothConnectionFinder(
+ const RemoteDevice& remote_device,
+ const device::BluetoothUUID& uuid,
+ const base::TimeDelta& polling_interval)
+ : remote_device_(remote_device),
+ uuid_(uuid),
+ polling_interval_(polling_interval),
+ has_delayed_poll_scheduled_(false),
+ weak_ptr_factory_(this) {
+}
+
+BluetoothConnectionFinder::~BluetoothConnectionFinder() {
+ UnregisterAsObserver();
+}
+
+void BluetoothConnectionFinder::Find(
+ const ConnectionCallback& connection_callback) {
+ if (!device::BluetoothAdapterFactory::IsBluetoothAdapterAvailable()) {
+ VLOG(1) << "[BCF] Bluetooth is unsupported on this platform. Aborting.";
+ return;
+ }
+
+ DCHECK(start_time_.is_null());
+ VLOG(1) << "[BCF] Finding Bluetooth connection...";
+
+ start_time_ = base::TimeTicks::Now();
+ connection_callback_ = connection_callback;
+
+ device::BluetoothAdapterFactory::GetAdapter(
+ base::Bind(&BluetoothConnectionFinder::OnAdapterInitialized,
+ weak_ptr_factory_.GetWeakPtr()));
+}
+
+scoped_ptr<Connection> BluetoothConnectionFinder::CreateConnection() {
+ return scoped_ptr<Connection>(new BluetoothConnection(remote_device_, uuid_));
+}
+
+bool BluetoothConnectionFinder::IsReadyToPoll() {
+ bool is_adapter_available =
+ adapter_.get() && adapter_->IsPresent() && adapter_->IsPowered();
+ VLOG(1) << "[BCF] Readiness: adapter="
+ << (is_adapter_available ? "available" : "unavailable");
+ return is_adapter_available;
+}
+
+void BluetoothConnectionFinder::PollIfReady() {
+ if (!IsReadyToPoll())
+ return;
+
+ // If there is a pending task to poll at a later time, the time requisite
+ // timeout has not yet elapsed since the previous polling attempt. In that
+ // case, keep waiting until the delayed task comes in.
+ if (has_delayed_poll_scheduled_)
+ return;
+
+ // If the |connection_| exists, wait for it to connect or fail prior to
+ // polling again.
+ if (connection_)
+ return;
+
+ VLOG(1) << "[BCF] Polling for connection...";
+ connection_ = CreateConnection();
+ connection_->AddObserver(this);
+ connection_->Connect();
+}
+
+void BluetoothConnectionFinder::DelayedPollIfReady() {
+ // Note that there is no longer a pending task, and therefore polling is
+ // permitted.
+ has_delayed_poll_scheduled_ = false;
+ PollIfReady();
+}
+
+void BluetoothConnectionFinder::UnregisterAsObserver() {
+ if (connection_) {
+ connection_->RemoveObserver(this);
+ // The connection is about to be released or destroyed, so no need to clear
+ // it explicitly here.
+ }
+
+ if (adapter_.get()) {
+ adapter_->RemoveObserver(this);
+ adapter_ = NULL;
+ }
+}
+
+void BluetoothConnectionFinder::OnAdapterInitialized(
+ scoped_refptr<BluetoothAdapter> adapter) {
+ adapter_ = adapter;
+ adapter_->AddObserver(this);
+ PollIfReady();
+}
+
+void BluetoothConnectionFinder::AdapterPresentChanged(BluetoothAdapter* adapter,
+ bool present) {
+ PollIfReady();
+}
+
+void BluetoothConnectionFinder::AdapterPoweredChanged(BluetoothAdapter* adapter,
+ bool powered) {
+ PollIfReady();
+}
+
+void BluetoothConnectionFinder::OnConnectionStatusChanged(
+ const Connection& connection,
+ Connection::Status old_status,
+ Connection::Status new_status) {
+ DCHECK_EQ(&connection, connection_.get());
+
+ if (connection_->IsConnected()) {
+ base::TimeDelta elapsed = base::TimeTicks::Now() - start_time_;
+ VLOG(1) << "[BCF] Connection found! Elapsed Time: "
+ << elapsed.InMilliseconds() << "ms.";
+ UnregisterAsObserver();
+ connection_callback_.Run(connection_.Pass());
+ } else if (old_status == Connection::IN_PROGRESS) {
+ VLOG(1) << "[BCF] Connection failed! Scheduling another polling iteration.";
+ connection_.reset();
+ has_delayed_poll_scheduled_ = true;
+ base::MessageLoopProxy::current()->PostDelayedTask(
+ FROM_HERE,
+ base::Bind(&BluetoothConnectionFinder::DelayedPollIfReady,
+ weak_ptr_factory_.GetWeakPtr()),
+ polling_interval_);
+ }
+}
+
+} // namespace proximity_auth

Powered by Google App Engine
This is Rietveld 408576698