Changeset View
Changeset View
Standalone View
Standalone View
sys/dev/ixgbe/if_ix.c
Show First 20 Lines • Show All 173 Lines • ▼ Show 20 Lines | |||||
static void ixgbe_get_slot_info(struct ixgbe_softc *); | static void ixgbe_get_slot_info(struct ixgbe_softc *); | ||||
static void ixgbe_check_wol_support(struct ixgbe_softc *); | static void ixgbe_check_wol_support(struct ixgbe_softc *); | ||||
static void ixgbe_enable_rx_drop(struct ixgbe_softc *); | static void ixgbe_enable_rx_drop(struct ixgbe_softc *); | ||||
static void ixgbe_disable_rx_drop(struct ixgbe_softc *); | static void ixgbe_disable_rx_drop(struct ixgbe_softc *); | ||||
static void ixgbe_add_hw_stats(struct ixgbe_softc *); | static void ixgbe_add_hw_stats(struct ixgbe_softc *); | ||||
static int ixgbe_set_flowcntl(struct ixgbe_softc *, int); | static int ixgbe_set_flowcntl(struct ixgbe_softc *, int); | ||||
static int ixgbe_set_advertise(struct ixgbe_softc *, int); | static int ixgbe_set_advertise(struct ixgbe_softc *, int); | ||||
static int ixgbe_get_advertise(struct ixgbe_softc *); | static int ixgbe_get_default_advertise(struct ixgbe_softc *); | ||||
static void ixgbe_setup_vlan_hw_support(if_ctx_t); | static void ixgbe_setup_vlan_hw_support(if_ctx_t); | ||||
static void ixgbe_config_gpie(struct ixgbe_softc *); | static void ixgbe_config_gpie(struct ixgbe_softc *); | ||||
static void ixgbe_config_delay_values(struct ixgbe_softc *); | static void ixgbe_config_delay_values(struct ixgbe_softc *); | ||||
/* Sysctl handlers */ | /* Sysctl handlers */ | ||||
static int ixgbe_sysctl_flowcntl(SYSCTL_HANDLER_ARGS); | static int ixgbe_sysctl_flowcntl(SYSCTL_HANDLER_ARGS); | ||||
static int ixgbe_sysctl_advertise(SYSCTL_HANDLER_ARGS); | static int ixgbe_sysctl_advertise(SYSCTL_HANDLER_ARGS); | ||||
static int ixgbe_sysctl_interrupt_rate_handler(SYSCTL_HANDLER_ARGS); | static int ixgbe_sysctl_interrupt_rate_handler(SYSCTL_HANDLER_ARGS); | ||||
▲ Show 20 Lines • Show All 925 Lines • ▼ Show 20 Lines | ixgbe_if_attach_post(if_ctx_t ctx) | ||||
ixgbe_bypass_init(sc); | ixgbe_bypass_init(sc); | ||||
/* Display NVM and Option ROM versions */ | /* Display NVM and Option ROM versions */ | ||||
ixgbe_print_fw_version(ctx); | ixgbe_print_fw_version(ctx); | ||||
/* Set an initial dmac value */ | /* Set an initial dmac value */ | ||||
sc->dmac = 0; | sc->dmac = 0; | ||||
/* Set initial advertised speeds (if applicable) */ | /* Set initial advertised speeds (if applicable) */ | ||||
sc->advertise = ixgbe_get_advertise(sc); | sc->advertise = ixgbe_get_default_advertise(sc); | ||||
if (sc->feat_cap & IXGBE_FEATURE_SRIOV) | if (sc->feat_cap & IXGBE_FEATURE_SRIOV) | ||||
ixgbe_define_iov_schemas(dev, &error); | ixgbe_define_iov_schemas(dev, &error); | ||||
/* Add sysctls */ | /* Add sysctls */ | ||||
ixgbe_add_device_sysctls(ctx); | ixgbe_add_device_sysctls(ctx); | ||||
return (0); | return (0); | ||||
▲ Show 20 Lines • Show All 148 Lines • ▼ Show 20 Lines | if (layer & IXGBE_PHYSICAL_LAYER_10GBASE_T) | ||||
ifmedia_add(sc->media, IFM_ETHER | IFM_10G_T, 0, NULL); | ifmedia_add(sc->media, IFM_ETHER | IFM_10G_T, 0, NULL); | ||||
if (layer & IXGBE_PHYSICAL_LAYER_1000BASE_T) | if (layer & IXGBE_PHYSICAL_LAYER_1000BASE_T) | ||||
ifmedia_add(sc->media, IFM_ETHER | IFM_1000_T, 0, NULL); | ifmedia_add(sc->media, IFM_ETHER | IFM_1000_T, 0, NULL); | ||||
if (layer & IXGBE_PHYSICAL_LAYER_100BASE_TX) | if (layer & IXGBE_PHYSICAL_LAYER_100BASE_TX) | ||||
ifmedia_add(sc->media, IFM_ETHER | IFM_100_TX, 0, NULL); | ifmedia_add(sc->media, IFM_ETHER | IFM_100_TX, 0, NULL); | ||||
if (layer & IXGBE_PHYSICAL_LAYER_10BASE_T) | if (layer & IXGBE_PHYSICAL_LAYER_10BASE_T) | ||||
ifmedia_add(sc->media, IFM_ETHER | IFM_10_T, 0, NULL); | ifmedia_add(sc->media, IFM_ETHER | IFM_10_T, 0, NULL); | ||||
if (hw->mac.type == ixgbe_mac_X550) { | |||||
ifmedia_add(sc->media, IFM_ETHER | IFM_2500_T, 0, NULL); | |||||
ifmedia_add(sc->media, IFM_ETHER | IFM_5000_T, 0, NULL); | |||||
} | |||||
if (layer & IXGBE_PHYSICAL_LAYER_SFP_PLUS_CU || | if (layer & IXGBE_PHYSICAL_LAYER_SFP_PLUS_CU || | ||||
layer & IXGBE_PHYSICAL_LAYER_SFP_ACTIVE_DA) | layer & IXGBE_PHYSICAL_LAYER_SFP_ACTIVE_DA) | ||||
ifmedia_add(sc->media, IFM_ETHER | IFM_10G_TWINAX, 0, | ifmedia_add(sc->media, IFM_ETHER | IFM_10G_TWINAX, 0, | ||||
NULL); | NULL); | ||||
if (layer & IXGBE_PHYSICAL_LAYER_10GBASE_LR) { | if (layer & IXGBE_PHYSICAL_LAYER_10GBASE_LR) { | ||||
ifmedia_add(sc->media, IFM_ETHER | IFM_10G_LR, 0, NULL); | ifmedia_add(sc->media, IFM_ETHER | IFM_10G_LR, 0, NULL); | ||||
if (hw->phy.multispeed_fiber) | if (hw->phy.multispeed_fiber) | ||||
▲ Show 20 Lines • Show All 105 Lines • ▼ Show 20 Lines | if (sfp) { | ||||
if (err) | if (err) | ||||
return; | return; | ||||
autoneg = hw->phy.autoneg_advertised; | autoneg = hw->phy.autoneg_advertised; | ||||
if ((!autoneg) && (hw->mac.ops.get_link_capabilities)) | if ((!autoneg) && (hw->mac.ops.get_link_capabilities)) | ||||
err = hw->mac.ops.get_link_capabilities(hw, &autoneg, | err = hw->mac.ops.get_link_capabilities(hw, &autoneg, | ||||
&negotiate); | &negotiate); | ||||
if (err) | if (err) | ||||
return; | return; | ||||
if (hw->mac.type == ixgbe_mac_X550 && | |||||
hw->phy.autoneg_advertised == 0) { | |||||
/* | |||||
* 2.5G and 5G autonegotiation speeds on X550 | |||||
* are disabled by default due to reported | |||||
* interoperability issues with some switches. | |||||
* | |||||
* The second condition checks if any operations | |||||
* involving setting autonegotiation speeds have | |||||
* been performed prior to this ixgbe_config_link() | |||||
* call. | |||||
* | |||||
* If hw->phy.autoneg_advertised does not | |||||
* equal 0, this means that the user might have | |||||
* set autonegotiation speeds via the sysctl | |||||
* before bringing the interface up. In this | |||||
* case, we should not disable 2.5G and 5G | |||||
* since that speeds might be selected by the | |||||
* user. | |||||
* | |||||
* Otherwise (i.e. if hw->phy.autoneg_advertised | |||||
* is set to 0), it is the first time we set | |||||
* autonegotiation preferences and the default | |||||
* set of speeds should exclude 2.5G and 5G. | |||||
*/ | |||||
autoneg &= ~(IXGBE_LINK_SPEED_2_5GB_FULL | | |||||
IXGBE_LINK_SPEED_5GB_FULL); | |||||
} | |||||
if (hw->mac.ops.setup_link) | if (hw->mac.ops.setup_link) | ||||
err = hw->mac.ops.setup_link(hw, autoneg, | err = hw->mac.ops.setup_link(hw, autoneg, | ||||
sc->link_up); | sc->link_up); | ||||
} | } | ||||
} /* ixgbe_config_link */ | } /* ixgbe_config_link */ | ||||
/************************************************************************ | /************************************************************************ | ||||
* ixgbe_update_stats_counters - Update board statistics counters. | * ixgbe_update_stats_counters - Update board statistics counters. | ||||
▲ Show 20 Lines • Show All 807 Lines • ▼ Show 20 Lines | case IXGBE_LINK_SPEED_1GB_FULL: | ||||
break; | break; | ||||
case IXGBE_LINK_SPEED_100_FULL: | case IXGBE_LINK_SPEED_100_FULL: | ||||
ifmr->ifm_active |= IFM_100_TX | IFM_FDX; | ifmr->ifm_active |= IFM_100_TX | IFM_FDX; | ||||
break; | break; | ||||
case IXGBE_LINK_SPEED_10_FULL: | case IXGBE_LINK_SPEED_10_FULL: | ||||
ifmr->ifm_active |= IFM_10_T | IFM_FDX; | ifmr->ifm_active |= IFM_10_T | IFM_FDX; | ||||
break; | break; | ||||
} | } | ||||
if (hw->mac.type == ixgbe_mac_X550) | |||||
switch (sc->link_speed) { | |||||
case IXGBE_LINK_SPEED_5GB_FULL: | |||||
ifmr->ifm_active |= IFM_5000_T | IFM_FDX; | |||||
break; | |||||
case IXGBE_LINK_SPEED_2_5GB_FULL: | |||||
ifmr->ifm_active |= IFM_2500_T | IFM_FDX; | |||||
break; | |||||
} | |||||
if (layer & IXGBE_PHYSICAL_LAYER_SFP_PLUS_CU || | if (layer & IXGBE_PHYSICAL_LAYER_SFP_PLUS_CU || | ||||
layer & IXGBE_PHYSICAL_LAYER_SFP_ACTIVE_DA) | layer & IXGBE_PHYSICAL_LAYER_SFP_ACTIVE_DA) | ||||
switch (sc->link_speed) { | switch (sc->link_speed) { | ||||
case IXGBE_LINK_SPEED_10GB_FULL: | case IXGBE_LINK_SPEED_10GB_FULL: | ||||
ifmr->ifm_active |= IFM_10G_TWINAX | IFM_FDX; | ifmr->ifm_active |= IFM_10G_TWINAX | IFM_FDX; | ||||
break; | break; | ||||
} | } | ||||
if (layer & IXGBE_PHYSICAL_LAYER_10GBASE_LR) | if (layer & IXGBE_PHYSICAL_LAYER_10GBASE_LR) | ||||
▲ Show 20 Lines • Show All 160 Lines • ▼ Show 20 Lines | case IFM_1000_SX: | ||||
break; | break; | ||||
case IFM_1000_T: | case IFM_1000_T: | ||||
speed |= IXGBE_LINK_SPEED_100_FULL; | speed |= IXGBE_LINK_SPEED_100_FULL; | ||||
speed |= IXGBE_LINK_SPEED_1GB_FULL; | speed |= IXGBE_LINK_SPEED_1GB_FULL; | ||||
break; | break; | ||||
case IFM_10G_TWINAX: | case IFM_10G_TWINAX: | ||||
speed |= IXGBE_LINK_SPEED_10GB_FULL; | speed |= IXGBE_LINK_SPEED_10GB_FULL; | ||||
break; | break; | ||||
case IFM_5000_T: | |||||
speed |= IXGBE_LINK_SPEED_5GB_FULL; | |||||
break; | |||||
case IFM_2500_T: | |||||
speed |= IXGBE_LINK_SPEED_2_5GB_FULL; | |||||
break; | |||||
case IFM_100_TX: | case IFM_100_TX: | ||||
speed |= IXGBE_LINK_SPEED_100_FULL; | speed |= IXGBE_LINK_SPEED_100_FULL; | ||||
break; | break; | ||||
case IFM_10_T: | case IFM_10_T: | ||||
speed |= IXGBE_LINK_SPEED_10_FULL; | speed |= IXGBE_LINK_SPEED_10_FULL; | ||||
break; | break; | ||||
default: | default: | ||||
goto invalid; | goto invalid; | ||||
} | } | ||||
hw->mac.autotry_restart = true; | hw->mac.autotry_restart = true; | ||||
hw->mac.ops.setup_link(hw, speed, true); | hw->mac.ops.setup_link(hw, speed, true); | ||||
sc->advertise = | sc->advertise = | ||||
((speed & IXGBE_LINK_SPEED_10GB_FULL) ? 4 : 0) | | ((speed & IXGBE_LINK_SPEED_10GB_FULL) ? 0x4 : 0) | | ||||
((speed & IXGBE_LINK_SPEED_1GB_FULL) ? 2 : 0) | | ((speed & IXGBE_LINK_SPEED_5GB_FULL) ? 0x20 : 0) | | ||||
((speed & IXGBE_LINK_SPEED_100_FULL) ? 1 : 0) | | ((speed & IXGBE_LINK_SPEED_2_5GB_FULL) ? 0x10 : 0) | | ||||
((speed & IXGBE_LINK_SPEED_10_FULL) ? 8 : 0); | ((speed & IXGBE_LINK_SPEED_1GB_FULL) ? 0x2 : 0) | | ||||
((speed & IXGBE_LINK_SPEED_100_FULL) ? 0x1 : 0) | | |||||
((speed & IXGBE_LINK_SPEED_10_FULL) ? 0x8 : 0); | |||||
return (0); | return (0); | ||||
invalid: | invalid: | ||||
device_printf(iflib_get_dev(ctx), "Invalid media type!\n"); | device_printf(iflib_get_dev(ctx), "Invalid media type!\n"); | ||||
return (EINVAL); | return (EINVAL); | ||||
} /* ixgbe_if_media_change */ | } /* ixgbe_if_media_change */ | ||||
▲ Show 20 Lines • Show All 1,654 Lines • ▼ Show 20 Lines | ixgbe_sysctl_advertise(SYSCTL_HANDLER_ARGS) | ||||
return ixgbe_set_advertise(sc, advertise); | return ixgbe_set_advertise(sc, advertise); | ||||
} /* ixgbe_sysctl_advertise */ | } /* ixgbe_sysctl_advertise */ | ||||
/************************************************************************ | /************************************************************************ | ||||
* ixgbe_set_advertise - Control advertised link speed | * ixgbe_set_advertise - Control advertised link speed | ||||
* | * | ||||
* Flags: | * Flags: | ||||
* 0x1 - advertise 100 Mb | * 0x1 - advertise 100 Mb | ||||
* 0x2 - advertise 1G | * 0x2 - advertise 1G | ||||
* 0x4 - advertise 10G | * 0x4 - advertise 10G | ||||
* 0x8 - advertise 10 Mb (yes, Mb) | * 0x8 - advertise 10 Mb (yes, Mb) | ||||
* 0x10 - advertise 2.5G (disabled by default) | |||||
* 0x20 - advertise 5G (disabled by default) | |||||
* | |||||
************************************************************************/ | ************************************************************************/ | ||||
static int | static int | ||||
ixgbe_set_advertise(struct ixgbe_softc *sc, int advertise) | ixgbe_set_advertise(struct ixgbe_softc *sc, int advertise) | ||||
{ | { | ||||
device_t dev = iflib_get_dev(sc->ctx); | device_t dev = iflib_get_dev(sc->ctx); | ||||
struct ixgbe_hw *hw; | struct ixgbe_hw *hw; | ||||
ixgbe_link_speed speed = 0; | ixgbe_link_speed speed = 0; | ||||
ixgbe_link_speed link_caps = 0; | ixgbe_link_speed link_caps = 0; | ||||
Show All 11 Lines | if (hw->phy.media_type == ixgbe_media_type_backplane) | ||||
return (ENODEV); | return (ENODEV); | ||||
if (!((hw->phy.media_type == ixgbe_media_type_copper) || | if (!((hw->phy.media_type == ixgbe_media_type_copper) || | ||||
(hw->phy.multispeed_fiber))) { | (hw->phy.multispeed_fiber))) { | ||||
device_printf(dev, "Advertised speed can only be set on copper or multispeed fiber media types.\n"); | device_printf(dev, "Advertised speed can only be set on copper or multispeed fiber media types.\n"); | ||||
return (EINVAL); | return (EINVAL); | ||||
} | } | ||||
if (advertise < 0x1 || advertise > 0xF) { | if (advertise < 0x1 || advertise > 0x3F) { | ||||
device_printf(dev, "Invalid advertised speed; valid modes are 0x1 through 0xF\n"); | device_printf(dev, "Invalid advertised speed; valid modes are 0x1 through 0x3F\n"); | ||||
return (EINVAL); | return (EINVAL); | ||||
} | } | ||||
if (hw->mac.ops.get_link_capabilities) { | if (hw->mac.ops.get_link_capabilities) { | ||||
err = hw->mac.ops.get_link_capabilities(hw, &link_caps, | err = hw->mac.ops.get_link_capabilities(hw, &link_caps, | ||||
&negotiate); | &negotiate); | ||||
if (err != IXGBE_SUCCESS) { | if (err != IXGBE_SUCCESS) { | ||||
device_printf(dev, "Unable to determine supported advertise speeds\n"); | device_printf(dev, "Unable to determine supported advertise speeds\n"); | ||||
Show All 25 Lines | ixgbe_set_advertise(struct ixgbe_softc *sc, int advertise) | ||||
} | } | ||||
if (advertise & 0x8) { | if (advertise & 0x8) { | ||||
if (!(link_caps & IXGBE_LINK_SPEED_10_FULL)) { | if (!(link_caps & IXGBE_LINK_SPEED_10_FULL)) { | ||||
device_printf(dev, "Interface does not support 10Mb advertised speed\n"); | device_printf(dev, "Interface does not support 10Mb advertised speed\n"); | ||||
return (EINVAL); | return (EINVAL); | ||||
} | } | ||||
speed |= IXGBE_LINK_SPEED_10_FULL; | speed |= IXGBE_LINK_SPEED_10_FULL; | ||||
} | } | ||||
if (advertise & 0x10) { | |||||
if (!(link_caps & IXGBE_LINK_SPEED_2_5GB_FULL)) { | |||||
device_printf(dev, "Interface does not support 2.5G advertised speed\n"); | |||||
return (EINVAL); | |||||
} | |||||
speed |= IXGBE_LINK_SPEED_2_5GB_FULL; | |||||
} | |||||
if (advertise & 0x20) { | |||||
if (!(link_caps & IXGBE_LINK_SPEED_5GB_FULL)) { | |||||
device_printf(dev, "Interface does not support 5G advertised speed\n"); | |||||
return (EINVAL); | |||||
} | |||||
speed |= IXGBE_LINK_SPEED_5GB_FULL; | |||||
} | |||||
hw->mac.autotry_restart = true; | hw->mac.autotry_restart = true; | ||||
hw->mac.ops.setup_link(hw, speed, true); | hw->mac.ops.setup_link(hw, speed, true); | ||||
sc->advertise = advertise; | sc->advertise = advertise; | ||||
return (0); | return (0); | ||||
} /* ixgbe_set_advertise */ | } /* ixgbe_set_advertise */ | ||||
/************************************************************************ | /************************************************************************ | ||||
* ixgbe_get_advertise - Get current advertised speed settings | * ixgbe_get_default_advertise - Get default advertised speed settings | ||||
* | * | ||||
* Formatted for sysctl usage. | * Formatted for sysctl usage. | ||||
* Flags: | * Flags: | ||||
* 0x1 - advertise 100 Mb | * 0x1 - advertise 100 Mb | ||||
* 0x2 - advertise 1G | * 0x2 - advertise 1G | ||||
* 0x4 - advertise 10G | * 0x4 - advertise 10G | ||||
* 0x8 - advertise 10 Mb (yes, Mb) | * 0x8 - advertise 10 Mb (yes, Mb) | ||||
* 0x10 - advertise 2.5G (disabled by default) | |||||
* 0x20 - advertise 5G (disabled by default) | |||||
************************************************************************/ | ************************************************************************/ | ||||
static int | static int | ||||
ixgbe_get_advertise(struct ixgbe_softc *sc) | ixgbe_get_default_advertise(struct ixgbe_softc *sc) | ||||
{ | { | ||||
struct ixgbe_hw *hw = &sc->hw; | struct ixgbe_hw *hw = &sc->hw; | ||||
int speed; | int speed; | ||||
ixgbe_link_speed link_caps = 0; | ixgbe_link_speed link_caps = 0; | ||||
s32 err; | s32 err; | ||||
bool negotiate = false; | bool negotiate = false; | ||||
/* | /* | ||||
* Advertised speed means nothing unless it's copper or | * Advertised speed means nothing unless it's copper or | ||||
* multi-speed fiber | * multi-speed fiber | ||||
*/ | */ | ||||
if (!(hw->phy.media_type == ixgbe_media_type_copper) && | if (!(hw->phy.media_type == ixgbe_media_type_copper) && | ||||
!(hw->phy.multispeed_fiber)) | !(hw->phy.multispeed_fiber)) | ||||
return (0); | return (0); | ||||
err = hw->mac.ops.get_link_capabilities(hw, &link_caps, &negotiate); | err = hw->mac.ops.get_link_capabilities(hw, &link_caps, &negotiate); | ||||
if (err != IXGBE_SUCCESS) | if (err != IXGBE_SUCCESS) | ||||
return (0); | return (0); | ||||
if (hw->mac.type == ixgbe_mac_X550) { | |||||
/* | |||||
* 2.5G and 5G autonegotiation speeds on X550 | |||||
* are disabled by default due to reported | |||||
* interoperability issues with some switches. | |||||
*/ | |||||
link_caps &= ~(IXGBE_LINK_SPEED_2_5GB_FULL | | |||||
IXGBE_LINK_SPEED_5GB_FULL); | |||||
} | |||||
speed = | speed = | ||||
((link_caps & IXGBE_LINK_SPEED_10GB_FULL) ? 4 : 0) | | ((link_caps & IXGBE_LINK_SPEED_10GB_FULL) ? 0x4 : 0) | | ||||
((link_caps & IXGBE_LINK_SPEED_1GB_FULL) ? 2 : 0) | | ((link_caps & IXGBE_LINK_SPEED_5GB_FULL) ? 0x20 : 0) | | ||||
((link_caps & IXGBE_LINK_SPEED_100_FULL) ? 1 : 0) | | ((link_caps & IXGBE_LINK_SPEED_2_5GB_FULL) ? 0x10 : 0) | | ||||
((link_caps & IXGBE_LINK_SPEED_10_FULL) ? 8 : 0); | ((link_caps & IXGBE_LINK_SPEED_1GB_FULL) ? 0x2 : 0) | | ||||
((link_caps & IXGBE_LINK_SPEED_100_FULL) ? 0x1 : 0) | | |||||
((link_caps & IXGBE_LINK_SPEED_10_FULL) ? 0x8 : 0); | |||||
return speed; | return speed; | ||||
} /* ixgbe_get_advertise */ | } /* ixgbe_get_default_advertise */ | ||||
/************************************************************************ | /************************************************************************ | ||||
* ixgbe_sysctl_dmac - Manage DMA Coalescing | * ixgbe_sysctl_dmac - Manage DMA Coalescing | ||||
* | * | ||||
* Control values: | * Control values: | ||||
* 0/1 - off / on (use default value of 1000) | * 0/1 - off / on (use default value of 1000) | ||||
* | * | ||||
* Legal timer values are: | * Legal timer values are: | ||||
▲ Show 20 Lines • Show All 549 Lines • Show Last 20 Lines |