mirror of
https://github.com/torvalds/linux.git
synced 2026-05-25 23:52:08 +02:00
mt76: mt7615: run key configuration in mt7615_set_key for usb/sdio devices
Since rate configuration is run holding dev mutex, we can run key configuration in mt7615_set_key for usb/sdio devices avoiding to schedule the workqueue Tested-by: Tested-by: YN Chen <yn.chen@mediatek.com> Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org> Signed-off-by: Felix Fietkau <nbd@nbd.name>
This commit is contained in:
parent
930e0eaddf
commit
faa72684b4
|
|
@ -1030,32 +1030,32 @@ void mt7615_mac_set_rates(struct mt7615_phy *phy, struct mt7615_sta *sta,
|
|||
}
|
||||
EXPORT_SYMBOL_GPL(mt7615_mac_set_rates);
|
||||
|
||||
int mt7615_mac_wtbl_update_key(struct mt7615_dev *dev,
|
||||
struct mt76_wcid *wcid,
|
||||
u8 *key, u8 keylen,
|
||||
enum mt7615_cipher_type cipher,
|
||||
enum set_key_cmd cmd)
|
||||
static int
|
||||
mt7615_mac_wtbl_update_key(struct mt7615_dev *dev, struct mt76_wcid *wcid,
|
||||
struct ieee80211_key_conf *key,
|
||||
enum mt7615_cipher_type cipher,
|
||||
enum set_key_cmd cmd)
|
||||
{
|
||||
u32 addr = mt7615_mac_wtbl_addr(dev, wcid->idx) + 30 * 4;
|
||||
u8 data[32] = {};
|
||||
|
||||
if (keylen > sizeof(data))
|
||||
if (key->keylen > sizeof(data))
|
||||
return -EINVAL;
|
||||
|
||||
mt76_rr_copy(dev, addr, data, sizeof(data));
|
||||
if (cmd == SET_KEY) {
|
||||
if (cipher == MT_CIPHER_TKIP) {
|
||||
/* Rx/Tx MIC keys are swapped */
|
||||
memcpy(data, key, 16);
|
||||
memcpy(data + 16, key + 24, 8);
|
||||
memcpy(data + 24, key + 16, 8);
|
||||
memcpy(data, key->key, 16);
|
||||
memcpy(data + 16, key->key + 24, 8);
|
||||
memcpy(data + 24, key->key + 16, 8);
|
||||
} else {
|
||||
if (cipher != MT_CIPHER_BIP_CMAC_128 && wcid->cipher)
|
||||
memmove(data + 16, data, 16);
|
||||
if (cipher != MT_CIPHER_BIP_CMAC_128 || !wcid->cipher)
|
||||
memcpy(data, key, keylen);
|
||||
memcpy(data, key->key, key->keylen);
|
||||
else if (cipher == MT_CIPHER_BIP_CMAC_128)
|
||||
memcpy(data + 16, key, 16);
|
||||
memcpy(data + 16, key->key, 16);
|
||||
}
|
||||
} else {
|
||||
if (wcid->cipher & ~BIT(cipher)) {
|
||||
|
|
@ -1070,12 +1070,11 @@ int mt7615_mac_wtbl_update_key(struct mt7615_dev *dev,
|
|||
|
||||
return 0;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(mt7615_mac_wtbl_update_key);
|
||||
|
||||
int mt7615_mac_wtbl_update_pk(struct mt7615_dev *dev,
|
||||
struct mt76_wcid *wcid,
|
||||
enum mt7615_cipher_type cipher,
|
||||
int keyidx, enum set_key_cmd cmd)
|
||||
static int
|
||||
mt7615_mac_wtbl_update_pk(struct mt7615_dev *dev, struct mt76_wcid *wcid,
|
||||
enum mt7615_cipher_type cipher,
|
||||
int keyidx, enum set_key_cmd cmd)
|
||||
{
|
||||
u32 addr = mt7615_mac_wtbl_addr(dev, wcid->idx), w0, w1;
|
||||
|
||||
|
|
@ -1107,12 +1106,11 @@ int mt7615_mac_wtbl_update_pk(struct mt7615_dev *dev,
|
|||
|
||||
return 0;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(mt7615_mac_wtbl_update_pk);
|
||||
|
||||
void mt7615_mac_wtbl_update_cipher(struct mt7615_dev *dev,
|
||||
struct mt76_wcid *wcid,
|
||||
enum mt7615_cipher_type cipher,
|
||||
enum set_key_cmd cmd)
|
||||
static void
|
||||
mt7615_mac_wtbl_update_cipher(struct mt7615_dev *dev, struct mt76_wcid *wcid,
|
||||
enum mt7615_cipher_type cipher,
|
||||
enum set_key_cmd cmd)
|
||||
{
|
||||
u32 addr = mt7615_mac_wtbl_addr(dev, wcid->idx);
|
||||
|
||||
|
|
@ -1130,12 +1128,11 @@ void mt7615_mac_wtbl_update_cipher(struct mt7615_dev *dev,
|
|||
mt76_clear(dev, addr + 2 * 4, MT_WTBL_W2_KEY_TYPE);
|
||||
}
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(mt7615_mac_wtbl_update_cipher);
|
||||
|
||||
int mt7615_mac_wtbl_set_key(struct mt7615_dev *dev,
|
||||
struct mt76_wcid *wcid,
|
||||
struct ieee80211_key_conf *key,
|
||||
enum set_key_cmd cmd)
|
||||
int __mt7615_mac_wtbl_set_key(struct mt7615_dev *dev,
|
||||
struct mt76_wcid *wcid,
|
||||
struct ieee80211_key_conf *key,
|
||||
enum set_key_cmd cmd)
|
||||
{
|
||||
enum mt7615_cipher_type cipher;
|
||||
int err;
|
||||
|
|
@ -1144,25 +1141,32 @@ int mt7615_mac_wtbl_set_key(struct mt7615_dev *dev,
|
|||
if (cipher == MT_CIPHER_NONE)
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
spin_lock_bh(&dev->mt76.lock);
|
||||
|
||||
mt7615_mac_wtbl_update_cipher(dev, wcid, cipher, cmd);
|
||||
err = mt7615_mac_wtbl_update_key(dev, wcid, key->key, key->keylen,
|
||||
cipher, cmd);
|
||||
err = mt7615_mac_wtbl_update_key(dev, wcid, key, cipher, cmd);
|
||||
if (err < 0)
|
||||
goto out;
|
||||
return err;
|
||||
|
||||
err = mt7615_mac_wtbl_update_pk(dev, wcid, cipher, key->keyidx,
|
||||
cmd);
|
||||
err = mt7615_mac_wtbl_update_pk(dev, wcid, cipher, key->keyidx, cmd);
|
||||
if (err < 0)
|
||||
goto out;
|
||||
return err;
|
||||
|
||||
if (cmd == SET_KEY)
|
||||
wcid->cipher |= BIT(cipher);
|
||||
else
|
||||
wcid->cipher &= ~BIT(cipher);
|
||||
|
||||
out:
|
||||
return 0;
|
||||
}
|
||||
|
||||
int mt7615_mac_wtbl_set_key(struct mt7615_dev *dev,
|
||||
struct mt76_wcid *wcid,
|
||||
struct ieee80211_key_conf *key,
|
||||
enum set_key_cmd cmd)
|
||||
{
|
||||
int err;
|
||||
|
||||
spin_lock_bh(&dev->mt76.lock);
|
||||
err = __mt7615_mac_wtbl_set_key(dev, wcid, key, cmd);
|
||||
spin_unlock_bh(&dev->mt76.lock);
|
||||
|
||||
return err;
|
||||
|
|
|
|||
|
|
@ -320,39 +320,6 @@ int mt7615_set_channel(struct mt7615_phy *phy)
|
|||
return ret;
|
||||
}
|
||||
|
||||
static int
|
||||
mt7615_queue_key_update(struct mt7615_dev *dev, enum set_key_cmd cmd,
|
||||
struct mt7615_sta *msta,
|
||||
struct ieee80211_key_conf *key)
|
||||
{
|
||||
struct mt7615_wtbl_desc *wd;
|
||||
|
||||
wd = kzalloc(sizeof(*wd), GFP_KERNEL);
|
||||
if (!wd)
|
||||
return -ENOMEM;
|
||||
|
||||
wd->type = MT7615_WTBL_KEY_DESC;
|
||||
wd->sta = msta;
|
||||
|
||||
wd->key.key = kmemdup(key->key, key->keylen, GFP_KERNEL);
|
||||
if (!wd->key.key) {
|
||||
kfree(wd);
|
||||
return -ENOMEM;
|
||||
}
|
||||
wd->key.cipher = key->cipher;
|
||||
wd->key.keyidx = key->keyidx;
|
||||
wd->key.keylen = key->keylen;
|
||||
wd->key.cmd = cmd;
|
||||
|
||||
spin_lock_bh(&dev->mt76.lock);
|
||||
list_add_tail(&wd->node, &dev->wd_head);
|
||||
spin_unlock_bh(&dev->mt76.lock);
|
||||
|
||||
queue_work(dev->mt76.wq, &dev->wtbl_work);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int mt7615_set_key(struct ieee80211_hw *hw, enum set_key_cmd cmd,
|
||||
struct ieee80211_vif *vif, struct ieee80211_sta *sta,
|
||||
struct ieee80211_key_conf *key)
|
||||
|
|
@ -406,7 +373,7 @@ static int mt7615_set_key(struct ieee80211_hw *hw, enum set_key_cmd cmd,
|
|||
if (mt76_is_mmio(&dev->mt76))
|
||||
err = mt7615_mac_wtbl_set_key(dev, wcid, key, cmd);
|
||||
else
|
||||
err = mt7615_queue_key_update(dev, cmd, msta, key);
|
||||
err = __mt7615_mac_wtbl_set_key(dev, wcid, key, cmd);
|
||||
|
||||
mt7615_mutex_release(dev);
|
||||
|
||||
|
|
|
|||
|
|
@ -108,15 +108,6 @@ struct mt7615_rate_desc {
|
|||
|
||||
enum mt7615_wtbl_desc_type {
|
||||
MT7615_WTBL_RATE_DESC,
|
||||
MT7615_WTBL_KEY_DESC
|
||||
};
|
||||
|
||||
struct mt7615_key_desc {
|
||||
enum set_key_cmd cmd;
|
||||
u32 cipher;
|
||||
s8 keyidx;
|
||||
u8 keylen;
|
||||
u8 *key;
|
||||
};
|
||||
|
||||
struct mt7615_wtbl_desc {
|
||||
|
|
@ -127,7 +118,6 @@ struct mt7615_wtbl_desc {
|
|||
|
||||
union {
|
||||
struct mt7615_rate_desc rate;
|
||||
struct mt7615_key_desc key;
|
||||
};
|
||||
};
|
||||
|
||||
|
|
@ -571,22 +561,13 @@ int mt7615_mac_write_txwi(struct mt7615_dev *dev, __le32 *txwi,
|
|||
struct ieee80211_sta *sta, int pid,
|
||||
struct ieee80211_key_conf *key, bool beacon);
|
||||
void mt7615_mac_set_timing(struct mt7615_phy *phy);
|
||||
int __mt7615_mac_wtbl_set_key(struct mt7615_dev *dev,
|
||||
struct mt76_wcid *wcid,
|
||||
struct ieee80211_key_conf *key,
|
||||
enum set_key_cmd cmd);
|
||||
int mt7615_mac_wtbl_set_key(struct mt7615_dev *dev, struct mt76_wcid *wcid,
|
||||
struct ieee80211_key_conf *key,
|
||||
enum set_key_cmd cmd);
|
||||
int mt7615_mac_wtbl_update_pk(struct mt7615_dev *dev,
|
||||
struct mt76_wcid *wcid,
|
||||
enum mt7615_cipher_type cipher,
|
||||
int keyidx, enum set_key_cmd cmd);
|
||||
void mt7615_mac_wtbl_update_cipher(struct mt7615_dev *dev,
|
||||
struct mt76_wcid *wcid,
|
||||
enum mt7615_cipher_type cipher,
|
||||
enum set_key_cmd cmd);
|
||||
int mt7615_mac_wtbl_update_key(struct mt7615_dev *dev,
|
||||
struct mt76_wcid *wcid,
|
||||
u8 *key, u8 keylen,
|
||||
enum mt7615_cipher_type cipher,
|
||||
enum set_key_cmd cmd);
|
||||
void mt7615_mac_reset_work(struct work_struct *work);
|
||||
u32 mt7615_mac_get_sta_tid_sn(struct mt7615_dev *dev, int wcid, u8 tid);
|
||||
|
||||
|
|
|
|||
|
|
@ -132,52 +132,6 @@ mt7663_usb_sdio_set_rates(struct mt7615_dev *dev,
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
mt7663_usb_sdio_set_key(struct mt7615_dev *dev,
|
||||
struct mt7615_wtbl_desc *wd)
|
||||
{
|
||||
struct mt7615_key_desc *key = &wd->key;
|
||||
struct mt7615_sta *sta = wd->sta;
|
||||
enum mt7615_cipher_type cipher;
|
||||
struct mt76_wcid *wcid;
|
||||
int err;
|
||||
|
||||
lockdep_assert_held(&dev->mt76.mutex);
|
||||
|
||||
if (!sta) {
|
||||
err = -EINVAL;
|
||||
goto out;
|
||||
}
|
||||
|
||||
cipher = mt7615_mac_get_cipher(key->cipher);
|
||||
if (cipher == MT_CIPHER_NONE) {
|
||||
err = -EOPNOTSUPP;
|
||||
goto out;
|
||||
}
|
||||
|
||||
wcid = &wd->sta->wcid;
|
||||
|
||||
mt7615_mac_wtbl_update_cipher(dev, wcid, cipher, key->cmd);
|
||||
err = mt7615_mac_wtbl_update_key(dev, wcid, key->key, key->keylen,
|
||||
cipher, key->cmd);
|
||||
if (err < 0)
|
||||
goto out;
|
||||
|
||||
err = mt7615_mac_wtbl_update_pk(dev, wcid, cipher, key->keyidx,
|
||||
key->cmd);
|
||||
if (err < 0)
|
||||
goto out;
|
||||
|
||||
if (key->cmd == SET_KEY)
|
||||
wcid->cipher |= BIT(cipher);
|
||||
else
|
||||
wcid->cipher &= ~BIT(cipher);
|
||||
out:
|
||||
kfree(key->key);
|
||||
|
||||
return err;
|
||||
}
|
||||
|
||||
void mt7663_usb_sdio_wtbl_work(struct work_struct *work)
|
||||
{
|
||||
struct mt7615_wtbl_desc *wd, *wd_next;
|
||||
|
|
@ -201,9 +155,6 @@ void mt7663_usb_sdio_wtbl_work(struct work_struct *work)
|
|||
case MT7615_WTBL_RATE_DESC:
|
||||
mt7663_usb_sdio_set_rates(dev, wd);
|
||||
break;
|
||||
case MT7615_WTBL_KEY_DESC:
|
||||
mt7663_usb_sdio_set_key(dev, wd);
|
||||
break;
|
||||
}
|
||||
|
||||
mt7615_mutex_release(dev);
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user