The branch main has been updated by np:

URL: 
https://cgit.FreeBSD.org/src/commit/?id=c231e86ce388a0d0fb64e0fd2ff736c990ec97bb

commit c231e86ce388a0d0fb64e0fd2ff736c990ec97bb
Author:     Navdeep Parhar <[email protected]>
AuthorDate: 2025-09-29 09:48:18 +0000
Commit:     Navdeep Parhar <[email protected]>
CommitDate: 2025-09-29 14:26:00 +0000

    cxgbe(4): Update the filtering code for T7
    
    There are new fields available and the width of the optional part has
    changed.  This affects the ntuples used by TOE/filters/hashfilters.
    
    MFC after:      3 days
    Sponsored by:   Chelsio Communications
---
 sys/dev/cxgbe/t4_filter.c      | 458 +++++++++++++++++++++++++++++------------
 sys/dev/cxgbe/t4_ioctl.h       |   8 +
 sys/dev/cxgbe/tom/t4_connect.c |  37 +++-
 sys/dev/cxgbe/tom/t4_tom.c     |   5 +-
 4 files changed, 368 insertions(+), 140 deletions(-)

diff --git a/sys/dev/cxgbe/t4_filter.c b/sys/dev/cxgbe/t4_filter.c
index 8d4552116d96..92f882dd38cf 100644
--- a/sys/dev/cxgbe/t4_filter.c
+++ b/sys/dev/cxgbe/t4_filter.c
@@ -322,48 +322,85 @@ remove_hftid(struct adapter *sc, struct filter_entry *f)
        LIST_REMOVE(f, link_tid);
 }
 
-/*
- * Input: driver's 32b filter mode.
- * Returns: hardware filter mode (bits to set in vlan_pri_map) for the input.
- */
 static uint16_t
-mode_to_fconf(uint32_t mode)
+mode_to_fconf_t4(uint32_t mode)
 {
        uint32_t fconf = 0;
 
        if (mode & T4_FILTER_IP_FRAGMENT)
                fconf |= F_FRAGMENTATION;
-
        if (mode & T4_FILTER_MPS_HIT_TYPE)
                fconf |= F_MPSHITTYPE;
-
        if (mode & T4_FILTER_MAC_IDX)
                fconf |= F_MACMATCH;
-
        if (mode & T4_FILTER_ETH_TYPE)
                fconf |= F_ETHERTYPE;
-
        if (mode & T4_FILTER_IP_PROTO)
                fconf |= F_PROTOCOL;
-
        if (mode & T4_FILTER_IP_TOS)
                fconf |= F_TOS;
-
        if (mode & T4_FILTER_VLAN)
                fconf |= F_VLAN;
-
        if (mode & T4_FILTER_VNIC)
                fconf |= F_VNIC_ID;
-
        if (mode & T4_FILTER_PORT)
                fconf |= F_PORT;
-
        if (mode & T4_FILTER_FCoE)
                fconf |= F_FCOE;
 
        return (fconf);
 }
 
