1 /* SPDX-License-Identifier: BSD-3-Clause 2 * Copyright(C) 2021 Marvell. 3 */ 4 5 #include <inttypes.h> 6 #include <math.h> 7 8 #include "cnxk_ethdev.h" 9 10 struct sdp_channel { 11 bool is_sdp_mask_set; 12 uint16_t channel; 13 uint16_t mask; 14 }; 15 16 struct flow_pre_l2_size_info { 17 uint8_t pre_l2_size_off; 18 uint8_t pre_l2_size_off_mask; 19 uint8_t pre_l2_size_shift_dir; 20 }; 21 22 static int 23 parse_outb_nb_desc(const char *key, const char *value, void *extra_args) 24 { 25 RTE_SET_USED(key); 26 uint32_t val; 27 28 val = atoi(value); 29 30 *(uint16_t *)extra_args = val; 31 32 return 0; 33 } 34 35 static int 36 parse_outb_nb_crypto_qs(const char *key, const char *value, void *extra_args) 37 { 38 RTE_SET_USED(key); 39 uint32_t val; 40 41 val = atoi(value); 42 43 if (val < 1 || val > 64) 44 return -EINVAL; 45 46 *(uint16_t *)extra_args = val; 47 48 return 0; 49 } 50 51 static int 52 parse_ipsec_in_max_spi(const char *key, const char *value, void *extra_args) 53 { 54 RTE_SET_USED(key); 55 uint32_t val; 56 57 val = atoi(value); 58 59 *(uint16_t *)extra_args = val; 60 61 return 0; 62 } 63 64 static int 65 parse_ipsec_out_max_sa(const char *key, const char *value, void *extra_args) 66 { 67 RTE_SET_USED(key); 68 uint32_t val; 69 70 val = atoi(value); 71 72 *(uint16_t *)extra_args = val; 73 74 return 0; 75 } 76 77 static int 78 parse_flow_max_priority(const char *key, const char *value, void *extra_args) 79 { 80 RTE_SET_USED(key); 81 uint16_t val; 82 83 val = atoi(value); 84 85 /* Limit the max priority to 32 */ 86 if (val < 1 || val > 32) 87 return -EINVAL; 88 89 *(uint16_t *)extra_args = val; 90 91 return 0; 92 } 93 94 static int 95 parse_flow_prealloc_size(const char *key, const char *value, void *extra_args) 96 { 97 RTE_SET_USED(key); 98 uint16_t val; 99 100 val = atoi(value); 101 102 /* Limit the prealloc size to 32 */ 103 if (val < 1 || val > 32) 104 return -EINVAL; 105 106 *(uint16_t *)extra_args = val; 107 108 return 0; 109 } 110 111 static int 112 parse_reta_size(const char *key, const char *value, void *extra_args) 113 { 114 RTE_SET_USED(key); 115 uint32_t val; 116 117 val = atoi(value); 118 119 if (val <= RTE_ETH_RSS_RETA_SIZE_64) 120 val = ROC_NIX_RSS_RETA_SZ_64; 121 else if (val > RTE_ETH_RSS_RETA_SIZE_64 && val <= RTE_ETH_RSS_RETA_SIZE_128) 122 val = ROC_NIX_RSS_RETA_SZ_128; 123 else if (val > RTE_ETH_RSS_RETA_SIZE_128 && val <= RTE_ETH_RSS_RETA_SIZE_256) 124 val = ROC_NIX_RSS_RETA_SZ_256; 125 else 126 val = ROC_NIX_RSS_RETA_SZ_64; 127 128 *(uint16_t *)extra_args = val; 129 130 return 0; 131 } 132 133 static int 134 parse_pre_l2_hdr_info(const char *key, const char *value, void *extra_args) 135 { 136 struct flow_pre_l2_size_info *info = 137 (struct flow_pre_l2_size_info *)extra_args; 138 char *tok1 = NULL, *tok2 = NULL; 139 uint16_t off, off_mask, dir; 140 141 RTE_SET_USED(key); 142 off = strtol(value, &tok1, 16); 143 tok1++; 144 off_mask = strtol(tok1, &tok2, 16); 145 tok2++; 146 dir = strtol(tok2, 0, 16); 147 if (off >= 256 || off_mask < 1 || off_mask >= 256 || dir > 1) 148 return -EINVAL; 149 info->pre_l2_size_off = off; 150 info->pre_l2_size_off_mask = off_mask; 151 info->pre_l2_size_shift_dir = dir; 152 153 return 0; 154 } 155 156 static int 157 parse_flag(const char *key, const char *value, void *extra_args) 158 { 159 RTE_SET_USED(key); 160 161 *(uint16_t *)extra_args = atoi(value); 162 163 return 0; 164 } 165 166 static int 167 parse_sqb_count(const char *key, const char *value, void *extra_args) 168 { 169 RTE_SET_USED(key); 170 uint32_t val; 171 172 val = atoi(value); 173 174 *(uint16_t *)extra_args = val; 175 176 return 0; 177 } 178 179 static int 180 parse_switch_header_type(const char *key, const char *value, void *extra_args) 181 { 182 RTE_SET_USED(key); 183 184 if (strcmp(value, "higig2") == 0) 185 *(uint16_t *)extra_args = ROC_PRIV_FLAGS_HIGIG; 186 187 if (strcmp(value, "dsa") == 0) 188 *(uint16_t *)extra_args = ROC_PRIV_FLAGS_EDSA; 189 190 if (strcmp(value, "chlen90b") == 0) 191 *(uint16_t *)extra_args = ROC_PRIV_FLAGS_LEN_90B; 192 193 if (strcmp(value, "exdsa") == 0) 194 *(uint16_t *)extra_args = ROC_PRIV_FLAGS_EXDSA; 195 196 if (strcmp(value, "vlan_exdsa") == 0) 197 *(uint16_t *)extra_args = ROC_PRIV_FLAGS_VLAN_EXDSA; 198 199 if (strcmp(value, "pre_l2") == 0) 200 *(uint16_t *)extra_args = ROC_PRIV_FLAGS_PRE_L2; 201 202 return 0; 203 } 204 205 static int 206 parse_sdp_channel_mask(const char *key, const char *value, void *extra_args) 207 { 208 RTE_SET_USED(key); 209 uint16_t chan = 0, mask = 0; 210 char *next = 0; 211 212 /* next will point to the separator '/' */ 213 chan = strtol(value, &next, 16); 214 mask = strtol(++next, 0, 16); 215 216 if (chan > GENMASK(11, 0) || mask > GENMASK(11, 0)) 217 return -EINVAL; 218 219 ((struct sdp_channel *)extra_args)->channel = chan; 220 ((struct sdp_channel *)extra_args)->mask = mask; 221 ((struct sdp_channel *)extra_args)->is_sdp_mask_set = true; 222 223 return 0; 224 } 225 226 #define CNXK_RSS_RETA_SIZE "reta_size" 227 #define CNXK_SCL_ENABLE "scalar_enable" 228 #define CNXK_MAX_SQB_COUNT "max_sqb_count" 229 #define CNXK_FLOW_PREALLOC_SIZE "flow_prealloc_size" 230 #define CNXK_FLOW_MAX_PRIORITY "flow_max_priority" 231 #define CNXK_SWITCH_HEADER_TYPE "switch_header" 232 #define CNXK_RSS_TAG_AS_XOR "tag_as_xor" 233 #define CNXK_LOCK_RX_CTX "lock_rx_ctx" 234 #define CNXK_IPSEC_IN_MAX_SPI "ipsec_in_max_spi" 235 #define CNXK_IPSEC_OUT_MAX_SA "ipsec_out_max_sa" 236 #define CNXK_OUTB_NB_DESC "outb_nb_desc" 237 #define CNXK_FORCE_INB_INL_DEV "force_inb_inl_dev" 238 #define CNXK_OUTB_NB_CRYPTO_QS "outb_nb_crypto_qs" 239 #define CNXK_SDP_CHANNEL_MASK "sdp_channel_mask" 240 #define CNXK_FLOW_PRE_L2_INFO "flow_pre_l2_info" 241 242 int 243 cnxk_ethdev_parse_devargs(struct rte_devargs *devargs, struct cnxk_eth_dev *dev) 244 { 245 uint16_t reta_sz = ROC_NIX_RSS_RETA_SZ_64; 246 uint16_t sqb_count = CNXK_NIX_TX_MAX_SQB; 247 struct flow_pre_l2_size_info pre_l2_info; 248 uint16_t ipsec_in_max_spi = BIT(8) - 1; 249 uint16_t ipsec_out_max_sa = BIT(12); 250 uint16_t flow_prealloc_size = 1; 251 uint16_t switch_header_type = 0; 252 uint16_t flow_max_priority = 3; 253 uint16_t force_inb_inl_dev = 0; 254 uint16_t outb_nb_crypto_qs = 1; 255 uint16_t outb_nb_desc = 8200; 256 struct sdp_channel sdp_chan; 257 uint16_t rss_tag_as_xor = 0; 258 uint16_t scalar_enable = 0; 259 uint8_t lock_rx_ctx = 0; 260 struct rte_kvargs *kvlist; 261 262 memset(&sdp_chan, 0, sizeof(sdp_chan)); 263 memset(&pre_l2_info, 0, sizeof(struct flow_pre_l2_size_info)); 264 265 if (devargs == NULL) 266 goto null_devargs; 267 268 kvlist = rte_kvargs_parse(devargs->args, NULL); 269 if (kvlist == NULL) 270 goto exit; 271 272 rte_kvargs_process(kvlist, CNXK_RSS_RETA_SIZE, &parse_reta_size, 273 &reta_sz); 274 rte_kvargs_process(kvlist, CNXK_SCL_ENABLE, &parse_flag, 275 &scalar_enable); 276 rte_kvargs_process(kvlist, CNXK_MAX_SQB_COUNT, &parse_sqb_count, 277 &sqb_count); 278 rte_kvargs_process(kvlist, CNXK_FLOW_PREALLOC_SIZE, 279 &parse_flow_prealloc_size, &flow_prealloc_size); 280 rte_kvargs_process(kvlist, CNXK_FLOW_MAX_PRIORITY, 281 &parse_flow_max_priority, &flow_max_priority); 282 rte_kvargs_process(kvlist, CNXK_SWITCH_HEADER_TYPE, 283 &parse_switch_header_type, &switch_header_type); 284 rte_kvargs_process(kvlist, CNXK_RSS_TAG_AS_XOR, &parse_flag, 285 &rss_tag_as_xor); 286 rte_kvargs_process(kvlist, CNXK_LOCK_RX_CTX, &parse_flag, &lock_rx_ctx); 287 rte_kvargs_process(kvlist, CNXK_IPSEC_IN_MAX_SPI, 288 &parse_ipsec_in_max_spi, &ipsec_in_max_spi); 289 rte_kvargs_process(kvlist, CNXK_IPSEC_OUT_MAX_SA, 290 &parse_ipsec_out_max_sa, &ipsec_out_max_sa); 291 rte_kvargs_process(kvlist, CNXK_OUTB_NB_DESC, &parse_outb_nb_desc, 292 &outb_nb_desc); 293 rte_kvargs_process(kvlist, CNXK_OUTB_NB_CRYPTO_QS, 294 &parse_outb_nb_crypto_qs, &outb_nb_crypto_qs); 295 rte_kvargs_process(kvlist, CNXK_FORCE_INB_INL_DEV, &parse_flag, 296 &force_inb_inl_dev); 297 rte_kvargs_process(kvlist, CNXK_SDP_CHANNEL_MASK, 298 &parse_sdp_channel_mask, &sdp_chan); 299 rte_kvargs_process(kvlist, CNXK_FLOW_PRE_L2_INFO, 300 &parse_pre_l2_hdr_info, &pre_l2_info); 301 rte_kvargs_free(kvlist); 302 303 null_devargs: 304 dev->scalar_ena = !!scalar_enable; 305 dev->inb.force_inl_dev = !!force_inb_inl_dev; 306 dev->inb.max_spi = ipsec_in_max_spi; 307 dev->outb.max_sa = ipsec_out_max_sa; 308 dev->outb.nb_desc = outb_nb_desc; 309 dev->outb.nb_crypto_qs = outb_nb_crypto_qs; 310 dev->nix.ipsec_in_max_spi = ipsec_in_max_spi; 311 dev->nix.ipsec_out_max_sa = ipsec_out_max_sa; 312 dev->nix.rss_tag_as_xor = !!rss_tag_as_xor; 313 dev->nix.max_sqb_count = sqb_count; 314 dev->nix.reta_sz = reta_sz; 315 dev->nix.lock_rx_ctx = lock_rx_ctx; 316 dev->npc.flow_prealloc_size = flow_prealloc_size; 317 dev->npc.flow_max_priority = flow_max_priority; 318 dev->npc.switch_header_type = switch_header_type; 319 dev->npc.sdp_channel = sdp_chan.channel; 320 dev->npc.sdp_channel_mask = sdp_chan.mask; 321 dev->npc.is_sdp_mask_set = sdp_chan.is_sdp_mask_set; 322 dev->npc.pre_l2_size_offset = pre_l2_info.pre_l2_size_off; 323 dev->npc.pre_l2_size_offset_mask = pre_l2_info.pre_l2_size_off_mask; 324 dev->npc.pre_l2_size_shift_dir = pre_l2_info.pre_l2_size_shift_dir; 325 return 0; 326 exit: 327 return -EINVAL; 328 } 329 330 RTE_PMD_REGISTER_PARAM_STRING(net_cnxk, 331 CNXK_RSS_RETA_SIZE "=<64|128|256>" 332 CNXK_SCL_ENABLE "=1" 333 CNXK_MAX_SQB_COUNT "=<8-512>" 334 CNXK_FLOW_PREALLOC_SIZE "=<1-32>" 335 CNXK_FLOW_MAX_PRIORITY "=<1-32>" 336 CNXK_SWITCH_HEADER_TYPE "=<higig2|dsa|chlen90b>" 337 CNXK_RSS_TAG_AS_XOR "=1" 338 CNXK_IPSEC_IN_MAX_SPI "=<1-65535>" 339 CNXK_OUTB_NB_DESC "=<1-65535>" 340 CNXK_FLOW_PRE_L2_INFO "=<0-255>/<1-255>/<0-1>" 341 CNXK_OUTB_NB_CRYPTO_QS "=<1-64>" 342 CNXK_FORCE_INB_INL_DEV "=1" 343 CNXK_SDP_CHANNEL_MASK "=<1-4095>/<1-4095>"); 344