Obtain client (STA) capabilities for bandsteering

I am searching for a way to determine if a STA connected supports dual band capability, as this is a key need for a bandsteering algorithm, because before you streer a STA you first need to know if the device can operate in the other band.

// ---------------------------------- First I will show how far i have reached --------------------------------------

Theoretically this information goes in the association request frames, but some devices does not include this information. In this example we have a device which indicates every operating class supported:

Here is clear that this device is only 5 GHz capable and supports operating classes for 20/40/80 MHz width. And this is correct, the device is a TP-Link RE200 operating as STA in the 5 GHz radio.

But with my mobile (Motorola G7) this is different, the information is missing. Anyway, I think that in this kind of cases there is no so much to do, maybe register when the device connects in each band so in the future the system can remember that capability.

So, the interesting part is obtaining the association frames of the wifi clients, or the capability information that they contain. The nearer I have been from it is by calling hostapd via ubus like this:

ubus call hostapd.wlan0 get_clients

And the answer is:

{
        "freq": 5745,
        "clients": {
                "24:46:c8:bb:08:5f": {
                        "auth": true,
                        "assoc": true,
                        "authorized": true,
                        "preauth": false,
                        "wds": false,
                        "wmm": true,
                        "ht": true,
                        "vht": false,
                        "wps": false,
                        "mfp": false,
                        "rrm": [
                                0,
                                0,
                                0,
                                0,
                                0
                        ],
                        "extended_capabilities": [
                                0,
                                0,
                                0,
                                2
                        ],
                        "aid": 1,
                        "signature": "wifi4|probe:0,1,45,221(0050f2,8),htcap:016e,htagg:03,htmcs:000000ff|assoc:0,1,48,45,221(0050f2,2),127,htcap:016e,htagg:03,htmcs:000000ff,extcap:00000002",
                        "bytes": {
                                "rx": 3240243,
                                "tx": 106593816
                        },
                        "airtime": {
                                "rx": 0,
                                "tx": 155166212
                        },
                        "packets": {
                                "rx": 16435,
                                "tx": 87252
                        },
                        "rate": {
                                "rx": 6000,
                                "tx": 150000
                        },
                        "signal": -33,
                        "capabilities": {

                        }
                }
        }
}

Where the relevant part seems to be the field named "signature", specifically the "assoc" section:

"signature": "wifi4
|probe:0,1,45,221(0050f2,8),htcap:016e,htagg:03,htmcs:000000ff
|assoc:0,1,48,45,221(0050f2,2),127,htcap:016e,htagg:03,htmcs:000000ff,extcap:00000002",

Here I have noticed that the number list "0,1,48,45,221,127" are the tag identifiers:

So, in the "signature" field all the tagged parameters of the association request frame are being registered, but no its content, just part of it, which is here in the second part of the section ("htcap:016e,htagg:03,htmcs:000000ff,extcap:00000002" in the example).

// ------------------------------------------------------- So... --------------------------------------------------------

  1. This is possible to obtain the whole association request information from a desired associated STA?

  2. There is another way to know the dual band capability of a STA device?

I think that answering this questions are a must to anyone who wants to develop a bandsteering algorithm.

So just to be clear, this is not related to OpenWrt, correct?

See: "Bind" client to specific SSID vs "band steering"

This is totally related to OpenWRT as I am trying to find a way to obtain association request frames and/or bandsteering capabilities of every STA associated via IPCs or tools available in OpenWRT systems to do bandsteering in OpenWRT wifi infrastructure devices.

The topic you recommend does not abord the issue, there are a discussion about bandsteering itself, but no about the problem of knowing which STA device is dual band capable. If your need goes about a specific device with a fixed MAC address maybe you do not need that, but in a true bandsteering algorithm you will need an automatized way to determine if a STA is dual band capable, because you don't know which devices will connect to your network. Or maybe you know them but you don't know their mac addresses (as today is really common the MAC address randomization feature.)

  • To be clear, you're referring to the client as STA...and the client is not OpenWrt, correct?
  • Are you saying that you're trying to program some Band Steering capability into OpenWrt?
    • Which means you're looking for non-OpenWrt data, correct?
  • Did you see in that thread - how the data is related to the STA, not the AP?

To be clear, are you saying that you wish obtain something from the client that it doesn't actually transmit?

If the STA doesn't transmit those details, then it's not capable - maybe I'm missing something?

