wifi: ath12k: Decrease ath12k_mac_station_assoc() stack usage

Building the ath12k driver with llvm-18.1.7-x86_64 produces the warning:

drivers/net/wireless/ath/ath12k/mac.c:5606:12: warning: stack frame size (1176) exceeds limit (1024) in 'ath12k_mac_op_sta_state' [-Wframe-larger-than]

ath12k_mac_op_sta_state() itself does not consume much stack, but it
calls ath12k_mac_handle_link_sta_state() which in turn calls
ath12k_mac_station_add(). Since those are both static functions with
only one caller, it is suspected that these both get inlined, and
their stack usage is reported for ath12k_mac_op_sta_state().

A major contributor to the ath12k_mac_station_assoc() stack usage is:

	struct ath12k_wmi_peer_assoc_arg peer_arg;

Avoid the excess stack usage by dynamically allocating peer_arg
instead of declaring it on the stack.

Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.3.1-00173-QCAHKSWPL_SILICONZ-1
Tested-on: WCN7850 hw2.0 PCI WLAN.HMT.1.0.c5-00481-QCAHMTSWPL_V1.0_V2.0_SILICONZ-3

Signed-off-by: Jeff Johnson <quic_jjohnson@quicinc.com>
Signed-off-by: Kalle Valo <quic_kvalo@quicinc.com>
Link: https://patch.msgid.link/20241217202618.1329312-5-kvalo@kernel.org
Signed-off-by: Jeff Johnson <jeff.johnson@oss.qualcomm.com>
This commit is contained in:
Jeff Johnson 2024-12-17 22:26:18 +02:00 committed by Jeff Johnson
parent 6ff412420e
commit bf2da5c4f5

View File

@ -4834,7 +4834,6 @@ static int ath12k_mac_station_assoc(struct ath12k *ar,
{
struct ieee80211_vif *vif = ath12k_ahvif_to_vif(arvif->ahvif);
struct ieee80211_sta *sta = ath12k_ahsta_to_sta(arsta->ahsta);
struct ath12k_wmi_peer_assoc_arg peer_arg;
struct ieee80211_link_sta *link_sta;
int ret;
struct cfg80211_chan_def def;
@ -4854,14 +4853,19 @@ static int ath12k_mac_station_assoc(struct ath12k *ar,
band = def.chan->band;
mask = &arvif->bitrate_mask;
ath12k_peer_assoc_prepare(ar, arvif, arsta, &peer_arg, reassoc);
struct ath12k_wmi_peer_assoc_arg *peer_arg __free(kfree) =
kzalloc(sizeof(*peer_arg), GFP_KERNEL);
if (!peer_arg)
return -ENOMEM;
if (peer_arg.peer_nss < 1) {
ath12k_peer_assoc_prepare(ar, arvif, arsta, peer_arg, reassoc);
if (peer_arg->peer_nss < 1) {
ath12k_warn(ar->ab,
"invalid peer NSS %d\n", peer_arg.peer_nss);
"invalid peer NSS %d\n", peer_arg->peer_nss);
return -EINVAL;
}
ret = ath12k_wmi_send_peer_assoc_cmd(ar, &peer_arg);
ret = ath12k_wmi_send_peer_assoc_cmd(ar, peer_arg);
if (ret) {
ath12k_warn(ar->ab, "failed to run peer assoc for STA %pM vdev %i: %d\n",
arsta->addr, arvif->vdev_id, ret);