Bug 1038645: Asynchronous Bluetooth Handsfree connection handling (under bluetooth2/), r=btian

This commit is contained in:
Thomas Zimmermann 2014-07-22 13:53:28 +02:00
parent 7d9b6e07cc
commit 0d80c39c22
4 changed files with 140 additions and 34 deletions

View File

@ -644,28 +644,52 @@ BluetoothHandsfreeInterface::Cleanup(BluetoothHandsfreeResultHandler* aRes)
/* Connect / Disconnect */
bt_status_t
BluetoothHandsfreeInterface::Connect(bt_bdaddr_t* aBdAddr)
void
BluetoothHandsfreeInterface::Connect(bt_bdaddr_t* aBdAddr,
BluetoothHandsfreeResultHandler* aRes)
{
return mInterface->connect(aBdAddr);
bt_status_t status = mInterface->connect(aBdAddr);
if (aRes) {
DispatchBluetoothHandsfreeResult(
aRes, &BluetoothHandsfreeResultHandler::Connect, status);
}
}
bt_status_t
BluetoothHandsfreeInterface::Disconnect(bt_bdaddr_t* aBdAddr)
void
BluetoothHandsfreeInterface::Disconnect(bt_bdaddr_t* aBdAddr,
BluetoothHandsfreeResultHandler* aRes)
{
return mInterface->disconnect(aBdAddr);
bt_status_t status = mInterface->disconnect(aBdAddr);
if (aRes) {
DispatchBluetoothHandsfreeResult(
aRes, &BluetoothHandsfreeResultHandler::Disconnect, status);
}
}
bt_status_t
BluetoothHandsfreeInterface::ConnectAudio(bt_bdaddr_t* aBdAddr)
void
BluetoothHandsfreeInterface::ConnectAudio(
bt_bdaddr_t* aBdAddr, BluetoothHandsfreeResultHandler* aRes)
{
return mInterface->connect_audio(aBdAddr);
bt_status_t status = mInterface->connect_audio(aBdAddr);
if (aRes) {
DispatchBluetoothHandsfreeResult(
aRes, &BluetoothHandsfreeResultHandler::ConnectAudio, status);
}
}
bt_status_t
BluetoothHandsfreeInterface::DisconnectAudio(bt_bdaddr_t* aBdAddr)
void
BluetoothHandsfreeInterface::DisconnectAudio(
bt_bdaddr_t* aBdAddr, BluetoothHandsfreeResultHandler* aRes)
{
return mInterface->disconnect_audio(aBdAddr);
bt_status_t status = mInterface->disconnect_audio(aBdAddr);
if (aRes) {
DispatchBluetoothHandsfreeResult(
aRes, &BluetoothHandsfreeResultHandler::DisconnectAudio, status);
}
}
/* Voice Recognition */

View File

@ -118,10 +118,14 @@ public:
/* Connect / Disconnect */
bt_status_t Connect(bt_bdaddr_t* aBdAddr);
bt_status_t Disconnect(bt_bdaddr_t* aBdAddr);
bt_status_t ConnectAudio(bt_bdaddr_t* aBdAddr);
bt_status_t DisconnectAudio(bt_bdaddr_t* aBdAddr);
void Connect(bt_bdaddr_t* aBdAddr,
BluetoothHandsfreeResultHandler* aRes);
void Disconnect(bt_bdaddr_t* aBdAddr,
BluetoothHandsfreeResultHandler* aRes);
void ConnectAudio(bt_bdaddr_t* aBdAddr,
BluetoothHandsfreeResultHandler* aRes);
void DisconnectAudio(bt_bdaddr_t* aBdAddr,
BluetoothHandsfreeResultHandler* aRes);
/* Voice Recognition */

View File