+static uint16_t
+mode_to_fconf_t7(uint32_t mode)
+{
+       uint32_t fconf = 0;
+
+       if (mode & T4_FILTER_TCPFLAGS)
+               fconf |= F_TCPFLAGS;
+       if (mode & T4_FILTER_SYNONLY)
+               fconf |= F_SYNONLY;
+       if (mode & T4_FILTER_ROCE)
+               fconf |= F_ROCE;
+       if (mode & T4_FILTER_IP_FRAGMENT)
+               fconf |= F_T7_FRAGMENTATION;
+       if (mode & T4_FILTER_MPS_HIT_TYPE)
+               fconf |= F_T7_MPSHITTYPE;
+       if (mode & T4_FILTER_MAC_IDX)
+               fconf |= F_T7_MACMATCH;
+       if (mode & T4_FILTER_ETH_TYPE)
+               fconf |= F_T7_ETHERTYPE;
+       if (mode & T4_FILTER_IP_PROTO)
+               fconf |= F_T7_PROTOCOL;
+       if (mode & T4_FILTER_IP_TOS)
+               fconf |= F_T7_TOS;
+       if (mode & T4_FILTER_VLAN)
+               fconf |= F_T7_VLAN;
+       if (mode & T4_FILTER_VNIC)
+               fconf |= F_T7_VNIC_ID;
+       if (mode & T4_FILTER_PORT)
+               fconf |= F_T7_PORT;
+       if (mode & T4_FILTER_FCoE)
+               fconf |= F_T7_FCOE;
+       if (mode & T4_FILTER_IPSECIDX)
+               fconf |= F_IPSECIDX;
+
+       return (fconf);
+}
+
+/*
+ * Input: driver's 32b filter mode.
+ * Returns: hardware filter mode (bits to set in vlan_pri_map) for the input.
+ */
+static uint16_t
+mode_to_fconf(struct adapter *sc, uint32_t mode)
+{
+       if (chip_id(sc) >= CHELSIO_T7)
+               return (mode_to_fconf_t7(mode));
+       else
+               return (mode_to_fconf_t4(mode));
+}
+
 /*
  * Input: driver's 32b filter mode.
  * Returns: hardware vnic mode (ingress config) matching the input.
@@ -389,65 +426,100 @@ check_fspec_against_fconf_iconf(struct adapter *sc,
        struct tp_params *tpp = &sc->params.tp;
        uint32_t fconf = 0;
 
-       if (fs->val.frag || fs->mask.frag)
-               fconf |= F_FRAGMENTATION;
-
-       if (fs->val.matchtype || fs->mask.matchtype)
-               fconf |= F_MPSHITTYPE;
-
-       if (fs->val.macidx || fs->mask.macidx)
-               fconf |= F_MACMATCH;
-
-       if (fs->val.ethtype || fs->mask.ethtype)
-               fconf |= F_ETHERTYPE;
-
-       if (fs->val.proto || fs->mask.proto)
-               fconf |= F_PROTOCOL;
-
-       if (fs->val.tos || fs->mask.tos)
-               fconf |= F_TOS;
-
-       if (fs->val.vlan_vld || fs->mask.vlan_vld)
-               fconf |= F_VLAN;
-
-       if (fs->val.ovlan_vld || fs->mask.ovlan_vld) {
-               if (tpp->vnic_mode != FW_VNIC_MODE_OUTER_VLAN)
-                       return (EINVAL);
-               fconf |= F_VNIC_ID;
-       }
-
-       if (fs->val.pfvf_vld || fs->mask.pfvf_vld) {
-               if (tpp->vnic_mode != FW_VNIC_MODE_PF_VF)
-                       return (EINVAL);
-               fconf |= F_VNIC_ID;
-       }
-
+       if (chip_id(sc) >= CHELSIO_T7) {
+               if (fs->val.tcpflags || fs->mask.tcpflags)
+                       fconf |= F_TCPFLAGS;
+               if (fs->val.synonly || fs->mask.synonly)
+                       fconf |= F_SYNONLY;
+               if (fs->val.roce || fs->mask.roce)
+                       fconf |= F_ROCE;
+               if (fs->val.frag || fs->mask.frag)
+                       fconf |= F_T7_FRAGMENTATION;
+               if (fs->val.matchtype || fs->mask.matchtype)
+                       fconf |= F_T7_MPSHITTYPE;
+               if (fs->val.macidx || fs->mask.macidx)
+                       fconf |= F_T7_MACMATCH;
+               if (fs->val.ethtype || fs->mask.ethtype)
+                       fconf |= F_T7_ETHERTYPE;
+               if (fs->val.proto || fs->mask.proto)
+                       fconf |= F_T7_PROTOCOL;
+               if (fs->val.tos || fs->mask.tos)
+                       fconf |= F_T7_TOS;
+               if (fs->val.vlan_vld || fs->mask.vlan_vld)
+                       fconf |= F_T7_VLAN;
+               if (fs->val.ovlan_vld || fs->mask.ovlan_vld) {
+                       if (tpp->vnic_mode != FW_VNIC_MODE_OUTER_VLAN)
+                               return (EINVAL);
+                       fconf |= F_T7_VNIC_ID;
+               }
+               if (fs->val.pfvf_vld || fs->mask.pfvf_vld) {
+                       if (tpp->vnic_mode != FW_VNIC_MODE_PF_VF)
+                               return (EINVAL);
+                       fconf |= F_T7_VNIC_ID;
+               }
 #ifdef notyet
-       if (fs->val.encap_vld || fs->mask.encap_vld) {
-               if (tpp->vnic_mode != FW_VNIC_MODE_ENCAP_EN);
+               if (fs->val.encap_vld || fs->mask.encap_vld) {
+                       if (tpp->vnic_mode != FW_VNIC_MODE_ENCAP_EN);
+                               return (EINVAL);
+                       fconf |= F_T7_VNIC_ID;
+               }
+#endif
+               if (fs->val.iport || fs->mask.iport)
+                       fconf |= F_T7_PORT;
+               if (fs->val.fcoe || fs->mask.fcoe)
+                       fconf |= F_T7_FCOE;
+               if (fs->val.ipsecidx || fs->mask.ipsecidx)
+                       fconf |= F_IPSECIDX;
+       } else {
+               if (fs->val.tcpflags || fs->mask.tcpflags ||
+                   fs->val.synonly || fs->mask.synonly ||
+                   fs->val.roce || fs->mask.roce ||
+                   fs->val.ipsecidx || fs->mask.ipsecidx)
                        return (EINVAL);
-               fconf |= F_VNIC_ID;
-       }
+               if (fs->val.frag || fs->mask.frag)
+                       fconf |= F_FRAGMENTATION;
+               if (fs->val.matchtype || fs->mask.matchtype)
+                       fconf |= F_MPSHITTYPE;
+               if (fs->val.macidx || fs->mask.macidx)
+                       fconf |= F_MACMATCH;
+               if (fs->val.ethtype || fs->mask.ethtype)
+                       fconf |= F_ETHERTYPE;
+               if (fs->val.proto || fs->mask.proto)
+                       fconf |= F_PROTOCOL;
+               if (fs->val.tos || fs->mask.tos)
+                       fconf |= F_TOS;
+               if (fs->val.vlan_vld || fs->mask.vlan_vld)
+                       fconf |= F_VLAN;
+               if (fs->val.ovlan_vld || fs->mask.ovlan_vld) {
+                       if (tpp->vnic_mode != FW_VNIC_MODE_OUTER_VLAN)
+                               return (EINVAL);
+                       fconf |= F_VNIC_ID;
+               }
+               if (fs->val.pfvf_vld || fs->mask.pfvf_vld) {
+                       if (tpp->vnic_mode != FW_VNIC_MODE_PF_VF)
+                               return (EINVAL);
+                       fconf |= F_VNIC_ID;
+               }
+#ifdef notyet
+               if (fs->val.encap_vld || fs->mask.encap_vld) {
+                       if (tpp->vnic_mode != FW_VNIC_MODE_ENCAP_EN);
+                               return (EINVAL);
+                       fconf |= F_VNIC_ID;
+               }
 #endif
-
-       if (fs->val.iport || fs->mask.iport)
-               fconf |= F_PORT;
-
-       if (fs->val.fcoe || fs->mask.fcoe)
-               fconf |= F_FCOE;
-
+               if (fs->val.iport || fs->mask.iport)
+                       fconf |= F_PORT;
+               if (fs->val.fcoe || fs->mask.fcoe)
+                       fconf |= F_FCOE;
+       }
        if ((tpp->filter_mode | fconf) != tpp->filter_mode)
                return (E2BIG);
 
        return (0);
 }
 
-/*
- * Input: hardware filter configuration (filter mode/mask, ingress config).
- * Input: driver's 32b filter mode matching the input.
- */
 static uint32_t
