1 /* SPDX-License-Identifier: BSD-3-Clause
2 * Copyright(C) 2019 Marvell International Ltd.
5 #include "otx2_ethdev.h"
8 otx2_nix_rss_tbl_init(struct otx2_eth_dev *dev,
9 uint8_t group, uint16_t *ind_tbl)
11 struct otx2_rss_info *rss = &dev->rss_info;
12 struct otx2_mbox *mbox = dev->mbox;
13 struct nix_aq_enq_req *req;
16 for (idx = 0; idx < rss->rss_size; idx++) {
17 req = otx2_mbox_alloc_msg_nix_aq_enq(mbox);
19 /* The shared memory buffer can be full.
22 otx2_mbox_msg_send(mbox, 0);
23 rc = otx2_mbox_wait_for_rsp(mbox, 0);
27 req = otx2_mbox_alloc_msg_nix_aq_enq(mbox);
31 req->rss.rq = ind_tbl[idx];
33 req->qidx = (group * rss->rss_size) + idx;
34 req->ctype = NIX_AQ_CTYPE_RSS;
35 req->op = NIX_AQ_INSTOP_INIT;
38 otx2_mbox_msg_send(mbox, 0);
39 rc = otx2_mbox_wait_for_rsp(mbox, 0);
47 otx2_nix_dev_reta_update(struct rte_eth_dev *eth_dev,
48 struct rte_eth_rss_reta_entry64 *reta_conf,
51 struct otx2_eth_dev *dev = otx2_eth_pmd_priv(eth_dev);
52 struct otx2_rss_info *rss = &dev->rss_info;
57 if (reta_size != dev->rss_info.rss_size) {
58 otx2_err("Size of hash lookup table configured "
59 "(%d) doesn't match the number hardware can supported "
60 "(%d)", reta_size, dev->rss_info.rss_size);
65 for (i = 0; i < (dev->rss_info.rss_size / RTE_RETA_GROUP_SIZE); i++) {
66 for (j = 0; j < RTE_RETA_GROUP_SIZE; j++) {
67 if ((reta_conf[i].mask >> j) & 0x01)
68 rss->ind_tbl[idx] = reta_conf[i].reta[j];
73 return otx2_nix_rss_tbl_init(dev, 0, dev->rss_info.ind_tbl);
80 otx2_nix_dev_reta_query(struct rte_eth_dev *eth_dev,
81 struct rte_eth_rss_reta_entry64 *reta_conf,
84 struct otx2_eth_dev *dev = otx2_eth_pmd_priv(eth_dev);
85 struct otx2_rss_info *rss = &dev->rss_info;
90 if (reta_size != dev->rss_info.rss_size) {
91 otx2_err("Size of hash lookup table configured "
92 "(%d) doesn't match the number hardware can supported "
93 "(%d)", reta_size, dev->rss_info.rss_size);
98 for (i = 0; i < (dev->rss_info.rss_size / RTE_RETA_GROUP_SIZE); i++) {
99 for (j = 0; j < RTE_RETA_GROUP_SIZE; j++)
100 if ((reta_conf[i].mask >> j) & 0x01)
101 reta_conf[i].reta[j] = rss->ind_tbl[j];
111 otx2_nix_rss_set_key(struct otx2_eth_dev *dev, uint8_t *key,
114 const uint8_t default_key[NIX_HASH_KEY_SIZE] = {
115 0xFE, 0xED, 0x0B, 0xAD, 0xFE, 0xED, 0x0B, 0xAD,
116 0xFE, 0xED, 0x0B, 0xAD, 0xFE, 0xED, 0x0B, 0xAD,
117 0xFE, 0xED, 0x0B, 0xAD, 0xFE, 0xED, 0x0B, 0xAD,
118 0xFE, 0xED, 0x0B, 0xAD, 0xFE, 0xED, 0x0B, 0xAD,
119 0xFE, 0xED, 0x0B, 0xAD, 0xFE, 0xED, 0x0B, 0xAD,
120 0xFE, 0xED, 0x0B, 0xAD, 0xFE, 0xED, 0x0B, 0xAD
122 struct otx2_rss_info *rss = &dev->rss_info;
127 if (key == NULL || key == 0) {
128 keyptr = (uint64_t *)(uintptr_t)default_key;
129 key_len = NIX_HASH_KEY_SIZE;
130 memset(rss->key, 0, key_len);
132 memcpy(rss->key, key, key_len);
133 keyptr = (uint64_t *)rss->key;
136 for (idx = 0; idx < (key_len >> 3); idx++) {
137 val = rte_cpu_to_be_64(*keyptr);
138 otx2_write64(val, dev->base + NIX_LF_RX_SECRETX(idx));
144 rss_get_key(struct otx2_eth_dev *dev, uint8_t *key)
146 uint64_t *keyptr = (uint64_t *)key;
150 for (idx = 0; idx < (NIX_HASH_KEY_SIZE >> 3); idx++) {
151 val = otx2_read64(dev->base + NIX_LF_RX_SECRETX(idx));
152 *keyptr = rte_be_to_cpu_64(val);
157 #define RSS_IPV4_ENABLE ( \
159 ETH_RSS_FRAG_IPV4 | \
160 ETH_RSS_NONFRAG_IPV4_UDP | \
161 ETH_RSS_NONFRAG_IPV4_TCP | \
162 ETH_RSS_NONFRAG_IPV4_SCTP)
164 #define RSS_IPV6_ENABLE ( \
166 ETH_RSS_FRAG_IPV6 | \
167 ETH_RSS_NONFRAG_IPV6_UDP | \
168 ETH_RSS_NONFRAG_IPV6_TCP | \
169 ETH_RSS_NONFRAG_IPV6_SCTP)
171 #define RSS_IPV6_EX_ENABLE ( \
173 ETH_RSS_IPV6_TCP_EX | \
176 #define RSS_MAX_LEVELS 3
178 #define RSS_IPV4_INDEX 0
179 #define RSS_IPV6_INDEX 1
180 #define RSS_TCP_INDEX 2
181 #define RSS_UDP_INDEX 3
182 #define RSS_SCTP_INDEX 4
183 #define RSS_DMAC_INDEX 5
186 otx2_rss_ethdev_to_nix(struct otx2_eth_dev *dev, uint64_t ethdev_rss,
189 uint32_t flow_key_type[RSS_MAX_LEVELS][6] = {
191 FLOW_KEY_TYPE_IPV4, FLOW_KEY_TYPE_IPV6,
192 FLOW_KEY_TYPE_TCP, FLOW_KEY_TYPE_UDP,
193 FLOW_KEY_TYPE_SCTP, FLOW_KEY_TYPE_ETH_DMAC
196 FLOW_KEY_TYPE_INNR_IPV4, FLOW_KEY_TYPE_INNR_IPV6,
197 FLOW_KEY_TYPE_INNR_TCP, FLOW_KEY_TYPE_INNR_UDP,
198 FLOW_KEY_TYPE_INNR_SCTP, FLOW_KEY_TYPE_INNR_ETH_DMAC
201 FLOW_KEY_TYPE_IPV4 | FLOW_KEY_TYPE_INNR_IPV4,
202 FLOW_KEY_TYPE_IPV6 | FLOW_KEY_TYPE_INNR_IPV6,
203 FLOW_KEY_TYPE_TCP | FLOW_KEY_TYPE_INNR_TCP,
204 FLOW_KEY_TYPE_UDP | FLOW_KEY_TYPE_INNR_UDP,
205 FLOW_KEY_TYPE_SCTP | FLOW_KEY_TYPE_INNR_SCTP,
206 FLOW_KEY_TYPE_ETH_DMAC | FLOW_KEY_TYPE_INNR_ETH_DMAC
209 uint32_t flowkey_cfg = 0;
211 dev->rss_info.nix_rss = ethdev_rss;
213 if (ethdev_rss & ETH_RSS_L3_SRC_ONLY)
214 flowkey_cfg |= FLOW_KEY_TYPE_L3_SRC;
216 if (ethdev_rss & ETH_RSS_L3_DST_ONLY)
217 flowkey_cfg |= FLOW_KEY_TYPE_L3_DST;
219 if (ethdev_rss & ETH_RSS_L4_SRC_ONLY)
220 flowkey_cfg |= FLOW_KEY_TYPE_L4_SRC;
222 if (ethdev_rss & ETH_RSS_L4_DST_ONLY)
223 flowkey_cfg |= FLOW_KEY_TYPE_L4_DST;
225 if (ethdev_rss & RSS_IPV4_ENABLE)
226 flowkey_cfg |= flow_key_type[rss_level][RSS_IPV4_INDEX];
228 if (ethdev_rss & RSS_IPV6_ENABLE)
229 flowkey_cfg |= flow_key_type[rss_level][RSS_IPV6_INDEX];
231 if (ethdev_rss & ETH_RSS_TCP)
232 flowkey_cfg |= flow_key_type[rss_level][RSS_TCP_INDEX];
234 if (ethdev_rss & ETH_RSS_UDP)
235 flowkey_cfg |= flow_key_type[rss_level][RSS_UDP_INDEX];
237 if (ethdev_rss & ETH_RSS_SCTP)
238 flowkey_cfg |= flow_key_type[rss_level][RSS_SCTP_INDEX];
240 if (ethdev_rss & ETH_RSS_L2_PAYLOAD)
241 flowkey_cfg |= flow_key_type[rss_level][RSS_DMAC_INDEX];
243 if (ethdev_rss & RSS_IPV6_EX_ENABLE)
244 flowkey_cfg |= FLOW_KEY_TYPE_IPV6_EXT;
246 if (ethdev_rss & ETH_RSS_PORT)
247 flowkey_cfg |= FLOW_KEY_TYPE_PORT;
249 if (ethdev_rss & ETH_RSS_NVGRE)
250 flowkey_cfg |= FLOW_KEY_TYPE_NVGRE;
252 if (ethdev_rss & ETH_RSS_VXLAN)
253 flowkey_cfg |= FLOW_KEY_TYPE_VXLAN;
255 if (ethdev_rss & ETH_RSS_GENEVE)
256 flowkey_cfg |= FLOW_KEY_TYPE_GENEVE;
258 if (ethdev_rss & ETH_RSS_GTPU)
259 flowkey_cfg |= FLOW_KEY_TYPE_GTPU;
265 otx2_rss_set_hf(struct otx2_eth_dev *dev, uint32_t flowkey_cfg,
266 uint8_t *alg_idx, uint8_t group, int mcam_index)
268 struct nix_rss_flowkey_cfg_rsp *rss_rsp;
269 struct otx2_mbox *mbox = dev->mbox;
270 struct nix_rss_flowkey_cfg *cfg;
275 dev->rss_info.flowkey_cfg = flowkey_cfg;
277 cfg = otx2_mbox_alloc_msg_nix_rss_flowkey_cfg(mbox);
279 cfg->flowkey_cfg = flowkey_cfg;
280 cfg->mcam_index = mcam_index; /* -1 indicates default group */
281 cfg->group = group; /* 0 is default group */
283 rc = otx2_mbox_process_msg(mbox, (void *)&rss_rsp);
288 *alg_idx = rss_rsp->alg_idx;
294 otx2_nix_rss_hash_update(struct rte_eth_dev *eth_dev,
295 struct rte_eth_rss_conf *rss_conf)
297 struct otx2_eth_dev *dev = otx2_eth_pmd_priv(eth_dev);
298 uint32_t flowkey_cfg;
304 if (rss_conf->rss_key && rss_conf->rss_key_len != NIX_HASH_KEY_SIZE) {
305 otx2_err("Hash key size mismatch %d vs %d",
306 rss_conf->rss_key_len, NIX_HASH_KEY_SIZE);
310 if (rss_conf->rss_key)
311 otx2_nix_rss_set_key(dev, rss_conf->rss_key,
312 (uint32_t)rss_conf->rss_key_len);
314 flowkey_cfg = otx2_rss_ethdev_to_nix(dev, rss_conf->rss_hf, 0);
316 rc = otx2_rss_set_hf(dev, flowkey_cfg, &alg_idx,
317 NIX_DEFAULT_RSS_CTX_GROUP,
318 NIX_DEFAULT_RSS_MCAM_IDX);
320 otx2_err("Failed to set RSS hash function rc=%d", rc);
324 dev->rss_info.alg_idx = alg_idx;
331 otx2_nix_rss_hash_conf_get(struct rte_eth_dev *eth_dev,
332 struct rte_eth_rss_conf *rss_conf)
334 struct otx2_eth_dev *dev = otx2_eth_pmd_priv(eth_dev);
336 if (rss_conf->rss_key)
337 rss_get_key(dev, rss_conf->rss_key);
339 rss_conf->rss_key_len = NIX_HASH_KEY_SIZE;
340 rss_conf->rss_hf = dev->rss_info.nix_rss;
346 otx2_nix_rss_config(struct rte_eth_dev *eth_dev)
348 struct otx2_eth_dev *dev = otx2_eth_pmd_priv(eth_dev);
349 uint32_t idx, qcnt = eth_dev->data->nb_rx_queues;
350 uint32_t flowkey_cfg;
355 /* Skip further configuration if selected mode is not RSS */
356 if (eth_dev->data->dev_conf.rxmode.mq_mode != ETH_MQ_RX_RSS)
359 /* Update default RSS key and cfg */
360 otx2_nix_rss_set_key(dev, NULL, 0);
362 /* Update default RSS RETA */
363 for (idx = 0; idx < dev->rss_info.rss_size; idx++)
364 dev->rss_info.ind_tbl[idx] = idx % qcnt;
366 /* Init RSS table context */
367 rc = otx2_nix_rss_tbl_init(dev, 0, dev->rss_info.ind_tbl);
369 otx2_err("Failed to init RSS table rc=%d", rc);
373 rss_hf = eth_dev->data->dev_conf.rx_adv_conf.rss_conf.rss_hf;
374 flowkey_cfg = otx2_rss_ethdev_to_nix(dev, rss_hf, 0);
376 rc = otx2_rss_set_hf(dev, flowkey_cfg, &alg_idx,
377 NIX_DEFAULT_RSS_CTX_GROUP,
378 NIX_DEFAULT_RSS_MCAM_IDX);
380 otx2_err("Failed to set RSS hash function rc=%d", rc);
384 dev->rss_info.alg_idx = alg_idx;