1*2846fe56SPrzemek Kitszel // SPDX-License-Identifier: GPL-2.0 2*2846fe56SPrzemek Kitszel /* Copyright (c) 2024, Intel Corporation. */ 3*2846fe56SPrzemek Kitszel 4*2846fe56SPrzemek Kitszel #include <linux/vmalloc.h> 5*2846fe56SPrzemek Kitszel 6*2846fe56SPrzemek Kitszel #include "ice.h" 7*2846fe56SPrzemek Kitszel #include "devlink.h" 8*2846fe56SPrzemek Kitszel #include "port.h" 9*2846fe56SPrzemek Kitszel #include "ice_lib.h" 10*2846fe56SPrzemek Kitszel #include "ice_fltr.h" 11*2846fe56SPrzemek Kitszel 12*2846fe56SPrzemek Kitszel static int ice_active_port_option = -1; 13*2846fe56SPrzemek Kitszel 14*2846fe56SPrzemek Kitszel /** 15*2846fe56SPrzemek Kitszel * ice_devlink_port_opt_speed_str - convert speed to a string 16*2846fe56SPrzemek Kitszel * @speed: speed value 17*2846fe56SPrzemek Kitszel */ 18*2846fe56SPrzemek Kitszel static const char *ice_devlink_port_opt_speed_str(u8 speed) 19*2846fe56SPrzemek Kitszel { 20*2846fe56SPrzemek Kitszel switch (speed & ICE_AQC_PORT_OPT_MAX_LANE_M) { 21*2846fe56SPrzemek Kitszel case ICE_AQC_PORT_OPT_MAX_LANE_100M: 22*2846fe56SPrzemek Kitszel return "0.1"; 23*2846fe56SPrzemek Kitszel case ICE_AQC_PORT_OPT_MAX_LANE_1G: 24*2846fe56SPrzemek Kitszel return "1"; 25*2846fe56SPrzemek Kitszel case ICE_AQC_PORT_OPT_MAX_LANE_2500M: 26*2846fe56SPrzemek Kitszel return "2.5"; 27*2846fe56SPrzemek Kitszel case ICE_AQC_PORT_OPT_MAX_LANE_5G: 28*2846fe56SPrzemek Kitszel return "5"; 29*2846fe56SPrzemek Kitszel case ICE_AQC_PORT_OPT_MAX_LANE_10G: 30*2846fe56SPrzemek Kitszel return "10"; 31*2846fe56SPrzemek Kitszel case ICE_AQC_PORT_OPT_MAX_LANE_25G: 32*2846fe56SPrzemek Kitszel return "25"; 33*2846fe56SPrzemek Kitszel case ICE_AQC_PORT_OPT_MAX_LANE_50G: 34*2846fe56SPrzemek Kitszel return "50"; 35*2846fe56SPrzemek Kitszel case ICE_AQC_PORT_OPT_MAX_LANE_100G: 36*2846fe56SPrzemek Kitszel return "100"; 37*2846fe56SPrzemek Kitszel } 38*2846fe56SPrzemek Kitszel 39*2846fe56SPrzemek Kitszel return "-"; 40*2846fe56SPrzemek Kitszel } 41*2846fe56SPrzemek Kitszel 42*2846fe56SPrzemek Kitszel #define ICE_PORT_OPT_DESC_LEN 50 43*2846fe56SPrzemek Kitszel /** 44*2846fe56SPrzemek Kitszel * ice_devlink_port_options_print - Print available port split options 45*2846fe56SPrzemek Kitszel * @pf: the PF to print split port options 46*2846fe56SPrzemek Kitszel * 47*2846fe56SPrzemek Kitszel * Prints a table with available port split options and max port speeds 48*2846fe56SPrzemek Kitszel */ 49*2846fe56SPrzemek Kitszel static void ice_devlink_port_options_print(struct ice_pf *pf) 50*2846fe56SPrzemek Kitszel { 51*2846fe56SPrzemek Kitszel u8 i, j, options_count, cnt, speed, pending_idx, active_idx; 52*2846fe56SPrzemek Kitszel struct ice_aqc_get_port_options_elem *options, *opt; 53*2846fe56SPrzemek Kitszel struct device *dev = ice_pf_to_dev(pf); 54*2846fe56SPrzemek Kitszel bool active_valid, pending_valid; 55*2846fe56SPrzemek Kitszel char desc[ICE_PORT_OPT_DESC_LEN]; 56*2846fe56SPrzemek Kitszel const char *str; 57*2846fe56SPrzemek Kitszel int status; 58*2846fe56SPrzemek Kitszel 59*2846fe56SPrzemek Kitszel options = kcalloc(ICE_AQC_PORT_OPT_MAX * ICE_MAX_PORT_PER_PCI_DEV, 60*2846fe56SPrzemek Kitszel sizeof(*options), GFP_KERNEL); 61*2846fe56SPrzemek Kitszel if (!options) 62*2846fe56SPrzemek Kitszel return; 63*2846fe56SPrzemek Kitszel 64*2846fe56SPrzemek Kitszel for (i = 0; i < ICE_MAX_PORT_PER_PCI_DEV; i++) { 65*2846fe56SPrzemek Kitszel opt = options + i * ICE_AQC_PORT_OPT_MAX; 66*2846fe56SPrzemek Kitszel options_count = ICE_AQC_PORT_OPT_MAX; 67*2846fe56SPrzemek Kitszel active_valid = 0; 68*2846fe56SPrzemek Kitszel 69*2846fe56SPrzemek Kitszel status = ice_aq_get_port_options(&pf->hw, opt, &options_count, 70*2846fe56SPrzemek Kitszel i, true, &active_idx, 71*2846fe56SPrzemek Kitszel &active_valid, &pending_idx, 72*2846fe56SPrzemek Kitszel &pending_valid); 73*2846fe56SPrzemek Kitszel if (status) { 74*2846fe56SPrzemek Kitszel dev_dbg(dev, "Couldn't read port option for port %d, err %d\n", 75*2846fe56SPrzemek Kitszel i, status); 76*2846fe56SPrzemek Kitszel goto err; 77*2846fe56SPrzemek Kitszel } 78*2846fe56SPrzemek Kitszel } 79*2846fe56SPrzemek Kitszel 80*2846fe56SPrzemek Kitszel dev_dbg(dev, "Available port split options and max port speeds (Gbps):\n"); 81*2846fe56SPrzemek Kitszel dev_dbg(dev, "Status Split Quad 0 Quad 1\n"); 82*2846fe56SPrzemek Kitszel dev_dbg(dev, " count L0 L1 L2 L3 L4 L5 L6 L7\n"); 83*2846fe56SPrzemek Kitszel 84*2846fe56SPrzemek Kitszel for (i = 0; i < options_count; i++) { 85*2846fe56SPrzemek Kitszel cnt = 0; 86*2846fe56SPrzemek Kitszel 87*2846fe56SPrzemek Kitszel if (i == ice_active_port_option) 88*2846fe56SPrzemek Kitszel str = "Active"; 89*2846fe56SPrzemek Kitszel else if ((i == pending_idx) && pending_valid) 90*2846fe56SPrzemek Kitszel str = "Pending"; 91*2846fe56SPrzemek Kitszel else 92*2846fe56SPrzemek Kitszel str = ""; 93*2846fe56SPrzemek Kitszel 94*2846fe56SPrzemek Kitszel cnt += snprintf(&desc[cnt], ICE_PORT_OPT_DESC_LEN - cnt, 95*2846fe56SPrzemek Kitszel "%-8s", str); 96*2846fe56SPrzemek Kitszel 97*2846fe56SPrzemek Kitszel cnt += snprintf(&desc[cnt], ICE_PORT_OPT_DESC_LEN - cnt, 98*2846fe56SPrzemek Kitszel "%-6u", options[i].pmd); 99*2846fe56SPrzemek Kitszel 100*2846fe56SPrzemek Kitszel for (j = 0; j < ICE_MAX_PORT_PER_PCI_DEV; ++j) { 101*2846fe56SPrzemek Kitszel speed = options[i + j * ICE_AQC_PORT_OPT_MAX].max_lane_speed; 102*2846fe56SPrzemek Kitszel str = ice_devlink_port_opt_speed_str(speed); 103*2846fe56SPrzemek Kitszel cnt += snprintf(&desc[cnt], ICE_PORT_OPT_DESC_LEN - cnt, 104*2846fe56SPrzemek Kitszel "%3s ", str); 105*2846fe56SPrzemek Kitszel } 106*2846fe56SPrzemek Kitszel 107*2846fe56SPrzemek Kitszel dev_dbg(dev, "%s\n", desc); 108*2846fe56SPrzemek Kitszel } 109*2846fe56SPrzemek Kitszel 110*2846fe56SPrzemek Kitszel err: 111*2846fe56SPrzemek Kitszel kfree(options); 112*2846fe56SPrzemek Kitszel } 113*2846fe56SPrzemek Kitszel 114*2846fe56SPrzemek Kitszel /** 115*2846fe56SPrzemek Kitszel * ice_devlink_aq_set_port_option - Send set port option admin queue command 116*2846fe56SPrzemek Kitszel * @pf: the PF to print split port options 117*2846fe56SPrzemek Kitszel * @option_idx: selected port option 118*2846fe56SPrzemek Kitszel * @extack: extended netdev ack structure 119*2846fe56SPrzemek Kitszel * 120*2846fe56SPrzemek Kitszel * Sends set port option admin queue command with selected port option and 121*2846fe56SPrzemek Kitszel * calls NVM write activate. 122*2846fe56SPrzemek Kitszel */ 123*2846fe56SPrzemek Kitszel static int 124*2846fe56SPrzemek Kitszel ice_devlink_aq_set_port_option(struct ice_pf *pf, u8 option_idx, 125*2846fe56SPrzemek Kitszel struct netlink_ext_ack *extack) 126*2846fe56SPrzemek Kitszel { 127*2846fe56SPrzemek Kitszel struct device *dev = ice_pf_to_dev(pf); 128*2846fe56SPrzemek Kitszel int status; 129*2846fe56SPrzemek Kitszel 130*2846fe56SPrzemek Kitszel status = ice_aq_set_port_option(&pf->hw, 0, true, option_idx); 131*2846fe56SPrzemek Kitszel if (status) { 132*2846fe56SPrzemek Kitszel dev_dbg(dev, "ice_aq_set_port_option, err %d aq_err %d\n", 133*2846fe56SPrzemek Kitszel status, pf->hw.adminq.sq_last_status); 134*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Port split request failed"); 135*2846fe56SPrzemek Kitszel return -EIO; 136*2846fe56SPrzemek Kitszel } 137*2846fe56SPrzemek Kitszel 138*2846fe56SPrzemek Kitszel status = ice_acquire_nvm(&pf->hw, ICE_RES_WRITE); 139*2846fe56SPrzemek Kitszel if (status) { 140*2846fe56SPrzemek Kitszel dev_dbg(dev, "ice_acquire_nvm failed, err %d aq_err %d\n", 141*2846fe56SPrzemek Kitszel status, pf->hw.adminq.sq_last_status); 142*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Failed to acquire NVM semaphore"); 143*2846fe56SPrzemek Kitszel return -EIO; 144*2846fe56SPrzemek Kitszel } 145*2846fe56SPrzemek Kitszel 146*2846fe56SPrzemek Kitszel status = ice_nvm_write_activate(&pf->hw, ICE_AQC_NVM_ACTIV_REQ_EMPR, NULL); 147*2846fe56SPrzemek Kitszel if (status) { 148*2846fe56SPrzemek Kitszel dev_dbg(dev, "ice_nvm_write_activate failed, err %d aq_err %d\n", 149*2846fe56SPrzemek Kitszel status, pf->hw.adminq.sq_last_status); 150*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Port split request failed to save data"); 151*2846fe56SPrzemek Kitszel ice_release_nvm(&pf->hw); 152*2846fe56SPrzemek Kitszel return -EIO; 153*2846fe56SPrzemek Kitszel } 154*2846fe56SPrzemek Kitszel 155*2846fe56SPrzemek Kitszel ice_release_nvm(&pf->hw); 156*2846fe56SPrzemek Kitszel 157*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Reboot required to finish port split"); 158*2846fe56SPrzemek Kitszel return 0; 159*2846fe56SPrzemek Kitszel } 160*2846fe56SPrzemek Kitszel 161*2846fe56SPrzemek Kitszel /** 162*2846fe56SPrzemek Kitszel * ice_devlink_port_split - .port_split devlink handler 163*2846fe56SPrzemek Kitszel * @devlink: devlink instance structure 164*2846fe56SPrzemek Kitszel * @port: devlink port structure 165*2846fe56SPrzemek Kitszel * @count: number of ports to split to 166*2846fe56SPrzemek Kitszel * @extack: extended netdev ack structure 167*2846fe56SPrzemek Kitszel * 168*2846fe56SPrzemek Kitszel * Callback for the devlink .port_split operation. 169*2846fe56SPrzemek Kitszel * 170*2846fe56SPrzemek Kitszel * Unfortunately, the devlink expression of available options is limited 171*2846fe56SPrzemek Kitszel * to just a number, so search for an FW port option which supports 172*2846fe56SPrzemek Kitszel * the specified number. As there could be multiple FW port options with 173*2846fe56SPrzemek Kitszel * the same port split count, allow switching between them. When the same 174*2846fe56SPrzemek Kitszel * port split count request is issued again, switch to the next FW port 175*2846fe56SPrzemek Kitszel * option with the same port split count. 176*2846fe56SPrzemek Kitszel * 177*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 178*2846fe56SPrzemek Kitszel */ 179*2846fe56SPrzemek Kitszel static int 180*2846fe56SPrzemek Kitszel ice_devlink_port_split(struct devlink *devlink, struct devlink_port *port, 181*2846fe56SPrzemek Kitszel unsigned int count, struct netlink_ext_ack *extack) 182*2846fe56SPrzemek Kitszel { 183*2846fe56SPrzemek Kitszel struct ice_aqc_get_port_options_elem options[ICE_AQC_PORT_OPT_MAX]; 184*2846fe56SPrzemek Kitszel u8 i, j, active_idx, pending_idx, new_option; 185*2846fe56SPrzemek Kitszel struct ice_pf *pf = devlink_priv(devlink); 186*2846fe56SPrzemek Kitszel u8 option_count = ICE_AQC_PORT_OPT_MAX; 187*2846fe56SPrzemek Kitszel struct device *dev = ice_pf_to_dev(pf); 188*2846fe56SPrzemek Kitszel bool active_valid, pending_valid; 189*2846fe56SPrzemek Kitszel int status; 190*2846fe56SPrzemek Kitszel 191*2846fe56SPrzemek Kitszel status = ice_aq_get_port_options(&pf->hw, options, &option_count, 192*2846fe56SPrzemek Kitszel 0, true, &active_idx, &active_valid, 193*2846fe56SPrzemek Kitszel &pending_idx, &pending_valid); 194*2846fe56SPrzemek Kitszel if (status) { 195*2846fe56SPrzemek Kitszel dev_dbg(dev, "Couldn't read port split options, err = %d\n", 196*2846fe56SPrzemek Kitszel status); 197*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Failed to get available port split options"); 198*2846fe56SPrzemek Kitszel return -EIO; 199*2846fe56SPrzemek Kitszel } 200*2846fe56SPrzemek Kitszel 201*2846fe56SPrzemek Kitszel new_option = ICE_AQC_PORT_OPT_MAX; 202*2846fe56SPrzemek Kitszel active_idx = pending_valid ? pending_idx : active_idx; 203*2846fe56SPrzemek Kitszel for (i = 1; i <= option_count; i++) { 204*2846fe56SPrzemek Kitszel /* In order to allow switching between FW port options with 205*2846fe56SPrzemek Kitszel * the same port split count, search for a new option starting 206*2846fe56SPrzemek Kitszel * from the active/pending option (with array wrap around). 207*2846fe56SPrzemek Kitszel */ 208*2846fe56SPrzemek Kitszel j = (active_idx + i) % option_count; 209*2846fe56SPrzemek Kitszel 210*2846fe56SPrzemek Kitszel if (count == options[j].pmd) { 211*2846fe56SPrzemek Kitszel new_option = j; 212*2846fe56SPrzemek Kitszel break; 213*2846fe56SPrzemek Kitszel } 214*2846fe56SPrzemek Kitszel } 215*2846fe56SPrzemek Kitszel 216*2846fe56SPrzemek Kitszel if (new_option == active_idx) { 217*2846fe56SPrzemek Kitszel dev_dbg(dev, "request to split: count: %u is already set and there are no other options\n", 218*2846fe56SPrzemek Kitszel count); 219*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Requested split count is already set"); 220*2846fe56SPrzemek Kitszel ice_devlink_port_options_print(pf); 221*2846fe56SPrzemek Kitszel return -EINVAL; 222*2846fe56SPrzemek Kitszel } 223*2846fe56SPrzemek Kitszel 224*2846fe56SPrzemek Kitszel if (new_option == ICE_AQC_PORT_OPT_MAX) { 225*2846fe56SPrzemek Kitszel dev_dbg(dev, "request to split: count: %u not found\n", count); 226*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Port split requested unsupported port config"); 227*2846fe56SPrzemek Kitszel ice_devlink_port_options_print(pf); 228*2846fe56SPrzemek Kitszel return -EINVAL; 229*2846fe56SPrzemek Kitszel } 230*2846fe56SPrzemek Kitszel 231*2846fe56SPrzemek Kitszel status = ice_devlink_aq_set_port_option(pf, new_option, extack); 232*2846fe56SPrzemek Kitszel if (status) 233*2846fe56SPrzemek Kitszel return status; 234*2846fe56SPrzemek Kitszel 235*2846fe56SPrzemek Kitszel ice_devlink_port_options_print(pf); 236*2846fe56SPrzemek Kitszel 237*2846fe56SPrzemek Kitszel return 0; 238*2846fe56SPrzemek Kitszel } 239*2846fe56SPrzemek Kitszel 240*2846fe56SPrzemek Kitszel /** 241*2846fe56SPrzemek Kitszel * ice_devlink_port_unsplit - .port_unsplit devlink handler 242*2846fe56SPrzemek Kitszel * @devlink: devlink instance structure 243*2846fe56SPrzemek Kitszel * @port: devlink port structure 244*2846fe56SPrzemek Kitszel * @extack: extended netdev ack structure 245*2846fe56SPrzemek Kitszel * 246*2846fe56SPrzemek Kitszel * Callback for the devlink .port_unsplit operation. 247*2846fe56SPrzemek Kitszel * Calls ice_devlink_port_split with split count set to 1. 248*2846fe56SPrzemek Kitszel * There could be no FW option available with split count 1. 249*2846fe56SPrzemek Kitszel * 250*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 251*2846fe56SPrzemek Kitszel */ 252*2846fe56SPrzemek Kitszel static int 253*2846fe56SPrzemek Kitszel ice_devlink_port_unsplit(struct devlink *devlink, struct devlink_port *port, 254*2846fe56SPrzemek Kitszel struct netlink_ext_ack *extack) 255*2846fe56SPrzemek Kitszel { 256*2846fe56SPrzemek Kitszel return ice_devlink_port_split(devlink, port, 1, extack); 257*2846fe56SPrzemek Kitszel } 258*2846fe56SPrzemek Kitszel 259*2846fe56SPrzemek Kitszel /** 260*2846fe56SPrzemek Kitszel * ice_devlink_set_port_split_options - Set port split options 261*2846fe56SPrzemek Kitszel * @pf: the PF to set port split options 262*2846fe56SPrzemek Kitszel * @attrs: devlink attributes 263*2846fe56SPrzemek Kitszel * 264*2846fe56SPrzemek Kitszel * Sets devlink port split options based on available FW port options 265*2846fe56SPrzemek Kitszel */ 266*2846fe56SPrzemek Kitszel static void 267*2846fe56SPrzemek Kitszel ice_devlink_set_port_split_options(struct ice_pf *pf, 268*2846fe56SPrzemek Kitszel struct devlink_port_attrs *attrs) 269*2846fe56SPrzemek Kitszel { 270*2846fe56SPrzemek Kitszel struct ice_aqc_get_port_options_elem options[ICE_AQC_PORT_OPT_MAX]; 271*2846fe56SPrzemek Kitszel u8 i, active_idx, pending_idx, option_count = ICE_AQC_PORT_OPT_MAX; 272*2846fe56SPrzemek Kitszel bool active_valid, pending_valid; 273*2846fe56SPrzemek Kitszel int status; 274*2846fe56SPrzemek Kitszel 275*2846fe56SPrzemek Kitszel status = ice_aq_get_port_options(&pf->hw, options, &option_count, 276*2846fe56SPrzemek Kitszel 0, true, &active_idx, &active_valid, 277*2846fe56SPrzemek Kitszel &pending_idx, &pending_valid); 278*2846fe56SPrzemek Kitszel if (status) { 279*2846fe56SPrzemek Kitszel dev_dbg(ice_pf_to_dev(pf), "Couldn't read port split options, err = %d\n", 280*2846fe56SPrzemek Kitszel status); 281*2846fe56SPrzemek Kitszel return; 282*2846fe56SPrzemek Kitszel } 283*2846fe56SPrzemek Kitszel 284*2846fe56SPrzemek Kitszel /* find the biggest available port split count */ 285*2846fe56SPrzemek Kitszel for (i = 0; i < option_count; i++) 286*2846fe56SPrzemek Kitszel attrs->lanes = max_t(int, attrs->lanes, options[i].pmd); 287*2846fe56SPrzemek Kitszel 288*2846fe56SPrzemek Kitszel attrs->splittable = attrs->lanes ? 1 : 0; 289*2846fe56SPrzemek Kitszel ice_active_port_option = active_idx; 290*2846fe56SPrzemek Kitszel } 291*2846fe56SPrzemek Kitszel 292*2846fe56SPrzemek Kitszel static const struct devlink_port_ops ice_devlink_port_ops = { 293*2846fe56SPrzemek Kitszel .port_split = ice_devlink_port_split, 294*2846fe56SPrzemek Kitszel .port_unsplit = ice_devlink_port_unsplit, 295*2846fe56SPrzemek Kitszel }; 296*2846fe56SPrzemek Kitszel 297*2846fe56SPrzemek Kitszel /** 298*2846fe56SPrzemek Kitszel * ice_devlink_set_switch_id - Set unique switch id based on pci dsn 299*2846fe56SPrzemek Kitszel * @pf: the PF to create a devlink port for 300*2846fe56SPrzemek Kitszel * @ppid: struct with switch id information 301*2846fe56SPrzemek Kitszel */ 302*2846fe56SPrzemek Kitszel static void 303*2846fe56SPrzemek Kitszel ice_devlink_set_switch_id(struct ice_pf *pf, struct netdev_phys_item_id *ppid) 304*2846fe56SPrzemek Kitszel { 305*2846fe56SPrzemek Kitszel struct pci_dev *pdev = pf->pdev; 306*2846fe56SPrzemek Kitszel u64 id; 307*2846fe56SPrzemek Kitszel 308*2846fe56SPrzemek Kitszel id = pci_get_dsn(pdev); 309*2846fe56SPrzemek Kitszel 310*2846fe56SPrzemek Kitszel ppid->id_len = sizeof(id); 311*2846fe56SPrzemek Kitszel put_unaligned_be64(id, &ppid->id); 312*2846fe56SPrzemek Kitszel } 313*2846fe56SPrzemek Kitszel 314*2846fe56SPrzemek Kitszel /** 315*2846fe56SPrzemek Kitszel * ice_devlink_create_pf_port - Create a devlink port for this PF 316*2846fe56SPrzemek Kitszel * @pf: the PF to create a devlink port for 317*2846fe56SPrzemek Kitszel * 318*2846fe56SPrzemek Kitszel * Create and register a devlink_port for this PF. 319*2846fe56SPrzemek Kitszel * This function has to be called under devl_lock. 320*2846fe56SPrzemek Kitszel * 321*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 322*2846fe56SPrzemek Kitszel */ 323*2846fe56SPrzemek Kitszel int ice_devlink_create_pf_port(struct ice_pf *pf) 324*2846fe56SPrzemek Kitszel { 325*2846fe56SPrzemek Kitszel struct devlink_port_attrs attrs = {}; 326*2846fe56SPrzemek Kitszel struct devlink_port *devlink_port; 327*2846fe56SPrzemek Kitszel struct devlink *devlink; 328*2846fe56SPrzemek Kitszel struct ice_vsi *vsi; 329*2846fe56SPrzemek Kitszel struct device *dev; 330*2846fe56SPrzemek Kitszel int err; 331*2846fe56SPrzemek Kitszel 332*2846fe56SPrzemek Kitszel devlink = priv_to_devlink(pf); 333*2846fe56SPrzemek Kitszel 334*2846fe56SPrzemek Kitszel dev = ice_pf_to_dev(pf); 335*2846fe56SPrzemek Kitszel 336*2846fe56SPrzemek Kitszel devlink_port = &pf->devlink_port; 337*2846fe56SPrzemek Kitszel 338*2846fe56SPrzemek Kitszel vsi = ice_get_main_vsi(pf); 339*2846fe56SPrzemek Kitszel if (!vsi) 340*2846fe56SPrzemek Kitszel return -EIO; 341*2846fe56SPrzemek Kitszel 342*2846fe56SPrzemek Kitszel attrs.flavour = DEVLINK_PORT_FLAVOUR_PHYSICAL; 343*2846fe56SPrzemek Kitszel attrs.phys.port_number = pf->hw.pf_id; 344*2846fe56SPrzemek Kitszel 345*2846fe56SPrzemek Kitszel /* As FW supports only port split options for whole device, 346*2846fe56SPrzemek Kitszel * set port split options only for first PF. 347*2846fe56SPrzemek Kitszel */ 348*2846fe56SPrzemek Kitszel if (pf->hw.pf_id == 0) 349*2846fe56SPrzemek Kitszel ice_devlink_set_port_split_options(pf, &attrs); 350*2846fe56SPrzemek Kitszel 351*2846fe56SPrzemek Kitszel ice_devlink_set_switch_id(pf, &attrs.switch_id); 352*2846fe56SPrzemek Kitszel 353*2846fe56SPrzemek Kitszel devlink_port_attrs_set(devlink_port, &attrs); 354*2846fe56SPrzemek Kitszel 355*2846fe56SPrzemek Kitszel err = devl_port_register_with_ops(devlink, devlink_port, vsi->idx, 356*2846fe56SPrzemek Kitszel &ice_devlink_port_ops); 357*2846fe56SPrzemek Kitszel if (err) { 358*2846fe56SPrzemek Kitszel dev_err(dev, "Failed to create devlink port for PF %d, error %d\n", 359*2846fe56SPrzemek Kitszel pf->hw.pf_id, err); 360*2846fe56SPrzemek Kitszel return err; 361*2846fe56SPrzemek Kitszel } 362*2846fe56SPrzemek Kitszel 363*2846fe56SPrzemek Kitszel return 0; 364*2846fe56SPrzemek Kitszel } 365*2846fe56SPrzemek Kitszel 366*2846fe56SPrzemek Kitszel /** 367*2846fe56SPrzemek Kitszel * ice_devlink_destroy_pf_port - Destroy the devlink_port for this PF 368*2846fe56SPrzemek Kitszel * @pf: the PF to cleanup 369*2846fe56SPrzemek Kitszel * 370*2846fe56SPrzemek Kitszel * Unregisters the devlink_port structure associated with this PF. 371*2846fe56SPrzemek Kitszel * This function has to be called under devl_lock. 372*2846fe56SPrzemek Kitszel */ 373*2846fe56SPrzemek Kitszel void ice_devlink_destroy_pf_port(struct ice_pf *pf) 374*2846fe56SPrzemek Kitszel { 375*2846fe56SPrzemek Kitszel devl_port_unregister(&pf->devlink_port); 376*2846fe56SPrzemek Kitszel } 377*2846fe56SPrzemek Kitszel 378*2846fe56SPrzemek Kitszel /** 379*2846fe56SPrzemek Kitszel * ice_devlink_port_get_vf_fn_mac - .port_fn_hw_addr_get devlink handler 380*2846fe56SPrzemek Kitszel * @port: devlink port structure 381*2846fe56SPrzemek Kitszel * @hw_addr: MAC address of the port 382*2846fe56SPrzemek Kitszel * @hw_addr_len: length of MAC address 383*2846fe56SPrzemek Kitszel * @extack: extended netdev ack structure 384*2846fe56SPrzemek Kitszel * 385*2846fe56SPrzemek Kitszel * Callback for the devlink .port_fn_hw_addr_get operation 386*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 387*2846fe56SPrzemek Kitszel */ 388*2846fe56SPrzemek Kitszel static int ice_devlink_port_get_vf_fn_mac(struct devlink_port *port, 389*2846fe56SPrzemek Kitszel u8 *hw_addr, int *hw_addr_len, 390*2846fe56SPrzemek Kitszel struct netlink_ext_ack *extack) 391*2846fe56SPrzemek Kitszel { 392*2846fe56SPrzemek Kitszel struct ice_vf *vf = container_of(port, struct ice_vf, devlink_port); 393*2846fe56SPrzemek Kitszel 394*2846fe56SPrzemek Kitszel ether_addr_copy(hw_addr, vf->dev_lan_addr); 395*2846fe56SPrzemek Kitszel *hw_addr_len = ETH_ALEN; 396*2846fe56SPrzemek Kitszel 397*2846fe56SPrzemek Kitszel return 0; 398*2846fe56SPrzemek Kitszel } 399*2846fe56SPrzemek Kitszel 400*2846fe56SPrzemek Kitszel /** 401*2846fe56SPrzemek Kitszel * ice_devlink_port_set_vf_fn_mac - .port_fn_hw_addr_set devlink handler 402*2846fe56SPrzemek Kitszel * @port: devlink port structure 403*2846fe56SPrzemek Kitszel * @hw_addr: MAC address of the port 404*2846fe56SPrzemek Kitszel * @hw_addr_len: length of MAC address 405*2846fe56SPrzemek Kitszel * @extack: extended netdev ack structure 406*2846fe56SPrzemek Kitszel * 407*2846fe56SPrzemek Kitszel * Callback for the devlink .port_fn_hw_addr_set operation 408*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 409*2846fe56SPrzemek Kitszel */ 410*2846fe56SPrzemek Kitszel static int ice_devlink_port_set_vf_fn_mac(struct devlink_port *port, 411*2846fe56SPrzemek Kitszel const u8 *hw_addr, 412*2846fe56SPrzemek Kitszel int hw_addr_len, 413*2846fe56SPrzemek Kitszel struct netlink_ext_ack *extack) 414*2846fe56SPrzemek Kitszel 415*2846fe56SPrzemek Kitszel { 416*2846fe56SPrzemek Kitszel struct devlink_port_attrs *attrs = &port->attrs; 417*2846fe56SPrzemek Kitszel struct devlink_port_pci_vf_attrs *pci_vf; 418*2846fe56SPrzemek Kitszel struct devlink *devlink = port->devlink; 419*2846fe56SPrzemek Kitszel struct ice_pf *pf; 420*2846fe56SPrzemek Kitszel u16 vf_id; 421*2846fe56SPrzemek Kitszel 422*2846fe56SPrzemek Kitszel pf = devlink_priv(devlink); 423*2846fe56SPrzemek Kitszel pci_vf = &attrs->pci_vf; 424*2846fe56SPrzemek Kitszel vf_id = pci_vf->vf; 425*2846fe56SPrzemek Kitszel 426*2846fe56SPrzemek Kitszel return __ice_set_vf_mac(pf, vf_id, hw_addr); 427*2846fe56SPrzemek Kitszel } 428*2846fe56SPrzemek Kitszel 429*2846fe56SPrzemek Kitszel static const struct devlink_port_ops ice_devlink_vf_port_ops = { 430*2846fe56SPrzemek Kitszel .port_fn_hw_addr_get = ice_devlink_port_get_vf_fn_mac, 431*2846fe56SPrzemek Kitszel .port_fn_hw_addr_set = ice_devlink_port_set_vf_fn_mac, 432*2846fe56SPrzemek Kitszel }; 433*2846fe56SPrzemek Kitszel 434*2846fe56SPrzemek Kitszel /** 435*2846fe56SPrzemek Kitszel * ice_devlink_create_vf_port - Create a devlink port for this VF 436*2846fe56SPrzemek Kitszel * @vf: the VF to create a port for 437*2846fe56SPrzemek Kitszel * 438*2846fe56SPrzemek Kitszel * Create and register a devlink_port for this VF. 439*2846fe56SPrzemek Kitszel * 440*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 441*2846fe56SPrzemek Kitszel */ 442*2846fe56SPrzemek Kitszel int ice_devlink_create_vf_port(struct ice_vf *vf) 443*2846fe56SPrzemek Kitszel { 444*2846fe56SPrzemek Kitszel struct devlink_port_attrs attrs = {}; 445*2846fe56SPrzemek Kitszel struct devlink_port *devlink_port; 446*2846fe56SPrzemek Kitszel struct devlink *devlink; 447*2846fe56SPrzemek Kitszel struct ice_vsi *vsi; 448*2846fe56SPrzemek Kitszel struct device *dev; 449*2846fe56SPrzemek Kitszel struct ice_pf *pf; 450*2846fe56SPrzemek Kitszel int err; 451*2846fe56SPrzemek Kitszel 452*2846fe56SPrzemek Kitszel pf = vf->pf; 453*2846fe56SPrzemek Kitszel dev = ice_pf_to_dev(pf); 454*2846fe56SPrzemek Kitszel devlink_port = &vf->devlink_port; 455*2846fe56SPrzemek Kitszel 456*2846fe56SPrzemek Kitszel vsi = ice_get_vf_vsi(vf); 457*2846fe56SPrzemek Kitszel if (!vsi) 458*2846fe56SPrzemek Kitszel return -EINVAL; 459*2846fe56SPrzemek Kitszel 460*2846fe56SPrzemek Kitszel attrs.flavour = DEVLINK_PORT_FLAVOUR_PCI_VF; 461*2846fe56SPrzemek Kitszel attrs.pci_vf.pf = pf->hw.pf_id; 462*2846fe56SPrzemek Kitszel attrs.pci_vf.vf = vf->vf_id; 463*2846fe56SPrzemek Kitszel 464*2846fe56SPrzemek Kitszel ice_devlink_set_switch_id(pf, &attrs.switch_id); 465*2846fe56SPrzemek Kitszel 466*2846fe56SPrzemek Kitszel devlink_port_attrs_set(devlink_port, &attrs); 467*2846fe56SPrzemek Kitszel devlink = priv_to_devlink(pf); 468*2846fe56SPrzemek Kitszel 469*2846fe56SPrzemek Kitszel err = devl_port_register_with_ops(devlink, devlink_port, vsi->idx, 470*2846fe56SPrzemek Kitszel &ice_devlink_vf_port_ops); 471*2846fe56SPrzemek Kitszel if (err) { 472*2846fe56SPrzemek Kitszel dev_err(dev, "Failed to create devlink port for VF %d, error %d\n", 473*2846fe56SPrzemek Kitszel vf->vf_id, err); 474*2846fe56SPrzemek Kitszel return err; 475*2846fe56SPrzemek Kitszel } 476*2846fe56SPrzemek Kitszel 477*2846fe56SPrzemek Kitszel return 0; 478*2846fe56SPrzemek Kitszel } 479*2846fe56SPrzemek Kitszel 480*2846fe56SPrzemek Kitszel /** 481*2846fe56SPrzemek Kitszel * ice_devlink_destroy_vf_port - Destroy the devlink_port for this VF 482*2846fe56SPrzemek Kitszel * @vf: the VF to cleanup 483*2846fe56SPrzemek Kitszel * 484*2846fe56SPrzemek Kitszel * Unregisters the devlink_port structure associated with this VF. 485*2846fe56SPrzemek Kitszel */ 486*2846fe56SPrzemek Kitszel void ice_devlink_destroy_vf_port(struct ice_vf *vf) 487*2846fe56SPrzemek Kitszel { 488*2846fe56SPrzemek Kitszel devl_rate_leaf_destroy(&vf->devlink_port); 489*2846fe56SPrzemek Kitszel devl_port_unregister(&vf->devlink_port); 490*2846fe56SPrzemek Kitszel } 491*2846fe56SPrzemek Kitszel 492*2846fe56SPrzemek Kitszel /** 493*2846fe56SPrzemek Kitszel * ice_devlink_create_sf_dev_port - Register virtual port for a subfunction 494*2846fe56SPrzemek Kitszel * @sf_dev: the subfunction device to create a devlink port for 495*2846fe56SPrzemek Kitszel * 496*2846fe56SPrzemek Kitszel * Register virtual flavour devlink port for the subfunction auxiliary device 497*2846fe56SPrzemek Kitszel * created after activating a dynamically added devlink port. 498*2846fe56SPrzemek Kitszel * 499*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 500*2846fe56SPrzemek Kitszel */ 501*2846fe56SPrzemek Kitszel int ice_devlink_create_sf_dev_port(struct ice_sf_dev *sf_dev) 502*2846fe56SPrzemek Kitszel { 503*2846fe56SPrzemek Kitszel struct devlink_port_attrs attrs = {}; 504*2846fe56SPrzemek Kitszel struct ice_dynamic_port *dyn_port; 505*2846fe56SPrzemek Kitszel struct devlink_port *devlink_port; 506*2846fe56SPrzemek Kitszel struct devlink *devlink; 507*2846fe56SPrzemek Kitszel struct ice_vsi *vsi; 508*2846fe56SPrzemek Kitszel 509*2846fe56SPrzemek Kitszel dyn_port = sf_dev->dyn_port; 510*2846fe56SPrzemek Kitszel vsi = dyn_port->vsi; 511*2846fe56SPrzemek Kitszel 512*2846fe56SPrzemek Kitszel devlink_port = &sf_dev->priv->devlink_port; 513*2846fe56SPrzemek Kitszel 514*2846fe56SPrzemek Kitszel attrs.flavour = DEVLINK_PORT_FLAVOUR_VIRTUAL; 515*2846fe56SPrzemek Kitszel 516*2846fe56SPrzemek Kitszel devlink_port_attrs_set(devlink_port, &attrs); 517*2846fe56SPrzemek Kitszel devlink = priv_to_devlink(sf_dev->priv); 518*2846fe56SPrzemek Kitszel 519*2846fe56SPrzemek Kitszel return devl_port_register(devlink, devlink_port, vsi->idx); 520*2846fe56SPrzemek Kitszel } 521*2846fe56SPrzemek Kitszel 522*2846fe56SPrzemek Kitszel /** 523*2846fe56SPrzemek Kitszel * ice_devlink_destroy_sf_dev_port - Destroy virtual port for a subfunction 524*2846fe56SPrzemek Kitszel * @sf_dev: the subfunction device to create a devlink port for 525*2846fe56SPrzemek Kitszel * 526*2846fe56SPrzemek Kitszel * Unregisters the virtual port associated with this subfunction. 527*2846fe56SPrzemek Kitszel */ 528*2846fe56SPrzemek Kitszel void ice_devlink_destroy_sf_dev_port(struct ice_sf_dev *sf_dev) 529*2846fe56SPrzemek Kitszel { 530*2846fe56SPrzemek Kitszel devl_port_unregister(&sf_dev->priv->devlink_port); 531*2846fe56SPrzemek Kitszel } 532*2846fe56SPrzemek Kitszel 533*2846fe56SPrzemek Kitszel /** 534*2846fe56SPrzemek Kitszel * ice_activate_dynamic_port - Activate a dynamic port 535*2846fe56SPrzemek Kitszel * @dyn_port: dynamic port instance to activate 536*2846fe56SPrzemek Kitszel * @extack: extack for reporting error messages 537*2846fe56SPrzemek Kitszel * 538*2846fe56SPrzemek Kitszel * Activate the dynamic port based on its flavour. 539*2846fe56SPrzemek Kitszel * 540*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 541*2846fe56SPrzemek Kitszel */ 542*2846fe56SPrzemek Kitszel static int 543*2846fe56SPrzemek Kitszel ice_activate_dynamic_port(struct ice_dynamic_port *dyn_port, 544*2846fe56SPrzemek Kitszel struct netlink_ext_ack *extack) 545*2846fe56SPrzemek Kitszel { 546*2846fe56SPrzemek Kitszel int err; 547*2846fe56SPrzemek Kitszel 548*2846fe56SPrzemek Kitszel if (dyn_port->active) 549*2846fe56SPrzemek Kitszel return 0; 550*2846fe56SPrzemek Kitszel 551*2846fe56SPrzemek Kitszel err = ice_sf_eth_activate(dyn_port, extack); 552*2846fe56SPrzemek Kitszel if (err) 553*2846fe56SPrzemek Kitszel return err; 554*2846fe56SPrzemek Kitszel 555*2846fe56SPrzemek Kitszel dyn_port->active = true; 556*2846fe56SPrzemek Kitszel 557*2846fe56SPrzemek Kitszel return 0; 558*2846fe56SPrzemek Kitszel } 559*2846fe56SPrzemek Kitszel 560*2846fe56SPrzemek Kitszel /** 561*2846fe56SPrzemek Kitszel * ice_deactivate_dynamic_port - Deactivate a dynamic port 562*2846fe56SPrzemek Kitszel * @dyn_port: dynamic port instance to deactivate 563*2846fe56SPrzemek Kitszel * 564*2846fe56SPrzemek Kitszel * Undo activation of a dynamic port. 565*2846fe56SPrzemek Kitszel */ 566*2846fe56SPrzemek Kitszel static void ice_deactivate_dynamic_port(struct ice_dynamic_port *dyn_port) 567*2846fe56SPrzemek Kitszel { 568*2846fe56SPrzemek Kitszel if (!dyn_port->active) 569*2846fe56SPrzemek Kitszel return; 570*2846fe56SPrzemek Kitszel 571*2846fe56SPrzemek Kitszel ice_sf_eth_deactivate(dyn_port); 572*2846fe56SPrzemek Kitszel dyn_port->active = false; 573*2846fe56SPrzemek Kitszel } 574*2846fe56SPrzemek Kitszel 575*2846fe56SPrzemek Kitszel /** 576*2846fe56SPrzemek Kitszel * ice_dealloc_dynamic_port - Deallocate and remove a dynamic port 577*2846fe56SPrzemek Kitszel * @dyn_port: dynamic port instance to deallocate 578*2846fe56SPrzemek Kitszel * 579*2846fe56SPrzemek Kitszel * Free resources associated with a dynamically added devlink port. Will 580*2846fe56SPrzemek Kitszel * deactivate the port if its currently active. 581*2846fe56SPrzemek Kitszel */ 582*2846fe56SPrzemek Kitszel static void ice_dealloc_dynamic_port(struct ice_dynamic_port *dyn_port) 583*2846fe56SPrzemek Kitszel { 584*2846fe56SPrzemek Kitszel struct devlink_port *devlink_port = &dyn_port->devlink_port; 585*2846fe56SPrzemek Kitszel struct ice_pf *pf = dyn_port->pf; 586*2846fe56SPrzemek Kitszel 587*2846fe56SPrzemek Kitszel ice_deactivate_dynamic_port(dyn_port); 588*2846fe56SPrzemek Kitszel 589*2846fe56SPrzemek Kitszel xa_erase(&pf->sf_nums, devlink_port->attrs.pci_sf.sf); 590*2846fe56SPrzemek Kitszel ice_eswitch_detach_sf(pf, dyn_port); 591*2846fe56SPrzemek Kitszel ice_vsi_free(dyn_port->vsi); 592*2846fe56SPrzemek Kitszel xa_erase(&pf->dyn_ports, dyn_port->vsi->idx); 593*2846fe56SPrzemek Kitszel kfree(dyn_port); 594*2846fe56SPrzemek Kitszel } 595*2846fe56SPrzemek Kitszel 596*2846fe56SPrzemek Kitszel /** 597*2846fe56SPrzemek Kitszel * ice_dealloc_all_dynamic_ports - Deallocate all dynamic devlink ports 598*2846fe56SPrzemek Kitszel * @pf: pointer to the pf structure 599*2846fe56SPrzemek Kitszel */ 600*2846fe56SPrzemek Kitszel void ice_dealloc_all_dynamic_ports(struct ice_pf *pf) 601*2846fe56SPrzemek Kitszel { 602*2846fe56SPrzemek Kitszel struct ice_dynamic_port *dyn_port; 603*2846fe56SPrzemek Kitszel unsigned long index; 604*2846fe56SPrzemek Kitszel 605*2846fe56SPrzemek Kitszel xa_for_each(&pf->dyn_ports, index, dyn_port) 606*2846fe56SPrzemek Kitszel ice_dealloc_dynamic_port(dyn_port); 607*2846fe56SPrzemek Kitszel } 608*2846fe56SPrzemek Kitszel 609*2846fe56SPrzemek Kitszel /** 610*2846fe56SPrzemek Kitszel * ice_devlink_port_new_check_attr - Check that new port attributes are valid 611*2846fe56SPrzemek Kitszel * @pf: pointer to the PF structure 612*2846fe56SPrzemek Kitszel * @new_attr: the attributes for the new port 613*2846fe56SPrzemek Kitszel * @extack: extack for reporting error messages 614*2846fe56SPrzemek Kitszel * 615*2846fe56SPrzemek Kitszel * Check that the attributes for the new port are valid before continuing to 616*2846fe56SPrzemek Kitszel * allocate the devlink port. 617*2846fe56SPrzemek Kitszel * 618*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 619*2846fe56SPrzemek Kitszel */ 620*2846fe56SPrzemek Kitszel static int 621*2846fe56SPrzemek Kitszel ice_devlink_port_new_check_attr(struct ice_pf *pf, 622*2846fe56SPrzemek Kitszel const struct devlink_port_new_attrs *new_attr, 623*2846fe56SPrzemek Kitszel struct netlink_ext_ack *extack) 624*2846fe56SPrzemek Kitszel { 625*2846fe56SPrzemek Kitszel if (new_attr->flavour != DEVLINK_PORT_FLAVOUR_PCI_SF) { 626*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Flavour other than pcisf is not supported"); 627*2846fe56SPrzemek Kitszel return -EOPNOTSUPP; 628*2846fe56SPrzemek Kitszel } 629*2846fe56SPrzemek Kitszel 630*2846fe56SPrzemek Kitszel if (new_attr->controller_valid) { 631*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Setting controller is not supported"); 632*2846fe56SPrzemek Kitszel return -EOPNOTSUPP; 633*2846fe56SPrzemek Kitszel } 634*2846fe56SPrzemek Kitszel 635*2846fe56SPrzemek Kitszel if (new_attr->port_index_valid) { 636*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Driver does not support user defined port index assignment"); 637*2846fe56SPrzemek Kitszel return -EOPNOTSUPP; 638*2846fe56SPrzemek Kitszel } 639*2846fe56SPrzemek Kitszel 640*2846fe56SPrzemek Kitszel if (new_attr->pfnum != pf->hw.pf_id) { 641*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Incorrect pfnum supplied"); 642*2846fe56SPrzemek Kitszel return -EINVAL; 643*2846fe56SPrzemek Kitszel } 644*2846fe56SPrzemek Kitszel 645*2846fe56SPrzemek Kitszel if (!pci_msix_can_alloc_dyn(pf->pdev)) { 646*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Dynamic MSIX-X interrupt allocation is not supported"); 647*2846fe56SPrzemek Kitszel return -EOPNOTSUPP; 648*2846fe56SPrzemek Kitszel } 649*2846fe56SPrzemek Kitszel 650*2846fe56SPrzemek Kitszel return 0; 651*2846fe56SPrzemek Kitszel } 652*2846fe56SPrzemek Kitszel 653*2846fe56SPrzemek Kitszel /** 654*2846fe56SPrzemek Kitszel * ice_devlink_port_del - devlink handler for port delete 655*2846fe56SPrzemek Kitszel * @devlink: pointer to devlink 656*2846fe56SPrzemek Kitszel * @port: devlink port to be deleted 657*2846fe56SPrzemek Kitszel * @extack: pointer to extack 658*2846fe56SPrzemek Kitszel * 659*2846fe56SPrzemek Kitszel * Deletes devlink port and deallocates all resources associated with 660*2846fe56SPrzemek Kitszel * created subfunction. 661*2846fe56SPrzemek Kitszel * 662*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 663*2846fe56SPrzemek Kitszel */ 664*2846fe56SPrzemek Kitszel static int 665*2846fe56SPrzemek Kitszel ice_devlink_port_del(struct devlink *devlink, struct devlink_port *port, 666*2846fe56SPrzemek Kitszel struct netlink_ext_ack *extack) 667*2846fe56SPrzemek Kitszel { 668*2846fe56SPrzemek Kitszel struct ice_dynamic_port *dyn_port; 669*2846fe56SPrzemek Kitszel 670*2846fe56SPrzemek Kitszel dyn_port = ice_devlink_port_to_dyn(port); 671*2846fe56SPrzemek Kitszel ice_dealloc_dynamic_port(dyn_port); 672*2846fe56SPrzemek Kitszel 673*2846fe56SPrzemek Kitszel return 0; 674*2846fe56SPrzemek Kitszel } 675*2846fe56SPrzemek Kitszel 676*2846fe56SPrzemek Kitszel /** 677*2846fe56SPrzemek Kitszel * ice_devlink_port_fn_hw_addr_set - devlink handler for mac address set 678*2846fe56SPrzemek Kitszel * @port: pointer to devlink port 679*2846fe56SPrzemek Kitszel * @hw_addr: hw address to set 680*2846fe56SPrzemek Kitszel * @hw_addr_len: hw address length 681*2846fe56SPrzemek Kitszel * @extack: extack for reporting error messages 682*2846fe56SPrzemek Kitszel * 683*2846fe56SPrzemek Kitszel * Sets mac address for the port, verifies arguments and copies address 684*2846fe56SPrzemek Kitszel * to the subfunction structure. 685*2846fe56SPrzemek Kitszel * 686*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 687*2846fe56SPrzemek Kitszel */ 688*2846fe56SPrzemek Kitszel static int 689*2846fe56SPrzemek Kitszel ice_devlink_port_fn_hw_addr_set(struct devlink_port *port, const u8 *hw_addr, 690*2846fe56SPrzemek Kitszel int hw_addr_len, 691*2846fe56SPrzemek Kitszel struct netlink_ext_ack *extack) 692*2846fe56SPrzemek Kitszel { 693*2846fe56SPrzemek Kitszel struct ice_dynamic_port *dyn_port; 694*2846fe56SPrzemek Kitszel 695*2846fe56SPrzemek Kitszel dyn_port = ice_devlink_port_to_dyn(port); 696*2846fe56SPrzemek Kitszel 697*2846fe56SPrzemek Kitszel if (dyn_port->attached) { 698*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, 699*2846fe56SPrzemek Kitszel "Ethernet address can be change only in detached state"); 700*2846fe56SPrzemek Kitszel return -EBUSY; 701*2846fe56SPrzemek Kitszel } 702*2846fe56SPrzemek Kitszel 703*2846fe56SPrzemek Kitszel if (hw_addr_len != ETH_ALEN || !is_valid_ether_addr(hw_addr)) { 704*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Invalid ethernet address"); 705*2846fe56SPrzemek Kitszel return -EADDRNOTAVAIL; 706*2846fe56SPrzemek Kitszel } 707*2846fe56SPrzemek Kitszel 708*2846fe56SPrzemek Kitszel ether_addr_copy(dyn_port->hw_addr, hw_addr); 709*2846fe56SPrzemek Kitszel 710*2846fe56SPrzemek Kitszel return 0; 711*2846fe56SPrzemek Kitszel } 712*2846fe56SPrzemek Kitszel 713*2846fe56SPrzemek Kitszel /** 714*2846fe56SPrzemek Kitszel * ice_devlink_port_fn_hw_addr_get - devlink handler for mac address get 715*2846fe56SPrzemek Kitszel * @port: pointer to devlink port 716*2846fe56SPrzemek Kitszel * @hw_addr: hw address to set 717*2846fe56SPrzemek Kitszel * @hw_addr_len: hw address length 718*2846fe56SPrzemek Kitszel * @extack: extack for reporting error messages 719*2846fe56SPrzemek Kitszel * 720*2846fe56SPrzemek Kitszel * Returns mac address for the port. 721*2846fe56SPrzemek Kitszel * 722*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 723*2846fe56SPrzemek Kitszel */ 724*2846fe56SPrzemek Kitszel static int 725*2846fe56SPrzemek Kitszel ice_devlink_port_fn_hw_addr_get(struct devlink_port *port, u8 *hw_addr, 726*2846fe56SPrzemek Kitszel int *hw_addr_len, 727*2846fe56SPrzemek Kitszel struct netlink_ext_ack *extack) 728*2846fe56SPrzemek Kitszel { 729*2846fe56SPrzemek Kitszel struct ice_dynamic_port *dyn_port; 730*2846fe56SPrzemek Kitszel 731*2846fe56SPrzemek Kitszel dyn_port = ice_devlink_port_to_dyn(port); 732*2846fe56SPrzemek Kitszel 733*2846fe56SPrzemek Kitszel ether_addr_copy(hw_addr, dyn_port->hw_addr); 734*2846fe56SPrzemek Kitszel *hw_addr_len = ETH_ALEN; 735*2846fe56SPrzemek Kitszel 736*2846fe56SPrzemek Kitszel return 0; 737*2846fe56SPrzemek Kitszel } 738*2846fe56SPrzemek Kitszel 739*2846fe56SPrzemek Kitszel /** 740*2846fe56SPrzemek Kitszel * ice_devlink_port_fn_state_set - devlink handler for port state set 741*2846fe56SPrzemek Kitszel * @port: pointer to devlink port 742*2846fe56SPrzemek Kitszel * @state: state to set 743*2846fe56SPrzemek Kitszel * @extack: extack for reporting error messages 744*2846fe56SPrzemek Kitszel * 745*2846fe56SPrzemek Kitszel * Activates or deactivates the port. 746*2846fe56SPrzemek Kitszel * 747*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 748*2846fe56SPrzemek Kitszel */ 749*2846fe56SPrzemek Kitszel static int 750*2846fe56SPrzemek Kitszel ice_devlink_port_fn_state_set(struct devlink_port *port, 751*2846fe56SPrzemek Kitszel enum devlink_port_fn_state state, 752*2846fe56SPrzemek Kitszel struct netlink_ext_ack *extack) 753*2846fe56SPrzemek Kitszel { 754*2846fe56SPrzemek Kitszel struct ice_dynamic_port *dyn_port; 755*2846fe56SPrzemek Kitszel 756*2846fe56SPrzemek Kitszel dyn_port = ice_devlink_port_to_dyn(port); 757*2846fe56SPrzemek Kitszel 758*2846fe56SPrzemek Kitszel switch (state) { 759*2846fe56SPrzemek Kitszel case DEVLINK_PORT_FN_STATE_ACTIVE: 760*2846fe56SPrzemek Kitszel return ice_activate_dynamic_port(dyn_port, extack); 761*2846fe56SPrzemek Kitszel 762*2846fe56SPrzemek Kitszel case DEVLINK_PORT_FN_STATE_INACTIVE: 763*2846fe56SPrzemek Kitszel ice_deactivate_dynamic_port(dyn_port); 764*2846fe56SPrzemek Kitszel break; 765*2846fe56SPrzemek Kitszel } 766*2846fe56SPrzemek Kitszel 767*2846fe56SPrzemek Kitszel return 0; 768*2846fe56SPrzemek Kitszel } 769*2846fe56SPrzemek Kitszel 770*2846fe56SPrzemek Kitszel /** 771*2846fe56SPrzemek Kitszel * ice_devlink_port_fn_state_get - devlink handler for port state get 772*2846fe56SPrzemek Kitszel * @port: pointer to devlink port 773*2846fe56SPrzemek Kitszel * @state: admin configured state of the port 774*2846fe56SPrzemek Kitszel * @opstate: current port operational state 775*2846fe56SPrzemek Kitszel * @extack: extack for reporting error messages 776*2846fe56SPrzemek Kitszel * 777*2846fe56SPrzemek Kitszel * Gets port state. 778*2846fe56SPrzemek Kitszel * 779*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 780*2846fe56SPrzemek Kitszel */ 781*2846fe56SPrzemek Kitszel static int 782*2846fe56SPrzemek Kitszel ice_devlink_port_fn_state_get(struct devlink_port *port, 783*2846fe56SPrzemek Kitszel enum devlink_port_fn_state *state, 784*2846fe56SPrzemek Kitszel enum devlink_port_fn_opstate *opstate, 785*2846fe56SPrzemek Kitszel struct netlink_ext_ack *extack) 786*2846fe56SPrzemek Kitszel { 787*2846fe56SPrzemek Kitszel struct ice_dynamic_port *dyn_port; 788*2846fe56SPrzemek Kitszel 789*2846fe56SPrzemek Kitszel dyn_port = ice_devlink_port_to_dyn(port); 790*2846fe56SPrzemek Kitszel 791*2846fe56SPrzemek Kitszel if (dyn_port->active) 792*2846fe56SPrzemek Kitszel *state = DEVLINK_PORT_FN_STATE_ACTIVE; 793*2846fe56SPrzemek Kitszel else 794*2846fe56SPrzemek Kitszel *state = DEVLINK_PORT_FN_STATE_INACTIVE; 795*2846fe56SPrzemek Kitszel 796*2846fe56SPrzemek Kitszel if (dyn_port->attached) 797*2846fe56SPrzemek Kitszel *opstate = DEVLINK_PORT_FN_OPSTATE_ATTACHED; 798*2846fe56SPrzemek Kitszel else 799*2846fe56SPrzemek Kitszel *opstate = DEVLINK_PORT_FN_OPSTATE_DETACHED; 800*2846fe56SPrzemek Kitszel 801*2846fe56SPrzemek Kitszel return 0; 802*2846fe56SPrzemek Kitszel } 803*2846fe56SPrzemek Kitszel 804*2846fe56SPrzemek Kitszel static const struct devlink_port_ops ice_devlink_port_sf_ops = { 805*2846fe56SPrzemek Kitszel .port_del = ice_devlink_port_del, 806*2846fe56SPrzemek Kitszel .port_fn_hw_addr_get = ice_devlink_port_fn_hw_addr_get, 807*2846fe56SPrzemek Kitszel .port_fn_hw_addr_set = ice_devlink_port_fn_hw_addr_set, 808*2846fe56SPrzemek Kitszel .port_fn_state_get = ice_devlink_port_fn_state_get, 809*2846fe56SPrzemek Kitszel .port_fn_state_set = ice_devlink_port_fn_state_set, 810*2846fe56SPrzemek Kitszel }; 811*2846fe56SPrzemek Kitszel 812*2846fe56SPrzemek Kitszel /** 813*2846fe56SPrzemek Kitszel * ice_reserve_sf_num - Reserve a subfunction number for this port 814*2846fe56SPrzemek Kitszel * @pf: pointer to the pf structure 815*2846fe56SPrzemek Kitszel * @new_attr: devlink port attributes requested 816*2846fe56SPrzemek Kitszel * @extack: extack for reporting error messages 817*2846fe56SPrzemek Kitszel * @sfnum: on success, the sf number reserved 818*2846fe56SPrzemek Kitszel * 819*2846fe56SPrzemek Kitszel * Reserve a subfunction number for this port. Only called for 820*2846fe56SPrzemek Kitszel * DEVLINK_PORT_FLAVOUR_PCI_SF ports. 821*2846fe56SPrzemek Kitszel * 822*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 823*2846fe56SPrzemek Kitszel */ 824*2846fe56SPrzemek Kitszel static int 825*2846fe56SPrzemek Kitszel ice_reserve_sf_num(struct ice_pf *pf, 826*2846fe56SPrzemek Kitszel const struct devlink_port_new_attrs *new_attr, 827*2846fe56SPrzemek Kitszel struct netlink_ext_ack *extack, u32 *sfnum) 828*2846fe56SPrzemek Kitszel { 829*2846fe56SPrzemek Kitszel int err; 830*2846fe56SPrzemek Kitszel 831*2846fe56SPrzemek Kitszel /* If user didn't request an explicit number, pick one */ 832*2846fe56SPrzemek Kitszel if (!new_attr->sfnum_valid) 833*2846fe56SPrzemek Kitszel return xa_alloc(&pf->sf_nums, sfnum, NULL, xa_limit_32b, 834*2846fe56SPrzemek Kitszel GFP_KERNEL); 835*2846fe56SPrzemek Kitszel 836*2846fe56SPrzemek Kitszel /* Otherwise, check and use the number provided */ 837*2846fe56SPrzemek Kitszel err = xa_insert(&pf->sf_nums, new_attr->sfnum, NULL, GFP_KERNEL); 838*2846fe56SPrzemek Kitszel if (err) { 839*2846fe56SPrzemek Kitszel if (err == -EBUSY) 840*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Subfunction with given sfnum already exists"); 841*2846fe56SPrzemek Kitszel return err; 842*2846fe56SPrzemek Kitszel } 843*2846fe56SPrzemek Kitszel 844*2846fe56SPrzemek Kitszel *sfnum = new_attr->sfnum; 845*2846fe56SPrzemek Kitszel 846*2846fe56SPrzemek Kitszel return 0; 847*2846fe56SPrzemek Kitszel } 848*2846fe56SPrzemek Kitszel 849*2846fe56SPrzemek Kitszel /** 850*2846fe56SPrzemek Kitszel * ice_devlink_create_sf_port - Register PCI subfunction devlink port 851*2846fe56SPrzemek Kitszel * @dyn_port: the dynamic port instance structure for this subfunction 852*2846fe56SPrzemek Kitszel * 853*2846fe56SPrzemek Kitszel * Register PCI subfunction flavour devlink port for a dynamically added 854*2846fe56SPrzemek Kitszel * subfunction port. 855*2846fe56SPrzemek Kitszel * 856*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 857*2846fe56SPrzemek Kitszel */ 858*2846fe56SPrzemek Kitszel int ice_devlink_create_sf_port(struct ice_dynamic_port *dyn_port) 859*2846fe56SPrzemek Kitszel { 860*2846fe56SPrzemek Kitszel struct devlink_port_attrs attrs = {}; 861*2846fe56SPrzemek Kitszel struct devlink_port *devlink_port; 862*2846fe56SPrzemek Kitszel struct devlink *devlink; 863*2846fe56SPrzemek Kitszel struct ice_vsi *vsi; 864*2846fe56SPrzemek Kitszel struct ice_pf *pf; 865*2846fe56SPrzemek Kitszel 866*2846fe56SPrzemek Kitszel vsi = dyn_port->vsi; 867*2846fe56SPrzemek Kitszel pf = dyn_port->pf; 868*2846fe56SPrzemek Kitszel 869*2846fe56SPrzemek Kitszel devlink_port = &dyn_port->devlink_port; 870*2846fe56SPrzemek Kitszel 871*2846fe56SPrzemek Kitszel attrs.flavour = DEVLINK_PORT_FLAVOUR_PCI_SF; 872*2846fe56SPrzemek Kitszel attrs.pci_sf.pf = pf->hw.pf_id; 873*2846fe56SPrzemek Kitszel attrs.pci_sf.sf = dyn_port->sfnum; 874*2846fe56SPrzemek Kitszel 875*2846fe56SPrzemek Kitszel devlink_port_attrs_set(devlink_port, &attrs); 876*2846fe56SPrzemek Kitszel devlink = priv_to_devlink(pf); 877*2846fe56SPrzemek Kitszel 878*2846fe56SPrzemek Kitszel return devl_port_register_with_ops(devlink, devlink_port, vsi->idx, 879*2846fe56SPrzemek Kitszel &ice_devlink_port_sf_ops); 880*2846fe56SPrzemek Kitszel } 881*2846fe56SPrzemek Kitszel 882*2846fe56SPrzemek Kitszel /** 883*2846fe56SPrzemek Kitszel * ice_devlink_destroy_sf_port - Destroy the devlink_port for this SF 884*2846fe56SPrzemek Kitszel * @dyn_port: the dynamic port instance structure for this subfunction 885*2846fe56SPrzemek Kitszel * 886*2846fe56SPrzemek Kitszel * Unregisters the devlink_port structure associated with this SF. 887*2846fe56SPrzemek Kitszel */ 888*2846fe56SPrzemek Kitszel void ice_devlink_destroy_sf_port(struct ice_dynamic_port *dyn_port) 889*2846fe56SPrzemek Kitszel { 890*2846fe56SPrzemek Kitszel devl_rate_leaf_destroy(&dyn_port->devlink_port); 891*2846fe56SPrzemek Kitszel devl_port_unregister(&dyn_port->devlink_port); 892*2846fe56SPrzemek Kitszel } 893*2846fe56SPrzemek Kitszel 894*2846fe56SPrzemek Kitszel /** 895*2846fe56SPrzemek Kitszel * ice_alloc_dynamic_port - Allocate new dynamic port 896*2846fe56SPrzemek Kitszel * @pf: pointer to the pf structure 897*2846fe56SPrzemek Kitszel * @new_attr: devlink port attributes requested 898*2846fe56SPrzemek Kitszel * @extack: extack for reporting error messages 899*2846fe56SPrzemek Kitszel * @devlink_port: index of newly created devlink port 900*2846fe56SPrzemek Kitszel * 901*2846fe56SPrzemek Kitszel * Allocate a new dynamic port instance and prepare it for configuration 902*2846fe56SPrzemek Kitszel * with devlink. 903*2846fe56SPrzemek Kitszel * 904*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 905*2846fe56SPrzemek Kitszel */ 906*2846fe56SPrzemek Kitszel static int 907*2846fe56SPrzemek Kitszel ice_alloc_dynamic_port(struct ice_pf *pf, 908*2846fe56SPrzemek Kitszel const struct devlink_port_new_attrs *new_attr, 909*2846fe56SPrzemek Kitszel struct netlink_ext_ack *extack, 910*2846fe56SPrzemek Kitszel struct devlink_port **devlink_port) 911*2846fe56SPrzemek Kitszel { 912*2846fe56SPrzemek Kitszel struct ice_dynamic_port *dyn_port; 913*2846fe56SPrzemek Kitszel struct ice_vsi *vsi; 914*2846fe56SPrzemek Kitszel u32 sfnum; 915*2846fe56SPrzemek Kitszel int err; 916*2846fe56SPrzemek Kitszel 917*2846fe56SPrzemek Kitszel err = ice_reserve_sf_num(pf, new_attr, extack, &sfnum); 918*2846fe56SPrzemek Kitszel if (err) 919*2846fe56SPrzemek Kitszel return err; 920*2846fe56SPrzemek Kitszel 921*2846fe56SPrzemek Kitszel dyn_port = kzalloc(sizeof(*dyn_port), GFP_KERNEL); 922*2846fe56SPrzemek Kitszel if (!dyn_port) { 923*2846fe56SPrzemek Kitszel err = -ENOMEM; 924*2846fe56SPrzemek Kitszel goto unroll_reserve_sf_num; 925*2846fe56SPrzemek Kitszel } 926*2846fe56SPrzemek Kitszel 927*2846fe56SPrzemek Kitszel vsi = ice_vsi_alloc(pf); 928*2846fe56SPrzemek Kitszel if (!vsi) { 929*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Unable to allocate VSI"); 930*2846fe56SPrzemek Kitszel err = -ENOMEM; 931*2846fe56SPrzemek Kitszel goto unroll_dyn_port_alloc; 932*2846fe56SPrzemek Kitszel } 933*2846fe56SPrzemek Kitszel 934*2846fe56SPrzemek Kitszel dyn_port->vsi = vsi; 935*2846fe56SPrzemek Kitszel dyn_port->pf = pf; 936*2846fe56SPrzemek Kitszel dyn_port->sfnum = sfnum; 937*2846fe56SPrzemek Kitszel eth_random_addr(dyn_port->hw_addr); 938*2846fe56SPrzemek Kitszel 939*2846fe56SPrzemek Kitszel err = xa_insert(&pf->dyn_ports, vsi->idx, dyn_port, GFP_KERNEL); 940*2846fe56SPrzemek Kitszel if (err) { 941*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Port index reservation failed"); 942*2846fe56SPrzemek Kitszel goto unroll_vsi_alloc; 943*2846fe56SPrzemek Kitszel } 944*2846fe56SPrzemek Kitszel 945*2846fe56SPrzemek Kitszel err = ice_eswitch_attach_sf(pf, dyn_port); 946*2846fe56SPrzemek Kitszel if (err) { 947*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, "Failed to attach SF to eswitch"); 948*2846fe56SPrzemek Kitszel goto unroll_xa_insert; 949*2846fe56SPrzemek Kitszel } 950*2846fe56SPrzemek Kitszel 951*2846fe56SPrzemek Kitszel *devlink_port = &dyn_port->devlink_port; 952*2846fe56SPrzemek Kitszel 953*2846fe56SPrzemek Kitszel return 0; 954*2846fe56SPrzemek Kitszel 955*2846fe56SPrzemek Kitszel unroll_xa_insert: 956*2846fe56SPrzemek Kitszel xa_erase(&pf->dyn_ports, vsi->idx); 957*2846fe56SPrzemek Kitszel unroll_vsi_alloc: 958*2846fe56SPrzemek Kitszel ice_vsi_free(vsi); 959*2846fe56SPrzemek Kitszel unroll_dyn_port_alloc: 960*2846fe56SPrzemek Kitszel kfree(dyn_port); 961*2846fe56SPrzemek Kitszel unroll_reserve_sf_num: 962*2846fe56SPrzemek Kitszel xa_erase(&pf->sf_nums, sfnum); 963*2846fe56SPrzemek Kitszel 964*2846fe56SPrzemek Kitszel return err; 965*2846fe56SPrzemek Kitszel } 966*2846fe56SPrzemek Kitszel 967*2846fe56SPrzemek Kitszel /** 968*2846fe56SPrzemek Kitszel * ice_devlink_port_new - devlink handler for the new port 969*2846fe56SPrzemek Kitszel * @devlink: pointer to devlink 970*2846fe56SPrzemek Kitszel * @new_attr: pointer to the port new attributes 971*2846fe56SPrzemek Kitszel * @extack: extack for reporting error messages 972*2846fe56SPrzemek Kitszel * @devlink_port: pointer to a new port 973*2846fe56SPrzemek Kitszel * 974*2846fe56SPrzemek Kitszel * Creates new devlink port, checks new port attributes and reject 975*2846fe56SPrzemek Kitszel * any unsupported parameters, allocates new subfunction for that port. 976*2846fe56SPrzemek Kitszel * 977*2846fe56SPrzemek Kitszel * Return: zero on success or an error code on failure. 978*2846fe56SPrzemek Kitszel */ 979*2846fe56SPrzemek Kitszel int 980*2846fe56SPrzemek Kitszel ice_devlink_port_new(struct devlink *devlink, 981*2846fe56SPrzemek Kitszel const struct devlink_port_new_attrs *new_attr, 982*2846fe56SPrzemek Kitszel struct netlink_ext_ack *extack, 983*2846fe56SPrzemek Kitszel struct devlink_port **devlink_port) 984*2846fe56SPrzemek Kitszel { 985*2846fe56SPrzemek Kitszel struct ice_pf *pf = devlink_priv(devlink); 986*2846fe56SPrzemek Kitszel int err; 987*2846fe56SPrzemek Kitszel 988*2846fe56SPrzemek Kitszel err = ice_devlink_port_new_check_attr(pf, new_attr, extack); 989*2846fe56SPrzemek Kitszel if (err) 990*2846fe56SPrzemek Kitszel return err; 991*2846fe56SPrzemek Kitszel 992*2846fe56SPrzemek Kitszel if (!ice_is_eswitch_mode_switchdev(pf)) { 993*2846fe56SPrzemek Kitszel NL_SET_ERR_MSG_MOD(extack, 994*2846fe56SPrzemek Kitszel "SF ports are only supported in eswitch switchdev mode"); 995*2846fe56SPrzemek Kitszel return -EOPNOTSUPP; 996*2846fe56SPrzemek Kitszel } 997*2846fe56SPrzemek Kitszel 998*2846fe56SPrzemek Kitszel return ice_alloc_dynamic_port(pf, new_attr, extack, devlink_port); 999*2846fe56SPrzemek Kitszel } 1000