@ -1418,6 +1418,17 @@ BluetoothHfpManager::ToggleCalls()
nsITelephonyService::CALL_STATE_CONNECTED;
}
class ConnectAudioResultHandler MOZ_FINAL
: public BluetoothHandsfreeResultHandler
{
public:
void OnError(bt_status_t aStatus) MOZ_OVERRIDE
{
BT_WARNING("BluetoothHandsfreeInterface::ConnectAudio failed: %d",
(int)aStatus);
}
};
bool
BluetoothHfpManager::ConnectSco()
{
@ -1429,12 +1440,23 @@ BluetoothHfpManager::ConnectSco()
bt_bdaddr_t deviceBdAddress;
StringToBdAddressType(mDeviceAddress, &deviceBdAddress);
NS_ENSURE_TRUE(BT_STATUS_SUCCESS ==
sBluetoothHfpInterface->ConnectAudio(&deviceBdAddress), false);
sBluetoothHfpInterface->ConnectAudio(&deviceBdAddress,
new ConnectAudioResultHandler());
return true;
}
class DisconnectAudioResultHandler MOZ_FINAL
: public BluetoothHandsfreeResultHandler
{
public:
void OnError(bt_status_t aStatus) MOZ_OVERRIDE
{
BT_WARNING("BluetoothHandsfreeInterface::DisconnectAudio failed: %d",
(int)aStatus);
}
};
bool
BluetoothHfpManager::DisconnectSco()
{
@ -1443,8 +1465,8 @@ BluetoothHfpManager::DisconnectSco()
bt_bdaddr_t deviceBdAddress;
StringToBdAddressType(mDeviceAddress, &deviceBdAddress);
NS_ENSURE_TRUE(BT_STATUS_SUCCESS ==
sBluetoothHfpInterface->DisconnectAudio(&deviceBdAddress), false);
sBluetoothHfpInterface->DisconnectAudio(&deviceBdAddress,
new DisconnectAudioResultHandler());
return true;
}
@ -1461,6 +1483,37 @@ BluetoothHfpManager::IsConnected()
return (mConnectionState == BTHF_CONNECTION_STATE_SLC_CONNECTED);
}
void
BluetoothHfpManager::OnConnectError()
{
MOZ_ASSERT(NS_IsMainThread());
mController->NotifyCompletion(NS_LITERAL_STRING(ERR_CONNECTION_FAILED));
mController = nullptr;
mDeviceAddress.Truncate();
}
class ConnectResultHandler MOZ_FINAL : public BluetoothHandsfreeResultHandler
{
public:
ConnectResultHandler(BluetoothHfpManager* aHfpManager)
: mHfpManager(aHfpManager)
{
MOZ_ASSERT(mHfpManager);
}
void OnError(bt_status_t aStatus) MOZ_OVERRIDE
{
BT_WARNING("BluetoothHandsfreeInterface::Connect failed: %d",
(int)aStatus);
mHfpManager->OnConnectError();
}
private:
BluetoothHfpManager* mHfpManager;
};
void
BluetoothHfpManager::Connect(const nsAString& aDeviceAddress,
BluetoothProfileController* aController)
@ -1482,17 +1535,42 @@ BluetoothHfpManager::Connect(const nsAString& aDeviceAddress,
bt_bdaddr_t deviceBdAddress;
StringToBdAddressType(aDeviceAddress, &deviceBdAddress);
bt_status_t result = sBluetoothHfpInterface->Connect(&deviceBdAddress);
if (BT_STATUS_SUCCESS != result) {
BT_LOGR("Failed to connect: %x", result);
aController->NotifyCompletion(NS_LITERAL_STRING(ERR_CONNECTION_FAILED));
return;
}
mDeviceAddress = aDeviceAddress;
mController = aController;
sBluetoothHfpInterface->Connect(&deviceBdAddress,
new ConnectResultHandler(this));
}
void
BluetoothHfpManager::OnDisconnectError()
{
MOZ_ASSERT(NS_IsMainThread());
mController->NotifyCompletion(NS_LITERAL_STRING(ERR_CONNECTION_FAILED));
}
class DisconnectResultHandler MOZ_FINAL : public BluetoothHandsfreeResultHandler
{
public:
DisconnectResultHandler(BluetoothHfpManager* aHfpManager)
: mHfpManager(aHfpManager)
{
MOZ_ASSERT(mHfpManager);
}
void OnError(bt_status_t aStatus) MOZ_OVERRIDE
{
BT_WARNING("BluetoothHandsfreeInterface::Disconnect failed: %d",
(int)aStatus);
mHfpManager->OnDisconnectError();
}
private:
BluetoothHfpManager* mHfpManager;
};
void
BluetoothHfpManager::Disconnect(BluetoothProfileController* aController)
{
@ -1508,14 +1586,10 @@ BluetoothHfpManager::Disconnect(BluetoothProfileController* aController)
bt_bdaddr_t deviceBdAddress;
StringToBdAddressType(mDeviceAddress, &deviceBdAddress);
bt_status_t result = sBluetoothHfpInterface->Disconnect(&deviceBdAddress);
if (BT_STATUS_SUCCESS != result) {
BT_LOGR("Failed to disconnect: %x", result);
aController->NotifyCompletion(NS_LITERAL_STRING(ERR_DISCONNECTION_FAILED));
return;
}
mController = aController;
sBluetoothHfpInterface->Disconnect(&deviceBdAddress,
new DisconnectResultHandler(this));
}
void

View File

@ -75,6 +75,10 @@ class BluetoothHfpManager : public BluetoothHfpManagerBase
{
public:
BT_DECL_HFP_MGR_BASE
void OnConnectError();
void OnDisconnectError();
virtual void GetName(nsACString& aName)
{
aName.AssignLiteral("HFP/HSP");