|
@@ -0,0 +1,97 @@
|
|
|
+--- a/station.c
|
|
|
++++ b/station.c
|
|
|
+@@ -29,13 +29,43 @@ enum plink_actions {
|
|
|
+ PLINK_ACTION_BLOCK,
|
|
|
+ };
|
|
|
+
|
|
|
++static void print_sta_bitrate(struct nlattr *nla, const char *name)
|
|
|
++{
|
|
|
++ struct nlattr *rinfo[NL80211_RATE_INFO_MAX + 1];
|
|
|
++
|
|
|
++ static struct nla_policy rate_policy[NL80211_RATE_INFO_MAX + 1] = {
|
|
|
++ [NL80211_RATE_INFO_BITRATE] = { .type = NLA_U16 },
|
|
|
++ [NL80211_RATE_INFO_MCS] = { .type = NLA_U8 },
|
|
|
++ [NL80211_RATE_INFO_40_MHZ_WIDTH] = { .type = NLA_FLAG },
|
|
|
++ [NL80211_RATE_INFO_SHORT_GI] = { .type = NLA_FLAG },
|
|
|
++ };
|
|
|
++
|
|
|
++ if (!nla)
|
|
|
++ return;
|
|
|
++
|
|
|
++ if (nla_parse_nested(rinfo, NL80211_RATE_INFO_MAX, nla, rate_policy)) {
|
|
|
++ fprintf(stderr, "failed to parse nested rate attributes!\n");
|
|
|
++ } else {
|
|
|
++ printf("\n\t%s:\t", name);
|
|
|
++ if (rinfo[NL80211_RATE_INFO_BITRATE]) {
|
|
|
++ int rate = nla_get_u16(rinfo[NL80211_RATE_INFO_BITRATE]);
|
|
|
++ printf("%d.%d MBit/s", rate / 10, rate % 10);
|
|
|
++ }
|
|
|
++
|
|
|
++ if (rinfo[NL80211_RATE_INFO_MCS])
|
|
|
++ printf(" MCS %d", nla_get_u8(rinfo[NL80211_RATE_INFO_MCS]));
|
|
|
++ if (rinfo[NL80211_RATE_INFO_40_MHZ_WIDTH])
|
|
|
++ printf(" 40Mhz");
|
|
|
++ if (rinfo[NL80211_RATE_INFO_SHORT_GI])
|
|
|
++ printf(" short GI");
|
|
|
++ }
|
|
|
++}
|
|
|
+
|
|
|
+ static int print_sta_handler(struct nl_msg *msg, void *arg)
|
|
|
+ {
|
|
|
+ struct nlattr *tb[NL80211_ATTR_MAX + 1];
|
|
|
+ struct genlmsghdr *gnlh = nlmsg_data(nlmsg_hdr(msg));
|
|
|
+ struct nlattr *sinfo[NL80211_STA_INFO_MAX + 1];
|
|
|
+- struct nlattr *rinfo[NL80211_RATE_INFO_MAX + 1];
|
|
|
+ char mac_addr[20], state_name[10], dev[20];
|
|
|
+ static struct nla_policy stats_policy[NL80211_STA_INFO_MAX + 1] = {
|
|
|
+ [NL80211_STA_INFO_INACTIVE_TIME] = { .type = NLA_U32 },
|
|
|
+@@ -45,6 +75,7 @@ static int print_sta_handler(struct nl_m
|
|
|
+ [NL80211_STA_INFO_TX_PACKETS] = { .type = NLA_U32 },
|
|
|
+ [NL80211_STA_INFO_SIGNAL] = { .type = NLA_U8 },
|
|
|
+ [NL80211_STA_INFO_TX_BITRATE] = { .type = NLA_NESTED },
|
|
|
++ [NL80211_STA_INFO_RX_BITRATE] = { .type = NLA_NESTED },
|
|
|
+ [NL80211_STA_INFO_LLID] = { .type = NLA_U16 },
|
|
|
+ [NL80211_STA_INFO_PLID] = { .type = NLA_U16 },
|
|
|
+ [NL80211_STA_INFO_PLINK_STATE] = { .type = NLA_U8 },
|
|
|
+@@ -52,13 +83,6 @@ static int print_sta_handler(struct nl_m
|
|
|
+ [NL80211_STA_INFO_TX_FAILED] = { .type = NLA_U32 },
|
|
|
+ };
|
|
|
+
|
|
|
+- static struct nla_policy rate_policy[NL80211_RATE_INFO_MAX + 1] = {
|
|
|
+- [NL80211_RATE_INFO_BITRATE] = { .type = NLA_U16 },
|
|
|
+- [NL80211_RATE_INFO_MCS] = { .type = NLA_U8 },
|
|
|
+- [NL80211_RATE_INFO_40_MHZ_WIDTH] = { .type = NLA_FLAG },
|
|
|
+- [NL80211_RATE_INFO_SHORT_GI] = { .type = NLA_FLAG },
|
|
|
+- };
|
|
|
+-
|
|
|
+ nla_parse(tb, NL80211_ATTR_MAX, genlmsg_attrdata(gnlh, 0),
|
|
|
+ genlmsg_attrlen(gnlh, 0), NULL);
|
|
|
+
|
|
|
+@@ -111,25 +135,8 @@ static int print_sta_handler(struct nl_m
|
|
|
+ printf("\n\tsignal avg:\t%d dBm",
|
|
|
+ (int8_t)nla_get_u8(sinfo[NL80211_STA_INFO_SIGNAL_AVG]));
|
|
|
+
|
|
|
+- if (sinfo[NL80211_STA_INFO_TX_BITRATE]) {
|
|
|
+- if (nla_parse_nested(rinfo, NL80211_RATE_INFO_MAX,
|
|
|
+- sinfo[NL80211_STA_INFO_TX_BITRATE], rate_policy)) {
|
|
|
+- fprintf(stderr, "failed to parse nested rate attributes!\n");
|
|
|
+- } else {
|
|
|
+- printf("\n\ttx bitrate:\t");
|
|
|
+- if (rinfo[NL80211_RATE_INFO_BITRATE]) {
|
|
|
+- int rate = nla_get_u16(rinfo[NL80211_RATE_INFO_BITRATE]);
|
|
|
+- printf("%d.%d MBit/s", rate / 10, rate % 10);
|
|
|
+- }
|
|
|
+-
|
|
|
+- if (rinfo[NL80211_RATE_INFO_MCS])
|
|
|
+- printf(" MCS %d", nla_get_u8(rinfo[NL80211_RATE_INFO_MCS]));
|
|
|
+- if (rinfo[NL80211_RATE_INFO_40_MHZ_WIDTH])
|
|
|
+- printf(" 40Mhz");
|
|
|
+- if (rinfo[NL80211_RATE_INFO_SHORT_GI])
|
|
|
+- printf(" short GI");
|
|
|
+- }
|
|
|
+- }
|
|
|
++ print_sta_bitrate(sinfo[NL80211_STA_INFO_TX_BITRATE], "tx bitrate");
|
|
|
++ print_sta_bitrate(sinfo[NL80211_STA_INFO_RX_BITRATE], "rx bitrate");
|
|
|
+
|
|
|
+ if (sinfo[NL80211_STA_INFO_LLID])
|
|
|
+ printf("\n\tmesh llid:\t%d",
|