summaryrefslogtreecommitdiffstats
path: root/device/usb
diff options
context:
space:
mode:
Diffstat (limited to 'device/usb')
-rw-r--r--device/usb/mock_usb_device_handle.h3
-rw-r--r--device/usb/usb_device_handle.h3
-rw-r--r--device/usb/usb_device_handle_impl.cc62
-rw-r--r--device/usb/usb_device_handle_impl.h6
-rw-r--r--device/usb/usb_device_handle_unittest.cc12
5 files changed, 63 insertions, 23 deletions
diff --git a/device/usb/mock_usb_device_handle.h b/device/usb/mock_usb_device_handle.h
index 26e6190..2cacafb 100644
--- a/device/usb/mock_usb_device_handle.h
+++ b/device/usb/mock_usb_device_handle.h
@@ -26,7 +26,8 @@ class MockUsbDeviceHandle : public UsbDeviceHandle {
void(int configuration_value, const ResultCallback& callback));
MOCK_METHOD2(ClaimInterface,
void(int interface_number, const ResultCallback& callback));
- MOCK_METHOD1(ReleaseInterface, bool(int interface_number));
+ MOCK_METHOD2(ReleaseInterface,
+ void(int interface_number, const ResultCallback& callback));
MOCK_METHOD3(SetInterfaceAlternateSetting,
void(int interface_number,
int alternate_setting,
diff --git a/device/usb/usb_device_handle.h b/device/usb/usb_device_handle.h
index b206cf1..31f0ec5 100644
--- a/device/usb/usb_device_handle.h
+++ b/device/usb/usb_device_handle.h
@@ -70,7 +70,8 @@ class UsbDeviceHandle : public base::RefCountedThreadSafe<UsbDeviceHandle> {
const ResultCallback& callback) = 0;
virtual void ClaimInterface(int interface_number,
const ResultCallback& callback) = 0;
- virtual bool ReleaseInterface(int interface_number) = 0;
+ virtual void ReleaseInterface(int interface_number,
+ const ResultCallback& callback) = 0;
virtual void SetInterfaceAlternateSetting(int interface_number,
int alternate_setting,
const ResultCallback& callback) = 0;
diff --git a/device/usb/usb_device_handle_impl.cc b/device/usb/usb_device_handle_impl.cc
index fa4c085..16f343e 100644
--- a/device/usb/usb_device_handle_impl.cc
+++ b/device/usb/usb_device_handle_impl.cc
@@ -147,13 +147,19 @@ class UsbDeviceHandleImpl::InterfaceClaimer
: public base::RefCountedThreadSafe<UsbDeviceHandleImpl::InterfaceClaimer> {
public:
InterfaceClaimer(scoped_refptr<UsbDeviceHandleImpl> handle,
- int interface_number);
+ int interface_number,
+ scoped_refptr<base::SingleThreadTaskRunner> task_runner);
+ int interface_number() const { return interface_number_; }
int alternate_setting() const { return alternate_setting_; }
void set_alternate_setting(const int alternate_setting) {
alternate_setting_ = alternate_setting;
}
+ void set_release_callback(const ResultCallback& callback) {
+ release_callback_ = callback;
+ }
+
private:
friend class base::RefCountedThreadSafe<InterfaceClaimer>;
~InterfaceClaimer();
@@ -161,19 +167,33 @@ class UsbDeviceHandleImpl::InterfaceClaimer
const scoped_refptr<UsbDeviceHandleImpl> handle_;
const int interface_number_;
int alternate_setting_;
+ const scoped_refptr<base::SingleThreadTaskRunner> task_runner_;
+ ResultCallback release_callback_;
+ base::ThreadChecker thread_checker_;
DISALLOW_COPY_AND_ASSIGN(InterfaceClaimer);
};
UsbDeviceHandleImpl::InterfaceClaimer::InterfaceClaimer(
scoped_refptr<UsbDeviceHandleImpl> handle,
- int interface_number)
+ int interface_number,
+ scoped_refptr<base::SingleThreadTaskRunner> task_runner)
: handle_(handle),
interface_number_(interface_number),
- alternate_setting_(0) {}
+ alternate_setting_(0),
+ task_runner_(task_runner) {}
UsbDeviceHandleImpl::InterfaceClaimer::~InterfaceClaimer() {
- libusb_release_interface(handle_->handle(), interface_number_);
+ DCHECK(thread_checker_.CalledOnValidThread());
+ int rc = libusb_release_interface(handle_->handle(), interface_number_);
+ if (rc != LIBUSB_SUCCESS) {
+ USB_LOG(DEBUG) << "Failed to release interface: "
+ << ConvertPlatformUsbErrorToString(rc);
+ }
+ if (!release_callback_.is_null()) {
+ task_runner_->PostTask(FROM_HERE,
+ base::Bind(release_callback_, rc == LIBUSB_SUCCESS));
+ }
}
// This inner class owns the underlying libusb_transfer and may outlast
@@ -581,12 +601,13 @@ void UsbDeviceHandleImpl::ClaimInterface(int interface_number,
interface_number, callback));
}
-bool UsbDeviceHandleImpl::ReleaseInterface(int interface_number) {
+void UsbDeviceHandleImpl::ReleaseInterface(int interface_number,
+ const ResultCallback& callback) {
DCHECK(thread_checker_.CalledOnValidThread());
- if (!device_)
- return false;
- if (!ContainsKey(claimed_interfaces_, interface_number))
- return false;
+ if (!device_ || !ContainsKey(claimed_interfaces_, interface_number)) {
+ task_runner_->PostTask(FROM_HERE, base::Bind(callback, false));
+ return;
+ }
// Cancel all the transfers on that interface.
InterfaceClaimer* interface_claimer =
@@ -596,10 +617,12 @@ bool UsbDeviceHandleImpl::ReleaseInterface(int interface_number) {
transfer->Cancel();
}
}
+ interface_claimer->AddRef();
+ interface_claimer->set_release_callback(callback);
+ blocking_task_runner_->ReleaseSoon(FROM_HERE, interface_claimer);
claimed_interfaces_.erase(interface_number);
RefreshEndpointMap();
- return true;
}
void UsbDeviceHandleImpl::SetInterfaceAlternateSetting(
@@ -790,25 +813,28 @@ void UsbDeviceHandleImpl::ClaimInterfaceOnBlockingThread(
int interface_number,
const ResultCallback& callback) {
int rv = libusb_claim_interface(handle_, interface_number);
- if (rv != LIBUSB_SUCCESS) {
+ scoped_refptr<InterfaceClaimer> interface_claimer;
+ if (rv == LIBUSB_SUCCESS) {
+ interface_claimer =
+ new InterfaceClaimer(this, interface_number, task_runner_);
+ } else {
USB_LOG(EVENT) << "Failed to claim interface: "
<< ConvertPlatformUsbErrorToString(rv);
}
task_runner_->PostTask(
FROM_HERE, base::Bind(&UsbDeviceHandleImpl::ClaimInterfaceComplete, this,
- interface_number, rv == LIBUSB_SUCCESS, callback));
+ interface_claimer, callback));
}
void UsbDeviceHandleImpl::ClaimInterfaceComplete(
- int interface_number,
- bool success,
+ scoped_refptr<InterfaceClaimer> interface_claimer,
const ResultCallback& callback) {
- if (success) {
- claimed_interfaces_[interface_number] =
- new InterfaceClaimer(this, interface_number);
+ if (interface_claimer) {
+ claimed_interfaces_[interface_claimer->interface_number()] =
+ interface_claimer;
RefreshEndpointMap();
}
- callback.Run(success);
+ callback.Run(interface_claimer);
}
void UsbDeviceHandleImpl::SetInterfaceAlternateSettingOnBlockingThread(
diff --git a/device/usb/usb_device_handle_impl.h b/device/usb/usb_device_handle_impl.h
index ce2daff..0cb2311 100644
--- a/device/usb/usb_device_handle_impl.h
+++ b/device/usb/usb_device_handle_impl.h
@@ -53,7 +53,8 @@ class UsbDeviceHandleImpl : public UsbDeviceHandle {
const ResultCallback& callback) override;
void ClaimInterface(int interface_number,
const ResultCallback& callback) override;
- bool ReleaseInterface(int interface_number) override;
+ void ReleaseInterface(int interface_number,
+ const ResultCallback& callback) override;
void SetInterfaceAlternateSetting(int interface_number,
int alternate_setting,
const ResultCallback& callback) override;
@@ -116,8 +117,7 @@ class UsbDeviceHandleImpl : public UsbDeviceHandle {
void SetConfigurationComplete(bool success, const ResultCallback& callback);
void ClaimInterfaceOnBlockingThread(int interface_number,
const ResultCallback& callback);
- void ClaimInterfaceComplete(int interface_number,
- bool success,
+ void ClaimInterfaceComplete(scoped_refptr<InterfaceClaimer> interface_claimer,
const ResultCallback& callback);
void SetInterfaceAlternateSettingOnBlockingThread(
int interface_number,
diff --git a/device/usb/usb_device_handle_unittest.cc b/device/usb/usb_device_handle_unittest.cc
index 1c116fd..5fac40a 100644
--- a/device/usb/usb_device_handle_unittest.cc
+++ b/device/usb/usb_device_handle_unittest.cc
@@ -164,6 +164,10 @@ TEST_F(UsbDeviceHandleTest, InterruptTransfer) {
<< "Mismatch at index " << i << ".";
}
+ TestResultCallback release_interface;
+ handle->ReleaseInterface(0, release_interface.callback());
+ ASSERT_TRUE(release_interface.WaitForResult());
+
handle->Close();
}
@@ -219,6 +223,10 @@ TEST_F(UsbDeviceHandleTest, BulkTransfer) {
<< "Mismatch at index " << i << ".";
}
+ TestResultCallback release_interface;
+ handle->ReleaseInterface(1, release_interface.callback());
+ ASSERT_TRUE(release_interface.WaitForResult());
+
handle->Close();
}
@@ -245,6 +253,10 @@ TEST_F(UsbDeviceHandleTest, SetInterfaceAlternateSetting) {
handle->SetInterfaceAlternateSetting(2, 1, set_interface.callback());
ASSERT_TRUE(set_interface.WaitForResult());
+ TestResultCallback release_interface;
+ handle->ReleaseInterface(2, release_interface.callback());
+ ASSERT_TRUE(release_interface.WaitForResult());
+
handle->Close();
}