add enhanced logic in Bluetooth plugin
authorYoungjae Shin <yj99.shin@samsung.com>
Tue, 19 Nov 2019 06:04:37 +0000 (15:04 +0900)
committerYoungjae Shin <yj99.shin@samsung.com>
Thu, 19 Mar 2020 04:30:37 +0000 (13:30 +0900)
bluetooth/BtAction.cpp
bluetooth/BtActionAudioConnect.cpp
bluetooth/BtActionAudioConnect.h
bluetooth/BtActionPower.cpp
bluetooth/BtActionPower.h
bluetooth/BtPlugin.cpp
bluetooth/tizen_bt_rule.xml
unittests/mdsp_test_bt.cpp
wifi/WifiActionPower.h

index ae784be..43539eb 100644 (file)
@@ -22,9 +22,8 @@ BtAction::BtAction(const std::string &name)
        : PluginAction(name)
 {
        int btRet = bt_initialize();
-       if (BT_ERROR_NONE != btRet) {
+       if (BT_ERROR_NONE != btRet)
                ERR("bt_initialize() Fail(%d)", btRet);
-       }
 }
 
 BtAction::~BtAction()
index 57fe412..cce118d 100644 (file)
@@ -15,7 +15,6 @@
  */
 #include "BtActionAudioConnect.h"
 
-#include <algorithm>
 #include <modes_errors.h>
 #include "plugin-log.h"
 
@@ -24,23 +23,99 @@ MODES_NAMESPACE_USE;
 const std::string BtActionAudioConnect::NAME = "audioConnect";
 
 BtActionAudioConnect::BtActionAudioConnect()
