Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/linville/wireless into for-davem
This commit is contained in:
commit
076e7779c0
14 changed files with 102 additions and 35 deletions
|
@ -75,6 +75,8 @@ static struct usb_device_id ath3k_table[] = {
|
|||
{ USB_DEVICE(0x0CF3, 0x311D) },
|
||||
{ USB_DEVICE(0x13d3, 0x3375) },
|
||||
{ USB_DEVICE(0x04CA, 0x3005) },
|
||||
{ USB_DEVICE(0x13d3, 0x3362) },
|
||||
{ USB_DEVICE(0x0CF3, 0xE004) },
|
||||
|
||||
/* Atheros AR5BBU12 with sflash firmware */
|
||||
{ USB_DEVICE(0x0489, 0xE02C) },
|
||||
|
@ -94,6 +96,8 @@ static struct usb_device_id ath3k_blist_tbl[] = {
|
|||
{ USB_DEVICE(0x0cf3, 0x311D), .driver_info = BTUSB_ATH3012 },
|
||||
{ USB_DEVICE(0x13d3, 0x3375), .driver_info = BTUSB_ATH3012 },
|
||||
{ USB_DEVICE(0x04ca, 0x3005), .driver_info = BTUSB_ATH3012 },
|
||||
{ USB_DEVICE(0x13d3, 0x3362), .driver_info = BTUSB_ATH3012 },
|
||||
{ USB_DEVICE(0x0cf3, 0xe004), .driver_info = BTUSB_ATH3012 },
|
||||
|
||||
{ } /* Terminating entry */
|
||||
};
|
||||
|
|
|
@ -101,12 +101,16 @@ static struct usb_device_id btusb_table[] = {
|
|||
{ USB_DEVICE(0x0c10, 0x0000) },
|
||||
|
||||
/* Broadcom BCM20702A0 */
|
||||
{ USB_DEVICE(0x0489, 0xe042) },
|
||||
{ USB_DEVICE(0x0a5c, 0x21e3) },
|
||||
{ USB_DEVICE(0x0a5c, 0x21e6) },
|
||||
{ USB_DEVICE(0x0a5c, 0x21e8) },
|
||||
{ USB_DEVICE(0x0a5c, 0x21f3) },
|
||||
{ USB_DEVICE(0x413c, 0x8197) },
|
||||
|
||||
/* Foxconn - Hon Hai */
|
||||
{ USB_DEVICE(0x0489, 0xe033) },
|
||||
|
||||
{ } /* Terminating entry */
|
||||
};
|
||||
|
||||
|
@ -133,6 +137,8 @@ static struct usb_device_id blacklist_table[] = {
|
|||
{ USB_DEVICE(0x0cf3, 0x311d), .driver_info = BTUSB_ATH3012 },
|
||||
{ USB_DEVICE(0x13d3, 0x3375), .driver_info = BTUSB_ATH3012 },
|
||||
{ USB_DEVICE(0x04ca, 0x3005), .driver_info = BTUSB_ATH3012 },
|
||||
{ USB_DEVICE(0x13d3, 0x3362), .driver_info = BTUSB_ATH3012 },
|
||||
{ USB_DEVICE(0x0cf3, 0xe004), .driver_info = BTUSB_ATH3012 },
|
||||
|
||||
/* Atheros AR5BBU12 with sflash firmware */
|
||||
{ USB_DEVICE(0x0489, 0xe02c), .driver_info = BTUSB_IGNORE },
|
||||
|
|
|
@ -220,6 +220,7 @@ static int ath_ahb_remove(struct platform_device *pdev)
|
|||
}
|
||||
|
||||
ath5k_deinit_ah(ah);
|
||||
iounmap(ah->iobase);
|
||||
platform_set_drvdata(pdev, NULL);
|
||||
ieee80211_free_hw(hw);
|
||||
|
||||
|
|
|
@ -4827,8 +4827,14 @@ static int b43_op_start(struct ieee80211_hw *hw)
|
|||
out_mutex_unlock:
|
||||
mutex_unlock(&wl->mutex);
|
||||
|
||||
/* reload configuration */
|
||||
b43_op_config(hw, ~0);
|
||||
/*
|
||||
* Configuration may have been overwritten during initialization.
|
||||
* Reload the configuration, but only if initialization was
|
||||
* successful. Reloading the configuration after a failed init
|
||||
* may hang the system.
|
||||
*/
|
||||
if (!err)
|
||||
b43_op_config(hw, ~0);
|
||||
|
||||
return err;
|
||||
}
|
||||
|
|
|
@ -108,9 +108,15 @@ static inline int brcmf_sdioh_f0_write_byte(struct brcmf_sdio_dev *sdiodev,
|
|||
sdio_release_host(sdfunc);
|
||||
}
|
||||
} else if (regaddr == SDIO_CCCR_ABORT) {
|
||||
sdfunc = kmemdup(sdiodev->func[0], sizeof(struct sdio_func),
|
||||
GFP_KERNEL);
|
||||
if (!sdfunc)
|
||||
return -ENOMEM;
|
||||
sdfunc->num = 0;
|
||||
sdio_claim_host(sdfunc);
|
||||
sdio_writeb(sdfunc, *byte, regaddr, &err_ret);
|
||||
sdio_release_host(sdfunc);
|
||||
kfree(sdfunc);
|
||||
} else if (regaddr < 0xF0) {
|
||||
brcmf_dbg(ERROR, "F0 Wr:0x%02x: write disallowed\n", regaddr);
|
||||
err_ret = -EPERM;
|
||||
|
@ -486,7 +492,7 @@ static int brcmf_ops_sdio_probe(struct sdio_func *func,
|
|||
kfree(bus_if);
|
||||
return -ENOMEM;
|
||||
}
|
||||
sdiodev->func[0] = func->card->sdio_func[0];
|
||||
sdiodev->func[0] = func;
|
||||
sdiodev->func[1] = func;
|
||||
sdiodev->bus_if = bus_if;
|
||||
bus_if->bus_priv.sdio = sdiodev;
|
||||
|
|
|
@ -574,6 +574,8 @@ struct brcmf_sdio {
|
|||
|
||||
struct task_struct *dpc_tsk;
|
||||
struct completion dpc_wait;
|
||||
struct list_head dpc_tsklst;
|
||||
spinlock_t dpc_tl_lock;
|
||||
|
||||
struct semaphore sdsem;
|
||||
|
||||
|
@ -2594,29 +2596,58 @@ static bool brcmf_sdbrcm_dpc(struct brcmf_sdio *bus)
|
|||
return resched;
|
||||
}
|
||||
|
||||
static inline void brcmf_sdbrcm_adddpctsk(struct brcmf_sdio *bus)
|
||||
{
|
||||
struct list_head *new_hd;
|
||||
unsigned long flags;
|
||||
|
||||
if (in_interrupt())
|
||||
new_hd = kzalloc(sizeof(struct list_head), GFP_ATOMIC);
|
||||
else
|
||||
new_hd = kzalloc(sizeof(struct list_head), GFP_KERNEL);
|
||||
if (new_hd == NULL)
|
||||
return;
|
||||
|
||||
spin_lock_irqsave(&bus->dpc_tl_lock, flags);
|
||||
list_add_tail(new_hd, &bus->dpc_tsklst);
|
||||
spin_unlock_irqrestore(&bus->dpc_tl_lock, flags);
|
||||
}
|
||||
|
||||
static int brcmf_sdbrcm_dpc_thread(void *data)
|
||||
{
|
||||
struct brcmf_sdio *bus = (struct brcmf_sdio *) data;
|
||||
struct list_head *cur_hd, *tmp_hd;
|
||||
unsigned long flags;
|
||||
|
||||
allow_signal(SIGTERM);
|
||||
/* Run until signal received */
|
||||
while (1) {
|
||||
if (kthread_should_stop())
|
||||
break;
|
||||
if (!wait_for_completion_interruptible(&bus->dpc_wait)) {
|
||||
/* Call bus dpc unless it indicated down
|
||||
(then clean stop) */
|
||||
if (bus->sdiodev->bus_if->state != BRCMF_BUS_DOWN) {
|
||||
if (brcmf_sdbrcm_dpc(bus))
|
||||
complete(&bus->dpc_wait);
|
||||
} else {
|
||||
|
||||
if (list_empty(&bus->dpc_tsklst))
|
||||
if (wait_for_completion_interruptible(&bus->dpc_wait))
|
||||
break;
|
||||
|
||||
spin_lock_irqsave(&bus->dpc_tl_lock, flags);
|
||||
list_for_each_safe(cur_hd, tmp_hd, &bus->dpc_tsklst) {
|
||||
spin_unlock_irqrestore(&bus->dpc_tl_lock, flags);
|
||||
|
||||
if (bus->sdiodev->bus_if->state == BRCMF_BUS_DOWN) {
|
||||
/* after stopping the bus, exit thread */
|
||||
brcmf_sdbrcm_bus_stop(bus->sdiodev->dev);
|
||||
bus->dpc_tsk = NULL;
|
||||
break;
|
||||
}
|
||||
} else
|
||||
break;
|
||||
|
||||
if (brcmf_sdbrcm_dpc(bus))
|
||||
brcmf_sdbrcm_adddpctsk(bus);
|
||||
|
||||
spin_lock_irqsave(&bus->dpc_tl_lock, flags);
|
||||
list_del(cur_hd);
|
||||
kfree(cur_hd);
|
||||
}
|
||||
spin_unlock_irqrestore(&bus->dpc_tl_lock, flags);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -2669,8 +2700,10 @@ static int brcmf_sdbrcm_bus_txdata(struct device *dev, struct sk_buff *pkt)
|
|||
/* Schedule DPC if needed to send queued packet(s) */
|
||||
if (!bus->dpc_sched) {
|
||||
bus->dpc_sched = true;
|
||||
if (bus->dpc_tsk)
|
||||
if (bus->dpc_tsk) {
|
||||
brcmf_sdbrcm_adddpctsk(bus);
|
||||
complete(&bus->dpc_wait);
|
||||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
|
@ -3514,8 +3547,10 @@ void brcmf_sdbrcm_isr(void *arg)
|
|||
brcmf_dbg(ERROR, "isr w/o interrupt configured!\n");
|
||||
|
||||
bus->dpc_sched = true;
|
||||
if (bus->dpc_tsk)
|
||||
if (bus->dpc_tsk) {
|
||||
brcmf_sdbrcm_adddpctsk(bus);
|
||||
complete(&bus->dpc_wait);
|
||||
}
|
||||
}
|
||||
|
||||
static bool brcmf_sdbrcm_bus_watchdog(struct brcmf_sdio *bus)
|
||||
|
@ -3559,8 +3594,10 @@ static bool brcmf_sdbrcm_bus_watchdog(struct brcmf_sdio *bus)
|
|||
bus->ipend = true;
|
||||
|
||||
bus->dpc_sched = true;
|
||||
if (bus->dpc_tsk)
|
||||
if (bus->dpc_tsk) {
|
||||
brcmf_sdbrcm_adddpctsk(bus);
|
||||
complete(&bus->dpc_wait);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3897,6 +3934,8 @@ void *brcmf_sdbrcm_probe(u32 regsva, struct brcmf_sdio_dev *sdiodev)
|
|||
}
|
||||
/* Initialize DPC thread */
|
||||
init_completion(&bus->dpc_wait);
|
||||
INIT_LIST_HEAD(&bus->dpc_tsklst);
|
||||
spin_lock_init(&bus->dpc_tl_lock);
|
||||
bus->dpc_tsk = kthread_run(brcmf_sdbrcm_dpc_thread,
|
||||
bus, "brcmf_dpc");
|
||||
if (IS_ERR(bus->dpc_tsk)) {
|
||||
|
|
|
@ -336,7 +336,7 @@ static const struct iwl_bt_params iwl6000_bt_params = {
|
|||
#define IWL_DEVICE_6005 \
|
||||
.fw_name_pre = IWL6005_FW_PRE, \
|
||||
.ucode_api_max = IWL6000G2_UCODE_API_MAX, \
|
||||
.ucode_api_ok = IWL6000G2B_UCODE_API_OK, \
|
||||
.ucode_api_ok = IWL6000G2_UCODE_API_OK, \
|
||||
.ucode_api_min = IWL6000G2_UCODE_API_MIN, \
|
||||
.max_inst_size = IWL60_RTC_INST_SIZE, \
|
||||
.max_data_size = IWL60_RTC_DATA_SIZE, \
|
||||
|
@ -390,7 +390,7 @@ const struct iwl_cfg iwl6005_2agn_mow2_cfg = {
|
|||
#define IWL_DEVICE_6030 \
|
||||
.fw_name_pre = IWL6030_FW_PRE, \
|
||||
.ucode_api_max = IWL6000G2_UCODE_API_MAX, \
|
||||
.ucode_api_ok = IWL6000G2_UCODE_API_OK, \
|
||||
.ucode_api_ok = IWL6000G2B_UCODE_API_OK, \
|
||||
.ucode_api_min = IWL6000G2_UCODE_API_MIN, \
|
||||
.max_inst_size = IWL60_RTC_INST_SIZE, \
|
||||
.max_data_size = IWL60_RTC_DATA_SIZE, \
|
||||
|
|
|
@ -479,6 +479,7 @@ static void wl1251_op_stop(struct ieee80211_hw *hw)
|
|||
cancel_work_sync(&wl->irq_work);
|
||||
cancel_work_sync(&wl->tx_work);
|
||||
cancel_work_sync(&wl->filter_work);
|
||||
cancel_delayed_work_sync(&wl->elp_work);
|
||||
|
||||
mutex_lock(&wl->mutex);
|
||||
|
||||
|
|
|
@ -315,8 +315,8 @@ static void __devexit wl1251_sdio_remove(struct sdio_func *func)
|
|||
|
||||
if (wl->irq)
|
||||
free_irq(wl->irq, wl);
|
||||
kfree(wl_sdio);
|
||||
wl1251_free_hw(wl);
|
||||
kfree(wl_sdio);
|
||||
|
||||
sdio_claim_host(func);
|
||||
sdio_release_irq(func);
|
||||
|
|
|
@ -314,6 +314,7 @@ struct hci_conn {
|
|||
|
||||
__u8 remote_cap;
|
||||
__u8 remote_auth;
|
||||
bool flush_key;
|
||||
|
||||
unsigned int sent;
|
||||
|
||||
|
@ -980,7 +981,7 @@ int mgmt_discoverable(struct hci_dev *hdev, u8 discoverable);
|
|||
int mgmt_connectable(struct hci_dev *hdev, u8 connectable);
|
||||
int mgmt_write_scan_failed(struct hci_dev *hdev, u8 scan, u8 status);
|
||||
int mgmt_new_link_key(struct hci_dev *hdev, struct link_key *key,
|
||||
u8 persistent);
|
||||
bool persistent);
|
||||
int mgmt_device_connected(struct hci_dev *hdev, bdaddr_t *bdaddr, u8 link_type,
|
||||
u8 addr_type, u32 flags, u8 *name, u8 name_len,
|
||||
u8 *dev_class);
|
||||
|
|
|
@ -1215,40 +1215,40 @@ struct link_key *hci_find_link_key(struct hci_dev *hdev, bdaddr_t *bdaddr)
|
|||
return NULL;
|
||||
}
|
||||
|
||||
static int hci_persistent_key(struct hci_dev *hdev, struct hci_conn *conn,
|
||||
static bool hci_persistent_key(struct hci_dev *hdev, struct hci_conn *conn,
|
||||
u8 key_type, u8 old_key_type)
|
||||
{
|
||||
/* Legacy key */
|
||||
if (key_type < 0x03)
|
||||
return 1;
|
||||
return true;
|
||||
|
||||
/* Debug keys are insecure so don't store them persistently */
|
||||
if (key_type == HCI_LK_DEBUG_COMBINATION)
|
||||
return 0;
|
||||
return false;
|
||||
|
||||
/* Changed combination key and there's no previous one */
|
||||
if (key_type == HCI_LK_CHANGED_COMBINATION && old_key_type == 0xff)
|
||||
return 0;
|
||||
return false;
|
||||
|
||||
/* Security mode 3 case */
|
||||
if (!conn)
|
||||
return 1;
|
||||
return true;
|
||||
|
||||
/* Neither local nor remote side had no-bonding as requirement */
|
||||
if (conn->auth_type > 0x01 && conn->remote_auth > 0x01)
|
||||
return 1;
|
||||
return true;
|
||||
|
||||
/* Local side had dedicated bonding as requirement */
|
||||
if (conn->auth_type == 0x02 || conn->auth_type == 0x03)
|
||||
return 1;
|
||||
return true;
|
||||
|
||||
/* Remote side had dedicated bonding as requirement */
|
||||
if (conn->remote_auth == 0x02 || conn->remote_auth == 0x03)
|
||||
return 1;
|
||||
return true;
|
||||
|
||||
/* If none of the above criteria match, then don't store the key
|
||||
* persistently */
|
||||
return 0;
|
||||
return false;
|
||||
}
|
||||
|
||||
struct smp_ltk *hci_find_ltk(struct hci_dev *hdev, __le16 ediv, u8 rand[8])
|
||||
|
@ -1285,7 +1285,8 @@ int hci_add_link_key(struct hci_dev *hdev, struct hci_conn *conn, int new_key,
|
|||
bdaddr_t *bdaddr, u8 *val, u8 type, u8 pin_len)
|
||||
{
|
||||
struct link_key *key, *old_key;
|
||||
u8 old_key_type, persistent;
|
||||
u8 old_key_type;
|
||||
bool persistent;
|
||||
|
||||
old_key = hci_find_link_key(hdev, bdaddr);
|
||||
if (old_key) {
|
||||
|
@ -1328,10 +1329,8 @@ int hci_add_link_key(struct hci_dev *hdev, struct hci_conn *conn, int new_key,
|
|||
|
||||
mgmt_new_link_key(hdev, key, persistent);
|
||||
|
||||
if (!persistent) {
|
||||
list_del(&key->list);
|
||||
kfree(key);
|
||||
}
|
||||
if (conn)
|
||||
conn->flush_key = !persistent;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -1901,6 +1901,8 @@ static inline void hci_disconn_complete_evt(struct hci_dev *hdev, struct sk_buff
|
|||
}
|
||||
|
||||
if (ev->status == 0) {
|
||||
if (conn->type == ACL_LINK && conn->flush_key)
|
||||
hci_remove_link_key(hdev, &conn->dst);
|
||||
hci_proto_disconn_cfm(conn, ev->reason);
|
||||
hci_conn_del(conn);
|
||||
}
|
||||
|
@ -2311,6 +2313,7 @@ static inline void hci_cmd_complete_evt(struct hci_dev *hdev, struct sk_buff *sk
|
|||
|
||||
case HCI_OP_USER_PASSKEY_NEG_REPLY:
|
||||
hci_cc_user_passkey_neg_reply(hdev, skb);
|
||||
break;
|
||||
|
||||
case HCI_OP_LE_SET_SCAN_PARAM:
|
||||
hci_cc_le_set_scan_param(hdev, skb);
|
||||
|
|
|
@ -2884,7 +2884,7 @@ int mgmt_write_scan_failed(struct hci_dev *hdev, u8 scan, u8 status)
|
|||
return 0;
|
||||
}
|
||||
|
||||
int mgmt_new_link_key(struct hci_dev *hdev, struct link_key *key, u8 persistent)
|
||||
int mgmt_new_link_key(struct hci_dev *hdev, struct link_key *key, bool persistent)
|
||||
{
|
||||
struct mgmt_ev_new_link_key ev;
|
||||
|
||||
|
|
|
@ -1158,7 +1158,8 @@ ieee80211_tx_prepare(struct ieee80211_sub_if_data *sdata,
|
|||
tx->sta = rcu_dereference(sdata->u.vlan.sta);
|
||||
if (!tx->sta && sdata->dev->ieee80211_ptr->use_4addr)
|
||||
return TX_DROP;
|
||||
} else if (info->flags & IEEE80211_TX_CTL_INJECTED) {
|
||||
} else if (info->flags & IEEE80211_TX_CTL_INJECTED ||
|
||||
tx->sdata->control_port_protocol == tx->skb->protocol) {
|
||||
tx->sta = sta_info_get_bss(sdata, hdr->addr1);
|
||||
}
|
||||
if (!tx->sta)
|
||||
|
|
Loading…
Reference in a new issue