Promotion of bt.lnx.2.1-00013.
CRs Change ID Subject
--------------------------------------------------------------------------------------------------------------
1055057 I260562e8f4586e27cbba3e496ee39f81964ceb1c Add longer delay while waiting for wcnss_filter to stop
1066801 Ib9e91b6adf0f9476add9af0c8e636feb89e01157 Avoid recursive locking in ssr_cleanup function.
Change-Id: Ifbf609b4b5e226a7f9c3231e06d003194b1cccb8
CRs-Fixed: 1055057, 1066801
diff --git a/libbt-vendor/src/bt_vendor_qcom.c b/libbt-vendor/src/bt_vendor_qcom.c
index cceeb59..6586f36 100644
--- a/libbt-vendor/src/bt_vendor_qcom.c
+++ b/libbt-vendor/src/bt_vendor_qcom.c
@@ -43,7 +43,7 @@
#define BT_VND_OP_GET_LINESPEED 30
#define STOP_WCNSS_FILTER 0xDD
-#define STOP_WAIT_TIMEOUT 100
+#define STOP_WAIT_TIMEOUT 1000
#define SOC_INIT_PROPERTY "wc_transport.soc_initialized"
@@ -281,35 +281,39 @@
ALOGV("%s: Entry ", __func__);
- property_get(BT_VND_FILTER_START, value, "false");
-
- if (strcmp(value, "false") == 0) {
- ALOGI("%s: hci_filter has been stopped already", __func__);
-// return;
- }
if ((soc_type = get_bt_soc_type()) == BT_SOC_CHEROKEE) {
- filter_ctrl = connect_to_local_socket("wcnssfilter_ctrl");
- if (filter_ctrl < 0) {
- ALOGI("%s: Error while connecting to CTRL_SOCK, filter should stopped: %d", __func__, filter_ctrl);
- //Ignore and fallback
- } else {
- retval = write(filter_ctrl, &stop_val, 1);
- if (retval != 1) {
- ALOGI("%s: problem writing to CTRL_SOCK, ignore: %d", __func__, retval);
- //Ignore and fallback
+ property_get("wc_transport.hci_filter_status", value, "0");
+ if (strcmp(value, "0") == 0) {
+ ALOGI("%s: hci_filter has been stopped already", __func__);
+ }
+ else {
+ filter_ctrl = connect_to_local_socket("wcnssfilter_ctrl");
+ if (filter_ctrl < 0) {
+ ALOGI("%s: Error while connecting to CTRL_SOCK, filter should stopped: %d",
+ __func__, filter_ctrl);
+ }
+ else {
+ retval = write(filter_ctrl, &stop_val, 1);
+ if (retval != 1) {
+ ALOGI("%s: problem writing to CTRL_SOCK, ignore: %d", __func__, retval);
+ //Ignore and fallback
+ }
+
+ close(filter_ctrl);
}
}
/* Ensure Filter is closed by checking the status before
RFKILL 0 operation. this should ideally comeout very
quick */
- for(i=0; i<5; i++) {
- property_get("wc_transport.hci_filter_status", value, "0");
- if (strcmp(value, "0") == 0) {
+ for(i=0; i<500; i++) {
+ property_get(BT_VND_FILTER_START, value, "false");
+ if (strcmp(value, "false") == 0) {
ALOGI("%s: WCNSS_FILTER stopped", __func__);
+ usleep(STOP_WAIT_TIMEOUT * 10);
break;
} else {
- /*sleep of 100ms, This should give enough time for FILTER to
+ /*sleep of 1ms, This should give enough time for FILTER to
exit with all necessary cleanup*/
usleep(STOP_WAIT_TIMEOUT);
}
@@ -710,9 +714,8 @@
return init;
}
-
-/** Requested operations */
-static int op(bt_vendor_opcode_t opcode, void *param)
+/* flavor of op without locks */
+static int __op(bt_vendor_opcode_t opcode, void *param)
{
int retval = BT_STATUS_SUCCESS;
int nCnt = 0;
@@ -732,12 +735,6 @@
bool skip_init = true;
int opcode_init = opcode;
ALOGV("++%s opcode %d", __FUNCTION__, opcode);
- pthread_mutex_lock(&q_lock);
- if (!q) {
- ALOGE("op called with NULL context");
- retval = -BT_STATUS_INVAL;
- goto out;
- }
switch(opcode_init)
{
@@ -1254,11 +1251,27 @@
}
out:
- pthread_mutex_unlock(&q_lock);
ALOGV("--%s", __FUNCTION__);
return retval;
}
+static int op(bt_vendor_opcode_t opcode, void *param)
+{
+ int ret;
+ ALOGV("++%s", __FUNCTION__);
+ pthread_mutex_lock(&q_lock);
+ if (!q) {
+ ALOGE("op called with NULL context");
+ ret = -BT_STATUS_INVAL;
+ goto out;
+ }
+ ret = __op(opcode, param);
+out:
+ pthread_mutex_unlock(&q_lock);
+ ALOGV("--%s ret = 0x%x", __FUNCTION__, ret);
+ return ret;
+}
+
static void ssr_cleanup(int reason)
{
int pwr_state = BT_VND_PWR_OFF;
@@ -1270,8 +1283,7 @@
pthread_mutex_lock(&q_lock);
if (!q) {
ALOGE("ssr_cleanup called with NULL context");
- pthread_mutex_unlock(&q_lock);
- return;
+ goto out;
}
if (property_set("wc_transport.patch_dnld_inprog", "null") < 0) {
ALOGE("Failed to set property");
@@ -1291,34 +1303,33 @@
* Then we should send special byte to crash SOC in
* WCNSS_Filter, so we do not need to power off UART here.
*/
- pthread_mutex_unlock(&q_lock);
- return;
+ goto out;
}
}
- /* release lock here as op holds lock anyways */
- pthread_mutex_unlock(&q_lock);
/* Close both ANT channel */
- op(BT_VND_OP_ANT_USERIAL_CLOSE, NULL);
+ __op(BT_VND_OP_ANT_USERIAL_CLOSE, NULL);
#endif
/* Close both BT channel */
- op(BT_VND_OP_USERIAL_CLOSE, NULL);
+ __op(BT_VND_OP_USERIAL_CLOSE, NULL);
#ifdef FM_OVER_UART
- op(BT_VND_OP_FM_USERIAL_CLOSE, NULL);
+ __op(BT_VND_OP_FM_USERIAL_CLOSE, NULL);
#endif
/*CTRL OFF twice to make sure hw
* turns off*/
#ifdef ENABLE_ANT
- op(BT_VND_OP_POWER_CTRL, &pwr_state);
+ __op(BT_VND_OP_POWER_CTRL, &pwr_state);
#endif
#ifdef FM_OVER_UART
- op(BT_VND_OP_POWER_CTRL, &pwr_state);
+ __op(BT_VND_OP_POWER_CTRL, &pwr_state);
#endif
}
/*Generally switching of chip should be enough*/
- op(BT_VND_OP_POWER_CTRL, &pwr_state);
+ __op(BT_VND_OP_POWER_CTRL, &pwr_state);
+out:
+ pthread_mutex_unlock(&q_lock);
ALOGI("--%s", __FUNCTION__);
}