diff options
author | Eliad Peller <eliad@wizery.com> | 2012-02-06 14:47:54 +0400 |
---|---|---|
committer | Luciano Coelho <coelho@ti.com> | 2012-02-15 10:38:35 +0400 |
commit | 3fcdab7066a31ae90ac2beba7d38e8e606374998 (patch) | |
tree | 17cec887b8fa6dc97c31ce0d5c820f9874cfc888 /drivers/net/wireless/wl12xx/main.c | |
parent | f95f9aad150238236b2338efa60a14891081026e (diff) | |
download | linux-3fcdab7066a31ae90ac2beba7d38e8e606374998.tar.xz |
wl12xx: Use a dedicated fw for PLT
A special PLT firmware is used for calibration.
Add multiple fw support by introducing a new fw_type member,
representing the currently saved fw (the actual fw state
can be determined by wl->state).
Signed-off-by: Gery Kahn <geryk@ti.com>
Signed-off-by: Eliad Peller <eliad@wizery.com>
Signed-off-by: Luciano Coelho <coelho@ti.com>
Diffstat (limited to 'drivers/net/wireless/wl12xx/main.c')
-rw-r--r-- | drivers/net/wireless/wl12xx/main.c | 53 |
1 files changed, 35 insertions, 18 deletions
diff --git a/drivers/net/wireless/wl12xx/main.c b/drivers/net/wireless/wl12xx/main.c index 723df48ed447..c10940703e8c 100644 --- a/drivers/net/wireless/wl12xx/main.c +++ b/drivers/net/wireless/wl12xx/main.c @@ -993,16 +993,29 @@ out: return IRQ_HANDLED; } -static int wl1271_fetch_firmware(struct wl1271 *wl) +static int wl12xx_fetch_firmware(struct wl1271 *wl, bool plt) { const struct firmware *fw; const char *fw_name; + enum wl12xx_fw_type fw_type; int ret; - if (wl->chip.id == CHIP_ID_1283_PG20) - fw_name = WL128X_FW_NAME; - else - fw_name = WL127X_FW_NAME; + if (plt) { + fw_type = WL12XX_FW_TYPE_PLT; + if (wl->chip.id == CHIP_ID_1283_PG20) + fw_name = WL128X_PLT_FW_NAME; + else + fw_name = WL127X_PLT_FW_NAME; + } else { + fw_type = WL12XX_FW_TYPE_NORMAL; + if (wl->chip.id == CHIP_ID_1283_PG20) + fw_name = WL128X_FW_NAME; + else + fw_name = WL127X_FW_NAME; + } + + if (wl->fw_type == fw_type) + return 0; wl1271_debug(DEBUG_BOOT, "booting firmware %s", fw_name); @@ -1021,6 +1034,7 @@ static int wl1271_fetch_firmware(struct wl1271 *wl) } vfree(wl->fw); + wl->fw_type = WL12XX_FW_TYPE_NONE; wl->fw_len = fw->size; wl->fw = vmalloc(wl->fw_len); @@ -1032,7 +1046,7 @@ static int wl1271_fetch_firmware(struct wl1271 *wl) memcpy(wl->fw, fw->data, wl->fw_len); ret = 0; - + wl->fw_type = fw_type; out: release_firmware(fw); @@ -1160,7 +1174,7 @@ static void wl1271_recovery_work(struct work_struct *work) mutex_lock(&wl->mutex); - if (wl->state != WL1271_STATE_ON) + if (wl->state != WL1271_STATE_ON || wl->plt) goto out_unlock; /* Avoid a recursive recovery */ @@ -1261,7 +1275,7 @@ out: return ret; } -static int wl1271_chip_wakeup(struct wl1271 *wl) +static int wl12xx_chip_wakeup(struct wl1271 *wl, bool plt) { int ret = 0; @@ -1316,11 +1330,9 @@ static int wl1271_chip_wakeup(struct wl1271 *wl) goto out; } - if (wl->fw == NULL) { - ret = wl1271_fetch_firmware(wl); - if (ret < 0) - goto out; - } + ret = wl12xx_fetch_firmware(wl, plt); + if (ret < 0) + goto out; /* No NVS from netlink, try to get it from the filesystem */ if (wl->nvs == NULL) { @@ -1352,7 +1364,7 @@ int wl1271_plt_start(struct wl1271 *wl) while (retries) { retries--; - ret = wl1271_chip_wakeup(wl); + ret = wl12xx_chip_wakeup(wl, true); if (ret < 0) goto power_off; @@ -1364,7 +1376,8 @@ int wl1271_plt_start(struct wl1271 *wl) if (ret < 0) goto irq_disable; - wl->state = WL1271_STATE_PLT; + wl->plt = true; + wl->state = WL1271_STATE_ON; wl1271_notice("firmware booted in PLT mode (%s)", wl->chip.fw_ver_str); @@ -1413,7 +1426,7 @@ int wl1271_plt_stop(struct wl1271 *wl) */ wl1271_disable_interrupts(wl); mutex_lock(&wl->mutex); - if (wl->state != WL1271_STATE_PLT) { + if (!wl->plt) { mutex_unlock(&wl->mutex); /* @@ -1440,6 +1453,7 @@ int wl1271_plt_stop(struct wl1271 *wl) wl1271_power_off(wl); wl->flags = 0; wl->state = WL1271_STATE_OFF; + wl->plt = false; wl->rx_counter = 0; mutex_unlock(&wl->mutex); @@ -1995,7 +2009,7 @@ static bool wl12xx_init_fw(struct wl1271 *wl) while (retries) { retries--; - ret = wl1271_chip_wakeup(wl); + ret = wl12xx_chip_wakeup(wl, false); if (ret < 0) goto power_off; @@ -2098,6 +2112,7 @@ static int wl1271_op_add_interface(struct ieee80211_hw *hw, goto out; } + ret = wl12xx_init_vif_data(wl, vif); if (ret < 0) goto out; @@ -5009,7 +5024,7 @@ out: static void wl1271_unregister_hw(struct wl1271 *wl) { - if (wl->state == WL1271_STATE_PLT) + if (wl->plt) wl1271_plt_stop(wl); unregister_netdevice_notifier(&wl1271_dev_notifier); @@ -5186,6 +5201,7 @@ static struct ieee80211_hw *wl1271_alloc_hw(void) spin_lock_init(&wl->wl_lock); wl->state = WL1271_STATE_OFF; + wl->fw_type = WL12XX_FW_TYPE_NONE; mutex_init(&wl->mutex); /* Apply default driver configuration. */ @@ -5253,6 +5269,7 @@ static int wl1271_free_hw(struct wl1271 *wl) vfree(wl->fw); wl->fw = NULL; + wl->fw_type = WL12XX_FW_TYPE_NONE; kfree(wl->nvs); wl->nvs = NULL; |