-fconf_to_mode(uint16_t hwmode, int vnic_mode)
+fconf_to_mode_t4(uint16_t hwmode, int vnic_mode)
 {
        uint32_t mode = T4_FILTER_IPv4 | T4_FILTER_IPv6 | T4_FILTER_IP_SADDR |
            T4_FILTER_IP_DADDR | T4_FILTER_IP_SPORT | T4_FILTER_IP_DPORT;
@@ -488,6 +560,69 @@ fconf_to_mode(uint16_t hwmode, int vnic_mode)
        return (mode);
 }
 
+static uint32_t
+fconf_to_mode_t7(uint16_t hwmode, int vnic_mode)
+{
+       uint32_t mode = T4_FILTER_IPv4 | T4_FILTER_IPv6 | T4_FILTER_IP_SADDR |
+           T4_FILTER_IP_DADDR | T4_FILTER_IP_SPORT | T4_FILTER_IP_DPORT;
+
+       if (hwmode & F_TCPFLAGS)
+               mode |= T4_FILTER_TCPFLAGS;
+       if (hwmode & F_SYNONLY)
+               mode |= T4_FILTER_SYNONLY;
+       if (hwmode & F_ROCE)
+               mode |= T4_FILTER_ROCE;
+       if (hwmode & F_T7_FRAGMENTATION)
+               mode |= T4_FILTER_IP_FRAGMENT;
+       if (hwmode & F_T7_MPSHITTYPE)
+               mode |= T4_FILTER_MPS_HIT_TYPE;
+       if (hwmode & F_T7_MACMATCH)
+               mode |= T4_FILTER_MAC_IDX;
+       if (hwmode & F_T7_ETHERTYPE)
+               mode |= T4_FILTER_ETH_TYPE;
+       if (hwmode & F_T7_PROTOCOL)
+               mode |= T4_FILTER_IP_PROTO;
+       if (hwmode & F_T7_TOS)
+               mode |= T4_FILTER_IP_TOS;
+       if (hwmode & F_T7_VLAN)
+               mode |= T4_FILTER_VLAN;
+       if (hwmode & F_T7_VNIC_ID)
+               mode |= T4_FILTER_VNIC; /* real meaning depends on vnic_mode. */
+       if (hwmode & F_T7_PORT)
+               mode |= T4_FILTER_PORT;
+       if (hwmode & F_T7_FCOE)
+               mode |= T4_FILTER_FCoE;
+       if (hwmode & F_IPSECIDX)
+               mode |= T4_FILTER_IPSECIDX;
+
+       switch (vnic_mode) {
+       case FW_VNIC_MODE_PF_VF:
+               mode |= T4_FILTER_IC_VNIC;
+               break;
+       case FW_VNIC_MODE_ENCAP_EN:
+               mode |= T4_FILTER_IC_ENCAP;
+               break;
+       case FW_VNIC_MODE_OUTER_VLAN:
+       default:
+               break;
+       }
+
+       return (mode);
+}
+
+/*
+ * Input: hardware filter configuration (filter mode/mask, ingress config).
+ * Output: driver's 32b filter mode matching the input.
+ */
+static inline uint32_t
+fconf_to_mode(struct adapter *sc, uint16_t hwmode, int vnic_mode)
+{
+       if (chip_id(sc) >= CHELSIO_T7)
+               return (fconf_to_mode_t7(hwmode, vnic_mode));
+       else
+               return (fconf_to_mode_t4(hwmode, vnic_mode));
+}
+
 int
 get_filter_mode(struct adapter *sc, uint32_t *mode)
 {
@@ -499,7 +634,7 @@ get_filter_mode(struct adapter *sc, uint32_t *mode)
 
        /* Non-zero incoming value in mode means "hashfilter mode". */
        filter_mode = *mode ? tp->filter_mask : tp->filter_mode;
-       *mode = fconf_to_mode(filter_mode, tp->vnic_mode);
+       *mode = fconf_to_mode(sc, filter_mode, tp->vnic_mode);
 
        return (0);
 }
