| From 00b059f02bfa01d1ce6c25ea6baf7ba72d523e40 Mon Sep 17 00:00:00 2001 |
| From: Sasha Levin <sashal@kernel.org> |
| Date: Wed, 10 Feb 2021 20:40:24 +0200 |
| Subject: wilc1000: Fix use of void pointer as a wrong struct type |
| |
| From: Vsevolod Kozlov <zaba@mm.st> |
| |
| [ Upstream commit 6fe91b69ceceea832a73d35185df04b3e877f399 ] |
| |
| ac_classify() expects a struct sk_buff* as its second argument, which is |
| a member of struct tx_complete_data. priv happens to be a pointer to |
| struct tx_complete_data, so passing it directly to ac_classify() leads |
| to wrong behaviour and occasional panics. |
| |
| Since there is only one caller of wilc_wlan_txq_add_net_pkt and it |
| already knows the type behind this pointer, and the structure is already |
| in the header file, change the function signature to use the real type |
| instead of void* in order to prevent confusion. |
| |
| Signed-off-by: Vsevolod Kozlov <zaba@mm.st> |
| Signed-off-by: Kalle Valo <kvalo@codeaurora.org> |
| Link: https://lore.kernel.org/r/YCQomJ1mO5BLxYOT@Vsevolods-Mini.lan |
| Signed-off-by: Sasha Levin <sashal@kernel.org> |
| --- |
| drivers/net/wireless/microchip/wilc1000/netdev.c | 2 +- |
| drivers/net/wireless/microchip/wilc1000/wlan.c | 15 ++++++++------- |
| drivers/net/wireless/microchip/wilc1000/wlan.h | 3 ++- |
| 3 files changed, 11 insertions(+), 9 deletions(-) |
| |
| diff --git a/drivers/net/wireless/microchip/wilc1000/netdev.c b/drivers/net/wireless/microchip/wilc1000/netdev.c |
| index 2a1fbbdd6a4b..0c188310919e 100644 |
| --- a/drivers/net/wireless/microchip/wilc1000/netdev.c |
| +++ b/drivers/net/wireless/microchip/wilc1000/netdev.c |
| @@ -737,7 +737,7 @@ netdev_tx_t wilc_mac_xmit(struct sk_buff *skb, struct net_device *ndev) |
| |
| vif->netstats.tx_packets++; |
| vif->netstats.tx_bytes += tx_data->size; |
| - queue_count = wilc_wlan_txq_add_net_pkt(ndev, (void *)tx_data, |
| + queue_count = wilc_wlan_txq_add_net_pkt(ndev, tx_data, |
| tx_data->buff, tx_data->size, |
| wilc_tx_complete); |
| |
| diff --git a/drivers/net/wireless/microchip/wilc1000/wlan.c b/drivers/net/wireless/microchip/wilc1000/wlan.c |
| index c12f27be9f79..31d51385ba93 100644 |
| --- a/drivers/net/wireless/microchip/wilc1000/wlan.c |
| +++ b/drivers/net/wireless/microchip/wilc1000/wlan.c |
| @@ -408,7 +408,8 @@ static inline u8 ac_change(struct wilc *wilc, u8 *ac) |
| return 1; |
| } |
| |
| -int wilc_wlan_txq_add_net_pkt(struct net_device *dev, void *priv, u8 *buffer, |
| +int wilc_wlan_txq_add_net_pkt(struct net_device *dev, |
| + struct tx_complete_data *tx_data, u8 *buffer, |
| u32 buffer_size, |
| void (*tx_complete_fn)(void *, int)) |
| { |
| @@ -420,27 +421,27 @@ int wilc_wlan_txq_add_net_pkt(struct net_device *dev, void *priv, u8 *buffer, |
| wilc = vif->wilc; |
| |
| if (wilc->quit) { |
| - tx_complete_fn(priv, 0); |
| + tx_complete_fn(tx_data, 0); |
| return 0; |
| } |
| |
| tqe = kmalloc(sizeof(*tqe), GFP_ATOMIC); |
| |
| if (!tqe) { |
| - tx_complete_fn(priv, 0); |
| + tx_complete_fn(tx_data, 0); |
| return 0; |
| } |
| tqe->type = WILC_NET_PKT; |
| tqe->buffer = buffer; |
| tqe->buffer_size = buffer_size; |
| tqe->tx_complete_func = tx_complete_fn; |
| - tqe->priv = priv; |
| + tqe->priv = tx_data; |
| tqe->vif = vif; |
| |
| - q_num = ac_classify(wilc, priv); |
| + q_num = ac_classify(wilc, tx_data->skb); |
| tqe->q_num = q_num; |
| if (ac_change(wilc, &q_num)) { |
| - tx_complete_fn(priv, 0); |
| + tx_complete_fn(tx_data, 0); |
| kfree(tqe); |
| return 0; |
| } |
| @@ -451,7 +452,7 @@ int wilc_wlan_txq_add_net_pkt(struct net_device *dev, void *priv, u8 *buffer, |
| tcp_process(dev, tqe); |
| wilc_wlan_txq_add_to_tail(dev, q_num, tqe); |
| } else { |
| - tx_complete_fn(priv, 0); |
| + tx_complete_fn(tx_data, 0); |
| kfree(tqe); |
| } |
| |
| diff --git a/drivers/net/wireless/microchip/wilc1000/wlan.h b/drivers/net/wireless/microchip/wilc1000/wlan.h |
| index 3d2104f19819..d55eb6b3a12a 100644 |
| --- a/drivers/net/wireless/microchip/wilc1000/wlan.h |
| +++ b/drivers/net/wireless/microchip/wilc1000/wlan.h |
| @@ -399,7 +399,8 @@ int wilc_wlan_firmware_download(struct wilc *wilc, const u8 *buffer, |
| u32 buffer_size); |
| int wilc_wlan_start(struct wilc *wilc); |
| int wilc_wlan_stop(struct wilc *wilc, struct wilc_vif *vif); |
| -int wilc_wlan_txq_add_net_pkt(struct net_device *dev, void *priv, u8 *buffer, |
| +int wilc_wlan_txq_add_net_pkt(struct net_device *dev, |
| + struct tx_complete_data *tx_data, u8 *buffer, |
| u32 buffer_size, |
| void (*tx_complete_fn)(void *, int)); |
| int wilc_wlan_handle_txq(struct wilc *wl, u32 *txq_count); |
| -- |
| 2.30.1 |
| |