git: eee6854c33c7 - stable/15 - cxgbe(4): Update the filtering code for T7
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Fri, 03 Oct 2025 00:04:32 UTC
The branch stable/15 has been updated by np:
URL: https://cgit.FreeBSD.org/src/commit/?id=eee6854c33c70579ea17453c3490b890da57628d
commit eee6854c33c70579ea17453c3490b890da57628d
Author: Navdeep Parhar <np@FreeBSD.org>
AuthorDate: 2025-09-29 09:48:18 +0000
Commit: Navdeep Parhar <np@FreeBSD.org>
CommitDate: 2025-10-02 22:09:06 +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.
Sponsored by: Chelsio Communications
(cherry picked from commit c231e86ce388a0d0fb64e0fd2ff736c990ec97bb)
---
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);
}
/*