linux/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fweh.h
<<
>>
Prefs
   1// SPDX-License-Identifier: ISC
   2/*
   3 * Copyright (c) 2012 Broadcom Corporation
   4 */
   5
   6
   7#ifndef FWEH_H_
   8#define FWEH_H_
   9
  10#include <asm/unaligned.h>
  11#include <linux/skbuff.h>
  12#include <linux/if_ether.h>
  13#include <linux/if.h>
  14
  15/* formward declarations */
  16struct brcmf_pub;
  17struct brcmf_if;
  18struct brcmf_cfg80211_info;
  19
  20/* list of firmware events */
  21#define BRCMF_FWEH_EVENT_ENUM_DEFLIST \
  22        BRCMF_ENUM_DEF(SET_SSID, 0) \
  23        BRCMF_ENUM_DEF(JOIN, 1) \
  24        BRCMF_ENUM_DEF(START, 2) \
  25        BRCMF_ENUM_DEF(AUTH, 3) \
  26        BRCMF_ENUM_DEF(AUTH_IND, 4) \
  27        BRCMF_ENUM_DEF(DEAUTH, 5) \
  28        BRCMF_ENUM_DEF(DEAUTH_IND, 6) \
  29        BRCMF_ENUM_DEF(ASSOC, 7) \
  30        BRCMF_ENUM_DEF(ASSOC_IND, 8) \
  31        BRCMF_ENUM_DEF(REASSOC, 9) \
  32        BRCMF_ENUM_DEF(REASSOC_IND, 10) \
  33        BRCMF_ENUM_DEF(DISASSOC, 11) \
  34        BRCMF_ENUM_DEF(DISASSOC_IND, 12) \
  35        BRCMF_ENUM_DEF(QUIET_START, 13) \
  36        BRCMF_ENUM_DEF(QUIET_END, 14) \
  37        BRCMF_ENUM_DEF(BEACON_RX, 15) \
  38        BRCMF_ENUM_DEF(LINK, 16) \
  39        BRCMF_ENUM_DEF(MIC_ERROR, 17) \
  40        BRCMF_ENUM_DEF(NDIS_LINK, 18) \
  41        BRCMF_ENUM_DEF(ROAM, 19) \
  42        BRCMF_ENUM_DEF(TXFAIL, 20) \
  43        BRCMF_ENUM_DEF(PMKID_CACHE, 21) \
  44        BRCMF_ENUM_DEF(RETROGRADE_TSF, 22) \
  45        BRCMF_ENUM_DEF(PRUNE, 23) \
  46        BRCMF_ENUM_DEF(AUTOAUTH, 24) \
  47        BRCMF_ENUM_DEF(EAPOL_MSG, 25) \
  48        BRCMF_ENUM_DEF(SCAN_COMPLETE, 26) \
  49        BRCMF_ENUM_DEF(ADDTS_IND, 27) \
  50        BRCMF_ENUM_DEF(DELTS_IND, 28) \
  51        BRCMF_ENUM_DEF(BCNSENT_IND, 29) \
  52        BRCMF_ENUM_DEF(BCNRX_MSG, 30) \
  53        BRCMF_ENUM_DEF(BCNLOST_MSG, 31) \
  54        BRCMF_ENUM_DEF(ROAM_PREP, 32) \
  55        BRCMF_ENUM_DEF(PFN_NET_FOUND, 33) \
  56        BRCMF_ENUM_DEF(PFN_NET_LOST, 34) \
  57        BRCMF_ENUM_DEF(RESET_COMPLETE, 35) \
  58        BRCMF_ENUM_DEF(JOIN_START, 36) \
  59        BRCMF_ENUM_DEF(ROAM_START, 37) \
  60        BRCMF_ENUM_DEF(ASSOC_START, 38) \
  61        BRCMF_ENUM_DEF(IBSS_ASSOC, 39) \
  62        BRCMF_ENUM_DEF(RADIO, 40) \
  63        BRCMF_ENUM_DEF(PSM_WATCHDOG, 41) \
  64        BRCMF_ENUM_DEF(PROBREQ_MSG, 44) \
  65        BRCMF_ENUM_DEF(SCAN_CONFIRM_IND, 45) \
  66        BRCMF_ENUM_DEF(PSK_SUP, 46) \
  67        BRCMF_ENUM_DEF(COUNTRY_CODE_CHANGED, 47) \
  68        BRCMF_ENUM_DEF(EXCEEDED_MEDIUM_TIME, 48) \
  69        BRCMF_ENUM_DEF(ICV_ERROR, 49) \
  70        BRCMF_ENUM_DEF(UNICAST_DECODE_ERROR, 50) \
  71        BRCMF_ENUM_DEF(MULTICAST_DECODE_ERROR, 51) \
  72        BRCMF_ENUM_DEF(TRACE, 52) \
  73        BRCMF_ENUM_DEF(IF, 54) \
  74        BRCMF_ENUM_DEF(P2P_DISC_LISTEN_COMPLETE, 55) \
  75        BRCMF_ENUM_DEF(RSSI, 56) \
  76        BRCMF_ENUM_DEF(EXTLOG_MSG, 58) \
  77        BRCMF_ENUM_DEF(ACTION_FRAME, 59) \
  78        BRCMF_ENUM_DEF(ACTION_FRAME_COMPLETE, 60) \
  79        BRCMF_ENUM_DEF(PRE_ASSOC_IND, 61) \
  80        BRCMF_ENUM_DEF(PRE_REASSOC_IND, 62) \
  81        BRCMF_ENUM_DEF(CHANNEL_ADOPTED, 63) \
  82        BRCMF_ENUM_DEF(AP_STARTED, 64) \
  83        BRCMF_ENUM_DEF(DFS_AP_STOP, 65) \
  84        BRCMF_ENUM_DEF(DFS_AP_RESUME, 66) \
  85        BRCMF_ENUM_DEF(ESCAN_RESULT, 69) \
  86        BRCMF_ENUM_DEF(ACTION_FRAME_OFF_CHAN_COMPLETE, 70) \
  87        BRCMF_ENUM_DEF(PROBERESP_MSG, 71) \
  88        BRCMF_ENUM_DEF(P2P_PROBEREQ_MSG, 72) \
  89        BRCMF_ENUM_DEF(DCS_REQUEST, 73) \
  90        BRCMF_ENUM_DEF(FIFO_CREDIT_MAP, 74) \
  91        BRCMF_ENUM_DEF(ACTION_FRAME_RX, 75) \
  92        BRCMF_ENUM_DEF(TDLS_PEER_EVENT, 92) \
  93        BRCMF_ENUM_DEF(BCMC_CREDIT_SUPPORT, 127)
  94
  95#define BRCMF_ENUM_DEF(id, val) \
  96        BRCMF_E_##id = (val),
  97
  98/* firmware event codes sent by the dongle */
  99enum brcmf_fweh_event_code {
 100        BRCMF_FWEH_EVENT_ENUM_DEFLIST
 101        /* this determines event mask length which must match
 102         * minimum length check in device firmware so it is
 103         * hard-coded here.
 104         */
 105        BRCMF_E_LAST = 139
 106};
 107#undef BRCMF_ENUM_DEF
 108
 109#define BRCMF_EVENTING_MASK_LEN         DIV_ROUND_UP(BRCMF_E_LAST, 8)
 110
 111/* flags field values in struct brcmf_event_msg */
 112#define BRCMF_EVENT_MSG_LINK            0x01
 113#define BRCMF_EVENT_MSG_FLUSHTXQ        0x02
 114#define BRCMF_EVENT_MSG_GROUP           0x04
 115
 116/* status field values in struct brcmf_event_msg */
 117#define BRCMF_E_STATUS_SUCCESS                  0
 118#define BRCMF_E_STATUS_FAIL                     1
 119#define BRCMF_E_STATUS_TIMEOUT                  2
 120#define BRCMF_E_STATUS_NO_NETWORKS              3
 121#define BRCMF_E_STATUS_ABORT                    4
 122#define BRCMF_E_STATUS_NO_ACK                   5
 123#define BRCMF_E_STATUS_UNSOLICITED              6
 124#define BRCMF_E_STATUS_ATTEMPT                  7
 125#define BRCMF_E_STATUS_PARTIAL                  8
 126#define BRCMF_E_STATUS_NEWSCAN                  9
 127#define BRCMF_E_STATUS_NEWASSOC                 10
 128#define BRCMF_E_STATUS_11HQUIET                 11
 129#define BRCMF_E_STATUS_SUPPRESS                 12
 130#define BRCMF_E_STATUS_NOCHANS                  13
 131#define BRCMF_E_STATUS_CS_ABORT                 15
 132#define BRCMF_E_STATUS_ERROR                    16
 133
 134/* status field values for PSK_SUP event */
 135#define BRCMF_E_STATUS_FWSUP_WAIT_M1            4
 136#define BRCMF_E_STATUS_FWSUP_PREP_M2            5
 137#define BRCMF_E_STATUS_FWSUP_COMPLETED          6
 138#define BRCMF_E_STATUS_FWSUP_TIMEOUT            7
 139#define BRCMF_E_STATUS_FWSUP_WAIT_M3            8
 140#define BRCMF_E_STATUS_FWSUP_PREP_M4            9
 141#define BRCMF_E_STATUS_FWSUP_WAIT_G1            10
 142#define BRCMF_E_STATUS_FWSUP_PREP_G2            11
 143
 144/* reason field values in struct brcmf_event_msg */
 145#define BRCMF_E_REASON_INITIAL_ASSOC            0
 146#define BRCMF_E_REASON_LOW_RSSI                 1
 147#define BRCMF_E_REASON_DEAUTH                   2
 148#define BRCMF_E_REASON_DISASSOC                 3
 149#define BRCMF_E_REASON_BCNS_LOST                4
 150#define BRCMF_E_REASON_MINTXRATE                9
 151#define BRCMF_E_REASON_TXFAIL                   10
 152
 153#define BRCMF_E_REASON_LINK_BSSCFG_DIS          4
 154#define BRCMF_E_REASON_FAST_ROAM_FAILED         5
 155#define BRCMF_E_REASON_DIRECTED_ROAM            6
 156#define BRCMF_E_REASON_TSPEC_REJECTED           7
 157#define BRCMF_E_REASON_BETTER_AP                8
 158
 159#define BRCMF_E_REASON_TDLS_PEER_DISCOVERED     0
 160#define BRCMF_E_REASON_TDLS_PEER_CONNECTED      1
 161#define BRCMF_E_REASON_TDLS_PEER_DISCONNECTED   2
 162
 163/* reason field values for PSK_SUP event */
 164#define BRCMF_E_REASON_FWSUP_OTHER              0
 165#define BRCMF_E_REASON_FWSUP_DECRYPT_KEY_DATA   1
 166#define BRCMF_E_REASON_FWSUP_BAD_UCAST_WEP128   2
 167#define BRCMF_E_REASON_FWSUP_BAD_UCAST_WEP40    3
 168#define BRCMF_E_REASON_FWSUP_UNSUP_KEY_LEN      4
 169#define BRCMF_E_REASON_FWSUP_PW_KEY_CIPHER      5
 170#define BRCMF_E_REASON_FWSUP_MSG3_TOO_MANY_IE   6
 171#define BRCMF_E_REASON_FWSUP_MSG3_IE_MISMATCH   7
 172#define BRCMF_E_REASON_FWSUP_NO_INSTALL_FLAG    8
 173#define BRCMF_E_REASON_FWSUP_MSG3_NO_GTK        9
 174#define BRCMF_E_REASON_FWSUP_GRP_KEY_CIPHER     10
 175#define BRCMF_E_REASON_FWSUP_GRP_MSG1_NO_GTK    11
 176#define BRCMF_E_REASON_FWSUP_GTK_DECRYPT_FAIL   12
 177#define BRCMF_E_REASON_FWSUP_SEND_FAIL          13
 178#define BRCMF_E_REASON_FWSUP_DEAUTH             14
 179#define BRCMF_E_REASON_FWSUP_WPA_PSK_TMO        15
 180#define BRCMF_E_REASON_FWSUP_WPA_PSK_M1_TMO     16
 181#define BRCMF_E_REASON_FWSUP_WPA_PSK_M3_TMO     17
 182
 183/* action field values for brcmf_ifevent */
 184#define BRCMF_E_IF_ADD                          1
 185#define BRCMF_E_IF_DEL                          2
 186#define BRCMF_E_IF_CHANGE                       3
 187
 188/* flag field values for brcmf_ifevent */
 189#define BRCMF_E_IF_FLAG_NOIF                    1
 190
 191/* role field values for brcmf_ifevent */
 192#define BRCMF_E_IF_ROLE_STA                     0
 193#define BRCMF_E_IF_ROLE_AP                      1
 194#define BRCMF_E_IF_ROLE_WDS                     2
 195#define BRCMF_E_IF_ROLE_P2P_GO                  3
 196#define BRCMF_E_IF_ROLE_P2P_CLIENT              4
 197
 198/**
 199 * definitions for event packet validation.
 200 */
 201#define BRCM_OUI                                "\x00\x10\x18"
 202#define BCMILCP_BCM_SUBTYPE_EVENT               1
 203#define BCMILCP_SUBTYPE_VENDOR_LONG             32769
 204
 205/**
 206 * struct brcm_ethhdr - broadcom specific ether header.
 207 *
 208 * @subtype: subtype for this packet.
 209 * @length: TODO: length of appended data.
 210 * @version: version indication.
 211 * @oui: OUI of this packet.
 212 * @usr_subtype: subtype for this OUI.
 213 */
 214struct brcm_ethhdr {
 215        __be16 subtype;
 216        __be16 length;
 217        u8 version;
 218        u8 oui[3];
 219        __be16 usr_subtype;
 220} __packed;
 221
 222struct brcmf_event_msg_be {
 223        __be16 version;
 224        __be16 flags;
 225        __be32 event_type;
 226        __be32 status;
 227        __be32 reason;
 228        __be32 auth_type;
 229        __be32 datalen;
 230        u8 addr[ETH_ALEN];
 231        char ifname[IFNAMSIZ];
 232        u8 ifidx;
 233        u8 bsscfgidx;
 234} __packed;
 235
 236/**
 237 * struct brcmf_event - contents of broadcom event packet.
 238 *
 239 * @eth: standard ether header.
 240 * @hdr: broadcom specific ether header.
 241 * @msg: common part of the actual event message.
 242 */
 243struct brcmf_event {
 244        struct ethhdr eth;
 245        struct brcm_ethhdr hdr;
 246        struct brcmf_event_msg_be msg;
 247} __packed;
 248
 249/**
 250 * struct brcmf_event_msg - firmware event message.
 251 *
 252 * @version: version information.
 253 * @flags: event flags.
 254 * @event_code: firmware event code.
 255 * @status: status information.
 256 * @reason: reason code.
 257 * @auth_type: authentication type.
 258 * @datalen: length of event data buffer.
 259 * @addr: ether address.
 260 * @ifname: interface name.
 261 * @ifidx: interface index.
 262 * @bsscfgidx: bsscfg index.
 263 */
 264struct brcmf_event_msg {
 265        u16 version;
 266        u16 flags;
 267        u32 event_code;
 268        u32 status;
 269        u32 reason;
 270        s32 auth_type;
 271        u32 datalen;
 272        u8 addr[ETH_ALEN];
 273        char ifname[IFNAMSIZ];
 274        u8 ifidx;
 275        u8 bsscfgidx;
 276};
 277
 278struct brcmf_if_event {
 279        u8 ifidx;
 280        u8 action;
 281        u8 flags;
 282        u8 bsscfgidx;
 283        u8 role;
 284};
 285
 286typedef int (*brcmf_fweh_handler_t)(struct brcmf_if *ifp,
 287                                    const struct brcmf_event_msg *evtmsg,
 288                                    void *data);
 289
 290/**
 291 * struct brcmf_fweh_info - firmware event handling information.
 292 *
 293 * @p2pdev_setup_ongoing: P2P device creation in progress.
 294 * @event_work: event worker.
 295 * @evt_q_lock: lock for event queue protection.
 296 * @event_q: event queue.
 297 * @evt_handler: registered event handlers.
 298 */
 299struct brcmf_fweh_info {
 300        bool p2pdev_setup_ongoing;
 301        struct work_struct event_work;
 302        spinlock_t evt_q_lock;
 303        struct list_head event_q;
 304        int (*evt_handler[BRCMF_E_LAST])(struct brcmf_if *ifp,
 305                                         const struct brcmf_event_msg *evtmsg,
 306                                         void *data);
 307};
 308
 309const char *brcmf_fweh_event_name(enum brcmf_fweh_event_code code);
 310
 311void brcmf_fweh_attach(struct brcmf_pub *drvr);
 312void brcmf_fweh_detach(struct brcmf_pub *drvr);
 313int brcmf_fweh_register(struct brcmf_pub *drvr, enum brcmf_fweh_event_code code,
 314                        int (*handler)(struct brcmf_if *ifp,
 315                                       const struct brcmf_event_msg *evtmsg,
 316                                       void *data));
 317void brcmf_fweh_unregister(struct brcmf_pub *drvr,
 318                           enum brcmf_fweh_event_code code);
 319int brcmf_fweh_activate_events(struct brcmf_if *ifp);
 320void brcmf_fweh_process_event(struct brcmf_pub *drvr,
 321                              struct brcmf_event *event_packet,
 322                              u32 packet_len, gfp_t gfp);
 323void brcmf_fweh_p2pdev_setup(struct brcmf_if *ifp, bool ongoing);
 324
 325static inline void brcmf_fweh_process_skb(struct brcmf_pub *drvr,
 326                                          struct sk_buff *skb, u16 stype,
 327                                          gfp_t gfp)
 328{
 329        struct brcmf_event *event_packet;
 330        u16 subtype, usr_stype;
 331
 332        /* only process events when protocol matches */
 333        if (skb->protocol != cpu_to_be16(ETH_P_LINK_CTL))
 334                return;
 335
 336        if ((skb->len + ETH_HLEN) < sizeof(*event_packet))
 337                return;
 338
 339        event_packet = (struct brcmf_event *)skb_mac_header(skb);
 340
 341        /* check subtype if needed */
 342        if (unlikely(stype)) {
 343                subtype = get_unaligned_be16(&event_packet->hdr.subtype);
 344                if (subtype != stype)
 345                        return;
 346        }
 347
 348        /* check for BRCM oui match */
 349        if (memcmp(BRCM_OUI, &event_packet->hdr.oui[0],
 350                   sizeof(event_packet->hdr.oui)))
 351                return;
 352
 353        /* final match on usr_subtype */
 354        usr_stype = get_unaligned_be16(&event_packet->hdr.usr_subtype);
 355        if (usr_stype != BCMILCP_BCM_SUBTYPE_EVENT)
 356                return;
 357
 358        brcmf_fweh_process_event(drvr, event_packet, skb->len + ETH_HLEN, gfp);
 359}
 360
 361#endif /* FWEH_H_ */
 362