Skip to content

Commit

Permalink
cfg80211: dynamically allocate per-tid stats for station info
Browse files Browse the repository at this point in the history
With the addition of TXQ stats in the per-tid statistics the struct
station_info grew significantly. This resulted in stack size warnings
due to the structure itself being above the limit for the warnings.

Add an allocation function that those who want to provide per-tid
stats should use to allocate the tid array, i.e.
struct station_info::pertid.

Cc: Toke Høiland-Jørgensen <toke@toke.dk>
Fixes: 52539ca ("cfg80211: Expose TXQ stats and parameters to userspace")
Signed-off-by: Arend van Spriel <aspriel@gmail.com>
[johannes: fix missing BIT() and logic by removing]
Signed-off-by: Johannes Berg <johannes.berg@intel.com>
  • Loading branch information
aspriel authored and jmberg-intel committed May 18, 2018
1 parent 57c6cb8 commit 8689c05
Show file tree
Hide file tree
Showing 4 changed files with 27 additions and 6 deletions.
10 changes: 9 additions & 1 deletion include/net/cfg80211.h
Original file line number Diff line number Diff line change
Expand Up @@ -1184,6 +1184,7 @@ struct cfg80211_tid_stats {
* @rx_duration: aggregate PPDU duration(usecs) for all the frames from a peer
* @pertid: per-TID statistics, see &struct cfg80211_tid_stats, using the last
* (IEEE80211_NUM_TIDS) index for MSDUs not encapsulated in QoS-MPDUs.
* Note that this doesn't use the @filled bit, but is used if non-NULL.
* @ack_signal: signal strength (in dBm) of the last ACK frame.
* @avg_ack_signal: average rssi value of ack packet for the no of msdu's has
* been sent.
Expand Down Expand Up @@ -1230,7 +1231,7 @@ struct station_info {
u64 rx_beacon;
u64 rx_duration;
u8 rx_beacon_signal_avg;
struct cfg80211_tid_stats pertid[IEEE80211_NUM_TIDS + 1];
struct cfg80211_tid_stats *pertid;
s8 ack_signal;
s8 avg_ack_signal;
};
Expand Down Expand Up @@ -5701,6 +5702,13 @@ void cfg80211_remain_on_channel_expired(struct wireless_dev *wdev, u64 cookie,
struct ieee80211_channel *chan,
gfp_t gfp);

/**
* cfg80211_sinfo_alloc_tid_stats - allocate per-tid statistics.
*
* @sinfo: the station information
* @gfp: allocation flags
*/
int cfg80211_sinfo_alloc_tid_stats(struct station_info *sinfo, gfp_t gfp);

/**
* cfg80211_new_sta - notify userspace about station
Expand Down
9 changes: 5 additions & 4 deletions net/mac80211/sta_info.c
Original file line number Diff line number Diff line change
Expand Up @@ -2233,11 +2233,12 @@ void sta_set_sinfo(struct sta_info *sta, struct station_info *sinfo)
sinfo->filled |= BIT(NL80211_STA_INFO_RX_BITRATE);
}

sinfo->filled |= BIT(NL80211_STA_INFO_TID_STATS);
for (i = 0; i < IEEE80211_NUM_TIDS + 1; i++) {
struct cfg80211_tid_stats *tidstats = &sinfo->pertid[i];
if (!cfg80211_sinfo_alloc_tid_stats(sinfo, GFP_KERNEL)) {
for (i = 0; i < IEEE80211_NUM_TIDS + 1; i++) {
struct cfg80211_tid_stats *tidstats = &sinfo->pertid[i];

sta_set_tidstats(sta, tidstats, i);
sta_set_tidstats(sta, tidstats, i);
}
}

if (ieee80211_vif_is_mesh(&sdata->vif)) {
Expand Down
3 changes: 2 additions & 1 deletion net/wireless/nl80211.c
Original file line number Diff line number Diff line change
Expand Up @@ -4658,7 +4658,7 @@ static int nl80211_send_station(struct sk_buff *msg, u32 cmd, u32 portid,
#undef PUT_SINFO
#undef PUT_SINFO_U64

if (sinfo->filled & BIT(NL80211_STA_INFO_TID_STATS)) {
if (sinfo->pertid) {
struct nlattr *tidsattr;
int tid;

Expand Down Expand Up @@ -4702,6 +4702,7 @@ static int nl80211_send_station(struct sk_buff *msg, u32 cmd, u32 portid,
}

nla_nest_end(msg, tidsattr);
kfree(sinfo->pertid);
}

nla_nest_end(msg, sinfoattr);
Expand Down
11 changes: 11 additions & 0 deletions net/wireless/util.c
Original file line number Diff line number Diff line change
Expand Up @@ -1787,6 +1787,17 @@ bool cfg80211_does_bw_fit_range(const struct ieee80211_freq_range *freq_range,
return false;
}

int cfg80211_sinfo_alloc_tid_stats(struct station_info *sinfo, gfp_t gfp)
{
sinfo->pertid = kcalloc(sizeof(*(sinfo->pertid)),
IEEE80211_NUM_TIDS + 1, gfp);
if (!sinfo->pertid)
return -ENOMEM;

return 0;
}
EXPORT_SYMBOL(cfg80211_sinfo_alloc_tid_stats);

/* See IEEE 802.1H for LLC/SNAP encapsulation/decapsulation */
/* Ethernet-II snap header (RFC1042 for most EtherTypes) */
const unsigned char rfc1042_header[] __aligned(2) =
Expand Down

0 comments on commit 8689c05

Please sign in to comment.