summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--CORE/SERVICES/COMMON/hif_msg_based.h4
-rw-r--r--CORE/SERVICES/HIF/sdio/linux/native_sdio/include/hif_internal.h3
-rw-r--r--CORE/SERVICES/HIF/sdio/linux/native_sdio/src/hif.c79
-rw-r--r--CORE/SERVICES/HTC/htc_recv.c5
4 files changed, 60 insertions, 31 deletions
diff --git a/CORE/SERVICES/COMMON/hif_msg_based.h b/CORE/SERVICES/COMMON/hif_msg_based.h
index af339aef1248..ae3332893730 100644
--- a/CORE/SERVICES/COMMON/hif_msg_based.h
+++ b/CORE/SERVICES/COMMON/hif_msg_based.h
@@ -149,9 +149,9 @@ void HIFSetBundleMode(HIF_DEVICE *hif_device, bool enabled, int rx_bundle_cnt);
#endif
#ifdef HIF_SDIO
-int hif_reset_target(HIF_DEVICE *hif_device);
+int hif_set_target_reset(HIF_DEVICE *hif_device);
#else
-static inline int hif_reset_target(HIF_DEVICE *hif_device)
+static inline int hif_set_target_reset(HIF_DEVICE *hif_device)
{
return 0;
}
diff --git a/CORE/SERVICES/HIF/sdio/linux/native_sdio/include/hif_internal.h b/CORE/SERVICES/HIF/sdio/linux/native_sdio/include/hif_internal.h
index 6199746ac33f..19fb0afb19ff 100644
--- a/CORE/SERVICES/HIF/sdio/linux/native_sdio/include/hif_internal.h
+++ b/CORE/SERVICES/HIF/sdio/linux/native_sdio/include/hif_internal.h
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2013-2014 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2013-2014, 2016 The Linux Foundation. All rights reserved.
*
* Previously licensed under the ISC license by Qualcomm Atheros, Inc.
*
@@ -119,6 +119,7 @@ struct hif_device {
void *htcContext;
/* mailbox swapping for control and data svc*/
A_BOOL swap_mailbox;
+ bool ctrl_response_timeout;
};
#define HIF_DMA_BUFFER_SIZE (4 * 1024)
diff --git a/CORE/SERVICES/HIF/sdio/linux/native_sdio/src/hif.c b/CORE/SERVICES/HIF/sdio/linux/native_sdio/src/hif.c
index 428b96e12f91..c1edb6c8d893 100644
--- a/CORE/SERVICES/HIF/sdio/linux/native_sdio/src/hif.c
+++ b/CORE/SERVICES/HIF/sdio/linux/native_sdio/src/hif.c
@@ -2584,9 +2584,59 @@ static void hif_flush_async_task(HIF_DEVICE *device)
}
}
+/**
+ * hif_reset_target() - Reset target device
+ * @hif_device: pointer to hif_device structure
+ *
+ * Reset the target by invoking power off and power on
+ * sequence to bring back target into active state.
+ * This API shall be called only when driver load/unload
+ * is in progress.
+ *
+ * Return: 0 on success, error for failure case.
+ */
+static int hif_reset_target(HIF_DEVICE *hif_device)
+{
+ int ret;
+
+ if (!hif_device || !hif_device->func|| !hif_device->func->card) {
+ AR_DEBUG_PRINTF(ATH_DEBUG_ERROR,
+ ("AR6000: %s invalid HIF DEVICE \n", __func__));
+ return -ENODEV;
+ }
+ /* Disable sdio func->pull down WLAN_EN-->pull down DAT_2 line */
+ ret = mmc_power_save_host(hif_device->func->card->host);
+ if(ret) {
+ AR_DEBUG_PRINTF(ATH_DEBUG_ERROR,
+ ("AR6000: %s Failed to save mmc Power host %d\n",
+ __func__, ret));
+ goto done;
+ }
+
+ /* pull up DAT_2 line->pull up WLAN_EN-->Enable sdio func */
+ ret = mmc_power_restore_host(hif_device->func->card->host);
+ if(ret) {
+ AR_DEBUG_PRINTF(ATH_DEBUG_ERROR,
+ ("AR6000: %s Failed to restore mmc Power host %d\n",
+ __func__, ret));
+ }
+
+done:
+ return ret;
+}
+
void HIFDetachHTC(HIF_DEVICE *device)
{
hif_flush_async_task(device);
+ if (device->ctrl_response_timeout) {
+ /* Reset the target by invoking power off and power on sequence to
+ * the card to bring back into active state.
+ */
+ if(hif_reset_target(device))
+ VOS_BUG(0);
+ device->ctrl_response_timeout = false;
+ }
+
A_MEMZERO(&device->htcCallbacks,sizeof(device->htcCallbacks));
}
@@ -2762,42 +2812,23 @@ static int hif_sdio_device_resume(struct device *dev)
#endif
/**
- * hif_reset_target() - Reset target device
+ * hif_set_target_reset() - Reset target device
* @hif_device: pointer to hif_device structure
*
- * Reset the target by invoking power off and power on
- * sequence to bring back target into active state.
+ * Set the target reset flag.
* This API shall be called only when driver load/unload
* is in progress.
*
* Return: 0 on success, error for failure case.
*/
-int hif_reset_target(HIF_DEVICE *hif_device)
+int hif_set_target_reset(HIF_DEVICE *hif_device)
{
- int ret;
-
if (!hif_device || !hif_device->func|| !hif_device->func->card) {
AR_DEBUG_PRINTF(ATH_DEBUG_ERROR,
("AR6000: %s invalid HIF DEVICE \n", __func__));
return -ENODEV;
}
- /* Disable sdio func->pull down WLAN_EN-->pull down DAT_2 line */
- ret = mmc_power_save_host(hif_device->func->card->host);
- if(ret) {
- AR_DEBUG_PRINTF(ATH_DEBUG_ERROR,
- ("AR6000: %s Failed to save mmc Power host %d\n",
- __func__, ret));
- goto done;
- }
-
- /* pull up DAT_2 line->pull up WLAN_EN-->Enable sdio func */
- ret = mmc_power_restore_host(hif_device->func->card->host);
- if(ret) {
- AR_DEBUG_PRINTF(ATH_DEBUG_ERROR,
- ("AR6000: %s Failed to restore mmc Power host %d\n",
- __func__, ret));
- }
+ hif_device->ctrl_response_timeout = true;
-done:
- return ret;
+ return 0;
}
diff --git a/CORE/SERVICES/HTC/htc_recv.c b/CORE/SERVICES/HTC/htc_recv.c
index b082a25941cf..e78121f0b2b5 100644
--- a/CORE/SERVICES/HTC/htc_recv.c
+++ b/CORE/SERVICES/HTC/htc_recv.c
@@ -585,10 +585,7 @@ A_STATUS HTCWaitRecvCtrlMessage(HTC_TARGET *target)
/* Wait for BMI request/response transaction to complete */
if(!adf_os_wait_for_completion_timeout(&target->CtrlResponseValid,
adf_os_msecs_to_ticks(HTC_CONTROL_RX_TIMEOUT))) {
- /* Reset the target by invoking power off and power on sequence to
- * the card to bring back into active state.
- */
- if(hif_reset_target(target->hif_dev))
+ if(hif_set_target_reset(target->hif_dev))
VOS_BUG(0);
return A_ERROR;
}