-       : BtAction(NAME)
+       : BtAction(NAME), cb(NULL), cbData(NULL)
 {
        bt_audio_initialize();
-       int btRet = bt_audio_set_connection_state_changed_cb(connectionStateChangedCb, this);
-       if (BT_ERROR_NONE != btRet) {
-               ERR("bt_device_set_bond_created_cb failed[%d]", btRet);
+}
+
+BtActionAudioConnect::~BtActionAudioConnect()
+{
+       bt_audio_deinitialize();
+}
+
+int BtActionAudioConnect::set(const std::string &val)
+{
+       if (!isBtAdapterEnabled()) {
+               ERR("BT is disabled");
+               return MODES_ERROR_SYSTEM;
+       }
+
+       requestVal = val;
+
+       bt_device_info_s *devInfo;
+       int ret = bt_adapter_get_bonded_device_info(val.c_str(), &devInfo);
+       if (BT_ERROR_NONE == ret) {
+               printBtDeviceInfo(devInfo);
+               bt_major_device_class_e devClass = devInfo->bt_class.major_device_class;
+               bt_adapter_free_device_info(devInfo);
+
+               return btAudioConnect(devClass, val.c_str());
+       } else if (BT_ERROR_REMOTE_DEVICE_NOT_BONDED == ret) {
+               DBG("BT device(%s) is not bonded", val.c_str());
+       } else {
+               ERR("bt_adapter_get_bonded_device_info() Fail(%s)", get_error_message(ret));
+               return MODES_ERROR_SYSTEM;
+       }
+
+       ret = bt_device_set_bond_created_cb(btDeviceBondCreatedCb, this);
+       if (ret != BT_ERROR_NONE) {
+               ERR("bt_device_set_bond_created_cb(%s) Fail(%s)", val.c_str(), get_error_message(ret));
+               return MODES_ERROR_SYSTEM;
        }
+
+       ret = bt_device_create_bond(val.c_str());
+       if (ret != BT_ERROR_NONE) {
+               ERR("bt_device_create_bond(%s) Fail(%s)", val.c_str(), get_error_message(ret));
+               return MODES_ERROR_SYSTEM;
+       }
+
+       return MODES_ERROR_NONE;
 }
 
-void BtActionAudioConnect::connectionStateChangedCb(int result, bool connected,
-       const char *remote_address, bt_audio_profile_type_e type, void *user_data)
+void BtActionAudioConnect::undo()
 {
-       INFO("remote_address: %s", remote_address);
+       int ret = bt_audio_disconnect(requestVal.c_str(), BT_AUDIO_PROFILE_TYPE_ALL);
+       if (BT_ERROR_NONE != ret)
+               ERR("bt_audio_disconnect(%s) Fail(%s)", requestVal.c_str(), get_error_message(ret));
+}
 
-       if (BT_ERROR_NONE != result) {
-               ERR("Connection_state_changed_cb() Fail(%d)", result);
+std::string BtActionAudioConnect::serialize()
+{
+       return requestVal;
+}
+
+int BtActionAudioConnect::parse(const std::string &archive)
+{
+       requestVal = archive;
+       return MODES_ERROR_NONE;
+}
+
+int BtActionAudioConnect::setChangedCallback(valueChangedCB callback, void * userData)
+{
+       RETV_IF(NULL == callback, MODES_ERROR_INVALID_PARAMETER);
+
+       int ret = bt_audio_set_connection_state_changed_cb(connectionStateChangedCb, userData);
+       if (BT_ERROR_NONE != ret) {
+               ERR("bt_audio_set_connection_state_changed_cb() Fail(%s)", get_error_message(ret));
+               return MODES_ERROR_SYSTEM;
        }
+
+       cb = callback;
+       cbData = userData;
+
+       return MODES_ERROR_NONE;
+}
+
+void BtActionAudioConnect::unSetChangedCallback(valueChangedCB callback, void * userData)
+{
+       RET_IF(NULL == callback);
+
+       int ret = bt_audio_unset_connection_state_changed_cb();
+       if (BT_ERROR_NONE != ret)
+               ERR("bt_audio_unset_connection_state_changed_cb() Fail(%s)", get_error_message(ret));
+
+       cb = NULL;
+       cbData = NULL;
 }
 
 bool BtActionAudioConnect::isBtAdapterEnabled()
@@ -58,118 +133,76 @@ bool BtActionAudioConnect::isBtAdapterEnabled()
                return true;
 }
 
-void BtActionAudioConnect::printBtDeviceInfo(bt_device_info_s *deviceInfo)
+void BtActionAudioConnect::connectionStateChangedCb(int result, bool connected,
+       const char *address, bt_audio_profile_type_e type, void *userData)
 {
-       if (deviceInfo == NULL) {
-               ERR("BT device info is NULL");
+       BtActionAudioConnect *action = (BtActionAudioConnect*)userData;
+
+       INFO("BT device(%s) connection(%d)", address, connected);
+       if (BT_ERROR_NONE != result) {
+               ERR("connectionStateChangedCb() Fail(%d)", result);
                return;
        }
 
-       DBG("BT Bonded Device Info ========================================");
-       DBG("remote_address    : [%s]", deviceInfo->remote_address);
-       DBG("remote_name       : [%s]", deviceInfo->remote_name);
-       DBG("major_class       : [%x]", deviceInfo->bt_class.major_device_class);
-       DBG("major_class       : [%x]", deviceInfo->bt_class.minor_device_class);
-       DBG("service_uuid      : [%s]", *(deviceInfo->service_uuid));
-       DBG("service_count     : [%d]", deviceInfo->service_count);
-       DBG("is_bonded         : [%d]", deviceInfo->is_bonded);
-       DBG("is_connected      : [%d]", deviceInfo->is_connected);
-       DBG("is_authorized     : [%d]", deviceInfo->is_authorized);
-       DBG("manufacturer_data : [%s]", deviceInfo->manufacturer_data);
-       DBG("==============================================================");
+       if (false == connected && action->requestVal == address)
+               action->cb(action->cbData);
 }
 
-bool BtActionAudioConnect::btAdapterBondedDeviceCb(bt_device_info_s *device_info, void *user_data)
+void BtActionAudioConnect::btDeviceBondCreatedCb(int result, bt_device_info_s *devInfo, void *userData)
 {
-       printBtDeviceInfo(device_info);
-       return true;
-}
-
-void BtActionAudioConnect::btDeviceBondCreatedCb(int result, bt_device_info_s *device_info, void *user_data)
-{
-       if (result != BT_ERROR_NONE) {
-               ERR("bt_device_bond_created_cb error [%d]!", result);
-               return;
-       }
-
-       printBtDeviceInfo(device_info);
-
-       if (device_info->is_connected) {
-               DBG("Already connected [%s][%s]", device_info->remote_name, device_info->remote_address);
+       if (BT_ERROR_NONE != result) {
+               ERR("btDeviceBondCreatedCb Fail(%s)", get_error_message(result));
                return;
        }
 
-       if (device_info->bt_class.major_device_class != BT_MAJOR_DEVICE_CLASS_AUDIO_VIDEO) {
-               ERR("BT device [%s][%s] is not AUDIO MAJOR Class", device_info->remote_name, device_info->remote_address);
+       BtActionAudioConnect *action = (BtActionAudioConnect*)userData;
+       printBtDeviceInfo(devInfo);
+       if (action->requestVal != devInfo->remote_address) {
+               ERR("Unknown BT device(%s)", devInfo->remote_address);
                return;
+       } else {
+               bt_device_unset_bond_created_cb();
        }
 
-       int btRet = bt_audio_connect(device_info->remote_address, BT_AUDIO_PROFILE_TYPE_ALL);
-       if (btRet != BT_ERROR_NONE) {
-               ERR("bt_audio_connect failed! [%s][%s]", device_info->remote_name, device_info->remote_address);
+       int ret = btAudioConnect(devInfo->bt_class.major_device_class, devInfo->remote_address);
+       if (BT_ERROR_NONE != ret) {
+               ERR("btAudioConnect() Fail(%d)", ret);
                return;
        }
 
-       DBG("BtActionAudioConnect Success! [%s][%s]", device_info->remote_name, device_info->remote_address);
+       DBG("BtActionAudioConnect(%s, %s) Success!", devInfo->remote_name, devInfo->remote_address);
 }
 
-int BtActionAudioConnect::set(const std::string &val)
+int BtActionAudioConnect::btAudioConnect(bt_major_device_class_e devClass, const char *address)
 {
-       if (!isBtAdapterEnabled()) {
-               ERR("BT is disabled");
-               return MODES_ERROR_SYSTEM;
-       }
-
-#if 0
-       // print current bonded list
-       if (bt_adapter_foreach_bonded_device(bt_adapter_bonded_device_cb, NULL) != BT_ERROR_NONE) {
-               ERR("bt_adapter_foreach_bonded_device() failed");
-               return MODES_ERROR_SYSTEM;
-       }
-#endif
-
-       int btRet;
-
-       btRet = bt_device_set_bond_created_cb(btDeviceBondCreatedCb, NULL);
-       if (btRet != BT_ERROR_NONE) {
-               ERR("bt_device_set_bond_created_cb [%s] failed!", val.c_str());
+       if (BT_MAJOR_DEVICE_CLASS_AUDIO_VIDEO != devClass) {
+               ERR("BT device(%s) is not AUDIO MAJOR Class", address);
                return MODES_ERROR_SYSTEM;
        }
 
-       btRet = bt_device_create_bond(val.c_str());
-       if (btRet != BT_ERROR_NONE) {
-               ERR("bt_device_create_bond [%s] failed!", val.c_str());
+       int ret = bt_audio_connect(address, BT_AUDIO_PROFILE_TYPE_ALL);
+       if (BT_ERROR_NONE != ret) {
+               ERR("bt_audio_connect(%s) Fail(%s)", address, get_error_message(ret));
                return MODES_ERROR_SYSTEM;
        }
 
-       DBG("bt_device_create_bond called!");
        return MODES_ERROR_NONE;
 }
 
-bt_device_info_s *BtActionAudioConnect::getBondedDeviceInfo(const std::string &val)
+void BtActionAudioConnect::printBtDeviceInfo(bt_device_info_s *devInfo)
 {
-       bt_device_info_s *deviceInfo = NULL;
-
-       int btRet = bt_adapter_get_bonded_device_info(val.c_str(), &deviceInfo);
-       if (btRet) {
-               ERR("bt_adapter_get_bonded_device_info() ret[%d] device address[%s]", btRet, val.c_str());
-               return NULL;
-       }
+       RET_IF(devInfo == NULL);
 
-       if (deviceInfo) {
-               printBtDeviceInfo(deviceInfo);
-               char *str = NULL;
-               if (deviceInfo->service_uuid == NULL) {
-                       INFO("No uuids");
-               } else {
-                       for (int i = 0; i < deviceInfo->service_count; i++) {
-                               bt_get_uuid_name(deviceInfo->service_uuid[i], &str);
-                               INFO("[%d / %d] %s (%s)", i, deviceInfo->service_count,
-                                       str ? str : "Unknown", deviceInfo->service_uuid[i]);
-                               str = NULL;
-                       }
-               }
-       }
-
-       return deviceInfo;
+       DBG("BT Bonded Device Info ========================================");
+       DBG("remote_address    : [%s]", devInfo->remote_address);
+       DBG("remote_name       : [%s]", devInfo->remote_name);
+       DBG("major_class       : [%x]", devInfo->bt_class.major_device_class);
+       DBG("major_class       : [%x]", devInfo->bt_class.minor_device_class);
+       DBG("service_uuid      : [%s]", *(devInfo->service_uuid));
+       DBG("service_count     : [%d]", devInfo->service_count);
+       DBG("is_bonded         : [%d]", devInfo->is_bonded);
+       DBG("is_connected      : [%d]", devInfo->is_connected);
+       DBG("is_authorized     : [%d]", devInfo->is_authorized);
+       DBG("manufacturer_data : [%s]", devInfo->manufacturer_data);
+       DBG("==============================================================");
 }
index eee8b1b..ddd4bec 100644 (file)
@@ -24,15 +24,23 @@ class BtActionAudioConnect : public BtAction {
 public:
        static const std::string NAME;
        BtActionAudioConnect();
+       ~BtActionAudioConnect();
 
        int set(const std::string &val) override;
+       void undo() override;
+       std::string serialize() override;
+       int parse(const std::string &archive) override;
+       int setChangedCallback(valueChangedCB callback, void *userData);
+       void unSetChangedCallback(valueChangedCB callback, void *userData);
 private:
        bool isBtAdapterEnabled();
-       bt_device_info_s *getBondedDeviceInfo(const std::string &val);
-       static void printBtDeviceInfo(bt_device_info_s * device_info);
-       static void connectionStateChangedCb(int result, bool connected, const char *remote_address, bt_audio_profile_type_e type, void *user_data);
-       static void btDeviceBondCreatedCb(int result, bt_device_info_s * device_info, void * user_data);
-       static bool btAdapterBondedDeviceCb(bt_device_info_s * device_info, void * user_data);
+       static void connectionStateChangedCb(int result, bool connected, const char *address, bt_audio_profile_type_e type, void *userData);
+       static void btDeviceBondCreatedCb(int result, bt_device_info_s *devInfo, void *userData);
+       static int btAudioConnect(bt_major_device_class_e devClass, const char *address);
+       static void printBtDeviceInfo(bt_device_info_s *devInfo);
+       valueChangedCB cb;
+       void *cbData;
+       std::string requestVal;
 };
 
 MODES_NAMESPACE_END
index 900b639..17b454e 100644 (file)
@@ -17,6 +17,7 @@
 
 #include <sstream>
 #include <modes_errors.h>
+#include <bluetooth.h>
 #include <bluetooth_internal.h>
 #include "plugin-log.h"
 
@@ -26,7 +27,7 @@ MODES_NAMESPACE_USE;
 const std::string BtActionPower::NAME = "power";
 
 BtActionPower::BtActionPower()
-       : BtAction(NAME), undoVal(false)
+       : BtAction(NAME), cb(NULL), cbData(NULL), undoVal(false), requestVal(false)
 {
 }
 
@@ -34,28 +35,29 @@ int BtActionPower::set(bool val)
 {
        if (val) {
                undoVal = false;
-               int btRet = bt_adapter_enable();
-               if (BT_ERROR_NONE != btRet) {
-                       if (BT_ERROR_ALREADY_DONE == btRet) {
+               int ret = bt_adapter_enable();
+               if (BT_ERROR_NONE != ret) {
+                       if (BT_ERROR_ALREADY_DONE == ret) {
                                undoVal = true;
                        } else {
-                               ERR("bt_adapter_enable() Fail(%d)", btRet);
+                               ERR("bt_adapter_enable() Fail(%d)", ret);
                                return MODES_ERROR_SYSTEM;
                        }
                }
        } else {
                undoVal = true;
-               int btRet = bt_adapter_disable();
-               if (BT_ERROR_NONE != btRet) {
-                       if (BT_ERROR_NOT_ENABLED == btRet) {
+               int ret = bt_adapter_disable();
+               if (BT_ERROR_NONE != ret) {
+                       if (BT_ERROR_NOT_ENABLED == ret) {
                                undoVal = false;
                        } else {
-                               ERR("bt_adapter_disable() Fail(%d)", btRet);
+                               ERR("bt_adapter_disable() Fail(%d)", ret);
                                return MODES_ERROR_SYSTEM;
                        }
                }
        }
 
+       requestVal = val;
        INFO("BT power changed to (%s) from (%s)", val ? "On" : "Off", undoVal ? "On" : "Off");
        return MODES_ERROR_NONE;
 }
@@ -80,3 +82,53 @@ int BtActionPower::parse(const std::string &archive)
 
        return MODES_ERROR_NONE;
 }
+
+int BtActionPower::setChangedCallback(valueChangedCB callback, void *userData)
+{
+       RETV_IF(NULL == callback, MODES_ERROR_INVALID_PARAMETER);
+
+       int ret = bt_adapter_set_state_changed_cb(btStateChangedCB, this);
+       if (BT_ERROR_NONE != ret) {
+               ERR("bt_adapter_set_state_changed_cb() Fail(%s)", get_error_message(ret));
+               return MODES_ERROR_SYSTEM;
+       }
+
+       cb = callback;
+       cbData = userData;
+
+       DBG("BtActionPower setChangedCallback() Success");
+       return MODES_ERROR_NONE;
+}
+void BtActionPower::unSetChangedCallback(valueChangedCB callback, void *userData)
+{
+       RET_IF(NULL == callback);
+
+       int ret = bt_adapter_unset_state_changed_cb();
+       if (BT_ERROR_NONE != ret)
+               ERR("bt_adapter_unset_state_changed_cb() Fail(%s)", get_error_message(ret));
+
+       cb = NULL;
+       cbData = NULL;
+
+       DBG("BtActionPower unSetChangedCallback() Success");
+}
+
+void BtActionPower::btStateChangedCB(int result, bt_adapter_state_e state, void *user_data)
+{
+       BtActionPower *action = (BtActionPower*)user_data;
+
+       RET_IF(NULL == user_data);
+
+       bool changedVal = action->requestVal;
+       if (state == BT_ADAPTER_ENABLED)
+               changedVal = true;
+       else if (state == BT_ADAPTER_DISABLED)
+               changedVal = false;
+       else
+               ERR("Unknown state(%d)", state);
+
+       INFO("state:%d", state);
+
+       if (changedVal != action->requestVal)
+               action->cb(action->cbData);
+}
index 8c2762f..c7bda95 100644 (file)
@@ -29,8 +29,14 @@ public:
        void undo() override;
        std::string serialize() override;
        int parse(const std::string & archive) override;
+       int setChangedCallback(valueChangedCB callback, void *userData);
+       void unSetChangedCallback(valueChangedCB callback, void *userData);
 private:
+       static void btStateChangedCB(int result, bt_adapter_state_e state, void *user_data);
+       valueChangedCB cb;
+       void *cbData;
        bool undoVal;
+       bool requestVal;
 };
 
 MODES_NAMESPACE_END
index f3fd2a7..d6bab67 100644 (file)
@@ -27,8 +27,6 @@ public:
        BtPlugin();
        ~BtPlugin();
 
-       int set(const std::string &key, int val, PluginAction **piAction) override;
-       int set(const std::string &key, double val, PluginAction **piAction) override;
        int set(const std::string &key, bool val, PluginAction **piAction) override;
        int set(const std::string &key, const std::string &val, PluginAction **piAction) override;
        void undo(PluginAction *piAction) override;
@@ -56,44 +54,13 @@ BtPlugin::~BtPlugin()
 {
 }
 
-int BtPlugin::set(const std::string &key, int val, PluginAction **piAction)
-{
-       BtAction *action = btFactory.createAction(key);
-       RETVM_IF(nullptr == action, MODES_ERROR_INVALID_PARAMETER, "action(%s) is null", key.c_str());
-
-       DBG("set [%s, %d]", key.c_str(), val);
-
-       int ret = action->set(val);
-       if (piAction)
-               *piAction = action;
-       else
-               btFactory.destroyAction(action);
-
-       return ret;
-}
-
-int BtPlugin::set(const std::string &key, double val, PluginAction **piAction)
-{
-       BtAction *action = btFactory.createAction(key);
-       RETVM_IF(nullptr == action, MODES_ERROR_INVALID_PARAMETER, "action(%s) is null", key.c_str());
-
-       DBG("set [%s, %f]", key.c_str(), val);
-
-       int ret = action->set(val);
-       if (piAction)
-               *piAction = action;
-       else
-               btFactory.destroyAction(action);
-
-       return ret;
-}
-
+//For BtActionPower
 int BtPlugin::set(const std::string &key, bool val, PluginAction **piAction)
 {
        BtAction *action = btFactory.createAction(key);
        RETVM_IF(nullptr == action, MODES_ERROR_INVALID_PARAMETER, "action(%s) is null", key.c_str());
 
-       DBG("set [%s, %s]", key.c_str(), (val ? "on" : "off"));
+       DBG("set(%s, %d)", key.c_str(), val);
 
        int ret = action->set(val);
        if (piAction)
@@ -104,12 +71,13 @@ int BtPlugin::set(const std::string &key, bool val, PluginAction **piAction)
        return ret;
 }
 
+//For BtActionAudioConnect
 int BtPlugin::set(const std::string &key, const std::string &val, PluginAction **piAction)
 {
        BtAction *action = btFactory.createAction(key);
        RETVM_IF(nullptr == action, MODES_ERROR_INVALID_PARAMETER, "action(%s) is null", key.c_str());
 
-       DBG("set [%s, %s]", key.c_str(), val.c_str());
+       DBG("set(%s, %s)", key.c_str(), val.c_str());
 
        int ret = action->set(val);
        if (piAction)
index 8020c06..1d53e8b 100644 (file)
@@ -8,7 +8,7 @@
       <domain>Network &amp; Connectivity</domain>
     </rule>
     <rule name="bluetooth.audioConnect" type="string" since="6.0" plugin="bluetooth">
-      <desc>bluetooth Audio Connect</desc>
+      <desc>bluetooth Audio Connect by Address</desc>
       <domain>Network &amp; Connectivity</domain>
     </rule>
   </actionRule>
index 23d3bc3..b0c76eb 100644 (file)
@@ -98,6 +98,7 @@ TEST_F(BtPluginTest, btTest)
 
        ret = plugin->set("power", false, nullptr);
        EXPECT_EQ(ret, MODES_ERROR_NONE);
+       sleep(3);//for avoiding the NOW_IN_PROGRESS error
 
        ret = plugin->set("power", true, nullptr);
        EXPECT_EQ(ret, MODES_ERROR_NONE);
index 4fa8e57..8996e64 100644 (file)
@@ -31,13 +31,12 @@ public:
        int parse(const std::string &archive) override;
        int setChangedCallback(valueChangedCB callback, void *userData) override;
        void unSetChangedCallback(valueChangedCB callback, void *userData) override;
-
-       valueChangedCB cb;
-       void *cbData;
 private:
        static void activateCB(wifi_manager_error_e result, void *user_data);
        static void deactivateCB(wifi_manager_error_e result, void *user_data);
        static void wifiStateChangedCB(wifi_manager_device_state_e state, void * user_data);
+       valueChangedCB cb;
+       void *cbData;
        bool oldVal;
        bool requestVal;
 };