cxgbe(4): Updates to link configuration.
- Update struct link_settings and associated shared code. - Add tunables to control FEC and autonegotiation. All ports inherit these values as their initial settings. hw.cxgbe.fec hw.cxgbe.autoneg - Add per-port sysctls to control FEC and autonegotiation. These can be modified at any time. dev.<port>.<n>.fec dev.<port>.<n>.autoneg MFC after: 3 days Sponsored by: Chelsio Communications
This commit is contained in:
parent
bd020573f1
commit
e646fbd053
@ -289,6 +289,24 @@ The default is 3 (both rx_pause and tx_pause = 1).
|
||||
This tunable establishes the default PAUSE settings for all ports.
|
||||
Settings can be displayed and controlled on a per-port basis via the
|
||||
dev.<port>.X.pause_settings sysctl.
|
||||
.It Va hw.cxgbe.fec
|
||||
FEC (Forward Error Correction) settings.
|
||||
0 diables FEC.
|
||||
Bit 0 enables RS FEC, bit 1 enables BASE-R RS, bit 3 is reserved.
|
||||
The default is -1 which lets the driver pick a value.
|
||||
This tunable establishes the default FEC settings for all ports.
|
||||
Settings can be displayed and controlled on a per-port basis via the
|
||||
dev.<port>.X.fec sysctl.
|
||||
.It Va hw.cxgbe.autoneg
|
||||
Link autonegotiation settings.
|
||||
This tunable establishes the default autonegotiation settings for all ports.
|
||||
Settings can be displayed and controlled on a per-port basis via the
|
||||
dev.<port>.X.autoneg sysctl.
|
||||
0 disables autonegotiation.
|
||||
1 enables autonegotiation.
|
||||
The default is -1 which lets the driver pick a value.
|
||||
dev.<port>.X.autoneg is -1 for port and module combinations that do not support
|
||||
autonegotiation.
|
||||
.It Va hw.cxgbe.buffer_packing
|
||||
Allow the hardware to deliver multiple frames in the same receive buffer
|
||||
opportunistically.
|
||||
|
@ -265,7 +265,6 @@ struct port_info {
|
||||
uint8_t tx_chan;
|
||||
uint8_t rx_chan_map; /* rx MPS channel bitmap */
|
||||
|
||||
int linkdnrc;
|
||||
struct link_config link_cfg;
|
||||
|
||||
struct timeval last_refreshed;
|
||||
@ -1098,7 +1097,7 @@ int t4_os_find_pci_capability(struct adapter *, int);
|
||||
int t4_os_pci_save_state(struct adapter *);
|
||||
int t4_os_pci_restore_state(struct adapter *);
|
||||
void t4_os_portmod_changed(const struct adapter *, int);
|
||||
void t4_os_link_changed(struct adapter *, int, int, int);
|
||||
void t4_os_link_changed(struct adapter *, int, int);
|
||||
void t4_iterate(void (*)(struct adapter *, void *), void *);
|
||||
void t4_init_devnames(struct adapter *);
|
||||
void t4_add_adapter(struct adapter *);
|
||||
|
@ -62,6 +62,12 @@ enum {
|
||||
PAUSE_AUTONEG = 1 << 2
|
||||
};
|
||||
|
||||
enum {
|
||||
FEC_RS = 1 << 0,
|
||||
FEC_BASER_RS = 1 << 1,
|
||||
FEC_RESERVED = 1 << 2,
|
||||
};
|
||||
|
||||
struct port_stats {
|
||||
u64 tx_octets; /* total # of octets in good frames */
|
||||
u64 tx_frames; /* all good frames */
|
||||
@ -392,12 +398,16 @@ struct trace_params {
|
||||
struct link_config {
|
||||
unsigned short supported; /* link capabilities */
|
||||
unsigned short advertising; /* advertised capabilities */
|
||||
unsigned int requested_speed; /* speed user has requested */
|
||||
unsigned int speed; /* actual link speed */
|
||||
unsigned short lp_advertising; /* peer advertised capabilities */
|
||||
unsigned int requested_speed; /* speed user has requested */
|
||||
unsigned int speed; /* actual link speed */
|
||||
unsigned char requested_fc; /* flow control user has requested */
|
||||
unsigned char fc; /* actual link flow control */
|
||||
unsigned char requested_fec; /* FEC user has requested */
|
||||
unsigned char fec; /* actual FEC */
|
||||
unsigned char autoneg; /* autonegotiating? */
|
||||
unsigned char link_ok; /* link up? */
|
||||
unsigned char link_down_rc; /* link down reason */
|
||||
};
|
||||
|
||||
#include "adapter.h"
|
||||
|
@ -3683,9 +3683,7 @@ void t4_ulprx_read_la(struct adapter *adap, u32 *la_buf)
|
||||
}
|
||||
}
|
||||
|
||||
#define ADVERT_MASK (FW_PORT_CAP_SPEED_100M | FW_PORT_CAP_SPEED_1G |\
|
||||
FW_PORT_CAP_SPEED_10G | FW_PORT_CAP_SPEED_25G | \
|
||||
FW_PORT_CAP_SPEED_40G | FW_PORT_CAP_SPEED_100G | \
|
||||
#define ADVERT_MASK (V_FW_PORT_CAP_SPEED(M_FW_PORT_CAP_SPEED) | \
|
||||
FW_PORT_CAP_ANEG)
|
||||
|
||||
/**
|
||||
@ -3705,14 +3703,23 @@ int t4_link_l1cfg(struct adapter *adap, unsigned int mbox, unsigned int port,
|
||||
struct link_config *lc)
|
||||
{
|
||||
struct fw_port_cmd c;
|
||||
unsigned int fc = 0, mdi = V_FW_PORT_CAP_MDI(FW_PORT_CAP_MDI_AUTO);
|
||||
unsigned int mdi = V_FW_PORT_CAP_MDI(FW_PORT_CAP_MDI_AUTO);
|
||||
unsigned int fc, fec;
|
||||
|
||||
lc->link_ok = 0;
|
||||
fc = 0;
|
||||
if (lc->requested_fc & PAUSE_RX)
|
||||
fc |= FW_PORT_CAP_FC_RX;
|
||||
if (lc->requested_fc & PAUSE_TX)
|
||||
fc |= FW_PORT_CAP_FC_TX;
|
||||
|
||||
fec = 0;
|
||||
if (lc->requested_fec & FEC_RS)
|
||||
fec |= FW_PORT_CAP_FEC_RS;
|
||||
if (lc->requested_fec & FEC_BASER_RS)
|
||||
fec |= FW_PORT_CAP_FEC_BASER_RS;
|
||||
if (lc->requested_fec & FEC_RESERVED)
|
||||
fec |= FW_PORT_CAP_FEC_RESERVED;
|
||||
|
||||
memset(&c, 0, sizeof(c));
|
||||
c.op_to_portid = cpu_to_be32(V_FW_CMD_OP(FW_PORT_CMD) |
|
||||
F_FW_CMD_REQUEST | F_FW_CMD_EXEC |
|
||||
@ -3723,13 +3730,16 @@ int t4_link_l1cfg(struct adapter *adap, unsigned int mbox, unsigned int port,
|
||||
|
||||
if (!(lc->supported & FW_PORT_CAP_ANEG)) {
|
||||
c.u.l1cfg.rcap = cpu_to_be32((lc->supported & ADVERT_MASK) |
|
||||
fc);
|
||||
lc->fc = lc->requested_fc & (PAUSE_RX | PAUSE_TX);
|
||||
fc | fec);
|
||||
lc->fc = lc->requested_fc & ~PAUSE_AUTONEG;
|
||||
lc->fec = lc->requested_fec;
|
||||
} else if (lc->autoneg == AUTONEG_DISABLE) {
|
||||
c.u.l1cfg.rcap = cpu_to_be32(lc->requested_speed | fc | mdi);
|
||||
lc->fc = lc->requested_fc & (PAUSE_RX | PAUSE_TX);
|
||||
c.u.l1cfg.rcap = cpu_to_be32(lc->requested_speed |
|
||||
fc | fec | mdi);
|
||||
lc->fc = lc->requested_fc & ~PAUSE_AUTONEG;
|
||||
lc->fec = lc->requested_fec;
|
||||
} else
|
||||
c.u.l1cfg.rcap = cpu_to_be32(lc->advertising | fc | mdi);
|
||||
c.u.l1cfg.rcap = cpu_to_be32(lc->advertising | fc | fec | mdi);
|
||||
|
||||
return t4_wr_mbox(adap, mbox, &c, sizeof(c), NULL);
|
||||
}
|
||||
@ -7517,18 +7527,14 @@ int t4_handle_fw_rpl(struct adapter *adap, const __be64 *rpl)
|
||||
}
|
||||
if (link_ok != lc->link_ok || speed != lc->speed ||
|
||||
fc != lc->fc) { /* something changed */
|
||||
int reason;
|
||||
|
||||
if (!link_ok && lc->link_ok)
|
||||
reason = G_FW_PORT_CMD_LINKDNRC(stat);
|
||||
else
|
||||
reason = -1;
|
||||
|
||||
lc->link_down_rc = G_FW_PORT_CMD_LINKDNRC(stat);
|
||||
lc->link_ok = link_ok;
|
||||
lc->speed = speed;
|
||||
lc->fc = fc;
|
||||
lc->supported = be16_to_cpu(p->u.info.pcap);
|
||||
t4_os_link_changed(adap, i, link_ok, reason);
|
||||
lc->lp_advertising = be16_to_cpu(p->u.info.lpacap);
|
||||
t4_os_link_changed(adap, i, link_ok);
|
||||
}
|
||||
} else {
|
||||
CH_WARN_RATELIMIT(adap, "Unknown firmware reply %d\n", opcode);
|
||||
@ -7562,17 +7568,34 @@ static void get_pci_mode(struct adapter *adapter,
|
||||
/**
|
||||
* init_link_config - initialize a link's SW state
|
||||
* @lc: structure holding the link state
|
||||
* @caps: link capabilities
|
||||
* @pcaps: supported link capabilities
|
||||
* @acaps: advertised link capabilities
|
||||
*
|
||||
* Initializes the SW state maintained for each link, including the link's
|
||||
* capabilities and default speed/flow-control/autonegotiation settings.
|
||||
*/
|
||||
static void init_link_config(struct link_config *lc, unsigned int caps)
|
||||
static void init_link_config(struct link_config *lc, unsigned int pcaps,
|
||||
unsigned int acaps)
|
||||
{
|
||||
lc->supported = caps;
|
||||
unsigned int fec;
|
||||
|
||||
lc->supported = pcaps;
|
||||
lc->lp_advertising = 0;
|
||||
lc->requested_speed = 0;
|
||||
lc->speed = 0;
|
||||
lc->requested_fc = lc->fc = PAUSE_RX | PAUSE_TX;
|
||||
lc->link_ok = 0;
|
||||
lc->link_down_rc = 255;
|
||||
|
||||
fec = 0;
|
||||
if (acaps & FW_PORT_CAP_FEC_RS)
|
||||
fec |= FEC_RS;
|
||||
if (acaps & FW_PORT_CAP_FEC_BASER_RS)
|
||||
fec |= FEC_BASER_RS;
|
||||
if (acaps & FW_PORT_CAP_FEC_RESERVED)
|
||||
fec |= FEC_RESERVED;
|
||||
lc->requested_fec = lc->fec = fec;
|
||||
|
||||
if (lc->supported & FW_PORT_CAP_ANEG) {
|
||||
lc->advertising = lc->supported & ADVERT_MASK;
|
||||
lc->autoneg = AUTONEG_ENABLE;
|
||||
@ -8126,7 +8149,8 @@ int t4_port_init(struct adapter *adap, int mbox, int pf, int vf, int port_id)
|
||||
p->port_type = G_FW_PORT_CMD_PTYPE(ret);
|
||||
p->mod_type = G_FW_PORT_CMD_MODTYPE(ret);
|
||||
|
||||
init_link_config(&p->link_cfg, be16_to_cpu(c.u.info.pcap));
|
||||
init_link_config(&p->link_cfg, be16_to_cpu(c.u.info.pcap),
|
||||
be16_to_cpu(c.u.info.acap));
|
||||
}
|
||||
|
||||
ret = t4_alloc_vi(adap, mbox, j, pf, vf, 1, addr, &rss_size);
|
||||
|
@ -358,6 +358,24 @@ TUNABLE_STR("hw.cxgbe.config_file", t4_cfg_file, sizeof(t4_cfg_file));
|
||||
static int t4_pause_settings = PAUSE_TX | PAUSE_RX;
|
||||
TUNABLE_INT("hw.cxgbe.pause_settings", &t4_pause_settings);
|
||||
|
||||
/*
|
||||
* Forward Error Correction settings (bit 0, 1, 2 = FEC_RS, FEC_BASER_RS,
|
||||
* FEC_RESERVED respectively).
|
||||
* -1 to run with the firmware default.
|
||||
* 0 to disable FEC.
|
||||
*/
|
||||
static int t4_fec = -1;
|
||||
TUNABLE_INT("hw.cxgbe.fec", &t4_fec);
|
||||
|
||||
/*
|
||||
* Link autonegotiation.
|
||||
* -1 to run with the firmware default.
|
||||
* 0 to disable.
|
||||
* 1 to enable.
|
||||
*/
|
||||
static int t4_autoneg = -1;
|
||||
TUNABLE_INT("hw.cxgbe.autoneg", &t4_autoneg);
|
||||
|
||||
/*
|
||||
* Firmware auto-install by driver during attach (0, 1, 2 = prohibited, allowed,
|
||||
* encouraged respectively).
|
||||
@ -493,6 +511,8 @@ static int sysctl_holdoff_pktc_idx(SYSCTL_HANDLER_ARGS);
|
||||
static int sysctl_qsize_rxq(SYSCTL_HANDLER_ARGS);
|
||||
static int sysctl_qsize_txq(SYSCTL_HANDLER_ARGS);
|
||||
static int sysctl_pause_settings(SYSCTL_HANDLER_ARGS);
|
||||
static int sysctl_fec(SYSCTL_HANDLER_ARGS);
|
||||
static int sysctl_autoneg(SYSCTL_HANDLER_ARGS);
|
||||
static int sysctl_handle_t4_reg64(SYSCTL_HANDLER_ARGS);
|
||||
static int sysctl_temperature(SYSCTL_HANDLER_ARGS);
|
||||
#ifdef SBUF_DRAIN
|
||||
@ -922,6 +942,7 @@ t4_attach(device_t dev)
|
||||
n10g = n1g = 0;
|
||||
for_each_port(sc, i) {
|
||||
struct port_info *pi;
|
||||
struct link_config *lc;
|
||||
|
||||
pi = malloc(sizeof(*pi), M_CXGBE, M_ZERO | M_WAITOK);
|
||||
sc->port[i] = pi;
|
||||
@ -950,12 +971,19 @@ t4_attach(device_t dev)
|
||||
goto done;
|
||||
}
|
||||
|
||||
pi->link_cfg.requested_fc &= ~(PAUSE_TX | PAUSE_RX);
|
||||
pi->link_cfg.requested_fc |= t4_pause_settings;
|
||||
pi->link_cfg.fc &= ~(PAUSE_TX | PAUSE_RX);
|
||||
pi->link_cfg.fc |= t4_pause_settings;
|
||||
lc = &pi->link_cfg;
|
||||
lc->requested_fc &= ~(PAUSE_TX | PAUSE_RX);
|
||||
lc->requested_fc |= t4_pause_settings;
|
||||
if (t4_fec != -1) {
|
||||
lc->requested_fec = t4_fec &
|
||||
G_FW_PORT_CAP_FEC(lc->supported);
|
||||
}
|
||||
if (lc->supported & FW_PORT_CAP_ANEG && t4_autoneg != -1) {
|
||||
lc->autoneg = t4_autoneg ? AUTONEG_ENABLE :
|
||||
AUTONEG_DISABLE;
|
||||
}
|
||||
|
||||
rc = -t4_link_l1cfg(sc, sc->mbox, pi->tx_chan, &pi->link_cfg);
|
||||
rc = -t4_link_l1cfg(sc, sc->mbox, pi->tx_chan, lc);
|
||||
if (rc != 0) {
|
||||
device_printf(dev, "port %d l1cfg failed: %d\n", i, rc);
|
||||
free(pi->vi, M_CXGBE);
|
||||
@ -978,8 +1006,6 @@ t4_attach(device_t dev)
|
||||
n1g++;
|
||||
}
|
||||
|
||||
pi->linkdnrc = -1;
|
||||
|
||||
pi->dev = device_add_child(dev, sc->names->ifnet_name, -1);
|
||||
if (pi->dev == NULL) {
|
||||
device_printf(dev,
|
||||
@ -4060,8 +4086,8 @@ cxgbe_uninit_synchronized(struct vi_info *vi)
|
||||
|
||||
pi->link_cfg.link_ok = 0;
|
||||
pi->link_cfg.speed = 0;
|
||||
pi->linkdnrc = -1;
|
||||
t4_os_link_changed(sc, pi->port_id, 0, -1);
|
||||
pi->link_cfg.link_down_rc = 255;
|
||||
t4_os_link_changed(sc, pi->port_id, 0);
|
||||
|
||||
return (0);
|
||||
}
|
||||
@ -5274,8 +5300,14 @@ cxgbe_sysctls(struct port_info *pi)
|
||||
}
|
||||
|
||||
SYSCTL_ADD_PROC(ctx, children, OID_AUTO, "pause_settings",
|
||||
CTLTYPE_STRING | CTLFLAG_RW, pi, PAUSE_TX, sysctl_pause_settings,
|
||||
"A", "PAUSE settings (bit 0 = rx_pause, bit 1 = tx_pause)");
|
||||
CTLTYPE_STRING | CTLFLAG_RW, pi, 0, sysctl_pause_settings, "A",
|
||||
"PAUSE settings (bit 0 = rx_pause, bit 1 = tx_pause)");
|
||||
SYSCTL_ADD_PROC(ctx, children, OID_AUTO, "fec",
|
||||
CTLTYPE_STRING | CTLFLAG_RW, pi, 0, sysctl_fec, "A",
|
||||
"Forward Error Correction (bit 0 = RS, bit 1 = BASER_RS)");
|
||||
SYSCTL_ADD_PROC(ctx, children, OID_AUTO, "autoneg",
|
||||
CTLTYPE_INT | CTLFLAG_RW, pi, 0, sysctl_autoneg, "I",
|
||||
"autonegotiation (-1 = not supported)");
|
||||
|
||||
SYSCTL_ADD_INT(ctx, children, OID_AUTO, "max_speed", CTLFLAG_RD, NULL,
|
||||
port_top_speed(pi), "max speed (in Gbps)");
|
||||
@ -5735,12 +5767,9 @@ sysctl_pause_settings(SYSCTL_HANDLER_ARGS)
|
||||
if (rc)
|
||||
return (rc);
|
||||
if ((lc->requested_fc & (PAUSE_TX | PAUSE_RX)) != n) {
|
||||
int link_ok = lc->link_ok;
|
||||
|
||||
lc->requested_fc &= ~(PAUSE_TX | PAUSE_RX);
|
||||
lc->requested_fc |= n;
|
||||
rc = -t4_link_l1cfg(sc, sc->mbox, pi->tx_chan, lc);
|
||||
lc->link_ok = link_ok; /* restore */
|
||||
}
|
||||
end_synchronized_op(sc, 0);
|
||||
}
|
||||
@ -5748,6 +5777,97 @@ sysctl_pause_settings(SYSCTL_HANDLER_ARGS)
|
||||
return (rc);
|
||||
}
|
||||
|
||||
static int
|
||||
sysctl_fec(SYSCTL_HANDLER_ARGS)
|
||||
{
|
||||
struct port_info *pi = arg1;
|
||||
struct adapter *sc = pi->adapter;
|
||||
struct link_config *lc = &pi->link_cfg;
|
||||
int rc;
|
||||
|
||||
if (req->newptr == NULL) {
|
||||
struct sbuf *sb;
|
||||
static char *bits = "\20\1RS\2BASER_RS\3RESERVED";
|
||||
|
||||
rc = sysctl_wire_old_buffer(req, 0);
|
||||
if (rc != 0)
|
||||
return(rc);
|
||||
|
||||
sb = sbuf_new_for_sysctl(NULL, NULL, 128, req);
|
||||
if (sb == NULL)
|
||||
return (ENOMEM);
|
||||
|
||||
sbuf_printf(sb, "%b", lc->fec & M_FW_PORT_CAP_FEC, bits);
|
||||
rc = sbuf_finish(sb);
|
||||
sbuf_delete(sb);
|
||||
} else {
|
||||
char s[2];
|
||||
int n;
|
||||
|
||||
s[0] = '0' + (lc->requested_fec & M_FW_PORT_CAP_FEC);
|
||||
s[1] = 0;
|
||||
|
||||
rc = sysctl_handle_string(oidp, s, sizeof(s), req);
|
||||
if (rc != 0)
|
||||
return(rc);
|
||||
|
||||
if (s[1] != 0)
|
||||
return (EINVAL);
|
||||
if (s[0] < '0' || s[0] > '9')
|
||||
return (EINVAL); /* not a number */
|
||||
n = s[0] - '0';
|
||||
if (n & ~M_FW_PORT_CAP_FEC)
|
||||
return (EINVAL); /* some other bit is set too */
|
||||
|
||||
rc = begin_synchronized_op(sc, &pi->vi[0], SLEEP_OK | INTR_OK,
|
||||
"t4fec");
|
||||
if (rc)
|
||||
return (rc);
|
||||
if ((lc->requested_fec & M_FW_PORT_CAP_FEC) != n) {
|
||||
lc->requested_fec = n &
|
||||
G_FW_PORT_CAP_FEC(lc->supported);
|
||||
rc = -t4_link_l1cfg(sc, sc->mbox, pi->tx_chan, lc);
|
||||
}
|
||||
end_synchronized_op(sc, 0);
|
||||
}
|
||||
|
||||
return (rc);
|
||||
}
|
||||
|
||||
static int
|
||||
sysctl_autoneg(SYSCTL_HANDLER_ARGS)
|
||||
{
|
||||
struct port_info *pi = arg1;
|
||||
struct adapter *sc = pi->adapter;
|
||||
struct link_config *lc = &pi->link_cfg;
|
||||
int rc, val, old;
|
||||
|
||||
if (lc->supported & FW_PORT_CAP_ANEG)
|
||||
val = lc->autoneg == AUTONEG_ENABLE ? 1 : 0;
|
||||
else
|
||||
val = -1;
|
||||
rc = sysctl_handle_int(oidp, &val, 0, req);
|
||||
if (rc != 0 || req->newptr == NULL)
|
||||
return (rc);
|
||||
if ((lc->supported & FW_PORT_CAP_ANEG) == 0)
|
||||
return (ENOTSUP);
|
||||
|
||||
val = val ? AUTONEG_ENABLE : AUTONEG_DISABLE;
|
||||
if (lc->autoneg == val)
|
||||
return (0); /* no change */
|
||||
|
||||
rc = begin_synchronized_op(sc, &pi->vi[0], SLEEP_OK | INTR_OK,
|
||||
"t4aneg");
|
||||
if (rc)
|
||||
return (rc);
|
||||
old = lc->autoneg;
|
||||
lc->autoneg = val;
|
||||
rc = -t4_link_l1cfg(sc, sc->mbox, pi->tx_chan, lc);
|
||||
if (rc != 0)
|
||||
lc->autoneg = old;
|
||||
return (rc);
|
||||
}
|
||||
|
||||
static int
|
||||
sysctl_handle_t4_reg64(SYSCTL_HANDLER_ARGS)
|
||||
{
|
||||
@ -6493,6 +6613,7 @@ sysctl_linkdnrc(SYSCTL_HANDLER_ARGS)
|
||||
{
|
||||
int rc = 0;
|
||||
struct port_info *pi = arg1;
|
||||
struct link_config *lc = &pi->link_cfg;
|
||||
struct sbuf *sb;
|
||||
|
||||
rc = sysctl_wire_old_buffer(req, 0);
|
||||
@ -6502,10 +6623,10 @@ sysctl_linkdnrc(SYSCTL_HANDLER_ARGS)
|
||||
if (sb == NULL)
|
||||
return (ENOMEM);
|
||||
|
||||
if (pi->linkdnrc < 0)
|
||||
if (lc->link_ok || lc->link_down_rc == 255)
|
||||
sbuf_printf(sb, "n/a");
|
||||
else
|
||||
sbuf_printf(sb, "%s", t4_link_down_rc_str(pi->linkdnrc));
|
||||
sbuf_printf(sb, "%s", t4_link_down_rc_str(lc->link_down_rc));
|
||||
|
||||
rc = sbuf_finish(sb);
|
||||
sbuf_delete(sb);
|
||||
@ -8973,19 +9094,13 @@ t4_os_portmod_changed(const struct adapter *sc, int idx)
|
||||
}
|
||||
|
||||
void
|
||||
t4_os_link_changed(struct adapter *sc, int idx, int link_stat, int reason)
|
||||
t4_os_link_changed(struct adapter *sc, int idx, int link_stat)
|
||||
{
|
||||
struct port_info *pi = sc->port[idx];
|
||||
struct vi_info *vi;
|
||||
struct ifnet *ifp;
|
||||
int v;
|
||||
|
||||
if (link_stat)
|
||||
pi->linkdnrc = -1;
|
||||
else {
|
||||
if (reason >= 0)
|
||||
pi->linkdnrc = reason;
|
||||
}
|
||||
for_each_vi(pi, v, vi) {
|
||||
ifp = vi->ifp;
|
||||
if (ifp == NULL)
|
||||
|
@ -668,8 +668,6 @@ t4vf_attach(device_t dev)
|
||||
n1g++;
|
||||
}
|
||||
|
||||
pi->linkdnrc = -1;
|
||||
|
||||
pi->dev = device_add_child(dev, sc->names->vf_ifnet_name, -1);
|
||||
if (pi->dev == NULL) {
|
||||
device_printf(dev,
|
||||
|
Loading…
Reference in New Issue
Block a user