]> asedeno.scripts.mit.edu Git - linux.git/commitdiff
Merge branch 'cxgb4-chtls-fix-issues-related-to-high-priority-region'
authorDavid S. Miller <davem@davemloft.net>
Wed, 18 Dec 2019 06:33:54 +0000 (22:33 -0800)
committerDavid S. Miller <davem@davemloft.net>
Wed, 18 Dec 2019 06:33:54 +0000 (22:33 -0800)
Shahjada Abul Husain says:

====================
cxgb4/chtls: fix issues related to high priority region

The high priority region introduced by:

commit c21939998802 ("cxgb4: add support for high priority filters")

had caused regression in some code paths, leading to connection
failures for the ULDs.

This series of patches attempt to fix the regressions.

Patch 1 fixes some code paths that have been missed to consider
the high priority region.

Patch 2 fixes ULD connection failures due to wrong TID base that
had been shifted after the high priority region.
====================

Signed-off-by: David S. Miller <davem@davemloft.net>
drivers/crypto/chelsio/chtls/chtls_cm.c
drivers/net/ethernet/chelsio/cxgb4/cxgb4_debugfs.c
drivers/net/ethernet/chelsio/cxgb4/cxgb4_filter.c
drivers/net/ethernet/chelsio/cxgb4/cxgb4_main.c
drivers/net/ethernet/chelsio/cxgb4/cxgb4_tc_flower.c
drivers/net/ethernet/chelsio/cxgb4/cxgb4_tc_matchall.c
drivers/net/ethernet/chelsio/cxgb4/cxgb4_uld.h

index aca75237bbcf83eb1d440bcdf1e4d3b702cff0a1..72e5b0f65a9163346fc0d0ffff2ea53723f5c357 100644 (file)
@@ -1273,7 +1273,7 @@ static int chtls_pass_accept_req(struct chtls_dev *cdev, struct sk_buff *skb)
        ctx = (struct listen_ctx *)data;
        lsk = ctx->lsk;
 
