mirror of
https://github.com/freebsd/freebsd-src
synced 2024-09-06 17:18:32 +00:00
bnxt: add support for Flow control setting using sysctl
Created sysctl node dev.bnxt.0.fc with following options. A. dev.bnxt.0.fc.autoneg B. dev.bnxt.0.fc.rx C. dev.bnxt.0.fc.tx Description:- dev.bnxt.0.fc: flow ctrl dev.bnxt.0.fc.autoneg: Enable or Disable Autoneg Flow Ctrl: 0 / 1 dev.bnxt.0.fc.rx: Enable or Disable Rx Flow Ctrl: 0 / 1 dev.bnxt.0.fc.tx: Enable or Disable Tx Flow Ctrl: 0 / 1 Submitted by: Bhargava Chenna Marreddy <bhargava.marreddy@broadcom.com> Reviewed by: shurd, sbruno Approved by: sbruno (mentor) Sponsored by: Broadcom Limited Differential Revision: https://reviews.freebsd.org/D12599
This commit is contained in:
parent
ffbde5ea28
commit
7b79d6d61a
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=324964
|
@ -211,6 +211,10 @@ __FBSDID("$FreeBSD$");
|
|||
#define BNXT_HWRM_LOCK_DESTROY(_softc) mtx_destroy(&(_softc)->hwrm_lock)
|
||||
#define BNXT_HWRM_LOCK_ASSERT(_softc) mtx_assert(&(_softc)->hwrm_lock, \
|
||||
MA_OWNED)
|
||||
#define BNXT_IS_FLOW_CTRL_CHANGED(link_info) \
|
||||
((link_info->last_flow_ctrl.tx != link_info->flow_ctrl.tx) || \
|
||||
(link_info->last_flow_ctrl.rx != link_info->flow_ctrl.rx) || \
|
||||
(link_info->last_flow_ctrl.autoneg != link_info->flow_ctrl.autoneg))
|
||||
|
||||
/* Chip info */
|
||||
#define BNXT_TSO_SIZE UINT16_MAX
|
||||
|
@ -288,6 +292,12 @@ struct bnxt_bar_info {
|
|||
int rid;
|
||||
};
|
||||
|
||||
struct bnxt_flow_ctrl {
|
||||
bool rx;
|
||||
bool tx;
|
||||
bool autoneg;
|
||||
};
|
||||
|
||||
struct bnxt_link_info {
|
||||
uint8_t media_type;
|
||||
uint8_t transceiver;
|
||||
|
@ -299,10 +309,8 @@ struct bnxt_link_info {
|
|||
uint8_t last_link_up;
|
||||
uint8_t duplex;
|
||||
uint8_t last_duplex;
|
||||
uint8_t pause;
|
||||
uint8_t last_pause;
|
||||
uint8_t auto_pause;
|
||||
uint8_t force_pause;
|
||||
struct bnxt_flow_ctrl flow_ctrl;
|
||||
struct bnxt_flow_ctrl last_flow_ctrl;
|
||||
uint8_t duplex_setting;
|
||||
uint8_t auto_mode;
|
||||
#define PHY_VER_LEN 3
|
||||
|
@ -320,7 +328,6 @@ struct bnxt_link_info {
|
|||
#define BNXT_AUTONEG_SPEED 1
|
||||
#define BNXT_AUTONEG_FLOW_CTRL 2
|
||||
uint8_t req_duplex;
|
||||
uint8_t req_flow_ctrl;
|
||||
uint16_t req_link_speed;
|
||||
};
|
||||
|
||||
|
@ -596,6 +603,8 @@ struct bnxt_softc {
|
|||
struct sysctl_oid *hw_stats_oid;
|
||||
struct sysctl_ctx_list hw_lro_ctx;
|
||||
struct sysctl_oid *hw_lro_oid;
|
||||
struct sysctl_ctx_list flow_ctrl_ctx;
|
||||
struct sysctl_oid *flow_ctrl_oid;
|
||||
|
||||
struct bnxt_ver_info *ver_info;
|
||||
struct bnxt_nvram_info *nvm_info;
|
||||
|
|
|
@ -503,33 +503,28 @@ static void
|
|||
bnxt_hwrm_set_pause_common(struct bnxt_softc *softc,
|
||||
struct hwrm_port_phy_cfg_input *req)
|
||||
{
|
||||
if (softc->link_info.autoneg & BNXT_AUTONEG_FLOW_CTRL) {
|
||||
struct bnxt_link_info *link_info = &softc->link_info;
|
||||
|
||||
if (link_info->flow_ctrl.autoneg) {
|
||||
req->auto_pause =
|
||||
HWRM_PORT_PHY_CFG_INPUT_AUTO_PAUSE_AUTONEG_PAUSE;
|
||||
if (softc->link_info.req_flow_ctrl &
|
||||
HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_RX)
|
||||
if (link_info->flow_ctrl.rx)
|
||||
req->auto_pause |=
|
||||
HWRM_PORT_PHY_CFG_INPUT_AUTO_PAUSE_RX;
|
||||
if (softc->link_info.req_flow_ctrl &
|
||||
HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_TX)
|
||||
if (link_info->flow_ctrl.tx)
|
||||
req->auto_pause |=
|
||||
HWRM_PORT_PHY_CFG_INPUT_AUTO_PAUSE_RX;
|
||||
HWRM_PORT_PHY_CFG_INPUT_AUTO_PAUSE_TX;
|
||||
req->enables |=
|
||||
htole32(HWRM_PORT_PHY_CFG_INPUT_ENABLES_AUTO_PAUSE);
|
||||
} else {
|
||||
if (softc->link_info.req_flow_ctrl &
|
||||
HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_RX)
|
||||
if (link_info->flow_ctrl.rx)
|
||||
req->force_pause |=
|
||||
HWRM_PORT_PHY_CFG_INPUT_FORCE_PAUSE_RX;
|
||||
if (softc->link_info.req_flow_ctrl &
|
||||
HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_TX)
|
||||
if (link_info->flow_ctrl.tx)
|
||||
req->force_pause |=
|
||||
HWRM_PORT_PHY_CFG_INPUT_FORCE_PAUSE_TX;
|
||||
req->enables |=
|
||||
htole32(HWRM_PORT_PHY_CFG_INPUT_ENABLES_FORCE_PAUSE);
|
||||
req->auto_pause = req->force_pause;
|
||||
req->enables |= htole32(
|
||||
HWRM_PORT_PHY_CFG_INPUT_ENABLES_AUTO_PAUSE);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -563,26 +558,7 @@ bnxt_hwrm_set_eee(struct bnxt_softc *softc, struct hwrm_port_phy_cfg_input *req)
|
|||
|
||||
int
|
||||
bnxt_hwrm_set_link_setting(struct bnxt_softc *softc, bool set_pause,
|
||||
bool set_eee)
|
||||
{
|
||||
struct hwrm_port_phy_cfg_input req = {0};
|
||||
|
||||
if (softc->flags & BNXT_FLAG_NPAR)
|
||||
return ENOTSUP;
|
||||
|
||||
bnxt_hwrm_cmd_hdr_init(softc, &req, HWRM_PORT_PHY_CFG);
|
||||
if (set_pause)
|
||||
bnxt_hwrm_set_pause_common(softc, &req);
|
||||
|
||||
bnxt_hwrm_set_link_common(softc, &req);
|
||||
if (set_eee)
|
||||
bnxt_hwrm_set_eee(softc, &req);
|
||||
return hwrm_send_message(softc, &req, sizeof(req));
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
bnxt_hwrm_set_pause(struct bnxt_softc *softc)
|
||||
bool set_eee, bool set_link)
|
||||
{
|
||||
struct hwrm_port_phy_cfg_input req = {0};
|
||||
int rc;
|
||||
|
@ -591,21 +567,32 @@ bnxt_hwrm_set_pause(struct bnxt_softc *softc)
|
|||
return ENOTSUP;
|
||||
|
||||
bnxt_hwrm_cmd_hdr_init(softc, &req, HWRM_PORT_PHY_CFG);
|
||||
bnxt_hwrm_set_pause_common(softc, &req);
|
||||
|
||||
if (set_pause) {
|
||||
bnxt_hwrm_set_pause_common(softc, &req);
|
||||
|
||||
if (softc->link_info.autoneg & BNXT_AUTONEG_FLOW_CTRL)
|
||||
if (softc->link_info.flow_ctrl.autoneg)
|
||||
set_link = true;
|
||||
}
|
||||
|
||||
if (set_link)
|
||||
bnxt_hwrm_set_link_common(softc, &req);
|
||||
|
||||
|
||||
if (set_eee)
|
||||
bnxt_hwrm_set_eee(softc, &req);
|
||||
|
||||
BNXT_HWRM_LOCK(softc);
|
||||
rc = _hwrm_send_message(softc, &req, sizeof(req));
|
||||
if (!rc && !(softc->link_info.autoneg & BNXT_AUTONEG_FLOW_CTRL)) {
|
||||
/* since changing of pause setting doesn't trigger any link
|
||||
* change event, the driver needs to update the current pause
|
||||
* result upon successfully return of the phy_cfg command */
|
||||
softc->link_info.pause =
|
||||
softc->link_info.force_pause = softc->link_info.req_flow_ctrl;
|
||||
softc->link_info.auto_pause = 0;
|
||||
bnxt_report_link(softc);
|
||||
|
||||
if (!rc) {
|
||||
if (set_pause) {
|
||||
/* since changing of 'force pause' setting doesn't
|
||||
* trigger any link change event, the driver needs to
|
||||
* update the current pause result upon successfully i
|
||||
* return of the phy_cfg command */
|
||||
if (!softc->link_info.flow_ctrl.autoneg)
|
||||
bnxt_report_link(softc);
|
||||
}
|
||||
}
|
||||
BNXT_HWRM_UNLOCK(softc);
|
||||
return rc;
|
||||
|
@ -1536,10 +1523,43 @@ bnxt_hwrm_port_phy_qcfg(struct bnxt_softc *softc)
|
|||
|
||||
link_info->phy_link_status = resp->link;
|
||||
link_info->duplex = resp->duplex_cfg;
|
||||
link_info->pause = resp->pause;
|
||||
link_info->auto_mode = resp->auto_mode;
|
||||
link_info->auto_pause = resp->auto_pause;
|
||||
link_info->force_pause = resp->force_pause;
|
||||
|
||||
/*
|
||||
* When AUTO_PAUSE_AUTONEG_PAUSE bit is set to 1,
|
||||
* the advertisement of pause is enabled.
|
||||
* 1. When the auto_mode is not set to none and this flag is set to 1,
|
||||
* then the auto_pause bits on this port are being advertised and
|
||||
* autoneg pause results are being interpreted.
|
||||
* 2. When the auto_mode is not set to none and this flag is set to 0,
|
||||
* the pause is forced as indicated in force_pause, and also
|
||||
* advertised as auto_pause bits, but the autoneg results are not
|
||||
* interpreted since the pause configuration is being forced.
|
||||
* 3. When the auto_mode is set to none and this flag is set to 1,
|
||||
* auto_pause bits should be ignored and should be set to 0.
|
||||
*/
|
||||
|
||||
link_info->flow_ctrl.autoneg = false;
|
||||
link_info->flow_ctrl.tx = false;
|
||||
link_info->flow_ctrl.rx = false;
|
||||
|
||||
if ((resp->auto_mode) &&
|
||||
(resp->auto_pause & BNXT_AUTO_PAUSE_AUTONEG_PAUSE)) {
|
||||
link_info->flow_ctrl.autoneg = true;
|
||||
}
|
||||
|
||||
if (link_info->flow_ctrl.autoneg) {
|
||||
if (resp->auto_pause & BNXT_PAUSE_TX)
|
||||
link_info->flow_ctrl.tx = true;
|
||||
if (resp->auto_pause & BNXT_PAUSE_RX)
|
||||
link_info->flow_ctrl.rx = true;
|
||||
} else {
|
||||
if (resp->force_pause & BNXT_PAUSE_TX)
|
||||
link_info->flow_ctrl.tx = true;
|
||||
if (resp->force_pause & BNXT_PAUSE_RX)
|
||||
link_info->flow_ctrl.rx = true;
|
||||
}
|
||||
|
||||
link_info->duplex_setting = resp->duplex_cfg;
|
||||
if (link_info->phy_link_status == HWRM_PORT_PHY_QCFG_OUTPUT_LINK_LINK)
|
||||
link_info->link_speed = le16toh(resp->link_speed);
|
||||
|
|
|
@ -32,6 +32,11 @@ __FBSDID("$FreeBSD$");
|
|||
#ifndef _BNXT_HWRM_H
|
||||
#define _BNXT_HWRM_H
|
||||
|
||||
#define BNXT_PAUSE_TX (HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_TX)
|
||||
#define BNXT_PAUSE_RX (HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_RX)
|
||||
#define BNXT_AUTO_PAUSE_AUTONEG_PAUSE \
|
||||
(HWRM_PORT_PHY_QCFG_OUTPUT_AUTO_PAUSE_AUTONEG_PAUSE)
|
||||
|
||||
/* HWRM Function Prototypes */
|
||||
int bnxt_alloc_hwrm_dma_mem(struct bnxt_softc *softc);
|
||||
void bnxt_free_hwrm_dma_mem(struct bnxt_softc *softc);
|
||||
|
@ -45,8 +50,8 @@ int bnxt_hwrm_func_drv_unrgtr(struct bnxt_softc *softc, bool shutdown);
|
|||
int bnxt_hwrm_func_qcaps(struct bnxt_softc *softc);
|
||||
int bnxt_hwrm_func_qcfg(struct bnxt_softc *softc);
|
||||
int bnxt_hwrm_func_reset(struct bnxt_softc *softc);
|
||||
int bnxt_hwrm_set_link_setting(struct bnxt_softc *, bool set_pause,
|
||||
bool set_eee);
|
||||
int bnxt_hwrm_set_link_setting(struct bnxt_softc *softc, bool set_pause,
|
||||
bool set_eee, bool set_link);
|
||||
int bnxt_hwrm_set_pause(struct bnxt_softc *softc);
|
||||
int bnxt_hwrm_vnic_ctx_alloc(struct bnxt_softc *softc, uint16_t *ctx_id);
|
||||
int bnxt_hwrm_vnic_cfg(struct bnxt_softc *softc, struct bnxt_vnic_info *vnic);
|
||||
|
|
|
@ -94,6 +94,16 @@ bnxt_init_sysctl_ctx(struct bnxt_softc *softc)
|
|||
return ENOMEM;
|
||||
}
|
||||
|
||||
sysctl_ctx_init(&softc->flow_ctrl_ctx);
|
||||
ctx = device_get_sysctl_ctx(softc->dev);
|
||||
softc->flow_ctrl_oid = SYSCTL_ADD_NODE(ctx,
|
||||
SYSCTL_CHILDREN(device_get_sysctl_tree(softc->dev)), OID_AUTO,
|
||||
"fc", CTLFLAG_RD, 0, "flow ctrl");
|
||||
if (!softc->flow_ctrl_oid) {
|
||||
sysctl_ctx_free(&softc->flow_ctrl_ctx);
|
||||
return ENOMEM;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -132,6 +142,14 @@ bnxt_free_sysctl_ctx(struct bnxt_softc *softc)
|
|||
softc->hw_lro_oid = NULL;
|
||||
}
|
||||
|
||||
if (softc->flow_ctrl_oid != NULL) {
|
||||
orc = sysctl_ctx_free(&softc->flow_ctrl_ctx);
|
||||
if (orc)
|
||||
rc = orc;
|
||||
else
|
||||
softc->flow_ctrl_oid = NULL;
|
||||
}
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
@ -1258,6 +1276,62 @@ BNXT_HW_LRO_FN(bnxt_hw_lro_set_max_agg_segs, max_agg_segs)
|
|||
BNXT_HW_LRO_FN(bnxt_hw_lro_set_max_aggs, max_aggs)
|
||||
BNXT_HW_LRO_FN(bnxt_hw_lro_set_min_agg_len, min_agg_len)
|
||||
|
||||
#define BNXT_FLOW_CTRL_FN(fn_name, arg) \
|
||||
static int \
|
||||
fn_name(SYSCTL_HANDLER_ARGS) { \
|
||||
struct bnxt_softc *softc = arg1; \
|
||||
int rc; \
|
||||
int val; \
|
||||
\
|
||||
if (softc == NULL) \
|
||||
return EBUSY; \
|
||||
\
|
||||
val = softc->link_info.flow_ctrl.arg; \
|
||||
rc = sysctl_handle_int(oidp, &val, 0, req); \
|
||||
if (rc || !req->newptr) \
|
||||
return rc; \
|
||||
\
|
||||
if (val) \
|
||||
val = 1; \
|
||||
\
|
||||
if (softc->link_info.flow_ctrl.arg != val) { \
|
||||
softc->link_info.flow_ctrl.arg = val; \
|
||||
rc = bnxt_hwrm_set_link_setting(softc, true, false, false);\
|
||||
rc = bnxt_hwrm_port_phy_qcfg(softc); \
|
||||
} \
|
||||
\
|
||||
return rc; \
|
||||
}
|
||||
|
||||
BNXT_FLOW_CTRL_FN(bnxt_flow_ctrl_tx, tx)
|
||||
BNXT_FLOW_CTRL_FN(bnxt_flow_ctrl_rx, rx)
|
||||
BNXT_FLOW_CTRL_FN(bnxt_flow_ctrl_autoneg, autoneg)
|
||||
int
|
||||
bnxt_create_pause_fc_sysctls(struct bnxt_softc *softc)
|
||||
{
|
||||
struct sysctl_oid *oid = softc->flow_ctrl_oid;
|
||||
|
||||
if (!oid)
|
||||
return ENOMEM;
|
||||
|
||||
SYSCTL_ADD_PROC(&softc->flow_ctrl_ctx, SYSCTL_CHILDREN(oid), OID_AUTO,
|
||||
"tx", CTLTYPE_INT|CTLFLAG_RWTUN, softc, 0,
|
||||
bnxt_flow_ctrl_tx, "A",
|
||||
"Enable or Disable Tx Flow Ctrl: 0 / 1");
|
||||
|
||||
SYSCTL_ADD_PROC(&softc->flow_ctrl_ctx, SYSCTL_CHILDREN(oid), OID_AUTO,
|
||||
"rx", CTLTYPE_INT|CTLFLAG_RWTUN, softc, 0,
|
||||
bnxt_flow_ctrl_rx, "A",
|
||||
"Enable or Disable Tx Flow Ctrl: 0 / 1");
|
||||
|
||||
SYSCTL_ADD_PROC(&softc->flow_ctrl_ctx, SYSCTL_CHILDREN(oid), OID_AUTO,
|
||||
"autoneg", CTLTYPE_INT|CTLFLAG_RWTUN, softc, 0,
|
||||
bnxt_flow_ctrl_autoneg, "A",
|
||||
"Enable or Disable Autoneg Flow Ctrl: 0 / 1");
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
bnxt_create_hw_lro_sysctls(struct bnxt_softc *softc)
|
||||
{
|
||||
|
|
|
@ -41,3 +41,4 @@ int bnxt_create_nvram_sysctls(struct bnxt_nvram_info *ni);
|
|||
int bnxt_create_config_sysctls_pre(struct bnxt_softc *softc);
|
||||
int bnxt_create_config_sysctls_post(struct bnxt_softc *softc);
|
||||
int bnxt_create_hw_lro_sysctls(struct bnxt_softc *softc);
|
||||
int bnxt_create_pause_fc_sysctls(struct bnxt_softc *softc);
|
||||
|
|
|
@ -878,6 +878,10 @@ bnxt_attach_pre(if_ctx_t ctx)
|
|||
if (rc)
|
||||
goto failed;
|
||||
|
||||
rc = bnxt_create_pause_fc_sysctls(softc);
|
||||
if (rc)
|
||||
goto failed;
|
||||
|
||||
/* Initialize the vlan list */
|
||||
SLIST_INIT(&softc->vnic_info.vlan_tags);
|
||||
softc->vnic_info.vlan_tag_list.idi_vaddr = NULL;
|
||||
|
@ -1377,13 +1381,10 @@ bnxt_media_status(if_ctx_t ctx, struct ifmediareq * ifmr)
|
|||
return;
|
||||
}
|
||||
|
||||
if (link_info->pause == (HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_TX |
|
||||
HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_RX))
|
||||
ifmr->ifm_active |= (IFM_ETH_RXPAUSE | IFM_ETH_TXPAUSE);
|
||||
else if (link_info->pause == HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_TX)
|
||||
ifmr->ifm_active |= IFM_ETH_TXPAUSE;
|
||||
else if (link_info->pause == HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_RX)
|
||||
if (link_info->flow_ctrl.rx)
|
||||
ifmr->ifm_active |= IFM_ETH_RXPAUSE;
|
||||
if (link_info->flow_ctrl.tx)
|
||||
ifmr->ifm_active |= IFM_ETH_TXPAUSE;
|
||||
|
||||
bnxt_report_link(softc);
|
||||
return;
|
||||
|
@ -1471,7 +1472,7 @@ bnxt_media_change(if_ctx_t ctx)
|
|||
softc->link_info.autoneg |= BNXT_AUTONEG_SPEED;
|
||||
break;
|
||||
}
|
||||
rc = bnxt_hwrm_set_link_setting(softc, true, true);
|
||||
rc = bnxt_hwrm_set_link_setting(softc, true, true, true);
|
||||
bnxt_media_status(softc->ctx, &ifmr);
|
||||
return rc;
|
||||
}
|
||||
|
@ -2096,18 +2097,6 @@ bnxt_probe_phy(struct bnxt_softc *softc)
|
|||
if (link_info->auto_mode != HWRM_PORT_PHY_QCFG_OUTPUT_AUTO_MODE_NONE)
|
||||
link_info->autoneg |= BNXT_AUTONEG_SPEED;
|
||||
|
||||
if (link_info->auto_pause & (HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_TX |
|
||||
HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_RX)) {
|
||||
if (link_info->auto_pause == (
|
||||
HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_TX |
|
||||
HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_RX))
|
||||
link_info->autoneg |= BNXT_AUTONEG_FLOW_CTRL;
|
||||
link_info->req_flow_ctrl = link_info->auto_pause;
|
||||
} else if (link_info->force_pause & (
|
||||
HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_TX |
|
||||
HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_RX)) {
|
||||
link_info->req_flow_ctrl = link_info->force_pause;
|
||||
}
|
||||
link_info->req_duplex = link_info->duplex_setting;
|
||||
if (link_info->autoneg & BNXT_AUTONEG_SPEED)
|
||||
link_info->req_link_speed = link_info->auto_link_speed;
|
||||
|
@ -2352,47 +2341,46 @@ bnxt_update_link(struct bnxt_softc *softc, bool chng_link_state)
|
|||
void
|
||||
bnxt_report_link(struct bnxt_softc *softc)
|
||||
{
|
||||
struct bnxt_link_info *link_info = &softc->link_info;
|
||||
const char *duplex = NULL, *flow_ctrl = NULL;
|
||||
|
||||
if (softc->link_info.link_up == softc->link_info.last_link_up) {
|
||||
if (!softc->link_info.link_up)
|
||||
if (link_info->link_up == link_info->last_link_up) {
|
||||
if (!link_info->link_up)
|
||||
return;
|
||||
if (softc->link_info.pause == softc->link_info.last_pause &&
|
||||
softc->link_info.duplex == softc->link_info.last_duplex)
|
||||
if ((link_info->duplex == link_info->last_duplex) &&
|
||||
(!(BNXT_IS_FLOW_CTRL_CHANGED(link_info))))
|
||||
return;
|
||||
}
|
||||
|
||||
if (softc->link_info.link_up) {
|
||||
if (softc->link_info.duplex ==
|
||||
if (link_info->link_up) {
|
||||
if (link_info->duplex ==
|
||||
HWRM_PORT_PHY_QCFG_OUTPUT_DUPLEX_CFG_FULL)
|
||||
duplex = "full duplex";
|
||||
else
|
||||
duplex = "half duplex";
|
||||
if (softc->link_info.pause == (
|
||||
HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_TX |
|
||||
HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_RX))
|
||||
if (link_info->flow_ctrl.tx & link_info->flow_ctrl.rx)
|
||||
flow_ctrl = "FC - receive & transmit";
|
||||
else if (softc->link_info.pause ==
|
||||
HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_TX)
|
||||
else if (link_info->flow_ctrl.tx)
|
||||
flow_ctrl = "FC - transmit";
|
||||
else if (softc->link_info.pause ==
|
||||
HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_RX)
|
||||
else if (link_info->flow_ctrl.rx)
|
||||
flow_ctrl = "FC - receive";
|
||||
else
|
||||
flow_ctrl = "FC - none";
|
||||
iflib_link_state_change(softc->ctx, LINK_STATE_UP,
|
||||
IF_Gbps(100));
|
||||
device_printf(softc->dev, "Link is UP %s, %s - %d Mbps \n", duplex,
|
||||
flow_ctrl, (softc->link_info.link_speed * 100));
|
||||
flow_ctrl, (link_info->link_speed * 100));
|
||||
} else {
|
||||
iflib_link_state_change(softc->ctx, LINK_STATE_DOWN,
|
||||
bnxt_get_baudrate(&softc->link_info));
|
||||
device_printf(softc->dev, "Link is Down\n");
|
||||
}
|
||||
|
||||
softc->link_info.last_link_up = softc->link_info.link_up;
|
||||
softc->link_info.last_pause = softc->link_info.pause;
|
||||
softc->link_info.last_duplex = softc->link_info.duplex;
|
||||
link_info->last_link_up = link_info->link_up;
|
||||
link_info->last_duplex = link_info->duplex;
|
||||
link_info->last_flow_ctrl.tx = link_info->flow_ctrl.tx;
|
||||
link_info->last_flow_ctrl.rx = link_info->flow_ctrl.rx;
|
||||
link_info->last_flow_ctrl.autoneg = link_info->flow_ctrl.autoneg;
|
||||
}
|
||||
|
||||
static int
|
||||
|
|
Loading…
Reference in a new issue