From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mga09.intel.com (mga09.intel.com [134.134.136.24]) by dpdk.org (Postfix) with ESMTP id 7910436E for ; Wed, 14 May 2014 14:56:52 +0200 (CEST) Received: from orsmga002.jf.intel.com ([10.7.209.21]) by orsmga102.jf.intel.com with ESMTP; 14 May 2014 05:51:57 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="4.97,1051,1389772800"; d="scan'208";a="540239747" Received: from irsmsx103.ger.corp.intel.com ([163.33.3.157]) by orsmga002.jf.intel.com with ESMTP; 14 May 2014 05:56:58 -0700 Received: from irsmsx107.ger.corp.intel.com (163.33.3.99) by IRSMSX103.ger.corp.intel.com (163.33.3.157) with Microsoft SMTP Server (TLS) id 14.3.123.3; Wed, 14 May 2014 13:56:57 +0100 Received: from irsmsx105.ger.corp.intel.com ([169.254.7.70]) by IRSMSX107.ger.corp.intel.com ([169.254.10.172]) with mapi id 14.03.0123.003; Wed, 14 May 2014 13:56:56 +0100 From: "Ananyev, Konstantin" To: Ivan Boule , "dev@dpdk.org" Thread-Topic: [dpdk-dev] [PATCH 2/5] ethdev: allow to set RSS hash computation flags and/or key Thread-Index: AQHPb1CweKOr79/Gc0O3Z0reZfNh/JtABayg Date: Wed, 14 May 2014 12:56:56 +0000 Message-ID: <2601191342CEEE43887BDE71AB9772580EFA663F@IRSMSX105.ger.corp.intel.com> References: <1398866126-16931-1-git-send-email-ivan.boule@6wind.com> <1398866126-16931-3-git-send-email-ivan.boule@6wind.com> <2601191342CEEE43887BDE71AB9772580EFA2293@IRSMSX105.ger.corp.intel.com> <53732CC2.4060906@6wind.com> In-Reply-To: <53732CC2.4060906@6wind.com> Accept-Language: en-IE, en-US Content-Language: en-US X-MS-Has-Attach: X-MS-TNEF-Correlator: x-originating-ip: [163.33.239.182] Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Subject: Re: [dpdk-dev] [PATCH 2/5] ethdev: allow to set RSS hash computation flags and/or key X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.15 Precedence: list List-Id: patches and discussions about DPDK List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Wed, 14 May 2014 12:56:53 -0000 Hi Ivan, Then may be instead of rss_hash_conf_update() introduce just rss_hash_updat= e() that will update only hash key and flags dynamically? In a same manner we have dev_rss_update/dev_rss_query today? BTW, I never tried myself to update RSSK and/or MRQE.RSS_Field_Enable on th= e fly. Though it is not forbidden explicitly, so I suppose it is ok to do that :) Thanks Konstantin =20 -----Original Message----- From: Ivan Boule [mailto:ivan.boule@6wind.com]=20 Sent: Wednesday, May 14, 2014 9:44 AM To: Ananyev, Konstantin; dev@dpdk.org Subject: Re: [dpdk-dev] [PATCH 2/5] ethdev: allow to set RSS hash computati= on flags and/or key Hi Konstantin, I apologize for my late answer. I had also read the Niantic documentation that stated to RSS should not=20 be enabled/disabled on the fly. In fact, RSS configuration patches are intended to enable the dynamic=20 changement of the RSS configuration of a port (RETA, hash key, hash=20 flags), rather than to only disable/enable RSS. In my opinion, initializing a port with multiple RX queues and RSS=20 disableddoes not make sense, and thus there is not reason for allowing=20 RSS to be then dynamically enabled in such a case. For the same reason, once having initialized a port with multiple RX=20 queuesand RSS enabled, it does not make sense to then disable RSS on=20 that port. Conversely, creating a single RX queue on a port with RSS enabled does=20 makesense to provide packet RSS hash values to the DPDK network stack,=20 but, again,it does not make sense to then disable RSS on that port. According to these considerations, I propose to update the dynamic RSS=20 configuration with tests that prevent disabling RSS once initially=20 enabled, or enabling RSS once initially disabled. Regards, Ivan On 05/02/2014 01:21 AM, Ananyev, Konstantin wrote: > Hi Ivan, > > About enabling/disabling RSS dynamically (without dev_stop/dev_start): > As I know 82599 spec explicitly states that RSS shouldn't be enabled/disa= bled dynamically. > From section 7.1.2.8 Receive-Side Scaling (RSS): > "... > Enabling rules: > * RSS is enabled in the MRQC register. > * RSS enabling cannot be done dynamically while it must be preceded by a = software > reset. > ... > Disabling rules: > * Disabling RSS on the fly is not allowed, and the 82599 must be reset af= ter RSS is > disabled. > ..." > > RETA table from other side can be updated on the fly. > As I remember that was the reason why we allow only dev_rss_reta_update()= to be used dynamically (without dev_start/dev_stop). > > Konstantin > > > > -----Original Message----- > From: dev [mailto:dev-bounces@dpdk.org] On Behalf Of Ivan Boule > Sent: Wednesday, April 30, 2014 2:55 PM > To: dev@dpdk.org > Subject: [dpdk-dev] [PATCH 2/5] ethdev: allow to set RSS hash computation= flags and/or key > > 1) Add a new function "rss_hash_conf_update" in the PMD API to dynamicall= y > update the RSS flags and/or the RSS key used by a NIC to compute the = RSS > hash of input packets. > The new function uses the existing data structure "rte_eth_rss_conf" = for > the argument that contains the new hash flags and/or the new hash key= to > use. > > 2) Add the ixgbe-specific function "ixgbe_dev_rss_hash_conf_update" and t= he > igb-specific function "eth_igb_rss_hash_conf_update" to update the RS= S > hash configuration of ixgbe and igb controllers respectively. > > Note: > Configuring the RSS hash flags and the RSS key used by a NIC consists= in > updating appropriate PCI registers of the NIC. > These operations have been manually tested with the interactive comma= nds > "write reg" and "write regbit" of the testpmd application. > > Signed-off-by: Ivan Boule > --- > lib/librte_ether/rte_ethdev.c | 23 +++++++++ > lib/librte_ether/rte_ethdev.h | 25 ++++++++++ > lib/librte_pmd_e1000/e1000_ethdev.h | 3 ++ > lib/librte_pmd_e1000/igb_ethdev.c | 1 + > lib/librte_pmd_e1000/igb_rxtx.c | 93 +++++++++++++++++++++-------= ------- > lib/librte_pmd_ixgbe/ixgbe_ethdev.c | 1 + > lib/librte_pmd_ixgbe/ixgbe_ethdev.h | 3 ++ > lib/librte_pmd_ixgbe/ixgbe_rxtx.c | 90 ++++++++++++++++++++--------= ----- > 8 files changed, 169 insertions(+), 70 deletions(-) > > diff --git a/lib/librte_ether/rte_ethdev.c b/lib/librte_ether/rte_ethdev.= c > index 473c98b..c00dff0 100644 > --- a/lib/librte_ether/rte_ethdev.c > +++ b/lib/librte_ether/rte_ethdev.c > @@ -1572,6 +1572,29 @@ rte_eth_dev_rss_reta_query(uint8_t port_id, struct= rte_eth_rss_reta *reta_conf) > } > =20 > int > +rte_eth_dev_rss_hash_conf_update(uint8_t port_id, > + struct rte_eth_rss_conf *rss_conf) > +{ > + struct rte_eth_dev *dev; > + uint16_t rss_hash_protos; > + > + if (port_id >=3D nb_ports) { > + PMD_DEBUG_TRACE("Invalid port_id=3D%d\n", port_id); > + return (-ENODEV); > + } > + rss_hash_protos =3D rss_conf->rss_hf; > + if ((rss_hash_protos !=3D 0) && > + ((rss_hash_protos & ETH_RSS_PROTO_MASK) =3D=3D 0)) { > + PMD_DEBUG_TRACE("Invalid rss_hash_protos=3D0x%x\n", > + rss_hash_protos); > + return (-EINVAL); > + } > + dev =3D &rte_eth_devices[port_id]; > + FUNC_PTR_OR_ERR_RET(*dev->dev_ops->rss_hash_conf_update, -ENOTSUP); > + return (*dev->dev_ops->rss_hash_conf_update)(dev, rss_conf); > +} > + > +int > rte_eth_led_on(uint8_t port_id) > { > struct rte_eth_dev *dev; > diff --git a/lib/librte_ether/rte_ethdev.h b/lib/librte_ether/rte_ethdev.= h > index dea7471..a970761 100644 > --- a/lib/librte_ether/rte_ethdev.h > +++ b/lib/librte_ether/rte_ethdev.h > @@ -331,6 +331,8 @@ struct rte_eth_rss_conf { > #define ETH_RSS_IPV4_UDP 0x0040 /**< IPv4/UDP packet. */ > #define ETH_RSS_IPV6_UDP 0x0080 /**< IPv6/UDP packet. */ > #define ETH_RSS_IPV6_UDP_EX 0x0100 /**< IPv6/UDP with extension headers= . */ > + > +#define ETH_RSS_PROTO_MASK 0x01FF /**< Mask of valid RSS hash protocols= */ > /* Definitions used for redirection table entry size */ > #define ETH_RSS_RETA_NUM_ENTRIES 128 > #define ETH_RSS_RETA_MAX_QUEUE 16 > @@ -966,6 +968,10 @@ typedef int (*reta_query_t)(struct rte_eth_dev *dev, > struct rte_eth_rss_reta *reta_conf); > /**< @internal Query RSS redirection table on an Ethernet device */ > =20 > +typedef int (*rss_hash_conf_update_t)(struct rte_eth_dev *dev, > + struct rte_eth_rss_conf *rss_conf); > +/**< @internal Update RSS hash configuration of an Ethernet device */ > + > typedef int (*eth_dev_led_on_t)(struct rte_eth_dev *dev); > /**< @internal Turn on SW controllable LED on an Ethernet device */ > =20 > @@ -1153,6 +1159,8 @@ struct eth_dev_ops { > bypass_wd_reset_t bypass_wd_reset; > #endif > =20 > + /** Configure RSS hash protocols. */ > + rss_hash_conf_update_t rss_hash_conf_update; > }; > =20 > /** > @@ -2859,6 +2867,23 @@ int rte_eth_dev_bypass_wd_timeout_show(uint8_t por= t, uint32_t *wd_timeout); > */ > int rte_eth_dev_bypass_wd_reset(uint8_t port); > =20 > + /** > + * Configuration of Receive Side Scaling hash computation of Ethernet de= vice. > + * > + * @param port > + * The port identifier of the Ethernet device. > + * @param rss_conf > + * The new configuration to use for RSS hash computation on the port. > + * @return > + * - (0) if successful. > + * - (-ENODEV) if port identifier is invalid. > + * - (-ENOTSUP) if hardware doesn't support. > + * - (-EINVAL) if bad parameter. > + */ > +int > +rte_eth_dev_rss_hash_conf_update(uint8_t port_id, > + struct rte_eth_rss_conf *rss_conf); > + > #ifdef __cplusplus > } > #endif > diff --git a/lib/librte_pmd_e1000/e1000_ethdev.h b/lib/librte_pmd_e1000/e= 1000_ethdev.h > index d09064e..e228c53 100644 > --- a/lib/librte_pmd_e1000/e1000_ethdev.h > +++ b/lib/librte_pmd_e1000/e1000_ethdev.h > @@ -138,6 +138,9 @@ uint16_t eth_igb_recv_pkts(void *rxq, struct rte_mbuf= **rx_pkts, > uint16_t eth_igb_recv_scattered_pkts(void *rxq, > struct rte_mbuf **rx_pkts, uint16_t nb_pkts); > =20 > +int eth_igb_rss_hash_conf_update(struct rte_eth_dev *dev, > + struct rte_eth_rss_conf *rss_conf); > + > int eth_igbvf_rx_init(struct rte_eth_dev *dev); > =20 > void eth_igbvf_tx_init(struct rte_eth_dev *dev); > diff --git a/lib/librte_pmd_e1000/igb_ethdev.c b/lib/librte_pmd_e1000/igb= _ethdev.c > index 673b4de..07ae149 100644 > --- a/lib/librte_pmd_e1000/igb_ethdev.c > +++ b/lib/librte_pmd_e1000/igb_ethdev.c > @@ -193,6 +193,7 @@ static struct eth_dev_ops eth_igb_ops =3D { > .mac_addr_remove =3D eth_igb_rar_clear, > .reta_update =3D eth_igb_rss_reta_update, > .reta_query =3D eth_igb_rss_reta_query, > + .rss_hash_conf_update =3D eth_igb_rss_hash_conf_update, > }; > =20 > /* > diff --git a/lib/librte_pmd_e1000/igb_rxtx.c b/lib/librte_pmd_e1000/igb_r= xtx.c > index 1ebe2f5..5499fd8 100644 > --- a/lib/librte_pmd_e1000/igb_rxtx.c > +++ b/lib/librte_pmd_e1000/igb_rxtx.c > @@ -1518,54 +1518,36 @@ igb_rss_disable(struct rte_eth_dev *dev) > E1000_WRITE_REG(hw, E1000_MRQC, mrqc); > } > =20 > -static void > -igb_rss_configure(struct rte_eth_dev *dev) > +int > +eth_igb_rss_hash_conf_update(struct rte_eth_dev *dev, > + struct rte_eth_rss_conf *rss_conf) > { > struct e1000_hw *hw; > - uint8_t *hash_key; > + uint8_t *hash_key; > uint32_t rss_key; > uint32_t mrqc; > - uint32_t shift; > uint16_t rss_hf; > uint16_t i; > =20 > hw =3D E1000_DEV_PRIVATE_TO_HW(dev->data->dev_private); > - > - rss_hf =3D dev->data->dev_conf.rx_adv_conf.rss_conf.rss_hf; > - if (rss_hf =3D=3D 0) /* Disable RSS. */ { > - igb_rss_disable(dev); > - return; > - } > - hash_key =3D dev->data->dev_conf.rx_adv_conf.rss_conf.rss_key; > - if (hash_key =3D=3D NULL) > - hash_key =3D rss_intel_key; /* Default hash key. */ > - > - /* Fill in RSS hash key. */ > - for (i =3D 0; i < 10; i++) { > - rss_key =3D hash_key[(i * 4)]; > - rss_key |=3D hash_key[(i * 4) + 1] << 8; > - rss_key |=3D hash_key[(i * 4) + 2] << 16; > - rss_key |=3D hash_key[(i * 4) + 3] << 24; > - E1000_WRITE_REG_ARRAY(hw, E1000_RSSRK(0), i, rss_key); > + hash_key =3D rss_conf->rss_key; > + if (hash_key !=3D NULL) { > + /* Fill in RSS hash key */ > + for (i =3D 0; i < 10; i++) { > + rss_key =3D hash_key[(i * 4)]; > + rss_key |=3D hash_key[(i * 4) + 1] << 8; > + rss_key |=3D hash_key[(i * 4) + 2] << 16; > + rss_key |=3D hash_key[(i * 4) + 3] << 24; > + E1000_WRITE_REG_ARRAY(hw, E1000_RSSRK(0), i, rss_key); > + } > } > - > - /* Fill in redirection table. */ > - shift =3D (hw->mac.type =3D=3D e1000_82575) ? 6 : 0; > - for (i =3D 0; i < 128; i++) { > - union e1000_reta { > - uint32_t dword; > - uint8_t bytes[4]; > - } reta; > - uint8_t q_idx; > - > - q_idx =3D (uint8_t) ((dev->data->nb_rx_queues > 1) ? > - i % dev->data->nb_rx_queues : 0); > - reta.bytes[i & 3] =3D (uint8_t) (q_idx << shift); > - if ((i & 3) =3D=3D 3) > - E1000_WRITE_REG(hw, E1000_RETA(i >> 2), reta.dword); > + rss_hf =3D rss_conf->rss_hf; > + if (rss_hf =3D=3D 0) { /* Disable RSS */ > + igb_rss_disable(dev); > + return 0; > } > =20 > - /* Set configured hashing functions in MRQC register. */ > + /* Set configured hashing protocols in MRQC register */ > mrqc =3D E1000_MRQC_ENABLE_RSS_4Q; /* RSS enabled. */ > if (rss_hf & ETH_RSS_IPV4) > mrqc |=3D E1000_MRQC_RSS_FIELD_IPV4; > @@ -1586,6 +1568,43 @@ igb_rss_configure(struct rte_eth_dev *dev) > if (rss_hf & ETH_RSS_IPV6_UDP_EX) > mrqc |=3D E1000_MRQC_RSS_FIELD_IPV6_UDP_EX; > E1000_WRITE_REG(hw, E1000_MRQC, mrqc); > + return 0; > +} > + > +static void > +igb_rss_configure(struct rte_eth_dev *dev) > +{ > + struct rte_eth_rss_conf rss_conf; > + struct e1000_hw *hw; > + uint32_t shift; > + uint16_t i; > + > + hw =3D E1000_DEV_PRIVATE_TO_HW(dev->data->dev_private); > + > + /* Fill in redirection table. */ > + shift =3D (hw->mac.type =3D=3D e1000_82575) ? 6 : 0; > + for (i =3D 0; i < 128; i++) { > + union e1000_reta { > + uint32_t dword; > + uint8_t bytes[4]; > + } reta; > + uint8_t q_idx; > + > + q_idx =3D (uint8_t) ((dev->data->nb_rx_queues > 1) ? > + i % dev->data->nb_rx_queues : 0); > + reta.bytes[i & 3] =3D (uint8_t) (q_idx << shift); > + if ((i & 3) =3D=3D 3) > + E1000_WRITE_REG(hw, E1000_RETA(i >> 2), reta.dword); > + } > + > + /* > + * Configure the RSS key and the RSS protocols used to compute > + * the RSS hash of input packets. > + */ > + rss_conf =3D dev->data->dev_conf.rx_adv_conf.rss_conf; > + if (rss_conf.rss_key =3D=3D NULL) > + rss_conf.rss_key =3D rss_intel_key; /* Default hash key */ > + (void) eth_igb_rss_hash_conf_update(dev, &rss_conf); > } > =20 > /* > diff --git a/lib/librte_pmd_ixgbe/ixgbe_ethdev.c b/lib/librte_pmd_ixgbe/i= xgbe_ethdev.c > index 6dd52d7..5910501 100644 > --- a/lib/librte_pmd_ixgbe/ixgbe_ethdev.c > +++ b/lib/librte_pmd_ixgbe/ixgbe_ethdev.c > @@ -300,6 +300,7 @@ static struct eth_dev_ops ixgbe_eth_dev_ops =3D { > .bypass_ver_show =3D ixgbe_bypass_ver_show, > .bypass_wd_reset =3D ixgbe_bypass_wd_reset, > #endif /* RTE_NIC_BYPASS */ > + .rss_hash_conf_update =3D ixgbe_dev_rss_hash_conf_update, > }; > =20 > /* > diff --git a/lib/librte_pmd_ixgbe/ixgbe_ethdev.h b/lib/librte_pmd_ixgbe/i= xgbe_ethdev.h > index 9d7e93f..3d33ad2 100644 > --- a/lib/librte_pmd_ixgbe/ixgbe_ethdev.h > +++ b/lib/librte_pmd_ixgbe/ixgbe_ethdev.h > @@ -235,6 +235,9 @@ uint16_t ixgbe_xmit_pkts(void *tx_queue, struct rte_m= buf **tx_pkts, > uint16_t ixgbe_xmit_pkts_simple(void *tx_queue, struct rte_mbuf **tx_pk= ts, > uint16_t nb_pkts); > =20 > +int ixgbe_dev_rss_hash_conf_update(struct rte_eth_dev *dev, > + struct rte_eth_rss_conf *rss_conf); > + > /* > * Flow director function prototypes > */ > diff --git a/lib/librte_pmd_ixgbe/ixgbe_rxtx.c b/lib/librte_pmd_ixgbe/ixg= be_rxtx.c > index 7930dbd..877ecfd 100644 > --- a/lib/librte_pmd_ixgbe/ixgbe_rxtx.c > +++ b/lib/librte_pmd_ixgbe/ixgbe_rxtx.c > @@ -2291,50 +2291,37 @@ ixgbe_rss_disable(struct rte_eth_dev *dev) > IXGBE_WRITE_REG(hw, IXGBE_MRQC, mrqc); > } > =20 > -static void > -ixgbe_rss_configure(struct rte_eth_dev *dev) > +int > +ixgbe_dev_rss_hash_conf_update(struct rte_eth_dev *dev, > + struct rte_eth_rss_conf *rss_conf) > { > struct ixgbe_hw *hw; > - uint8_t *hash_key; > - uint32_t rss_key; > + uint8_t *hash_key; > uint32_t mrqc; > - uint32_t reta; > + uint32_t rss_key; > uint16_t rss_hf; > uint16_t i; > - uint16_t j; > =20 > - PMD_INIT_FUNC_TRACE(); > hw =3D IXGBE_DEV_PRIVATE_TO_HW(dev->data->dev_private); > - > - rss_hf =3D dev->data->dev_conf.rx_adv_conf.rss_conf.rss_hf; > + hash_key =3D rss_conf->rss_key; > + if (hash_key !=3D NULL) { > + /* Fill in RSS hash key */ > + for (i =3D 0; i < 10; i++) { > + rss_key =3D hash_key[(i * 4)]; > + rss_key |=3D hash_key[(i * 4) + 1] << 8; > + rss_key |=3D hash_key[(i * 4) + 2] << 16; > + rss_key |=3D hash_key[(i * 4) + 3] << 24; > + IXGBE_WRITE_REG_ARRAY(hw, IXGBE_RSSRK(0), i, rss_key); > + } > + } > + rss_hf =3D rss_conf->rss_hf; > if (rss_hf =3D=3D 0) { /* Disable RSS */ > ixgbe_rss_disable(dev); > - return; > - } > - hash_key =3D dev->data->dev_conf.rx_adv_conf.rss_conf.rss_key; > - if (hash_key =3D=3D NULL) > - hash_key =3D rss_intel_key; /* Default hash key */ > - > - /* Fill in RSS hash key */ > - for (i =3D 0; i < 10; i++) { > - rss_key =3D hash_key[(i * 4)]; > - rss_key |=3D hash_key[(i * 4) + 1] << 8; > - rss_key |=3D hash_key[(i * 4) + 2] << 16; > - rss_key |=3D hash_key[(i * 4) + 3] << 24; > - IXGBE_WRITE_REG_ARRAY(hw, IXGBE_RSSRK(0), i, rss_key); > - } > - > - /* Fill in redirection table */ > - reta =3D 0; > - for (i =3D 0, j =3D 0; i < 128; i++, j++) { > - if (j =3D=3D dev->data->nb_rx_queues) j =3D 0; > - reta =3D (reta << 8) | j; > - if ((i & 3) =3D=3D 3) > - IXGBE_WRITE_REG(hw, IXGBE_RETA(i >> 2), rte_bswap32(reta)); > + return 0; > } > =20 > - /* Set configured hashing functions in MRQC register */ > - mrqc =3D IXGBE_MRQC_RSSEN; /* RSS enable */ > + /* Set configured hashing protocols in MRQC register */ > + mrqc =3D IXGBE_MRQC_RSSEN; /* Enable RSS */ > if (rss_hf & ETH_RSS_IPV4) > mrqc |=3D IXGBE_MRQC_RSS_FIELD_IPV4; > if (rss_hf & ETH_RSS_IPV4_TCP) > @@ -2354,6 +2341,43 @@ ixgbe_rss_configure(struct rte_eth_dev *dev) > if (rss_hf & ETH_RSS_IPV6_UDP_EX) > mrqc |=3D IXGBE_MRQC_RSS_FIELD_IPV6_EX_UDP; > IXGBE_WRITE_REG(hw, IXGBE_MRQC, mrqc); > + return 0; > +} > + > +static void > +ixgbe_rss_configure(struct rte_eth_dev *dev) > +{ > + struct rte_eth_rss_conf rss_conf; > + struct ixgbe_hw *hw; > + uint32_t reta; > + uint16_t i; > + uint16_t j; > + > + PMD_INIT_FUNC_TRACE(); > + hw =3D IXGBE_DEV_PRIVATE_TO_HW(dev->data->dev_private); > + > + /* > + * Fill in redirection table > + * The byte-swap is needed because NIC registers are in > + * little-endian order. > + */ > + reta =3D 0; > + for (i =3D 0, j =3D 0; i < 128; i++, j++) { > + if (j =3D=3D dev->data->nb_rx_queues) j =3D 0; > + reta =3D (reta << 8) | j; > + if ((i & 3) =3D=3D 3) > + IXGBE_WRITE_REG(hw, IXGBE_RETA(i >> 2), > + rte_bswap32(reta)); > + } > + > + /* > + * Configure the RSS key and the RSS protocols used to compute > + * the RSS hash of input packets. > + */ > + rss_conf =3D dev->data->dev_conf.rx_adv_conf.rss_conf; > + if (rss_conf.rss_key =3D=3D NULL) > + rss_conf.rss_key =3D rss_intel_key; /* Default hash key */ > + (void) ixgbe_dev_rss_hash_conf_update(dev, &rss_conf); > } > =20 > #define NUM_VFTA_REGISTERS 128 --=20 Ivan Boule 6WIND Development Engineer