-       if (unlikely(tid >= cdev->tids->ntids)) {
+       if (unlikely(tid_out_of_range(cdev->tids, tid))) {
                pr_info("passive open TID %u too large\n", tid);
                return 1;
        }
index b6a79536e14324e4fae2eb7f7e54ab66e72a3c58..9a96b01dad560872ecaec089ea40b0c057d02dc3 100644 (file)
@@ -3171,14 +3171,12 @@ static const struct file_operations mem_debugfs_fops = {
 
 static int tid_info_show(struct seq_file *seq, void *v)
 {
-       unsigned int tid_start = 0;
        struct adapter *adap = seq->private;
-       const struct tid_info *t = &adap->tids;
-       enum chip_type chip = CHELSIO_CHIP_VERSION(adap->params.chip);
-
-       if (chip > CHELSIO_T5)
-               tid_start = t4_read_reg(adap, LE_DB_ACTIVE_TABLE_START_INDEX_A);
+       const struct tid_info *t;
+       enum chip_type chip;
 
+       t = &adap->tids;
+       chip = CHELSIO_CHIP_VERSION(adap->params.chip);
        if (t4_read_reg(adap, LE_DB_CONFIG_A) & HASHEN_F) {
                unsigned int sb;
                seq_printf(seq, "Connections in use: %u\n",
@@ -3190,9 +3188,9 @@ static int tid_info_show(struct seq_file *seq, void *v)
                        sb = t4_read_reg(adap, LE_DB_SRVR_START_INDEX_A);
 
                if (sb) {
-                       seq_printf(seq, "TID range: %u..%u/%u..%u", tid_start,
+                       seq_printf(seq, "TID range: %u..%u/%u..%u", t->tid_base,
                                   sb - 1, adap->tids.hash_base,
-                                  t->ntids - 1);
+                                  t->tid_base + t->ntids - 1);
                        seq_printf(seq, ", in use: %u/%u\n",
                                   atomic_read(&t->tids_in_use),
                                   atomic_read(&t->hash_tids_in_use));
@@ -3201,14 +3199,14 @@ static int tid_info_show(struct seq_file *seq, void *v)
                                   t->aftid_base,
                                   t->aftid_end,
                                   adap->tids.hash_base,
-                                  t->ntids - 1);
+                                  t->tid_base + t->ntids - 1);
                        seq_printf(seq, ", in use: %u/%u\n",
                                   atomic_read(&t->tids_in_use),
                                   atomic_read(&t->hash_tids_in_use));
                } else {
                        seq_printf(seq, "TID range: %u..%u",
                                   adap->tids.hash_base,
-                                  t->ntids - 1);
+                                  t->tid_base + t->ntids - 1);
                        seq_printf(seq, ", in use: %u\n",
                                   atomic_read(&t->hash_tids_in_use));
                }
@@ -3216,8 +3214,8 @@ static int tid_info_show(struct seq_file *seq, void *v)
                seq_printf(seq, "Connections in use: %u\n",
                           atomic_read(&t->conns_in_use));
 
-               seq_printf(seq, "TID range: %u..%u", tid_start,
-                          tid_start + t->ntids - 1);
+               seq_printf(seq, "TID range: %u..%u", t->tid_base,
+                          t->tid_base + t->ntids - 1);
                seq_printf(seq, ", in use: %u\n",
                           atomic_read(&t->tids_in_use));
        }
index 6a5b0346dad936abd6d8d0c13321d61664f62821..2a2938bbb93a31b88b463d4105dac57585641c86 100644 (file)
@@ -361,20 +361,22 @@ static int get_filter_count(struct adapter *adapter, unsigned int fidx,
 
        tcb_base = t4_read_reg(adapter, TP_CMM_TCB_BASE_A);
        if (is_hashfilter(adapter) && hash) {
-               if (fidx < adapter->tids.ntids) {
-                       f = adapter->tids.tid_tab[fidx];
-                       if (!f)
-                               return -EINVAL;
-               } else {
+               if (tid_out_of_range(&adapter->tids, fidx))
                        return -E2BIG;
-               }
+               f = adapter->tids.tid_tab[fidx - adapter->tids.tid_base];
+               if (!f)
+                       return -EINVAL;
        } else {
-               if ((fidx != (adapter->tids.nftids +
-                             adapter->tids.nsftids - 1)) &&
-                   fidx >= adapter->tids.nftids)
+               if ((fidx != (adapter->tids.nftids + adapter->tids.nsftids +
+                             adapter->tids.nhpftids - 1)) &&
+                   fidx >= (adapter->tids.nftids + adapter->tids.nhpftids))
                        return -E2BIG;
 
-               f = &adapter->tids.ftid_tab[fidx];
+               if (fidx < adapter->tids.nhpftids)
+                       f = &adapter->tids.hpftid_tab[fidx];
+               else
+                       f = &adapter->tids.ftid_tab[fidx -
+                                                   adapter->tids.nhpftids];
                if (!f->valid)
                        return -EINVAL;
        }
@@ -480,6 +482,7 @@ int cxgb4_get_free_ftid(struct net_device *dev, int family)
                ftid -= n;
        }
        spin_unlock_bh(&t->ftid_lock);
+       ftid += t->nhpftids;
 
        return found ? ftid : -ENOMEM;
 }
@@ -815,10 +818,14 @@ int delete_filter(struct adapter *adapter, unsigned int fidx)
        struct filter_entry *f;
        int ret;
 
-       if (fidx >= adapter->tids.nftids + adapter->tids.nsftids)
+       if (fidx >= adapter->tids.nftids + adapter->tids.nsftids +
+                   adapter->tids.nhpftids)
                return -EINVAL;
 
-       f = &adapter->tids.ftid_tab[fidx];
+       if (fidx < adapter->tids.nhpftids)
+               f = &adapter->tids.hpftid_tab[fidx];
+       else
+               f = &adapter->tids.ftid_tab[fidx - adapter->tids.nhpftids];
        ret = writable_filter(f);
        if (ret)
                return ret;