(There's also more threads:)

The STA can be OpenWRT or not. But as are OpenWRT is targeted to infrastructure devices 99% of the associated stations probably will no be OpenWRT.

As I said, the information at least should be in the association frames, which any WiFi Device transmits (in other case, there won't be WiFi association). So for sure OpenWRT gets this information and I showed proofs of that, and I showed that what I get is incomplete, so I ask if there is a way to obtain the full info.

And of course I am also asking for a workaround in case of the association frame is incomplete, or any other problem in obtaining it, to improve the robustness of the solution (in all or some specific cases), as I obviosly don't know all in the universe and maybe there is a guy with a great alternative idea to do that which is out of my knowledge today. For example: "hey buddy, if you detect that the STA is associated in 2.4 GHz and you see it is VHT capable... as VHT is just for 5.8 GHz, you can infer that is a dual band device in that case, right?"

About what I am developing, yes, I am developing a band steering algorithm which is part of a biger proyect, which in short words is a whole WiFi Alliance Multi-AP v1 (aka "EasyMesh") implementantion for OpenWRT in Python3.

1 Like

Are you saying the AP can force transmission of these frames?

And force transmission...from the other band???

Please explain how an AP forces the STA to do this (OpenWrt or otherwise)?

Maybe I'm missing something here.

I thought the threads where clear, but it seems like you're still saying/beleiving the AP can make the STA give more information, is that correct?

On a router?

Cool!

EDIT - see, this should help you understand the process as implemented by one OEM: https://documentation.meraki.com/MR/Radio_Settings/Band_Steering#How_Band_Steering_works

Hope this helps.

1 Like

The Association Frame Request is always sent by any STA who wants to associate to a BSS. Here you can check in this .pcaps the process of simply connecting a device. AP does not need to force anything, the information is received in the association (or re-association) of the device. Also the EasyMesh specification defines that the proper way to obtain the complete STA capabilities is to copy the last association frame request of the desired STA.

Yes, in almost "all" the openwrt devices with a minimum hardware spec which is 128 RAM / 16 Flash for the complete version or 64 RAM / 8 Flash for "only agent/slave" devices (not capable/recommendable of running the controller). I have pretty solved all the onboarding and autoconfiguration processes and now I am working in things like advanced capabilities information, radio configurations, topology discovering and a clean client steering.

1 Like

An update:

Via hostapd_cli you can find the "operating classes list" and maybe all the information carried in the association frames. For example:

hostapd_cli -i wlan0 sta 2C:DB:07:54:47:7D

2c:db:07:54:47:7d
flags=[AUTH][ASSOC][AUTHORIZED][WMM][HT][VHT]
aid=1
capability=0x1111
listen_interval=250
supported_rates=8c 12 98 24 b0 48 60 6c
timeout_next=NULLFUNC POLL
dot11RSNAStatsSTAAddress=2c:db:07:54:47:7d
dot11RSNAStatsVersion=1
dot11RSNAStatsSelectedPairwiseCipher=00-0f-ac-4
dot11RSNAStatsTKIPLocalMICFailures=0
dot11RSNAStatsTKIPRemoteMICFailures=0
wpa=2
AKMSuiteSelector=00-0f-ac-2
hostapdWPAPTKState=11
hostapdWPAPTKGroupState=0
rx_packets=12499
tx_packets=37804
rx_bytes=1300663
tx_bytes=56117870
inactive_msec=272
signal=-37
rx_rate_info=8667 vhtmcs 9 vhtnss 2 shortGI
tx_rate_info=7800 vhtmcs 8 vhtnss 2 shortGI
rx_vht_mcs_map=fffa
tx_vht_mcs_map=fffa
ht_mcs_bitmask=ffff0000000000000000
connected_time=160
supp_op_classes=80515354737475767778797a7b7c7d7e7f8081
min_txpower=0
max_txpower=15
vht_caps_info=0x038001b2
ht_caps_info=0x09e7
ext_capab=04008880014000c00000

Where supp_op_classes are a list of bytes, hex encoded. Just to help if someone does not know about what are they, 802.11 stablishes "world operating classes" which are codes/numbers which classify the spectrum capabilities of a radio.

For example, operating classes \x51 \53 x\54 (81, 83 and 84 in decimal) are 2.4 GHz Op classes, while the rest are for 5.8 GHz. So there you can find that this device is dual band capable, and also in which possible channel configurations. For example, operating class 81 is channels 1-13 with 20 MHz width.

Unfortunatelly this seems not to be available via ubus. And just to clarify, if a device does not send this information like my mobile, is time to think about workaround methods to infer the dual band capability of that devices, at least to discover it sometimes while sometimes that could not be possible. A contention strategy could be just remember if the device has been seen connected in each band in the past, and this information should be valid until the device leaves the network for a while (some mins, an hour, not more).

hostapd's (out-of-tree-) ubus integration only contains features other have found necessary so far, it can be extended as necessary (e.g. https://github.com/openwrt/openwrt/pull/4934).

2 Likes

Thanks, I will be checking this