linux/net/mac80211/mesh_plink.c
<<
>>
Prefs
   1/*
   2 * Copyright (c) 2008, 2009 open80211s Ltd.
   3 * Author:     Luis Carlos Cobo <luisca@cozybit.com>
   4 *
   5 * This program is free software; you can redistribute it and/or modify
   6 * it under the terms of the GNU General Public License version 2 as
   7 * published by the Free Software Foundation.
   8 */
   9#include <linux/gfp.h>
  10#include <linux/kernel.h>
  11#include <linux/random.h>
  12#include "ieee80211_i.h"
  13#include "rate.h"
  14#include "mesh.h"
  15
  16#define PLINK_GET_LLID(p) (p + 2)
  17#define PLINK_GET_PLID(p) (p + 4)
  18
  19#define mod_plink_timer(s, t) (mod_timer(&s->plink_timer, \
  20                                jiffies + HZ * t / 1000))
  21
  22/* We only need a valid sta if user configured a minimum rssi_threshold. */
  23#define rssi_threshold_check(sta, sdata) \
  24                (sdata->u.mesh.mshcfg.rssi_threshold == 0 ||\
  25                (sta && (s8) -ewma_read(&sta->avg_signal) > \
  26                sdata->u.mesh.mshcfg.rssi_threshold))
  27
  28enum plink_event {
  29        PLINK_UNDEFINED,
  30        OPN_ACPT,
  31        OPN_RJCT,
  32        OPN_IGNR,
  33        CNF_ACPT,
  34        CNF_RJCT,
  35        CNF_IGNR,
  36        CLS_ACPT,
  37        CLS_IGNR
  38};
  39
  40static const char * const mplstates[] = {
  41        [NL80211_PLINK_LISTEN] = "LISTEN",
  42        [NL80211_PLINK_OPN_SNT] = "OPN-SNT",
  43        [NL80211_PLINK_OPN_RCVD] = "OPN-RCVD",
  44        [NL80211_PLINK_CNF_RCVD] = "CNF_RCVD",
  45        [NL80211_PLINK_ESTAB] = "ESTAB",
  46        [NL80211_PLINK_HOLDING] = "HOLDING",
  47        [NL80211_PLINK_BLOCKED] = "BLOCKED"
  48};
  49
  50static const char * const mplevents[] = {
  51        [PLINK_UNDEFINED] = "NONE",
  52        [OPN_ACPT] = "OPN_ACPT",
  53        [OPN_RJCT] = "OPN_RJCT",
  54        [OPN_IGNR] = "OPN_IGNR",
  55        [CNF_ACPT] = "CNF_ACPT",
  56        [CNF_RJCT] = "CNF_RJCT",
  57        [CNF_IGNR] = "CNF_IGNR",
  58        [CLS_ACPT] = "CLS_ACPT",
  59        [CLS_IGNR] = "CLS_IGNR"
  60};
  61
  62static int mesh_plink_frame_tx(struct ieee80211_sub_if_data *sdata,
  63                               enum ieee80211_self_protected_actioncode action,
  64                               u8 *da, __le16 llid, __le16 plid, __le16 reason);
  65
  66/**
  67 * mesh_plink_fsm_restart - restart a mesh peer link finite state machine
  68 *
  69 * @sta: mesh peer link to restart
  70 *
  71 * Locking: this function must be called holding sta->lock
  72 */
  73static inline void mesh_plink_fsm_restart(struct sta_info *sta)
  74{
  75        sta->plink_state = NL80211_PLINK_LISTEN;
  76        sta->llid = sta->plid = sta->reason = 0;
  77        sta->plink_retries = 0;
  78}
  79
  80/*
  81 * mesh_set_short_slot_time - enable / disable ERP short slot time.
  82 *
  83 * The standard indirectly mandates mesh STAs to turn off short slot time by
  84 * disallowing advertising this (802.11-2012 8.4.1.4), but that doesn't mean we
  85 * can't be sneaky about it. Enable short slot time if all mesh STAs in the
  86 * MBSS support ERP rates.
  87 *
  88 * Returns BSS_CHANGED_ERP_SLOT or 0 for no change.
  89 */
  90static u32 mesh_set_short_slot_time(struct ieee80211_sub_if_data *sdata)
  91{
  92        struct ieee80211_local *local = sdata->local;
  93        enum ieee80211_band band = ieee80211_get_sdata_band(sdata);
  94        struct ieee80211_supported_band *sband = local->hw.wiphy->bands[band];
  95        struct sta_info *sta;
  96        u32 erp_rates = 0, changed = 0;
  97        int i;
  98        bool short_slot = false;
  99
 100        if (band == IEEE80211_BAND_5GHZ) {
 101                /* (IEEE 802.11-2012 19.4.5) */
 102                short_slot = true;
 103                goto out;
 104        } else if (band != IEEE80211_BAND_2GHZ ||
 105                   (band == IEEE80211_BAND_2GHZ &&
 106                    local->hw.flags & IEEE80211_HW_2GHZ_SHORT_SLOT_INCAPABLE))
 107                goto out;
 108
 109        for (i = 0; i < sband->n_bitrates; i++)
 110                if (sband->bitrates[i].flags & IEEE80211_RATE_ERP_G)
 111                        erp_rates |= BIT(i);
 112
 113        if (!erp_rates)
 114                goto out;
 115
 116        rcu_read_lock();
 117        list_for_each_entry_rcu(sta, &local->sta_list, list) {
 118                if (sdata != sta->sdata ||
 119                    sta->plink_state != NL80211_PLINK_ESTAB)
 120                        continue;
 121
 122                short_slot = false;
 123                if (erp_rates & sta->sta.supp_rates[band])
 124                        short_slot = true;
 125                 else
 126                        break;
 127        }
 128        rcu_read_unlock();
 129
 130out:
 131        if (sdata->vif.bss_conf.use_short_slot != short_slot) {
 132                sdata->vif.bss_conf.use_short_slot = short_slot;
 133                changed = BSS_CHANGED_ERP_SLOT;
 134                mpl_dbg(sdata, "mesh_plink %pM: ERP short slot time %d\n",
 135                        sdata->vif.addr, short_slot);
 136        }
 137        return changed;
 138}
 139
 140/**
 141 * mesh_set_ht_prot_mode - set correct HT protection mode
 142 *
 143 * Section 9.23.3.5 of IEEE 80211-2012 describes the protection rules for HT
 144 * mesh STA in a MBSS. Three HT protection modes are supported for now, non-HT
 145 * mixed mode, 20MHz-protection and no-protection mode. non-HT mixed mode is
 146 * selected if any non-HT peers are present in our MBSS.  20MHz-protection mode
 147 * is selected if all peers in our 20/40MHz MBSS support HT and atleast one
 148 * HT20 peer is present. Otherwise no-protection mode is selected.
 149 */
 150static u32 mesh_set_ht_prot_mode(struct ieee80211_sub_if_data *sdata)
 151{
 152        struct ieee80211_local *local = sdata->local;
 153        struct sta_info *sta;
 154        u16 ht_opmode;
 155        bool non_ht_sta = false, ht20_sta = false;
 156
 157        if (sdata->vif.bss_conf.chandef.width == NL80211_CHAN_WIDTH_20_NOHT)
 158                return 0;
 159
 160        rcu_read_lock();
 161        list_for_each_entry_rcu(sta, &local->sta_list, list) {
 162                if (sdata != sta->sdata ||
 163                    sta->plink_state != NL80211_PLINK_ESTAB)
 164                        continue;
 165
 166                if (sta->sta.bandwidth > IEEE80211_STA_RX_BW_20)
 167                        continue;
 168
 169                if (!sta->sta.ht_cap.ht_supported) {
 170                        mpl_dbg(sdata, "nonHT sta (%pM) is present\n",
 171                                       sta->sta.addr);
 172                        non_ht_sta = true;
 173                        break;
 174                }
 175
 176                mpl_dbg(sdata, "HT20 sta (%pM) is present\n", sta->sta.addr);
 177                ht20_sta = true;
 178        }
 179        rcu_read_unlock();
 180
 181        if (non_ht_sta)
 182                ht_opmode = IEEE80211_HT_OP_MODE_PROTECTION_NONHT_MIXED;
 183        else if (ht20_sta &&
 184                 sdata->vif.bss_conf.chandef.width > NL80211_CHAN_WIDTH_20)
 185                ht_opmode = IEEE80211_HT_OP_MODE_PROTECTION_20MHZ;
 186        else
 187                ht_opmode = IEEE80211_HT_OP_MODE_PROTECTION_NONE;
 188
 189        if (sdata->vif.bss_conf.ht_operation_mode == ht_opmode)
 190                return 0;
 191
 192        sdata->vif.bss_conf.ht_operation_mode = ht_opmode;
 193        sdata->u.mesh.mshcfg.ht_opmode = ht_opmode;
 194        mpl_dbg(sdata, "selected new HT protection mode %d\n", ht_opmode);
 195        return BSS_CHANGED_HT;
 196}
 197
 198/**
 199 * __mesh_plink_deactivate - deactivate mesh peer link
 200 *
 201 * @sta: mesh peer link to deactivate
 202 *
 203 * All mesh paths with this peer as next hop will be flushed
 204 * Returns beacon changed flag if the beacon content changed.
 205 *
 206 * Locking: the caller must hold sta->lock
 207 */
 208static u32 __mesh_plink_deactivate(struct sta_info *sta)
 209{
 210        struct ieee80211_sub_if_data *sdata = sta->sdata;
 211        u32 changed = 0;
 212
 213        if (sta->plink_state == NL80211_PLINK_ESTAB)
 214                changed = mesh_plink_dec_estab_count(sdata);
 215        sta->plink_state = NL80211_PLINK_BLOCKED;
 216        mesh_path_flush_by_nexthop(sta);
 217
 218        ieee80211_mps_sta_status_update(sta);
 219        changed |= ieee80211_mps_local_status_update(sdata);
 220
 221        return changed;
 222}
 223
 224/**
 225 * mesh_plink_deactivate - deactivate mesh peer link
 226 *
 227 * @sta: mesh peer link to deactivate
 228 *
 229 * All mesh paths with this peer as next hop will be flushed
 230 */
 231u32 mesh_plink_deactivate(struct sta_info *sta)
 232{
 233        struct ieee80211_sub_if_data *sdata = sta->sdata;
 234        u32 changed;
 235
 236        spin_lock_bh(&sta->lock);
 237        changed = __mesh_plink_deactivate(sta);
 238        sta->reason = cpu_to_le16(WLAN_REASON_MESH_PEER_CANCELED);
 239        mesh_plink_frame_tx(sdata, WLAN_SP_MESH_PEERING_CLOSE,
 240                            sta->sta.addr, sta->llid, sta->plid,
 241                            sta->reason);
 242        spin_unlock_bh(&sta->lock);
 243
 244        return changed;
 245}
 246
 247static int mesh_plink_frame_tx(struct ieee80211_sub_if_data *sdata,
 248                               enum ieee80211_self_protected_actioncode action,
 249                               u8 *da, __le16 llid, __le16 plid, __le16 reason)
 250{
 251        struct ieee80211_local *local = sdata->local;
 252        struct sk_buff *skb;
 253        struct ieee80211_tx_info *info;
 254        struct ieee80211_mgmt *mgmt;
 255        bool include_plid = false;
 256        u16 peering_proto = 0;
 257        u8 *pos, ie_len = 4;
 258        int hdr_len = offsetof(struct ieee80211_mgmt, u.action.u.self_prot) +
 259                      sizeof(mgmt->u.action.u.self_prot);
 260        int err = -ENOMEM;
 261
 262        skb = dev_alloc_skb(local->tx_headroom +
 263                            hdr_len +
 264                            2 + /* capability info */
 265                            2 + /* AID */
 266                            2 + 8 + /* supported rates */
 267                            2 + (IEEE80211_MAX_SUPP_RATES - 8) +
 268                            2 + sdata->u.mesh.mesh_id_len +
 269                            2 + sizeof(struct ieee80211_meshconf_ie) +
 270                            2 + sizeof(struct ieee80211_ht_cap) +
 271                            2 + sizeof(struct ieee80211_ht_operation) +
 272                            2 + 8 + /* peering IE */
 273                            sdata->u.mesh.ie_len);
 274        if (!skb)
 275                return -1;
 276        info = IEEE80211_SKB_CB(skb);
 277        skb_reserve(skb, local->tx_headroom);
 278        mgmt = (struct ieee80211_mgmt *) skb_put(skb, hdr_len);
 279        memset(mgmt, 0, hdr_len);
 280        mgmt->frame_control = cpu_to_le16(IEEE80211_FTYPE_MGMT |
 281                                          IEEE80211_STYPE_ACTION);
 282        memcpy(mgmt->da, da, ETH_ALEN);
 283        memcpy(mgmt->sa, sdata->vif.addr, ETH_ALEN);
 284        memcpy(mgmt->bssid, sdata->vif.addr, ETH_ALEN);
 285        mgmt->u.action.category = WLAN_CATEGORY_SELF_PROTECTED;
 286        mgmt->u.action.u.self_prot.action_code = action;
 287
 288        if (action != WLAN_SP_MESH_PEERING_CLOSE) {
 289                enum ieee80211_band band = ieee80211_get_sdata_band(sdata);
 290
 291                /* capability info */
 292                pos = skb_put(skb, 2);
 293                memset(pos, 0, 2);
 294                if (action == WLAN_SP_MESH_PEERING_CONFIRM) {
 295                        /* AID */
 296                        pos = skb_put(skb, 2);
 297                        memcpy(pos + 2, &plid, 2);
 298                }
 299                if (ieee80211_add_srates_ie(sdata, skb, true, band) ||
 300                    ieee80211_add_ext_srates_ie(sdata, skb, true, band) ||
 301                    mesh_add_rsn_ie(sdata, skb) ||
 302                    mesh_add_meshid_ie(sdata, skb) ||
 303                    mesh_add_meshconf_ie(sdata, skb))
 304                        goto free;
 305        } else {        /* WLAN_SP_MESH_PEERING_CLOSE */
 306                info->flags |= IEEE80211_TX_CTL_NO_ACK;
 307                if (mesh_add_meshid_ie(sdata, skb))
 308                        goto free;
 309        }
 310
 311        /* Add Mesh Peering Management element */
 312        switch (action) {
 313        case WLAN_SP_MESH_PEERING_OPEN:
 314                break;
 315        case WLAN_SP_MESH_PEERING_CONFIRM:
 316                ie_len += 2;
 317                include_plid = true;
 318                break;
 319        case WLAN_SP_MESH_PEERING_CLOSE:
 320                if (plid) {
 321                        ie_len += 2;
 322                        include_plid = true;
 323                }
 324                ie_len += 2;    /* reason code */
 325                break;
 326        default:
 327                err = -EINVAL;
 328                goto free;
 329        }
 330
 331        if (WARN_ON(skb_tailroom(skb) < 2 + ie_len))
 332                goto free;
 333
 334        pos = skb_put(skb, 2 + ie_len);
 335        *pos++ = WLAN_EID_PEER_MGMT;
 336        *pos++ = ie_len;
 337        memcpy(pos, &peering_proto, 2);
 338        pos += 2;
 339        memcpy(pos, &llid, 2);
 340        pos += 2;
 341        if (include_plid) {
 342                memcpy(pos, &plid, 2);
 343                pos += 2;
 344        }
 345        if (action == WLAN_SP_MESH_PEERING_CLOSE) {
 346                memcpy(pos, &reason, 2);
 347                pos += 2;
 348        }
 349
 350        if (action != WLAN_SP_MESH_PEERING_CLOSE) {
 351                if (mesh_add_ht_cap_ie(sdata, skb) ||
 352                    mesh_add_ht_oper_ie(sdata, skb))
 353                        goto free;
 354        }
 355
 356        if (mesh_add_vendor_ies(sdata, skb))
 357                goto free;
 358
 359        ieee80211_tx_skb(sdata, skb);
 360        return 0;
 361free:
 362        kfree_skb(skb);
 363        return err;
 364}
 365
 366static void mesh_sta_info_init(struct ieee80211_sub_if_data *sdata,
 367                               struct sta_info *sta,
 368                               struct ieee802_11_elems *elems, bool insert)
 369{
 370        struct ieee80211_local *local = sdata->local;
 371        enum ieee80211_band band = ieee80211_get_sdata_band(sdata);
 372        struct ieee80211_supported_band *sband;
 373        u32 rates, basic_rates = 0, changed = 0;
 374
 375        sband = local->hw.wiphy->bands[band];
 376        rates = ieee80211_sta_get_rates(local, elems, band, &basic_rates);
 377
 378        spin_lock_bh(&sta->lock);
 379        sta->last_rx = jiffies;
 380
 381        /* rates and capabilities don't change during peering */
 382        if (sta->plink_state == NL80211_PLINK_ESTAB)
 383                goto out;
 384
 385        if (sta->sta.supp_rates[band] != rates)
 386                changed |= IEEE80211_RC_SUPP_RATES_CHANGED;
 387        sta->sta.supp_rates[band] = rates;
 388
 389        if (ieee80211_ht_cap_ie_to_sta_ht_cap(sdata, sband,
 390                                              elems->ht_cap_elem, sta))
 391                changed |= IEEE80211_RC_BW_CHANGED;
 392
 393        /* HT peer is operating 20MHz-only */
 394        if (elems->ht_operation &&
 395            !(elems->ht_operation->ht_param &
 396              IEEE80211_HT_PARAM_CHAN_WIDTH_ANY)) {
 397                if (sta->sta.bandwidth != IEEE80211_STA_RX_BW_20)
 398                        changed |= IEEE80211_RC_BW_CHANGED;
 399                sta->sta.bandwidth = IEEE80211_STA_RX_BW_20;
 400        }
 401
 402        if (insert)
 403                rate_control_rate_init(sta);
 404        else
 405                rate_control_rate_update(local, sband, sta, changed);
 406out:
 407        spin_unlock_bh(&sta->lock);
 408}
 409
 410static struct sta_info *
 411__mesh_sta_info_alloc(struct ieee80211_sub_if_data *sdata, u8 *hw_addr)
 412{
 413        struct sta_info *sta;
 414
 415        if (sdata->local->num_sta >= MESH_MAX_PLINKS)
 416                return NULL;
 417
 418        sta = sta_info_alloc(sdata, hw_addr, GFP_KERNEL);
 419        if (!sta)
 420                return NULL;
 421
 422        sta->plink_state = NL80211_PLINK_LISTEN;
 423
 424        sta_info_pre_move_state(sta, IEEE80211_STA_AUTH);
 425        sta_info_pre_move_state(sta, IEEE80211_STA_ASSOC);
 426        sta_info_pre_move_state(sta, IEEE80211_STA_AUTHORIZED);
 427
 428        set_sta_flag(sta, WLAN_STA_WME);
 429
 430        return sta;
 431}
 432
 433static struct sta_info *
 434mesh_sta_info_alloc(struct ieee80211_sub_if_data *sdata, u8 *addr,
 435                    struct ieee802_11_elems *elems)
 436{
 437        struct sta_info *sta = NULL;
 438
 439        /* Userspace handles station allocation */
 440        if (sdata->u.mesh.user_mpm ||
 441            sdata->u.mesh.security & IEEE80211_MESH_SEC_AUTHED)
 442                cfg80211_notify_new_peer_candidate(sdata->dev, addr,
 443                                                   elems->ie_start,
 444                                                   elems->total_len,
 445                                                   GFP_KERNEL);
 446        else
 447                sta = __mesh_sta_info_alloc(sdata, addr);
 448
 449        return sta;
 450}
 451
 452/*
 453 * mesh_sta_info_get - return mesh sta info entry for @addr.
 454 *
 455 * @sdata: local meshif
 456 * @addr: peer's address
 457 * @elems: IEs from beacon or mesh peering frame.
 458 *
 459 * Return existing or newly allocated sta_info under RCU read lock.
 460 * (re)initialize with given IEs.
 461 */
 462static struct sta_info *
 463mesh_sta_info_get(struct ieee80211_sub_if_data *sdata,
 464                  u8 *addr, struct ieee802_11_elems *elems) __acquires(RCU)
 465{
 466        struct sta_info *sta = NULL;
 467
 468        rcu_read_lock();
 469        sta = sta_info_get(sdata, addr);
 470        if (sta) {
 471                mesh_sta_info_init(sdata, sta, elems, false);
 472        } else {
 473                rcu_read_unlock();
 474                /* can't run atomic */
 475                sta = mesh_sta_info_alloc(sdata, addr, elems);
 476                if (!sta) {
 477                        rcu_read_lock();
 478                        return NULL;
 479                }
 480
 481                mesh_sta_info_init(sdata, sta, elems, true);
 482
 483                if (sta_info_insert_rcu(sta))
 484                        return NULL;
 485        }
 486
 487        return sta;
 488}
 489
 490/*
 491 * mesh_neighbour_update - update or initialize new mesh neighbor.
 492 *
 493 * @sdata: local meshif
 494 * @addr: peer's address
 495 * @elems: IEs from beacon or mesh peering frame
 496 *
 497 * Initiates peering if appropriate.
 498 */
 499void mesh_neighbour_update(struct ieee80211_sub_if_data *sdata,
 500                           u8 *hw_addr,
 501                           struct ieee802_11_elems *elems)
 502{
 503        struct sta_info *sta;
 504        u32 changed = 0;
 505
 506        sta = mesh_sta_info_get(sdata, hw_addr, elems);
 507        if (!sta)
 508                goto out;
 509
 510        if (mesh_peer_accepts_plinks(elems) &&
 511            sta->plink_state == NL80211_PLINK_LISTEN &&
 512            sdata->u.mesh.accepting_plinks &&
 513            sdata->u.mesh.mshcfg.auto_open_plinks &&
 514            rssi_threshold_check(sta, sdata))
 515                changed = mesh_plink_open(sta);
 516
 517        ieee80211_mps_frame_release(sta, elems);
 518out:
 519        rcu_read_unlock();
 520        ieee80211_mbss_info_change_notify(sdata, changed);
 521}
 522
 523static void mesh_plink_timer(unsigned long data)
 524{
 525        struct sta_info *sta;
 526        __le16 llid, plid, reason;
 527        struct ieee80211_sub_if_data *sdata;
 528        struct mesh_config *mshcfg;
 529
 530        /*
 531         * This STA is valid because sta_info_destroy() will
 532         * del_timer_sync() this timer after having made sure
 533         * it cannot be readded (by deleting the plink.)
 534         */
 535        sta = (struct sta_info *) data;
 536
 537        if (sta->sdata->local->quiescing)
 538                return;
 539
 540        spin_lock_bh(&sta->lock);
 541        if (sta->ignore_plink_timer) {
 542                sta->ignore_plink_timer = false;
 543                spin_unlock_bh(&sta->lock);
 544                return;
 545        }
 546        mpl_dbg(sta->sdata,
 547                "Mesh plink timer for %pM fired on state %s\n",
 548                sta->sta.addr, mplstates[sta->plink_state]);
 549        reason = 0;
 550        llid = sta->llid;
 551        plid = sta->plid;
 552        sdata = sta->sdata;
 553        mshcfg = &sdata->u.mesh.mshcfg;
 554
 555        switch (sta->plink_state) {
 556        case NL80211_PLINK_OPN_RCVD:
 557        case NL80211_PLINK_OPN_SNT:
 558                /* retry timer */
 559                if (sta->plink_retries < mshcfg->dot11MeshMaxRetries) {
 560                        u32 rand;
 561                        mpl_dbg(sta->sdata,
 562                                "Mesh plink for %pM (retry, timeout): %d %d\n",
 563                                sta->sta.addr, sta->plink_retries,
 564                                sta->plink_timeout);
 565                        get_random_bytes(&rand, sizeof(u32));
 566                        sta->plink_timeout = sta->plink_timeout +
 567                                             rand % sta->plink_timeout;
 568                        ++sta->plink_retries;
 569                        mod_plink_timer(sta, sta->plink_timeout);
 570                        spin_unlock_bh(&sta->lock);
 571                        mesh_plink_frame_tx(sdata, WLAN_SP_MESH_PEERING_OPEN,
 572                                            sta->sta.addr, llid, 0, 0);
 573                        break;
 574                }
 575                reason = cpu_to_le16(WLAN_REASON_MESH_MAX_RETRIES);
 576                /* fall through on else */
 577        case NL80211_PLINK_CNF_RCVD:
 578                /* confirm timer */
 579                if (!reason)
 580                        reason = cpu_to_le16(WLAN_REASON_MESH_CONFIRM_TIMEOUT);
 581                sta->plink_state = NL80211_PLINK_HOLDING;
 582                mod_plink_timer(sta, mshcfg->dot11MeshHoldingTimeout);
 583                spin_unlock_bh(&sta->lock);
 584                mesh_plink_frame_tx(sdata, WLAN_SP_MESH_PEERING_CLOSE,
 585                                    sta->sta.addr, llid, plid, reason);
 586                break;
 587        case NL80211_PLINK_HOLDING:
 588                /* holding timer */
 589                del_timer(&sta->plink_timer);
 590                mesh_plink_fsm_restart(sta);
 591                spin_unlock_bh(&sta->lock);
 592                break;
 593        default:
 594                spin_unlock_bh(&sta->lock);
 595                break;
 596        }
 597}
 598
 599static inline void mesh_plink_timer_set(struct sta_info *sta, int timeout)
 600{
 601        sta->plink_timer.expires = jiffies + (HZ * timeout / 1000);
 602        sta->plink_timer.data = (unsigned long) sta;
 603        sta->plink_timer.function = mesh_plink_timer;
 604        sta->plink_timeout = timeout;
 605        add_timer(&sta->plink_timer);
 606}
 607
 608u32 mesh_plink_open(struct sta_info *sta)
 609{
 610        __le16 llid;
 611        struct ieee80211_sub_if_data *sdata = sta->sdata;
 612        u32 changed;
 613
 614        if (!test_sta_flag(sta, WLAN_STA_AUTH))
 615                return 0;
 616
 617        spin_lock_bh(&sta->lock);
 618        get_random_bytes(&llid, 2);
 619        sta->llid = llid;
 620        if (sta->plink_state != NL80211_PLINK_LISTEN &&
 621            sta->plink_state != NL80211_PLINK_BLOCKED) {
 622                spin_unlock_bh(&sta->lock);
 623                return 0;
 624        }
 625        sta->plink_state = NL80211_PLINK_OPN_SNT;
 626        mesh_plink_timer_set(sta, sdata->u.mesh.mshcfg.dot11MeshRetryTimeout);
 627        spin_unlock_bh(&sta->lock);
 628        mpl_dbg(sdata,
 629                "Mesh plink: starting establishment with %pM\n",
 630                sta->sta.addr);
 631
 632        /* set the non-peer mode to active during peering */
 633        changed = ieee80211_mps_local_status_update(sdata);
 634
 635        mesh_plink_frame_tx(sdata, WLAN_SP_MESH_PEERING_OPEN,
 636                            sta->sta.addr, llid, 0, 0);
 637        return changed;
 638}
 639
 640u32 mesh_plink_block(struct sta_info *sta)
 641{
 642        u32 changed;
 643
 644        spin_lock_bh(&sta->lock);
 645        changed = __mesh_plink_deactivate(sta);
 646        sta->plink_state = NL80211_PLINK_BLOCKED;
 647        spin_unlock_bh(&sta->lock);
 648
 649        return changed;
 650}
 651
 652
 653void mesh_rx_plink_frame(struct ieee80211_sub_if_data *sdata,
 654                         struct ieee80211_mgmt *mgmt, size_t len,
 655                         struct ieee80211_rx_status *rx_status)
 656{
 657        struct mesh_config *mshcfg = &sdata->u.mesh.mshcfg;
 658        struct ieee802_11_elems elems;
 659        struct sta_info *sta;
 660        enum plink_event event;
 661        enum ieee80211_self_protected_actioncode ftype;
 662        size_t baselen;
 663        bool matches_local = true;
 664        u8 ie_len;
 665        u8 *baseaddr;
 666        u32 changed = 0;
 667        __le16 plid, llid, reason;
 668
 669        /* need action_code, aux */
 670        if (len < IEEE80211_MIN_ACTION_SIZE + 3)
 671                return;
 672
 673        if (sdata->u.mesh.user_mpm)
 674                /* userspace must register for these */
 675                return;
 676
 677        if (is_multicast_ether_addr(mgmt->da)) {
 678                mpl_dbg(sdata,
 679                        "Mesh plink: ignore frame from multicast address\n");
 680                return;
 681        }
 682
 683        baseaddr = mgmt->u.action.u.self_prot.variable;
 684        baselen = (u8 *) mgmt->u.action.u.self_prot.variable - (u8 *) mgmt;
 685        if (mgmt->u.action.u.self_prot.action_code ==
 686                                                WLAN_SP_MESH_PEERING_CONFIRM) {
 687                baseaddr += 4;
 688                baselen += 4;
 689        }
 690        ieee802_11_parse_elems(baseaddr, len - baselen, true, &elems);
 691
 692        if (!elems.peering) {
 693                mpl_dbg(sdata,
 694                        "Mesh plink: missing necessary peer link ie\n");
 695                return;
 696        }
 697
 698        if (elems.rsn_len &&
 699            sdata->u.mesh.security == IEEE80211_MESH_SEC_NONE) {
 700                mpl_dbg(sdata,
 701                        "Mesh plink: can't establish link with secure peer\n");
 702                return;
 703        }
 704
 705        ftype = mgmt->u.action.u.self_prot.action_code;
 706        ie_len = elems.peering_len;
 707        if ((ftype == WLAN_SP_MESH_PEERING_OPEN && ie_len != 4) ||
 708            (ftype == WLAN_SP_MESH_PEERING_CONFIRM && ie_len != 6) ||
 709            (ftype == WLAN_SP_MESH_PEERING_CLOSE && ie_len != 6
 710                                                        && ie_len != 8)) {
 711                mpl_dbg(sdata,
 712                        "Mesh plink: incorrect plink ie length %d %d\n",
 713                        ftype, ie_len);
 714                return;
 715        }
 716
 717        if (ftype != WLAN_SP_MESH_PEERING_CLOSE &&
 718            (!elems.mesh_id || !elems.mesh_config)) {
 719                mpl_dbg(sdata, "Mesh plink: missing necessary ie\n");
 720                return;
 721        }
 722        /* Note the lines below are correct, the llid in the frame is the plid
 723         * from the point of view of this host.
 724         */
 725        memcpy(&plid, PLINK_GET_LLID(elems.peering), 2);
 726        if (ftype == WLAN_SP_MESH_PEERING_CONFIRM ||
 727            (ftype == WLAN_SP_MESH_PEERING_CLOSE && ie_len == 8))
 728                memcpy(&llid, PLINK_GET_PLID(elems.peering), 2);
 729
 730        /* WARNING: Only for sta pointer, is dropped & re-acquired */
 731        rcu_read_lock();
 732
 733        sta = sta_info_get(sdata, mgmt->sa);
 734        if (!sta && ftype != WLAN_SP_MESH_PEERING_OPEN) {
 735                mpl_dbg(sdata, "Mesh plink: cls or cnf from unknown peer\n");
 736                rcu_read_unlock();
 737                return;
 738        }
 739
 740        if (ftype == WLAN_SP_MESH_PEERING_OPEN &&
 741            !rssi_threshold_check(sta, sdata)) {
 742                mpl_dbg(sdata, "Mesh plink: %pM does not meet rssi threshold\n",
 743                        mgmt->sa);
 744                rcu_read_unlock();
 745                return;
 746        }
 747
 748        if (sta && !test_sta_flag(sta, WLAN_STA_AUTH)) {
 749                mpl_dbg(sdata, "Mesh plink: Action frame from non-authed peer\n");
 750                rcu_read_unlock();
 751                return;
 752        }
 753
 754        if (sta && sta->plink_state == NL80211_PLINK_BLOCKED) {
 755                rcu_read_unlock();
 756                return;
 757        }
 758
 759        /* Now we will figure out the appropriate event... */
 760        event = PLINK_UNDEFINED;
 761        if (ftype != WLAN_SP_MESH_PEERING_CLOSE &&
 762            !mesh_matches_local(sdata, &elems)) {
 763                matches_local = false;
 764                switch (ftype) {
 765                case WLAN_SP_MESH_PEERING_OPEN:
 766                        event = OPN_RJCT;
 767                        break;
 768                case WLAN_SP_MESH_PEERING_CONFIRM:
 769                        event = CNF_RJCT;
 770                        break;
 771                default:
 772                        break;
 773                }
 774        }
 775
 776        if (!sta && !matches_local) {
 777                rcu_read_unlock();
 778                reason = cpu_to_le16(WLAN_REASON_MESH_CONFIG);
 779                llid = 0;
 780                mesh_plink_frame_tx(sdata, WLAN_SP_MESH_PEERING_CLOSE,
 781                                    mgmt->sa, llid, plid, reason);
 782                return;
 783        } else if (!sta) {
 784                /* ftype == WLAN_SP_MESH_PEERING_OPEN */
 785                if (!mesh_plink_free_count(sdata)) {
 786                        mpl_dbg(sdata, "Mesh plink error: no more free plinks\n");
 787                        rcu_read_unlock();
 788                        return;
 789                }
 790                event = OPN_ACPT;
 791        } else if (matches_local) {
 792                switch (ftype) {
 793                case WLAN_SP_MESH_PEERING_OPEN:
 794                        if (!mesh_plink_free_count(sdata) ||
 795                            (sta->plid && sta->plid != plid))
 796                                event = OPN_IGNR;
 797                        else
 798                                event = OPN_ACPT;
 799                        break;
 800                case WLAN_SP_MESH_PEERING_CONFIRM:
 801                        if (!mesh_plink_free_count(sdata) ||
 802                            (sta->llid != llid || sta->plid != plid))
 803                                event = CNF_IGNR;
 804                        else
 805                                event = CNF_ACPT;
 806                        break;
 807                case WLAN_SP_MESH_PEERING_CLOSE:
 808                        if (sta->plink_state == NL80211_PLINK_ESTAB)
 809                                /* Do not check for llid or plid. This does not
 810                                 * follow the standard but since multiple plinks
 811                                 * per sta are not supported, it is necessary in
 812                                 * order to avoid a livelock when MP A sees an
 813                                 * establish peer link to MP B but MP B does not
 814                                 * see it. This can be caused by a timeout in
 815                                 * B's peer link establishment or B beign
 816                                 * restarted.
 817                                 */
 818                                event = CLS_ACPT;
 819                        else if (sta->plid != plid)
 820                                event = CLS_IGNR;
 821                        else if (ie_len == 7 && sta->llid != llid)
 822                                event = CLS_IGNR;
 823                        else
 824                                event = CLS_ACPT;
 825                        break;
 826                default:
 827                        mpl_dbg(sdata, "Mesh plink: unknown frame subtype\n");
 828                        rcu_read_unlock();
 829                        return;
 830                }
 831        }
 832
 833        if (event == OPN_ACPT) {
 834                rcu_read_unlock();
 835                /* allocate sta entry if necessary and update info */
 836                sta = mesh_sta_info_get(sdata, mgmt->sa, &elems);
 837                if (!sta) {
 838                        mpl_dbg(sdata, "Mesh plink: failed to init peer!\n");
 839                        rcu_read_unlock();
 840                        return;
 841                }
 842        }
 843
 844        mpl_dbg(sdata, "peer %pM in state %s got event %s\n", mgmt->sa,
 845                       mplstates[sta->plink_state], mplevents[event]);
 846        reason = 0;
 847        spin_lock_bh(&sta->lock);
 848        switch (sta->plink_state) {
 849                /* spin_unlock as soon as state is updated at each case */
 850        case NL80211_PLINK_LISTEN:
 851                switch (event) {
 852                case CLS_ACPT:
 853                        mesh_plink_fsm_restart(sta);
 854                        spin_unlock_bh(&sta->lock);
 855                        break;
 856                case OPN_ACPT:
 857                        sta->plink_state = NL80211_PLINK_OPN_RCVD;
 858                        sta->plid = plid;
 859                        get_random_bytes(&llid, 2);
 860                        sta->llid = llid;
 861                        mesh_plink_timer_set(sta,
 862                                             mshcfg->dot11MeshRetryTimeout);
 863
 864                        /* set the non-peer mode to active during peering */
 865                        changed |= ieee80211_mps_local_status_update(sdata);
 866
 867                        spin_unlock_bh(&sta->lock);
 868                        mesh_plink_frame_tx(sdata,
 869                                            WLAN_SP_MESH_PEERING_OPEN,
 870                                            sta->sta.addr, llid, 0, 0);
 871                        mesh_plink_frame_tx(sdata,
 872                                            WLAN_SP_MESH_PEERING_CONFIRM,
 873                                            sta->sta.addr, llid, plid, 0);
 874                        break;
 875                default:
 876                        spin_unlock_bh(&sta->lock);
 877                        break;
 878                }
 879                break;
 880
 881        case NL80211_PLINK_OPN_SNT:
 882                switch (event) {
 883                case OPN_RJCT:
 884                case CNF_RJCT:
 885                        reason = cpu_to_le16(WLAN_REASON_MESH_CONFIG);
 886                case CLS_ACPT:
 887                        if (!reason)
 888                                reason = cpu_to_le16(WLAN_REASON_MESH_CLOSE);
 889                        sta->reason = reason;
 890                        sta->plink_state = NL80211_PLINK_HOLDING;
 891                        if (!mod_plink_timer(sta,
 892                                             mshcfg->dot11MeshHoldingTimeout))
 893                                sta->ignore_plink_timer = true;
 894
 895                        llid = sta->llid;
 896                        spin_unlock_bh(&sta->lock);
 897                        mesh_plink_frame_tx(sdata,
 898                                            WLAN_SP_MESH_PEERING_CLOSE,
 899                                            sta->sta.addr, llid, plid, reason);
 900                        break;
 901                case OPN_ACPT:
 902                        /* retry timer is left untouched */
 903                        sta->plink_state = NL80211_PLINK_OPN_RCVD;
 904                        sta->plid = plid;
 905                        llid = sta->llid;
 906                        spin_unlock_bh(&sta->lock);
 907                        mesh_plink_frame_tx(sdata,
 908                                            WLAN_SP_MESH_PEERING_CONFIRM,
 909                                            sta->sta.addr, llid, plid, 0);
 910                        break;
 911                case CNF_ACPT:
 912                        sta->plink_state = NL80211_PLINK_CNF_RCVD;
 913                        if (!mod_plink_timer(sta,
 914                                             mshcfg->dot11MeshConfirmTimeout))
 915                                sta->ignore_plink_timer = true;
 916
 917                        spin_unlock_bh(&sta->lock);
 918                        break;
 919                default:
 920                        spin_unlock_bh(&sta->lock);
 921                        break;
 922                }
 923                break;
 924
 925        case NL80211_PLINK_OPN_RCVD:
 926                switch (event) {
 927                case OPN_RJCT:
 928                case CNF_RJCT:
 929                        reason = cpu_to_le16(WLAN_REASON_MESH_CONFIG);
 930                case CLS_ACPT:
 931                        if (!reason)
 932                                reason = cpu_to_le16(WLAN_REASON_MESH_CLOSE);
 933                        sta->reason = reason;
 934                        sta->plink_state = NL80211_PLINK_HOLDING;
 935                        if (!mod_plink_timer(sta,
 936                                             mshcfg->dot11MeshHoldingTimeout))
 937                                sta->ignore_plink_timer = true;
 938
 939                        llid = sta->llid;
 940                        spin_unlock_bh(&sta->lock);
 941                        mesh_plink_frame_tx(sdata, WLAN_SP_MESH_PEERING_CLOSE,
 942                                            sta->sta.addr, llid, plid, reason);
 943                        break;
 944                case OPN_ACPT:
 945                        llid = sta->llid;
 946                        spin_unlock_bh(&sta->lock);
 947                        mesh_plink_frame_tx(sdata,
 948                                            WLAN_SP_MESH_PEERING_CONFIRM,
 949                                            sta->sta.addr, llid, plid, 0);
 950                        break;
 951                case CNF_ACPT:
 952                        del_timer(&sta->plink_timer);
 953                        sta->plink_state = NL80211_PLINK_ESTAB;
 954                        spin_unlock_bh(&sta->lock);
 955                        changed |= mesh_plink_inc_estab_count(sdata);
 956                        changed |= mesh_set_ht_prot_mode(sdata);
 957                        changed |= mesh_set_short_slot_time(sdata);
 958                        mpl_dbg(sdata, "Mesh plink with %pM ESTABLISHED\n",
 959                                sta->sta.addr);
 960                        ieee80211_mps_sta_status_update(sta);
 961                        changed |= ieee80211_mps_set_sta_local_pm(sta,
 962                                                       mshcfg->power_mode);
 963                        break;
 964                default:
 965                        spin_unlock_bh(&sta->lock);
 966                        break;
 967                }
 968                break;
 969
 970        case NL80211_PLINK_CNF_RCVD:
 971                switch (event) {
 972                case OPN_RJCT:
 973                case CNF_RJCT:
 974                        reason = cpu_to_le16(WLAN_REASON_MESH_CONFIG);
 975                case CLS_ACPT:
 976                        if (!reason)
 977                                reason = cpu_to_le16(WLAN_REASON_MESH_CLOSE);
 978                        sta->reason = reason;
 979                        sta->plink_state = NL80211_PLINK_HOLDING;
 980                        if (!mod_plink_timer(sta,
 981                                             mshcfg->dot11MeshHoldingTimeout))
 982                                sta->ignore_plink_timer = true;
 983
 984                        llid = sta->llid;
 985                        spin_unlock_bh(&sta->lock);
 986                        mesh_plink_frame_tx(sdata,
 987                                            WLAN_SP_MESH_PEERING_CLOSE,
 988                                            sta->sta.addr, llid, plid, reason);
 989                        break;
 990                case OPN_ACPT:
 991                        del_timer(&sta->plink_timer);
 992                        sta->plink_state = NL80211_PLINK_ESTAB;
 993                        spin_unlock_bh(&sta->lock);
 994                        changed |= mesh_plink_inc_estab_count(sdata);
 995                        changed |= mesh_set_ht_prot_mode(sdata);
 996                        changed |= mesh_set_short_slot_time(sdata);
 997                        mpl_dbg(sdata, "Mesh plink with %pM ESTABLISHED\n",
 998                                sta->sta.addr);
 999                        mesh_plink_frame_tx(sdata,
1000                                            WLAN_SP_MESH_PEERING_CONFIRM,
1001                                            sta->sta.addr, llid, plid, 0);
1002                        ieee80211_mps_sta_status_update(sta);
1003                        changed |= ieee80211_mps_set_sta_local_pm(sta,
1004                                                        mshcfg->power_mode);
1005                        break;
1006                default:
1007                        spin_unlock_bh(&sta->lock);
1008                        break;
1009                }
1010                break;
1011
1012        case NL80211_PLINK_ESTAB:
1013                switch (event) {
1014                case CLS_ACPT:
1015                        reason = cpu_to_le16(WLAN_REASON_MESH_CLOSE);
1016                        sta->reason = reason;
1017                        changed |= __mesh_plink_deactivate(sta);
1018                        sta->plink_state = NL80211_PLINK_HOLDING;
1019                        llid = sta->llid;
1020                        mod_plink_timer(sta, mshcfg->dot11MeshHoldingTimeout);
1021                        spin_unlock_bh(&sta->lock);
1022                        changed |= mesh_set_ht_prot_mode(sdata);
1023                        changed |= mesh_set_short_slot_time(sdata);
1024                        mesh_plink_frame_tx(sdata, WLAN_SP_MESH_PEERING_CLOSE,
1025                                            sta->sta.addr, llid, plid, reason);
1026                        break;
1027                case OPN_ACPT:
1028                        llid = sta->llid;
1029                        spin_unlock_bh(&sta->lock);
1030                        mesh_plink_frame_tx(sdata,
1031                                            WLAN_SP_MESH_PEERING_CONFIRM,
1032                                            sta->sta.addr, llid, plid, 0);
1033                        break;
1034                default:
1035                        spin_unlock_bh(&sta->lock);
1036                        break;
1037                }
1038                break;
1039        case NL80211_PLINK_HOLDING:
1040                switch (event) {
1041                case CLS_ACPT:
1042                        if (del_timer(&sta->plink_timer))
1043                                sta->ignore_plink_timer = 1;
1044                        mesh_plink_fsm_restart(sta);
1045                        spin_unlock_bh(&sta->lock);
1046                        break;
1047                case OPN_ACPT:
1048                case CNF_ACPT:
1049                case OPN_RJCT:
1050                case CNF_RJCT:
1051                        llid = sta->llid;
1052                        reason = sta->reason;
1053                        spin_unlock_bh(&sta->lock);
1054                        mesh_plink_frame_tx(sdata, WLAN_SP_MESH_PEERING_CLOSE,
1055                                            sta->sta.addr, llid, plid, reason);
1056                        break;
1057                default:
1058                        spin_unlock_bh(&sta->lock);
1059                }
1060                break;
1061        default:
1062                /* should not get here, PLINK_BLOCKED is dealt with at the
1063                 * beginning of the function
1064                 */
1065                spin_unlock_bh(&sta->lock);
1066                break;
1067        }
1068
1069        rcu_read_unlock();
1070
1071        if (changed)
1072                ieee80211_mbss_info_change_notify(sdata, changed);
1073}
1074