@@ -1606,7 +1613,7 @@ static int cxgb4_del_hash_filter(struct net_device *dev, int filter_id,
        netdev_dbg(dev, "%s: filter_id = %d ; nftids = %d\n",
                   __func__, filter_id, adapter->tids.nftids);
 
-       if (filter_id > adapter->tids.ntids)
+       if (tid_out_of_range(t, filter_id))
                return -E2BIG;
 
        f = lookup_tid(t, filter_id);
index be750f2de23cd7b3153564032bbff5571111f820..1930e39f195e99668cdd80bf4c1ce7cf0dea96d4 100644 (file)
@@ -1447,8 +1447,8 @@ static void mk_tid_release(struct sk_buff *skb, unsigned int chan,
 static void cxgb4_queue_tid_release(struct tid_info *t, unsigned int chan,
                                    unsigned int tid)
 {
-       void **p = &t->tid_tab[tid];
        struct adapter *adap = container_of(t, struct adapter, tids);
+       void **p = &t->tid_tab[tid - t->tid_base];
 
        spin_lock_bh(&adap->tid_release_lock);
        *p = adap->tid_release_head;
@@ -1500,13 +1500,13 @@ static void process_tid_release_list(struct work_struct *work)
 void cxgb4_remove_tid(struct tid_info *t, unsigned int chan, unsigned int tid,
                      unsigned short family)
 {
-       struct sk_buff *skb;
        struct adapter *adap = container_of(t, struct adapter, tids);
+       struct sk_buff *skb;
 
-       WARN_ON(tid >= t->ntids);
+       WARN_ON(tid_out_of_range(&adap->tids, tid));
 
-       if (t->tid_tab[tid]) {
-               t->tid_tab[tid] = NULL;
+       if (t->tid_tab[tid - adap->tids.tid_base]) {
+               t->tid_tab[tid - adap->tids.tid_base] = NULL;
                atomic_dec(&t->conns_in_use);
                if (t->hash_base && (tid >= t->hash_base)) {
                        if (family == AF_INET6)
@@ -4727,6 +4727,9 @@ static int adap_init0(struct adapter *adap, int vpd_skip)
                        adap->rawf_start = val[0];
                        adap->rawf_cnt = val[1] - val[0] + 1;
                }
+
+               adap->tids.tid_base =
+                       t4_read_reg(adap, LE_DB_ACTIVE_TABLE_START_INDEX_A);
        }
 
        /* qids (ingress/egress) returned from firmware can be anywhere
index 706b71e1b6c163a65afd11574baae3005805a477..bb5513bdd293efdfd2421c1a7b6b706609c5b955 100644 (file)
@@ -672,7 +672,8 @@ int cxgb4_tc_flower_replace(struct net_device *dev,
                 * 0 to driver. However, the hardware TCAM index
                 * starts from 0. Hence, the -1 here.
                 */
-               if (cls->common.prio <= adap->tids.nftids) {
+               if (cls->common.prio <= (adap->tids.nftids +
+                                        adap->tids.nhpftids)) {
                        fidx = cls->common.prio - 1;
                        if (fidx < adap->tids.nhpftids)
                                fs->prio = 1;
index 53e8db8b25469905558dfe6b90e13020ffce7e23..24c3c2dc7171a0c59bfa8aec7b2028ad2a282172 100644 (file)
@@ -137,7 +137,7 @@ static int cxgb4_matchall_alloc_filter(struct net_device *dev,
         * -1 here. 1 slot is enough to create a wildcard matchall
         * VIID rule.
         */
-       if (cls->common.prio <= adap->tids.nftids)
+       if (cls->common.prio <= (adap->tids.nftids + adap->tids.nhpftids))
                fidx = cls->common.prio - 1;
        else
                fidx = cxgb4_get_free_ftid(dev, PF_INET);
index e69de9a296aeba142e83c626d37c8faf3aa88e4e..d9d27bc1ae67c28a011b7e886b52180ddc87513f 100644 (file)
@@ -99,6 +99,7 @@ struct eotid_entry {
  */
 struct tid_info {
        void **tid_tab;
+       unsigned int tid_base;
        unsigned int ntids;
 
        struct serv_entry *stid_tab;
@@ -152,9 +153,15 @@ struct tid_info {
 
 static inline void *lookup_tid(const struct tid_info *t, unsigned int tid)
 {
+       tid -= t->tid_base;
        return tid < t->ntids ? t->tid_tab[tid] : NULL;
 }
 
+static inline bool tid_out_of_range(const struct tid_info *t, unsigned int tid)
+{
+       return ((tid - t->tid_base) >= t->ntids);
+}
+
 static inline void *lookup_atid(const struct tid_info *t, unsigned int atid)
 {
        return atid < t->natids ? t->atid_tab[atid].data : NULL;
@@ -176,7 +183,7 @@ static inline void *lookup_stid(const struct tid_info *t, unsigned int stid)
 static inline void cxgb4_insert_tid(struct tid_info *t, void *data,
                                    unsigned int tid, unsigned short family)
 {
-       t->tid_tab[tid] = data;
+       t->tid_tab[tid - t->tid_base] = data;
        if (t->hash_base && (tid >= t->hash_base)) {
                if (family == AF_INET6)
                        atomic_add(2, &t->hash_tids_in_use);