@@ -512,7 +647,7 @@ set_filter_mode(struct adapter *sc, uint32_t mode)
        uint16_t fconf;
 
        iconf = mode_to_iconf(mode);
-       fconf = mode_to_fconf(mode);
+       fconf = mode_to_fconf(sc, mode);
        if ((iconf == -1 || iconf == tp->vnic_mode) && fconf == tp->filter_mode)
                return (0);     /* Nothing to do */
 
@@ -554,7 +689,7 @@ set_filter_mask(struct adapter *sc, uint32_t mode)
        uint16_t fmask;
 
        iconf = mode_to_iconf(mode);
-       fmask = mode_to_fconf(mode);
+       fmask = mode_to_fconf(sc, mode);
        if ((iconf == -1 || iconf == tp->vnic_mode) && fmask == tp->filter_mask)
                return (0);     /* Nothing to do */
 
@@ -811,71 +946,138 @@ hashfilter_ntuple(struct adapter *sc, const struct 
t4_filter_specification *fs,
        struct tp_params *tp = &sc->params.tp;
        uint16_t fmask;
 
-       *ftuple = fmask = 0;
-
        /*
         * Initialize each of the fields which we care about which are present
         * in the Compressed Filter Tuple.
         */
-       if (tp->vlan_shift >= 0 && fs->mask.vlan) {
-               *ftuple |= (uint64_t)(F_FT_VLAN_VLD | fs->val.vlan) <<
-                   tp->vlan_shift;
-               fmask |= F_VLAN;
-       }
-
-       if (tp->port_shift >= 0 && fs->mask.iport) {
-               *ftuple |= (uint64_t)fs->val.iport << tp->port_shift;
-               fmask |= F_PORT;
-       }
-
-       if (tp->protocol_shift >= 0 && fs->mask.proto) {
-               *ftuple |= (uint64_t)fs->val.proto << tp->protocol_shift;
-               fmask |= F_PROTOCOL;
-       }
-
-       if (tp->tos_shift >= 0 && fs->mask.tos) {
-               *ftuple |= (uint64_t)(fs->val.tos) << tp->tos_shift;
-               fmask |= F_TOS;
-       }
-
-       if (tp->vnic_shift >= 0 && fs->mask.vnic) {
-               /* vnic_mode was already validated. */
-               if (tp->vnic_mode == FW_VNIC_MODE_PF_VF)
-                       MPASS(fs->mask.pfvf_vld);
-               else if (tp->vnic_mode == FW_VNIC_MODE_OUTER_VLAN)
-                       MPASS(fs->mask.ovlan_vld);
+#define SFF(V, S) ((uint64_t)(V) << S) /* Shifted Filter Field. */
+       *ftuple = fmask = 0;
+       if (chip_id(sc) >= CHELSIO_T7) {
+               if (tp->ipsecidx_shift >= 0 && fs->mask.ipsecidx) {
+                       *ftuple |= SFF(fs->val.ipsecidx, tp->ipsecidx_shift);
+                       fmask |= F_IPSECIDX;
+               }
+               if (tp->fcoe_shift >= 0 && fs->mask.fcoe) {
+                       *ftuple |= SFF(fs->val.fcoe, tp->fcoe_shift);
+                       fmask |= F_T7_FCOE;
+               }
+               if (tp->port_shift >= 0 && fs->mask.iport) {
+                       *ftuple |= (uint64_t)fs->val.iport << tp->port_shift;
+                       fmask |= F_T7_PORT;
+               }
+               if (tp->vnic_shift >= 0 && fs->mask.vnic) {
+                       /* vnic_mode was already validated. */
+                       if (tp->vnic_mode == FW_VNIC_MODE_PF_VF)
+                               MPASS(fs->mask.pfvf_vld);
+                       else if (tp->vnic_mode == FW_VNIC_MODE_OUTER_VLAN)
+                               MPASS(fs->mask.ovlan_vld);
 #ifdef notyet
-               else if (tp->vnic_mode == FW_VNIC_MODE_ENCAP_EN)
-                       MPASS(fs->mask.encap_vld);
+                       else if (tp->vnic_mode == FW_VNIC_MODE_ENCAP_EN)
+                               MPASS(fs->mask.encap_vld);
 #endif
-               *ftuple |= ((1ULL << 16) | fs->val.vnic) << tp->vnic_shift;
-               fmask |= F_VNIC_ID;
-       }
-
-       if (tp->macmatch_shift >= 0 && fs->mask.macidx) {
-               *ftuple |= (uint64_t)(fs->val.macidx) << tp->macmatch_shift;
-               fmask |= F_MACMATCH;
-       }
-
-       if (tp->ethertype_shift >= 0 && fs->mask.ethtype) {
-               *ftuple |= (uint64_t)(fs->val.ethtype) << tp->ethertype_shift;
-               fmask |= F_ETHERTYPE;
-       }
-
-       if (tp->matchtype_shift >= 0 && fs->mask.matchtype) {
-               *ftuple |= (uint64_t)(fs->val.matchtype) << tp->matchtype_shift;
-               fmask |= F_MPSHITTYPE;
-       }
-
-       if (tp->frag_shift >= 0 && fs->mask.frag) {
-               *ftuple |= (uint64_t)(fs->val.frag) << tp->frag_shift;
-               fmask |= F_FRAGMENTATION;
-       }
-
-       if (tp->fcoe_shift >= 0 && fs->mask.fcoe) {
-               *ftuple |= (uint64_t)(fs->val.fcoe) << tp->fcoe_shift;
-               fmask |= F_FCOE;
+                       *ftuple |= SFF(F_FT_VNID_ID_VLD | fs->val.vnic, 
tp->vnic_shift);
+                       fmask |= F_T7_VNIC_ID;
+               }
+               if (tp->vlan_shift >= 0 && fs->mask.vlan) {
+                       *ftuple |= SFF(F_FT_VLAN_VLD | fs->val.vlan, 
tp->vlan_shift);
+                       fmask |= F_T7_VLAN;
+               }
+               if (tp->tos_shift >= 0 && fs->mask.tos) {
+                       *ftuple |= SFF(fs->val.tos, tp->tos_shift);
+                       fmask |= F_T7_TOS;
+               }
+               if (tp->protocol_shift >= 0 && fs->mask.proto) {
+                       *ftuple |= SFF(fs->val.proto, tp->protocol_shift);
+                       fmask |= F_T7_PROTOCOL;
+               }
+               if (tp->ethertype_shift >= 0 && fs->mask.ethtype) {
+                       *ftuple |= SFF(fs->val.ethtype, tp->ethertype_shift);
+                       fmask |= F_T7_ETHERTYPE;
+               }
+               if (tp->macmatch_shift >= 0 && fs->mask.macidx) {
+                       *ftuple |= SFF(fs->val.macidx, tp->macmatch_shift);
+                       fmask |= F_T7_MACMATCH;
+               }
+               if (tp->matchtype_shift >= 0 && fs->mask.matchtype) {
+                       *ftuple |= SFF(fs->val.matchtype, tp->matchtype_shift);
+                       fmask |= F_T7_MPSHITTYPE;
+               }
+               if (tp->frag_shift >= 0 && fs->mask.frag) {
+                       *ftuple |= SFF(fs->val.frag, tp->frag_shift);
+                       fmask |= F_T7_FRAGMENTATION;
+               }
+               if (tp->roce_shift >= 0 && fs->mask.roce) {
+                       *ftuple |= SFF(fs->val.roce, tp->roce_shift);
+                       fmask |= F_ROCE;
+               }
+               if (tp->synonly_shift >= 0 && fs->mask.synonly) {
+                       *ftuple |= SFF(fs->val.synonly, tp->synonly_shift);
+                       fmask |= F_SYNONLY;
+               }
+               if (tp->tcpflags_shift >= 0 && fs->mask.tcpflags) {
+                       *ftuple |= SFF(fs->val.tcpflags, tp->synonly_shift);
+                       fmask |= F_TCPFLAGS;
+               }
+       } else {
+               if (fs->mask.ipsecidx || fs->mask.roce || fs->mask.synonly ||
+                   fs->mask.tcpflags) {
+                       MPASS(tp->ipsecidx_shift == -1);
+                       MPASS(tp->roce_shift == -1);
+                       MPASS(tp->synonly_shift == -1);
+                       MPASS(tp->tcpflags_shift == -1);
+                       return (EINVAL);
+               }
+               if (tp->fcoe_shift >= 0 && fs->mask.fcoe) {
+                       *ftuple |= SFF(fs->val.fcoe, tp->fcoe_shift);
+                       fmask |= F_FCOE;
+               }
+               if (tp->port_shift >= 0 && fs->mask.iport) {
+                       *ftuple |= (uint64_t)fs->val.iport << tp->port_shift;
+                       fmask |= F_PORT;
+               }
+               if (tp->vnic_shift >= 0 && fs->mask.vnic) {
+                       /* vnic_mode was already validated. */
+                       if (tp->vnic_mode == FW_VNIC_MODE_PF_VF)
+                               MPASS(fs->mask.pfvf_vld);
+                       else if (tp->vnic_mode == FW_VNIC_MODE_OUTER_VLAN)
+                               MPASS(fs->mask.ovlan_vld);
+#ifdef notyet
+                       else if (tp->vnic_mode == FW_VNIC_MODE_ENCAP_EN)
+                               MPASS(fs->mask.encap_vld);
+#endif
+                       *ftuple |= SFF(F_FT_VNID_ID_VLD | fs->val.vnic, 
tp->vnic_shift);
+                       fmask |= F_VNIC_ID;
+               }
+               if (tp->vlan_shift >= 0 && fs->mask.vlan) {
+                       *ftuple |= SFF(F_FT_VLAN_VLD | fs->val.vlan, 
tp->vlan_shift);
+                       fmask |= F_VLAN;
+               }
+               if (tp->tos_shift >= 0 && fs->mask.tos) {
+                       *ftuple |= SFF(fs->val.tos, tp->tos_shift);
+                       fmask |= F_TOS;
+               }
+               if (tp->protocol_shift >= 0 && fs->mask.proto) {
+                       *ftuple |= SFF(fs->val.proto, tp->protocol_shift);
+                       fmask |= F_PROTOCOL;
+               }
+               if (tp->ethertype_shift >= 0 && fs->mask.ethtype) {
+                       *ftuple |= SFF(fs->val.ethtype, tp->ethertype_shift);
+                       fmask |= F_ETHERTYPE;
+               }
+               if (tp->macmatch_shift >= 0 && fs->mask.macidx) {
+                       *ftuple |= SFF(fs->val.macidx, tp->macmatch_shift);
+                       fmask |= F_MACMATCH;
+               }
+               if (tp->matchtype_shift >= 0 && fs->mask.matchtype) {
+                       *ftuple |= SFF(fs->val.matchtype, tp->matchtype_shift);
+                       fmask |= F_MPSHITTYPE;
+               }
+               if (tp->frag_shift >= 0 && fs->mask.frag) {
+                       *ftuple |= SFF(fs->val.frag, tp->frag_shift);
+                       fmask |= F_FRAGMENTATION;
+               }
        }
+#undef SFF
 
        /* A hashfilter must conform to the hardware filter mask. */
        if (fmask != tp->filter_mask)
@@ -1594,7 +1796,7 @@ static int
 act_open_cpl_len16(struct adapter *sc, int isipv6)
 {
        int idx;
-       static const int sz_table[3][2] = {
+       static const int sz_table[4][2] = {
                {
                        howmany(sizeof (struct cpl_act_open_req), 16),
                        howmany(sizeof (struct cpl_act_open_req6), 16)
@@ -1607,10 +1809,14 @@ act_open_cpl_len16(struct adapter *sc, int isipv6)
                        howmany(sizeof (struct cpl_t6_act_open_req), 16),
                        howmany(sizeof (struct cpl_t6_act_open_req6), 16)
                },
+               {
+                       howmany(sizeof (struct cpl_t7_act_open_req), 16),
+                       howmany(sizeof (struct cpl_t7_act_open_req6), 16)
+               },
        };
 
        MPASS(chip_id(sc) >= CHELSIO_T4);
-       idx = min(chip_id(sc) - CHELSIO_T4, 2);
+       idx = min(chip_id(sc) - CHELSIO_T4, 3);
 
        return (sz_table[idx][!!isipv6]);
 }
diff --git a/sys/dev/cxgbe/t4_ioctl.h b/sys/dev/cxgbe/t4_ioctl.h
index 4698986c0a0e..f7c8ee24d596 100644
--- a/sys/dev/cxgbe/t4_ioctl.h
+++ b/sys/dev/cxgbe/t4_ioctl.h
@@ -120,6 +120,10 @@ struct t4_i2c_data {
 #define T4_FILTER_MAC_IDX      0x2000  /* MPS MAC address match index */
 #define T4_FILTER_MPS_HIT_TYPE 0x4000  /* MPS match type */
 #define T4_FILTER_IP_FRAGMENT  0x8000  /* IP fragment */
+#define T4_FILTER_IPSECIDX     0x10000
+#define T4_FILTER_ROCE         0x20000
+#define T4_FILTER_SYNONLY      0x40000
+#define T4_FILTER_TCPFLAGS     0x80000
 /*
  * T4_FILTER_VNIC's real meaning depends on the ingress config.
  */
@@ -200,6 +204,10 @@ struct t4_filter_tuple {
        uint32_t vlan_vld:1;    /* VLAN valid */
        uint32_t ovlan_vld:1;   /* outer VLAN tag valid, value in "vnic" */
        uint32_t pfvf_vld:1;    /* VNIC id (PF/VF) valid, value in "vnic" */
+       uint32_t roce:1;
+       uint32_t synonly:1;
+       uint32_t tcpflags:6;
+       uint32_t ipsecidx:12;
 };
 
 struct t4_filter_specification {
diff --git a/sys/dev/cxgbe/tom/t4_connect.c b/sys/dev/cxgbe/tom/t4_connect.c
index fc092eab3223..c236ee060bc2 100644
--- a/sys/dev/cxgbe/tom/t4_connect.c
+++ b/sys/dev/cxgbe/tom/t4_connect.c
@@ -211,7 +211,7 @@ static inline int
 act_open_cpl_size(struct adapter *sc, int isipv6)
 {
        int idx;
-       static const int sz_table[3][2] = {
+       static const int sz_table[4][2] = {
                {
                        sizeof (struct cpl_act_open_req),
                        sizeof (struct cpl_act_open_req6)
@@ -224,10 +224,14 @@ act_open_cpl_size(struct adapter *sc, int isipv6)
                        sizeof (struct cpl_t6_act_open_req),
                        sizeof (struct cpl_t6_act_open_req6)
                },
+               {
+                       sizeof (struct cpl_t7_act_open_req),
+                       sizeof (struct cpl_t7_act_open_req6)
+               },
        };
 
        MPASS(chip_id(sc) >= CHELSIO_T4);
-       idx = min(chip_id(sc) - CHELSIO_T4, 2);
+       idx = min(chip_id(sc) - CHELSIO_T4, 3);
 
        return (sz_table[idx][!!isipv6]);
 }
@@ -261,6 +265,7 @@ t4_connect(struct toedev *tod, struct socket *so, struct 
nhop_object *nh,
        struct offload_settings settings;
        struct epoch_tracker et;
        uint16_t vid = 0xfff, pcp = 0;
+       uint64_t ntuple;
 
        INP_WLOCK_ASSERT(inp);
        KASSERT(nam->sa_family == AF_INET || nam->sa_family == AF_INET6,
@@ -314,10 +319,12 @@ t4_connect(struct toedev *tod, struct socket *so, struct 
nhop_object *nh,
        qid_atid = V_TID_QID(toep->ofld_rxq->iq.abs_id) | V_TID_TID(toep->tid) |
            V_TID_COOKIE(CPL_COOKIE_TOM);
 
+       ntuple = select_ntuple(vi, toep->l2te);
        if (isipv6) {
                struct cpl_act_open_req6 *cpl = wrtod(wr);
                struct cpl_t5_act_open_req6 *cpl5 = (void *)cpl;
                struct cpl_t6_act_open_req6 *cpl6 = (void *)cpl;
+               struct cpl_t7_act_open_req6 *cpl7 = (void *)cpl;
 
                if ((inp->inp_vflag & INP_IPV6) == 0)
                        DONT_OFFLOAD_ACTIVE_OPEN(ENOTSUP);
@@ -329,18 +336,23 @@ t4_connect(struct toedev *tod, struct socket *so, struct 
nhop_object *nh,
                switch (chip_id(sc)) {
                case CHELSIO_T4:
                        INIT_TP_WR(cpl, 0);
-                       cpl->params = select_ntuple(vi, toep->l2te);
+                       cpl->params = htobe32((uint32_t)ntuple);
                        break;
                case CHELSIO_T5:
                        INIT_TP_WR(cpl5, 0);
                        cpl5->iss = htobe32(tp->iss);
-                       cpl5->params = select_ntuple(vi, toep->l2te);
+                       cpl5->params = htobe64(V_FILTER_TUPLE(ntuple));
                        break;
                case CHELSIO_T6:
-               default:
                        INIT_TP_WR(cpl6, 0);
                        cpl6->iss = htobe32(tp->iss);
-                       cpl6->params = select_ntuple(vi, toep->l2te);
+                       cpl6->params = htobe64(V_FILTER_TUPLE(ntuple));
+                       break;
+               case CHELSIO_T7:
+               default:
+                       INIT_TP_WR(cpl7, 0);
+                       cpl7->iss = htobe32(tp->iss);
+                       cpl7->params = htobe64(V_T7_FILTER_TUPLE(ntuple));
                        break;
                }
                OPCODE_TID(cpl) = htobe32(MK_OPCODE_TID(CPL_ACT_OPEN_REQ6,
@@ -362,23 +374,28 @@ t4_connect(struct toedev *tod, struct socket *so, struct 
nhop_object *nh,
                struct cpl_act_open_req *cpl = wrtod(wr);
                struct cpl_t5_act_open_req *cpl5 = (void *)cpl;
                struct cpl_t6_act_open_req *cpl6 = (void *)cpl;
+               struct cpl_t7_act_open_req *cpl7 = (void *)cpl;
 
                switch (chip_id(sc)) {
                case CHELSIO_T4:
                        INIT_TP_WR(cpl, 0);
-                       cpl->params = select_ntuple(vi, toep->l2te);
+                       cpl->params = htobe32((uint32_t)ntuple);
                        break;
                case CHELSIO_T5:
                        INIT_TP_WR(cpl5, 0);
                        cpl5->iss = htobe32(tp->iss);
-                       cpl5->params = select_ntuple(vi, toep->l2te);
+                       cpl5->params = htobe64(V_FILTER_TUPLE(ntuple));
                        break;
                case CHELSIO_T6:
-               default:
                        INIT_TP_WR(cpl6, 0);
                        cpl6->iss = htobe32(tp->iss);
-                       cpl6->params = select_ntuple(vi, toep->l2te);
+                       cpl6->params = htobe64(V_FILTER_TUPLE(ntuple));
                        break;
+               case CHELSIO_T7:
+               default:
+                       INIT_TP_WR(cpl7, 0);
+                       cpl7->iss = htobe32(tp->iss);
+                       cpl7->params = htobe64(V_T7_FILTER_TUPLE(ntuple));
                }
                OPCODE_TID(cpl) = htobe32(MK_OPCODE_TID(CPL_ACT_OPEN_REQ,
                    qid_atid));
diff --git a/sys/dev/cxgbe/tom/t4_tom.c b/sys/dev/cxgbe/tom/t4_tom.c
index 024164ef4c51..82d8f724b382 100644
--- a/sys/dev/cxgbe/tom/t4_tom.c
+++ b/sys/dev/cxgbe/tom/t4_tom.c
@@ -1232,10 +1232,7 @@ select_ntuple(struct vi_info *vi, struct l2t_entry *e)
                    tp->vnic_shift;
        }
 
-       if (is_t4(sc))
-               return (htobe32((uint32_t)ntuple));
-       else
-               return (htobe64(V_FILTER_TUPLE(ntuple)));
+       return (ntuple);
 }
 
 /*

Reply via email to