Merge git://git.kernel.org/pub/scm/linux/kernel/git/davem/net
Pull networking fixes from David Miller: 1) The netlink attribute passed in to dev_set_alias() is not necessarily NULL terminated, don't use strlcpy() on it. From Alexander Potapenko. 2) Fix implementation of atomics in arm64 bpf JIT, from Daniel Borkmann. 3) Correct the release of netdevs and driver private data in certain circumstances. 4) Sanitize netlink message length properly in decnet, from Mateusz Jurczyk. 5) Don't leak kernel data in rtnl_fill_vfinfo() netlink blobs. From Yuval Mintz. 6) Hash secret is never initialized in ipv6 ILA translation code, from Arnd Bergmann. I guess those clang warnings about unused inline functions are useful for something! 7) Fix endian selection in bpf_endian.h, from Daniel Borkmann. 8) Sanitize sockaddr length before dereferncing any fields in AF_UNIX and CAIF. From Mateusz Jurczyk. 9) Fix timestamping for GMAC3 chips in stmmac driver, from Mario Molitor. 10) Do not leak netdev on dev_alloc_name() errors in mac80211, from Johannes Berg. 11) Fix locking in sctp_for_each_endpoint(), from Xin Long. 12) Fix wrong memset size on 32-bit in snmp6, from Christian Perle. 13) Fix use after free in ip_mc_clear_src(), from WANG Cong. 14) Fix regressions caused by ICMP rate limiting changes in 4.11, from Jesper Dangaard Brouer. * git://git.kernel.org/pub/scm/linux/kernel/git/davem/net: (91 commits) i40e: Fix a sleep-in-atomic bug net: don't global ICMP rate limit packets originating from loopback net/act_pedit: fix an error code net: update undefined ->ndo_change_mtu() comment net_sched: move tcf_lock down after gen_replace_estimator() caif: Add sockaddr length check before accessing sa_family in connect handler qed: fix dump of context data qmi_wwan: new Telewell and Sierra device IDs net: phy: Fix MDIO_THUNDER dependencies netconsole: Remove duplicate "netconsole: " logging prefix igmp: acquire pmc lock for ip_mc_clear_src() r8152: give the device version net: rps: fix uninitialized symbol warning mac80211: don't send SMPS action frame in AP mode when not needed mac80211/wpa: use constant time memory comparison for MACs mac80211: set bss_info data before configuring the channel mac80211: remove 5/10 MHz rate code from station MLME mac80211: Fix incorrect condition when checking rx timestamp mac80211: don't look at the PM bit of BAR frames i40e: fix handling of HW ATR eviction ...
This commit is contained in:
commit
a090bd4ff8
|
@ -122,7 +122,7 @@ associated flow of the packet. The hash is either provided by hardware
|
|||
or will be computed in the stack. Capable hardware can pass the hash in
|
||||
the receive descriptor for the packet; this would usually be the same
|
||||
hash used for RSS (e.g. computed Toeplitz hash). The hash is saved in
|
||||
skb->rx_hash and can be used elsewhere in the stack as a hash of the
|
||||
skb->hash and can be used elsewhere in the stack as a hash of the
|
||||
packet’s flow.
|
||||
|
||||
Each receive hardware queue has an associated list of CPUs to which
|
||||
|
|
|
@ -36,6 +36,7 @@ int bpf_jit_enable __read_mostly;
|
|||
#define TMP_REG_1 (MAX_BPF_JIT_REG + 0)
|
||||
#define TMP_REG_2 (MAX_BPF_JIT_REG + 1)
|
||||
#define TCALL_CNT (MAX_BPF_JIT_REG + 2)
|
||||
#define TMP_REG_3 (MAX_BPF_JIT_REG + 3)
|
||||
|
||||
/* Map BPF registers to A64 registers */
|
||||
static const int bpf2a64[] = {
|
||||
|
@ -57,6 +58,7 @@ static const int bpf2a64[] = {
|
|||
/* temporary registers for internal BPF JIT */
|
||||
[TMP_REG_1] = A64_R(10),
|
||||
[TMP_REG_2] = A64_R(11),
|
||||
[TMP_REG_3] = A64_R(12),
|
||||
/* tail_call_cnt */
|
||||
[TCALL_CNT] = A64_R(26),
|
||||
/* temporary register for blinding constants */
|
||||
|
@ -319,6 +321,7 @@ static int build_insn(const struct bpf_insn *insn, struct jit_ctx *ctx)
|
|||
const u8 src = bpf2a64[insn->src_reg];
|
||||
const u8 tmp = bpf2a64[TMP_REG_1];
|
||||
const u8 tmp2 = bpf2a64[TMP_REG_2];
|
||||
const u8 tmp3 = bpf2a64[TMP_REG_3];
|
||||
const s16 off = insn->off;
|
||||
const s32 imm = insn->imm;
|
||||
const int i = insn - ctx->prog->insnsi;
|
||||
|
@ -689,10 +692,10 @@ emit_cond_jmp:
|
|||
emit(A64_PRFM(tmp, PST, L1, STRM), ctx);
|
||||
emit(A64_LDXR(isdw, tmp2, tmp), ctx);
|
||||
emit(A64_ADD(isdw, tmp2, tmp2, src), ctx);
|
||||
emit(A64_STXR(isdw, tmp2, tmp, tmp2), ctx);
|
||||
emit(A64_STXR(isdw, tmp2, tmp, tmp3), ctx);
|
||||
jmp_offset = -3;
|
||||
check_imm19(jmp_offset);
|
||||
emit(A64_CBNZ(0, tmp2, jmp_offset), ctx);
|
||||
emit(A64_CBNZ(0, tmp3, jmp_offset), ctx);
|
||||
break;
|
||||
|
||||
/* R0 = ntohx(*(size *)(((struct sk_buff *)R6)->data + imm)) */
|
||||
|
|
|
@ -1066,7 +1066,7 @@ static void ssip_pn_setup(struct net_device *dev)
|
|||
dev->addr_len = 1;
|
||||
dev->tx_queue_len = SSIP_TXQUEUE_LEN;
|
||||
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->header_ops = &phonet_header_ops;
|
||||
}
|
||||
|
||||
|
|
|
@ -90,10 +90,13 @@ enum ad_link_speed_type {
|
|||
AD_LINK_SPEED_100MBPS,
|
||||
AD_LINK_SPEED_1000MBPS,
|
||||
AD_LINK_SPEED_2500MBPS,
|
||||
AD_LINK_SPEED_5000MBPS,
|
||||
AD_LINK_SPEED_10000MBPS,
|
||||
AD_LINK_SPEED_14000MBPS,
|
||||
AD_LINK_SPEED_20000MBPS,
|
||||
AD_LINK_SPEED_25000MBPS,
|
||||
AD_LINK_SPEED_40000MBPS,
|
||||
AD_LINK_SPEED_50000MBPS,
|
||||
AD_LINK_SPEED_56000MBPS,
|
||||
AD_LINK_SPEED_100000MBPS,
|
||||
};
|
||||
|
@ -259,10 +262,13 @@ static inline int __check_agg_selection_timer(struct port *port)
|
|||
* %AD_LINK_SPEED_100MBPS,
|
||||
* %AD_LINK_SPEED_1000MBPS,
|
||||
* %AD_LINK_SPEED_2500MBPS,
|
||||
* %AD_LINK_SPEED_5000MBPS,
|
||||
* %AD_LINK_SPEED_10000MBPS
|
||||
* %AD_LINK_SPEED_14000MBPS,
|
||||
* %AD_LINK_SPEED_20000MBPS
|
||||
* %AD_LINK_SPEED_25000MBPS
|
||||
* %AD_LINK_SPEED_40000MBPS
|
||||
* %AD_LINK_SPEED_50000MBPS
|
||||
* %AD_LINK_SPEED_56000MBPS
|
||||
* %AD_LINK_SPEED_100000MBPS
|
||||
*/
|
||||
|
@ -296,10 +302,18 @@ static u16 __get_link_speed(struct port *port)
|
|||
speed = AD_LINK_SPEED_2500MBPS;
|
||||
break;
|
||||
|
||||
case SPEED_5000:
|
||||
speed = AD_LINK_SPEED_5000MBPS;
|
||||
break;
|
||||
|
||||
case SPEED_10000:
|
||||
speed = AD_LINK_SPEED_10000MBPS;
|
||||
break;
|
||||
|
||||
case SPEED_14000:
|
||||
speed = AD_LINK_SPEED_14000MBPS;
|
||||
break;
|
||||
|
||||
case SPEED_20000:
|
||||
speed = AD_LINK_SPEED_20000MBPS;
|
||||
break;
|
||||
|
@ -312,6 +326,10 @@ static u16 __get_link_speed(struct port *port)
|
|||
speed = AD_LINK_SPEED_40000MBPS;
|
||||
break;
|
||||
|
||||
case SPEED_50000:
|
||||
speed = AD_LINK_SPEED_50000MBPS;
|
||||
break;
|
||||
|
||||
case SPEED_56000:
|
||||
speed = AD_LINK_SPEED_56000MBPS;
|
||||
break;
|
||||
|
@ -707,9 +725,15 @@ static u32 __get_agg_bandwidth(struct aggregator *aggregator)
|
|||
case AD_LINK_SPEED_2500MBPS:
|
||||
bandwidth = nports * 2500;
|
||||
break;
|
||||
case AD_LINK_SPEED_5000MBPS:
|
||||
bandwidth = nports * 5000;
|
||||
break;
|
||||
case AD_LINK_SPEED_10000MBPS:
|
||||
bandwidth = nports * 10000;
|
||||
break;
|
||||
case AD_LINK_SPEED_14000MBPS:
|
||||
bandwidth = nports * 14000;
|
||||
break;
|
||||
case AD_LINK_SPEED_20000MBPS:
|
||||
bandwidth = nports * 20000;
|
||||
break;
|
||||
|
@ -719,6 +743,9 @@ static u32 __get_agg_bandwidth(struct aggregator *aggregator)
|
|||
case AD_LINK_SPEED_40000MBPS:
|
||||
bandwidth = nports * 40000;
|
||||
break;
|
||||
case AD_LINK_SPEED_50000MBPS:
|
||||
bandwidth = nports * 50000;
|
||||
break;
|
||||
case AD_LINK_SPEED_56000MBPS:
|
||||
bandwidth = nports * 56000;
|
||||
break;
|
||||
|
|
|
@ -4192,7 +4192,6 @@ static void bond_destructor(struct net_device *bond_dev)
|
|||
struct bonding *bond = netdev_priv(bond_dev);
|
||||
if (bond->wq)
|
||||
destroy_workqueue(bond->wq);
|
||||
free_netdev(bond_dev);
|
||||
}
|
||||
|
||||
void bond_setup(struct net_device *bond_dev)
|
||||
|
@ -4212,7 +4211,8 @@ void bond_setup(struct net_device *bond_dev)
|
|||
bond_dev->netdev_ops = &bond_netdev_ops;
|
||||
bond_dev->ethtool_ops = &bond_ethtool_ops;
|
||||
|
||||
bond_dev->destructor = bond_destructor;
|
||||
bond_dev->needs_free_netdev = true;
|
||||
bond_dev->priv_destructor = bond_destructor;
|
||||
|
||||
SET_NETDEV_DEVTYPE(bond_dev, &bond_type);
|
||||
|
||||
|
@ -4736,7 +4736,7 @@ int bond_create(struct net *net, const char *name)
|
|||
|
||||
rtnl_unlock();
|
||||
if (res < 0)
|
||||
bond_destructor(bond_dev);
|
||||
free_netdev(bond_dev);
|
||||
return res;
|
||||
}
|
||||
|
||||
|
|
|
@ -1121,7 +1121,7 @@ static void cfhsi_setup(struct net_device *dev)
|
|||
dev->flags = IFF_POINTOPOINT | IFF_NOARP;
|
||||
dev->mtu = CFHSI_MAX_CAIF_FRAME_SZ;
|
||||
dev->priv_flags |= IFF_NO_QUEUE;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->netdev_ops = &cfhsi_netdevops;
|
||||
for (i = 0; i < CFHSI_PRIO_LAST; ++i)
|
||||
skb_queue_head_init(&cfhsi->qhead[i]);
|
||||
|
|
|
@ -428,7 +428,7 @@ static void caifdev_setup(struct net_device *dev)
|
|||
dev->flags = IFF_POINTOPOINT | IFF_NOARP;
|
||||
dev->mtu = CAIF_MAX_MTU;
|
||||
dev->priv_flags |= IFF_NO_QUEUE;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
skb_queue_head_init(&serdev->head);
|
||||
serdev->common.link_select = CAIF_LINK_LOW_LATENCY;
|
||||
serdev->common.use_frag = true;
|
||||
|
|
|
@ -712,7 +712,7 @@ static void cfspi_setup(struct net_device *dev)
|
|||
dev->flags = IFF_NOARP | IFF_POINTOPOINT;
|
||||
dev->priv_flags |= IFF_NO_QUEUE;
|
||||
dev->mtu = SPI_MAX_PAYLOAD_SIZE;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
skb_queue_head_init(&cfspi->qhead);
|
||||
skb_queue_head_init(&cfspi->chead);
|
||||
cfspi->cfdev.link_select = CAIF_LINK_HIGH_BANDW;
|
||||
|
|
|
@ -617,7 +617,7 @@ static void cfv_netdev_setup(struct net_device *netdev)
|
|||
netdev->tx_queue_len = 100;
|
||||
netdev->flags = IFF_POINTOPOINT | IFF_NOARP;
|
||||
netdev->mtu = CFV_DEF_MTU_SIZE;
|
||||
netdev->destructor = free_netdev;
|
||||
netdev->needs_free_netdev = true;
|
||||
}
|
||||
|
||||
/* Create debugfs counters for the device */
|
||||
|
|
|
@ -391,6 +391,9 @@ void can_change_state(struct net_device *dev, struct can_frame *cf,
|
|||
can_update_state_error_stats(dev, new_state);
|
||||
priv->state = new_state;
|
||||
|
||||
if (!cf)
|
||||
return;
|
||||
|
||||
if (unlikely(new_state == CAN_STATE_BUS_OFF)) {
|
||||
cf->can_id |= CAN_ERR_BUSOFF;
|
||||
return;
|
||||
|
|
|
@ -489,7 +489,7 @@ int peak_canfd_handle_msgs_list(struct peak_canfd_priv *priv,
|
|||
struct pucan_rx_msg *msg_list, int msg_count)
|
||||
{
|
||||
void *msg_ptr = msg_list;
|
||||
int i, msg_size;
|
||||
int i, msg_size = 0;
|
||||
|
||||
for (i = 0; i < msg_count; i++) {
|
||||
msg_size = peak_canfd_handle_msg(priv, msg_ptr);
|
||||
|
|
|
@ -417,7 +417,7 @@ static int slc_open(struct net_device *dev)
|
|||
static void slc_free_netdev(struct net_device *dev)
|
||||
{
|
||||
int i = dev->base_addr;
|
||||
free_netdev(dev);
|
||||
|
||||
slcan_devs[i] = NULL;
|
||||
}
|
||||
|
||||
|
@ -436,7 +436,8 @@ static const struct net_device_ops slc_netdev_ops = {
|
|||
static void slc_setup(struct net_device *dev)
|
||||
{
|
||||
dev->netdev_ops = &slc_netdev_ops;
|
||||
dev->destructor = slc_free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->priv_destructor = slc_free_netdev;
|
||||
|
||||
dev->hard_header_len = 0;
|
||||
dev->addr_len = 0;
|
||||
|
@ -761,8 +762,6 @@ static void __exit slcan_exit(void)
|
|||
if (sl->tty) {
|
||||
printk(KERN_ERR "%s: tty discipline still running\n",
|
||||
dev->name);
|
||||
/* Intentionally leak the control block. */
|
||||
dev->destructor = NULL;
|
||||
}
|
||||
|
||||
unregister_netdev(dev);
|
||||
|
|
|
@ -265,6 +265,8 @@ static int gs_cmd_reset(struct gs_usb *gsusb, struct gs_can *gsdev)
|
|||
sizeof(*dm),
|
||||
1000);
|
||||
|
||||
kfree(dm);
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
|
|
@ -908,8 +908,6 @@ static int peak_usb_probe(struct usb_interface *intf,
|
|||
const struct peak_usb_adapter *peak_usb_adapter = NULL;
|
||||
int i, err = -ENOMEM;
|
||||
|
||||
usb_dev = interface_to_usbdev(intf);
|
||||
|
||||
/* get corresponding PCAN-USB adapter */
|
||||
for (i = 0; i < ARRAY_SIZE(peak_usb_adapters_list); i++)
|
||||
if (peak_usb_adapters_list[i]->device_id == usb_id_product) {
|
||||
|
@ -920,7 +918,7 @@ static int peak_usb_probe(struct usb_interface *intf,
|
|||
if (!peak_usb_adapter) {
|
||||
/* should never come except device_id bad usage in this file */
|
||||
pr_err("%s: didn't find device id. 0x%x in devices list\n",
|
||||
PCAN_USB_DRIVER_NAME, usb_dev->descriptor.idProduct);
|
||||
PCAN_USB_DRIVER_NAME, usb_id_product);
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
|
|
|
@ -152,7 +152,7 @@ static const struct net_device_ops vcan_netdev_ops = {
|
|||
static void vcan_setup(struct net_device *dev)
|
||||
{
|
||||
dev->type = ARPHRD_CAN;
|
||||
dev->mtu = CAN_MTU;
|
||||
dev->mtu = CANFD_MTU;
|
||||
dev->hard_header_len = 0;
|
||||
dev->addr_len = 0;
|
||||
dev->tx_queue_len = 0;
|
||||
|
@ -163,7 +163,7 @@ static void vcan_setup(struct net_device *dev)
|
|||
dev->flags |= IFF_ECHO;
|
||||
|
||||
dev->netdev_ops = &vcan_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
}
|
||||
|
||||
static struct rtnl_link_ops vcan_link_ops __read_mostly = {
|
||||
|
|
|
@ -150,13 +150,13 @@ static const struct net_device_ops vxcan_netdev_ops = {
|
|||
static void vxcan_setup(struct net_device *dev)
|
||||
{
|
||||
dev->type = ARPHRD_CAN;
|
||||
dev->mtu = CAN_MTU;
|
||||
dev->mtu = CANFD_MTU;
|
||||
dev->hard_header_len = 0;
|
||||
dev->addr_len = 0;
|
||||
dev->tx_queue_len = 0;
|
||||
dev->flags = (IFF_NOARP|IFF_ECHO);
|
||||
dev->netdev_ops = &vxcan_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
}
|
||||
|
||||
/* forward declaration for rtnl_create_link() */
|
||||
|
|
|
@ -328,7 +328,6 @@ static void dummy_free_netdev(struct net_device *dev)
|
|||
struct dummy_priv *priv = netdev_priv(dev);
|
||||
|
||||
kfree(priv->vfinfo);
|
||||
free_netdev(dev);
|
||||
}
|
||||
|
||||
static void dummy_setup(struct net_device *dev)
|
||||
|
@ -338,7 +337,8 @@ static void dummy_setup(struct net_device *dev)
|
|||
/* Initialize the device structure. */
|
||||
dev->netdev_ops = &dummy_netdev_ops;
|
||||
dev->ethtool_ops = &dummy_ethtool_ops;
|
||||
dev->destructor = dummy_free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->priv_destructor = dummy_free_netdev;
|
||||
|
||||
/* Fill in device structure with ethernet-generic values. */
|
||||
dev->flags |= IFF_NOARP;
|
||||
|
|
|
@ -61,6 +61,8 @@
|
|||
|
||||
#define ENA_MMIO_READ_TIMEOUT 0xFFFFFFFF
|
||||
|
||||
#define ENA_REGS_ADMIN_INTR_MASK 1
|
||||
|
||||
/*****************************************************************************/
|
||||
/*****************************************************************************/
|
||||
/*****************************************************************************/
|
||||
|
@ -232,11 +234,9 @@ static struct ena_comp_ctx *__ena_com_submit_admin_cmd(struct ena_com_admin_queu
|
|||
tail_masked = admin_queue->sq.tail & queue_size_mask;
|
||||
|
||||
/* In case of queue FULL */
|
||||
cnt = admin_queue->sq.tail - admin_queue->sq.head;
|
||||
cnt = atomic_read(&admin_queue->outstanding_cmds);
|
||||
if (cnt >= admin_queue->q_depth) {
|
||||
pr_debug("admin queue is FULL (tail %d head %d depth: %d)\n",
|
||||
admin_queue->sq.tail, admin_queue->sq.head,
|
||||
admin_queue->q_depth);
|
||||
pr_debug("admin queue is full.\n");
|
||||
admin_queue->stats.out_of_space++;
|
||||
return ERR_PTR(-ENOSPC);
|
||||
}
|
||||
|
@ -508,15 +508,20 @@ static int ena_com_comp_status_to_errno(u8 comp_status)
|
|||
static int ena_com_wait_and_process_admin_cq_polling(struct ena_comp_ctx *comp_ctx,
|
||||
struct ena_com_admin_queue *admin_queue)
|
||||
{
|
||||
unsigned long flags;
|
||||
u32 start_time;
|
||||
unsigned long flags, timeout;
|
||||
int ret;
|
||||
|
||||
start_time = ((u32)jiffies_to_usecs(jiffies));
|
||||
timeout = jiffies + ADMIN_CMD_TIMEOUT_US;
|
||||
|
||||
while (comp_ctx->status == ENA_CMD_SUBMITTED) {
|
||||
if ((((u32)jiffies_to_usecs(jiffies)) - start_time) >
|
||||
ADMIN_CMD_TIMEOUT_US) {
|
||||
while (1) {
|
||||
spin_lock_irqsave(&admin_queue->q_lock, flags);
|
||||
ena_com_handle_admin_completion(admin_queue);
|
||||
spin_unlock_irqrestore(&admin_queue->q_lock, flags);
|
||||
|
||||
if (comp_ctx->status != ENA_CMD_SUBMITTED)
|
||||
break;
|
||||
|
||||
if (time_is_before_jiffies(timeout)) {
|
||||
pr_err("Wait for completion (polling) timeout\n");
|
||||
/* ENA didn't have any completion */
|
||||
spin_lock_irqsave(&admin_queue->q_lock, flags);
|
||||
|
@ -528,10 +533,6 @@ static int ena_com_wait_and_process_admin_cq_polling(struct ena_comp_ctx *comp_c
|
|||
goto err;
|
||||
}
|
||||
|
||||
spin_lock_irqsave(&admin_queue->q_lock, flags);
|
||||
ena_com_handle_admin_completion(admin_queue);
|
||||
spin_unlock_irqrestore(&admin_queue->q_lock, flags);
|
||||
|
||||
msleep(100);
|
||||
}
|
||||
|
||||
|
@ -1455,6 +1456,12 @@ void ena_com_admin_destroy(struct ena_com_dev *ena_dev)
|
|||
|
||||
void ena_com_set_admin_polling_mode(struct ena_com_dev *ena_dev, bool polling)
|
||||
{
|
||||
u32 mask_value = 0;
|
||||
|
||||
if (polling)
|
||||
mask_value = ENA_REGS_ADMIN_INTR_MASK;
|
||||
|
||||
writel(mask_value, ena_dev->reg_bar + ENA_REGS_INTR_MASK_OFF);
|
||||
ena_dev->admin_queue.polling = polling;
|
||||
}
|
||||
|
||||
|
|
|
@ -80,7 +80,6 @@ static const struct ena_stats ena_stats_tx_strings[] = {
|
|||
ENA_STAT_TX_ENTRY(tx_poll),
|
||||
ENA_STAT_TX_ENTRY(doorbells),
|
||||
ENA_STAT_TX_ENTRY(prepare_ctx_err),
|
||||
ENA_STAT_TX_ENTRY(missing_tx_comp),
|
||||
ENA_STAT_TX_ENTRY(bad_req_id),
|
||||
};
|
||||
|
||||
|
@ -94,6 +93,7 @@ static const struct ena_stats ena_stats_rx_strings[] = {
|
|||
ENA_STAT_RX_ENTRY(dma_mapping_err),
|
||||
ENA_STAT_RX_ENTRY(bad_desc_num),
|
||||
ENA_STAT_RX_ENTRY(rx_copybreak_pkt),
|
||||
ENA_STAT_RX_ENTRY(empty_rx_ring),
|
||||
};
|
||||
|
||||
static const struct ena_stats ena_stats_ena_com_strings[] = {
|
||||
|
|
|
@ -190,6 +190,7 @@ static void ena_init_io_rings(struct ena_adapter *adapter)
|
|||
rxr->sgl_size = adapter->max_rx_sgl_size;
|
||||
rxr->smoothed_interval =
|
||||
ena_com_get_nonadaptive_moderation_interval_rx(ena_dev);
|
||||
rxr->empty_rx_queue = 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1078,6 +1079,26 @@ inline void ena_adjust_intr_moderation(struct ena_ring *rx_ring,
|
|||
rx_ring->per_napi_bytes = 0;
|
||||
}
|
||||
|
||||
static inline void ena_unmask_interrupt(struct ena_ring *tx_ring,
|
||||
struct ena_ring *rx_ring)
|
||||
{
|
||||
struct ena_eth_io_intr_reg intr_reg;
|
||||
|
||||
/* Update intr register: rx intr delay,
|
||||
* tx intr delay and interrupt unmask
|
||||
*/
|
||||
ena_com_update_intr_reg(&intr_reg,
|
||||
rx_ring->smoothed_interval,
|
||||
tx_ring->smoothed_interval,
|
||||
true);
|
||||
|
||||
/* It is a shared MSI-X.
|
||||
* Tx and Rx CQ have pointer to it.
|
||||
* So we use one of them to reach the intr reg
|
||||
*/
|
||||
ena_com_unmask_intr(rx_ring->ena_com_io_cq, &intr_reg);
|
||||
}
|
||||
|
||||
static inline void ena_update_ring_numa_node(struct ena_ring *tx_ring,
|
||||
struct ena_ring *rx_ring)
|
||||
{
|
||||
|
@ -1108,7 +1129,6 @@ static int ena_io_poll(struct napi_struct *napi, int budget)
|
|||
{
|
||||
struct ena_napi *ena_napi = container_of(napi, struct ena_napi, napi);
|
||||
struct ena_ring *tx_ring, *rx_ring;
|
||||
struct ena_eth_io_intr_reg intr_reg;
|
||||
|
||||
u32 tx_work_done;
|
||||
u32 rx_work_done;
|
||||
|
@ -1149,22 +1169,9 @@ static int ena_io_poll(struct napi_struct *napi, int budget)
|
|||
if (ena_com_get_adaptive_moderation_enabled(rx_ring->ena_dev))
|
||||
ena_adjust_intr_moderation(rx_ring, tx_ring);
|
||||
|
||||
/* Update intr register: rx intr delay,
|
||||
* tx intr delay and interrupt unmask
|
||||
*/
|
||||
ena_com_update_intr_reg(&intr_reg,
|
||||
rx_ring->smoothed_interval,
|
||||
tx_ring->smoothed_interval,
|
||||
true);
|
||||
|
||||
/* It is a shared MSI-X.
|
||||
* Tx and Rx CQ have pointer to it.
|
||||
* So we use one of them to reach the intr reg
|
||||
*/
|
||||
ena_com_unmask_intr(rx_ring->ena_com_io_cq, &intr_reg);
|
||||
ena_unmask_interrupt(tx_ring, rx_ring);
|
||||
}
|
||||
|
||||
|
||||
ena_update_ring_numa_node(tx_ring, rx_ring);
|
||||
|
||||
ret = rx_work_done;
|
||||
|
@ -1485,6 +1492,11 @@ static int ena_up_complete(struct ena_adapter *adapter)
|
|||
|
||||
ena_napi_enable_all(adapter);
|
||||
|
||||
/* Enable completion queues interrupt */
|
||||
for (i = 0; i < adapter->num_queues; i++)
|
||||
ena_unmask_interrupt(&adapter->tx_ring[i],
|
||||
&adapter->rx_ring[i]);
|
||||
|
||||
/* schedule napi in case we had pending packets
|
||||
* from the last time we disable napi
|
||||
*/
|
||||
|
@ -1532,6 +1544,7 @@ static int ena_create_io_tx_queue(struct ena_adapter *adapter, int qid)
|
|||
"Failed to get TX queue handlers. TX queue num %d rc: %d\n",
|
||||
qid, rc);
|
||||
ena_com_destroy_io_queue(ena_dev, ena_qid);
|
||||
return rc;
|
||||
}
|
||||
|
||||
ena_com_update_numa_node(tx_ring->ena_com_io_cq, ctx.numa_node);
|
||||
|
@ -1596,6 +1609,7 @@ static int ena_create_io_rx_queue(struct ena_adapter *adapter, int qid)
|
|||
"Failed to get RX queue handlers. RX queue num %d rc: %d\n",
|
||||
qid, rc);
|
||||
ena_com_destroy_io_queue(ena_dev, ena_qid);
|
||||
return rc;
|
||||
}
|
||||
|
||||
ena_com_update_numa_node(rx_ring->ena_com_io_cq, ctx.numa_node);
|
||||
|
@ -1981,6 +1995,7 @@ static netdev_tx_t ena_start_xmit(struct sk_buff *skb, struct net_device *dev)
|
|||
|
||||
tx_info->tx_descs = nb_hw_desc;
|
||||
tx_info->last_jiffies = jiffies;
|
||||
tx_info->print_once = 0;
|
||||
|
||||
tx_ring->next_to_use = ENA_TX_RING_IDX_NEXT(next_to_use,
|
||||
tx_ring->ring_size);
|
||||
|
@ -2550,13 +2565,44 @@ err:
|
|||
"Reset attempt failed. Can not reset the device\n");
|
||||
}
|
||||
|
||||
static void check_for_missing_tx_completions(struct ena_adapter *adapter)
|
||||
static int check_missing_comp_in_queue(struct ena_adapter *adapter,
|
||||
struct ena_ring *tx_ring)
|
||||
{
|
||||
struct ena_tx_buffer *tx_buf;
|
||||
unsigned long last_jiffies;
|
||||
u32 missed_tx = 0;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < tx_ring->ring_size; i++) {
|
||||
tx_buf = &tx_ring->tx_buffer_info[i];
|
||||
last_jiffies = tx_buf->last_jiffies;
|
||||
if (unlikely(last_jiffies &&
|
||||
time_is_before_jiffies(last_jiffies + TX_TIMEOUT))) {
|
||||
if (!tx_buf->print_once)
|
||||
netif_notice(adapter, tx_err, adapter->netdev,
|
||||
"Found a Tx that wasn't completed on time, qid %d, index %d.\n",
|
||||
tx_ring->qid, i);
|
||||
|
||||
tx_buf->print_once = 1;
|
||||
missed_tx++;
|
||||
|
||||
if (unlikely(missed_tx > MAX_NUM_OF_TIMEOUTED_PACKETS)) {
|
||||
netif_err(adapter, tx_err, adapter->netdev,
|
||||
"The number of lost tx completions is above the threshold (%d > %d). Reset the device\n",
|
||||
missed_tx, MAX_NUM_OF_TIMEOUTED_PACKETS);
|
||||
set_bit(ENA_FLAG_TRIGGER_RESET, &adapter->flags);
|
||||
return -EIO;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void check_for_missing_tx_completions(struct ena_adapter *adapter)
|
||||
{
|
||||
struct ena_ring *tx_ring;
|
||||
int i, j, budget;
|
||||
u32 missed_tx;
|
||||
int i, budget, rc;
|
||||
|
||||
/* Make sure the driver doesn't turn the device in other process */
|
||||
smp_rmb();
|
||||
|
@ -2572,31 +2618,9 @@ static void check_for_missing_tx_completions(struct ena_adapter *adapter)
|
|||
for (i = adapter->last_monitored_tx_qid; i < adapter->num_queues; i++) {
|
||||
tx_ring = &adapter->tx_ring[i];
|
||||
|
||||
for (j = 0; j < tx_ring->ring_size; j++) {
|
||||
tx_buf = &tx_ring->tx_buffer_info[j];
|
||||
last_jiffies = tx_buf->last_jiffies;
|
||||
if (unlikely(last_jiffies && time_is_before_jiffies(last_jiffies + TX_TIMEOUT))) {
|
||||
netif_notice(adapter, tx_err, adapter->netdev,
|
||||
"Found a Tx that wasn't completed on time, qid %d, index %d.\n",
|
||||
tx_ring->qid, j);
|
||||
|
||||
u64_stats_update_begin(&tx_ring->syncp);
|
||||
missed_tx = tx_ring->tx_stats.missing_tx_comp++;
|
||||
u64_stats_update_end(&tx_ring->syncp);
|
||||
|
||||
/* Clear last jiffies so the lost buffer won't
|
||||
* be counted twice.
|
||||
*/
|
||||
tx_buf->last_jiffies = 0;
|
||||
|
||||
if (unlikely(missed_tx > MAX_NUM_OF_TIMEOUTED_PACKETS)) {
|
||||
netif_err(adapter, tx_err, adapter->netdev,
|
||||
"The number of lost tx completion is above the threshold (%d > %d). Reset the device\n",
|
||||
missed_tx, MAX_NUM_OF_TIMEOUTED_PACKETS);
|
||||
set_bit(ENA_FLAG_TRIGGER_RESET, &adapter->flags);
|
||||
}
|
||||
}
|
||||
}
|
||||
rc = check_missing_comp_in_queue(adapter, tx_ring);
|
||||
if (unlikely(rc))
|
||||
return;
|
||||
|
||||
budget--;
|
||||
if (!budget)
|
||||
|
@ -2606,6 +2630,58 @@ static void check_for_missing_tx_completions(struct ena_adapter *adapter)
|
|||
adapter->last_monitored_tx_qid = i % adapter->num_queues;
|
||||
}
|
||||
|
||||
/* trigger napi schedule after 2 consecutive detections */
|
||||
#define EMPTY_RX_REFILL 2
|
||||
/* For the rare case where the device runs out of Rx descriptors and the
|
||||
* napi handler failed to refill new Rx descriptors (due to a lack of memory
|
||||
* for example).
|
||||
* This case will lead to a deadlock:
|
||||
* The device won't send interrupts since all the new Rx packets will be dropped
|
||||
* The napi handler won't allocate new Rx descriptors so the device will be
|
||||
* able to send new packets.
|
||||
*
|
||||
* This scenario can happen when the kernel's vm.min_free_kbytes is too small.
|
||||
* It is recommended to have at least 512MB, with a minimum of 128MB for
|
||||
* constrained environment).
|
||||
*
|
||||
* When such a situation is detected - Reschedule napi
|
||||
*/
|
||||
static void check_for_empty_rx_ring(struct ena_adapter *adapter)
|
||||
{
|
||||
struct ena_ring *rx_ring;
|
||||
int i, refill_required;
|
||||
|
||||
if (!test_bit(ENA_FLAG_DEV_UP, &adapter->flags))
|
||||
return;
|
||||
|
||||
if (test_bit(ENA_FLAG_TRIGGER_RESET, &adapter->flags))
|
||||
return;
|
||||
|
||||
for (i = 0; i < adapter->num_queues; i++) {
|
||||
rx_ring = &adapter->rx_ring[i];
|
||||
|
||||
refill_required =
|
||||
ena_com_sq_empty_space(rx_ring->ena_com_io_sq);
|
||||
if (unlikely(refill_required == (rx_ring->ring_size - 1))) {
|
||||
rx_ring->empty_rx_queue++;
|
||||
|
||||
if (rx_ring->empty_rx_queue >= EMPTY_RX_REFILL) {
|
||||
u64_stats_update_begin(&rx_ring->syncp);
|
||||
rx_ring->rx_stats.empty_rx_ring++;
|
||||
u64_stats_update_end(&rx_ring->syncp);
|
||||
|
||||
netif_err(adapter, drv, adapter->netdev,
|
||||
"trigger refill for ring %d\n", i);
|
||||
|
||||
napi_schedule(rx_ring->napi);
|
||||
rx_ring->empty_rx_queue = 0;
|
||||
}
|
||||
} else {
|
||||
rx_ring->empty_rx_queue = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Check for keep alive expiration */
|
||||
static void check_for_missing_keep_alive(struct ena_adapter *adapter)
|
||||
{
|
||||
|
@ -2660,6 +2736,8 @@ static void ena_timer_service(unsigned long data)
|
|||
|
||||
check_for_missing_tx_completions(adapter);
|
||||
|
||||
check_for_empty_rx_ring(adapter);
|
||||
|
||||
if (debug_area)
|
||||
ena_dump_stats_to_buf(adapter, debug_area);
|
||||
|
||||
|
@ -2840,6 +2918,11 @@ static void ena_release_bars(struct ena_com_dev *ena_dev, struct pci_dev *pdev)
|
|||
{
|
||||
int release_bars;
|
||||
|
||||
if (ena_dev->mem_bar)
|
||||
devm_iounmap(&pdev->dev, ena_dev->mem_bar);
|
||||
|
||||
devm_iounmap(&pdev->dev, ena_dev->reg_bar);
|
||||
|
||||
release_bars = pci_select_bars(pdev, IORESOURCE_MEM) & ENA_BAR_MASK;
|
||||
pci_release_selected_regions(pdev, release_bars);
|
||||
}
|
||||
|
@ -2927,8 +3010,9 @@ static int ena_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
|
|||
goto err_free_ena_dev;
|
||||
}
|
||||
|
||||
ena_dev->reg_bar = ioremap(pci_resource_start(pdev, ENA_REG_BAR),
|
||||
pci_resource_len(pdev, ENA_REG_BAR));
|
||||
ena_dev->reg_bar = devm_ioremap(&pdev->dev,
|
||||
pci_resource_start(pdev, ENA_REG_BAR),
|
||||
pci_resource_len(pdev, ENA_REG_BAR));
|
||||
if (!ena_dev->reg_bar) {
|
||||
dev_err(&pdev->dev, "failed to remap regs bar\n");
|
||||
rc = -EFAULT;
|
||||
|
@ -2948,8 +3032,9 @@ static int ena_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
|
|||
ena_set_push_mode(pdev, ena_dev, &get_feat_ctx);
|
||||
|
||||
if (ena_dev->tx_mem_queue_type == ENA_ADMIN_PLACEMENT_POLICY_DEV) {
|
||||
ena_dev->mem_bar = ioremap_wc(pci_resource_start(pdev, ENA_MEM_BAR),
|
||||
pci_resource_len(pdev, ENA_MEM_BAR));
|
||||
ena_dev->mem_bar = devm_ioremap_wc(&pdev->dev,
|
||||
pci_resource_start(pdev, ENA_MEM_BAR),
|
||||
pci_resource_len(pdev, ENA_MEM_BAR));
|
||||
if (!ena_dev->mem_bar) {
|
||||
rc = -EFAULT;
|
||||
goto err_device_destroy;
|
||||
|
|
|
@ -45,7 +45,7 @@
|
|||
|
||||
#define DRV_MODULE_VER_MAJOR 1
|
||||
#define DRV_MODULE_VER_MINOR 1
|
||||
#define DRV_MODULE_VER_SUBMINOR 2
|
||||
#define DRV_MODULE_VER_SUBMINOR 7
|
||||
|
||||
#define DRV_MODULE_NAME "ena"
|
||||
#ifndef DRV_MODULE_VERSION
|
||||
|
@ -146,7 +146,18 @@ struct ena_tx_buffer {
|
|||
u32 tx_descs;
|
||||
/* num of buffers used by this skb */
|
||||
u32 num_of_bufs;
|
||||
/* Save the last jiffies to detect missing tx packets */
|
||||
|
||||
/* Used for detect missing tx packets to limit the number of prints */
|
||||
u32 print_once;
|
||||
/* Save the last jiffies to detect missing tx packets
|
||||
*
|
||||
* sets to non zero value on ena_start_xmit and set to zero on
|
||||
* napi and timer_Service_routine.
|
||||
*
|
||||
* while this value is not protected by lock,
|
||||
* a given packet is not expected to be handled by ena_start_xmit
|
||||
* and by napi/timer_service at the same time.
|
||||
*/
|
||||
unsigned long last_jiffies;
|
||||
struct ena_com_buf bufs[ENA_PKT_MAX_BUFS];
|
||||
} ____cacheline_aligned;
|
||||
|
@ -170,7 +181,6 @@ struct ena_stats_tx {
|
|||
u64 napi_comp;
|
||||
u64 tx_poll;
|
||||
u64 doorbells;
|
||||
u64 missing_tx_comp;
|
||||
u64 bad_req_id;
|
||||
};
|
||||
|
||||
|
@ -184,6 +194,7 @@ struct ena_stats_rx {
|
|||
u64 dma_mapping_err;
|
||||
u64 bad_desc_num;
|
||||
u64 rx_copybreak_pkt;
|
||||
u64 empty_rx_ring;
|
||||
};
|
||||
|
||||
struct ena_ring {
|
||||
|
@ -231,6 +242,7 @@ struct ena_ring {
|
|||
struct ena_stats_tx tx_stats;
|
||||
struct ena_stats_rx rx_stats;
|
||||
};
|
||||
int empty_rx_queue;
|
||||
} ____cacheline_aligned;
|
||||
|
||||
struct ena_stats_dev {
|
||||
|
|
|
@ -193,9 +193,6 @@ int hw_atl_utils_hw_get_regs(struct aq_hw_s *self,
|
|||
struct aq_hw_caps_s *aq_hw_caps,
|
||||
u32 *regs_buff);
|
||||
|
||||
int hw_atl_utils_hw_get_settings(struct aq_hw_s *self,
|
||||
struct ethtool_cmd *cmd);
|
||||
|
||||
int hw_atl_utils_hw_set_power(struct aq_hw_s *self,
|
||||
unsigned int power_state);
|
||||
|
||||
|
|
|
@ -3883,15 +3883,26 @@ netdev_tx_t bnx2x_start_xmit(struct sk_buff *skb, struct net_device *dev)
|
|||
/* when transmitting in a vf, start bd must hold the ethertype
|
||||
* for fw to enforce it
|
||||
*/
|
||||
u16 vlan_tci = 0;
|
||||
#ifndef BNX2X_STOP_ON_ERROR
|
||||
if (IS_VF(bp))
|
||||
if (IS_VF(bp)) {
|
||||
#endif
|
||||
tx_start_bd->vlan_or_ethertype =
|
||||
cpu_to_le16(ntohs(eth->h_proto));
|
||||
/* Still need to consider inband vlan for enforced */
|
||||
if (__vlan_get_tag(skb, &vlan_tci)) {
|
||||
tx_start_bd->vlan_or_ethertype =
|
||||
cpu_to_le16(ntohs(eth->h_proto));
|
||||
} else {
|
||||
tx_start_bd->bd_flags.as_bitfield |=
|
||||
(X_ETH_INBAND_VLAN <<
|
||||
ETH_TX_BD_FLAGS_VLAN_MODE_SHIFT);
|
||||
tx_start_bd->vlan_or_ethertype =
|
||||
cpu_to_le16(vlan_tci);
|
||||
}
|
||||
#ifndef BNX2X_STOP_ON_ERROR
|
||||
else
|
||||
} else {
|
||||
/* used by FW for packet accounting */
|
||||
tx_start_bd->vlan_or_ethertype = cpu_to_le16(pkt_prod);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
|
|
|
@ -901,6 +901,8 @@ static void bnx2x_vf_flr(struct bnx2x *bp, struct bnx2x_virtf *vf)
|
|||
/* release VF resources */
|
||||
bnx2x_vf_free_resc(bp, vf);
|
||||
|
||||
vf->malicious = false;
|
||||
|
||||
/* re-open the mailbox */
|
||||
bnx2x_vf_enable_mbx(bp, vf->abs_vfid);
|
||||
return;
|
||||
|
@ -1822,9 +1824,11 @@ get_vf:
|
|||
vf->abs_vfid, qidx);
|
||||
bnx2x_vf_handle_rss_update_eqe(bp, vf);
|
||||
case EVENT_RING_OPCODE_VF_FLR:
|
||||
case EVENT_RING_OPCODE_MALICIOUS_VF:
|
||||
/* Do nothing for now */
|
||||
return 0;
|
||||
case EVENT_RING_OPCODE_MALICIOUS_VF:
|
||||
vf->malicious = true;
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
@ -1905,6 +1909,13 @@ void bnx2x_iov_adjust_stats_req(struct bnx2x *bp)
|
|||
continue;
|
||||
}
|
||||
|
||||
if (vf->malicious) {
|
||||
DP_AND((BNX2X_MSG_IOV | BNX2X_MSG_STATS),
|
||||
"vf %d malicious so no stats for it\n",
|
||||
vf->abs_vfid);
|
||||
continue;
|
||||
}
|
||||
|
||||
DP_AND((BNX2X_MSG_IOV | BNX2X_MSG_STATS),
|
||||
"add addresses for vf %d\n", vf->abs_vfid);
|
||||
for_each_vfq(vf, j) {
|
||||
|
@ -3042,7 +3053,7 @@ void bnx2x_vf_pci_dealloc(struct bnx2x *bp)
|
|||
{
|
||||
BNX2X_PCI_FREE(bp->vf2pf_mbox, bp->vf2pf_mbox_mapping,
|
||||
sizeof(struct bnx2x_vf_mbx_msg));
|
||||
BNX2X_PCI_FREE(bp->vf2pf_mbox, bp->pf2vf_bulletin_mapping,
|
||||
BNX2X_PCI_FREE(bp->pf2vf_bulletin, bp->pf2vf_bulletin_mapping,
|
||||
sizeof(union pf_vf_bulletin));
|
||||
}
|
||||
|
||||
|
|
|
@ -141,6 +141,7 @@ struct bnx2x_virtf {
|
|||
#define VF_RESET 3 /* VF FLR'd, pending cleanup */
|
||||
|
||||
bool flr_clnup_stage; /* true during flr cleanup */
|
||||
bool malicious; /* true if FW indicated so, until FLR */
|
||||
|
||||
/* dma */
|
||||
dma_addr_t fw_stat_map;
|
||||
|
|
|
@ -4525,7 +4525,7 @@ static void dummy_setup(struct net_device *dev)
|
|||
/* Initialize the device structure. */
|
||||
dev->netdev_ops = &cxgb4_mgmt_netdev_ops;
|
||||
dev->ethtool_ops = &cxgb4_mgmt_ethtool_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
}
|
||||
|
||||
static int config_mgmt_dev(struct pci_dev *pdev)
|
||||
|
|
|
@ -343,6 +343,7 @@ static int emac_reset(struct emac_instance *dev)
|
|||
{
|
||||
struct emac_regs __iomem *p = dev->emacp;
|
||||
int n = 20;
|
||||
bool __maybe_unused try_internal_clock = false;
|
||||
|
||||
DBG(dev, "reset" NL);
|
||||
|
||||
|
@ -355,6 +356,7 @@ static int emac_reset(struct emac_instance *dev)
|
|||
}
|
||||
|
||||
#ifdef CONFIG_PPC_DCR_NATIVE
|
||||
do_retry:
|
||||
/*
|
||||
* PPC460EX/GT Embedded Processor Advanced User's Manual
|
||||
* section 28.10.1 Mode Register 0 (EMACx_MR0) states:
|
||||
|
@ -362,10 +364,19 @@ static int emac_reset(struct emac_instance *dev)
|
|||
* of the EMAC. If none is present, select the internal clock
|
||||
* (SDR0_ETH_CFG[EMACx_PHY_CLK] = 1).
|
||||
* After a soft reset, select the external clock.
|
||||
*
|
||||
* The AR8035-A PHY Meraki MR24 does not provide a TX Clk if the
|
||||
* ethernet cable is not attached. This causes the reset to timeout
|
||||
* and the PHY detection code in emac_init_phy() is unable to
|
||||
* communicate and detect the AR8035-A PHY. As a result, the emac
|
||||
* driver bails out early and the user has no ethernet.
|
||||
* In order to stay compatible with existing configurations, the
|
||||
* driver will temporarily switch to the internal clock, after
|
||||
* the first reset fails.
|
||||
*/
|
||||
if (emac_has_feature(dev, EMAC_FTR_460EX_PHY_CLK_FIX)) {
|
||||
if (dev->phy_address == 0xffffffff &&
|
||||
dev->phy_map == 0xffffffff) {
|
||||
if (try_internal_clock || (dev->phy_address == 0xffffffff &&
|
||||
dev->phy_map == 0xffffffff)) {
|
||||
/* No PHY: select internal loop clock before reset */
|
||||
dcri_clrset(SDR0, SDR0_ETH_CFG,
|
||||
0, SDR0_ETH_CFG_ECS << dev->cell_index);
|
||||
|
@ -383,8 +394,15 @@ static int emac_reset(struct emac_instance *dev)
|
|||
|
||||
#ifdef CONFIG_PPC_DCR_NATIVE
|
||||
if (emac_has_feature(dev, EMAC_FTR_460EX_PHY_CLK_FIX)) {
|
||||
if (dev->phy_address == 0xffffffff &&
|
||||
dev->phy_map == 0xffffffff) {
|
||||
if (!n && !try_internal_clock) {
|
||||
/* first attempt has timed out. */
|
||||
n = 20;
|
||||
try_internal_clock = true;
|
||||
goto do_retry;
|
||||
}
|
||||
|
||||
if (try_internal_clock || (dev->phy_address == 0xffffffff &&
|
||||
dev->phy_map == 0xffffffff)) {
|
||||
/* No PHY: restore external clock source after reset */
|
||||
dcri_clrset(SDR0, SDR0_ETH_CFG,
|
||||
SDR0_ETH_CFG_ECS << dev->cell_index, 0);
|
||||
|
@ -2460,20 +2478,24 @@ static int emac_mii_bus_reset(struct mii_bus *bus)
|
|||
return emac_reset(dev);
|
||||
}
|
||||
|
||||
static int emac_mdio_phy_start_aneg(struct mii_phy *phy,
|
||||
struct phy_device *phy_dev)
|
||||
{
|
||||
phy_dev->autoneg = phy->autoneg;
|
||||
phy_dev->speed = phy->speed;
|
||||
phy_dev->duplex = phy->duplex;
|
||||
phy_dev->advertising = phy->advertising;
|
||||
return phy_start_aneg(phy_dev);
|
||||
}
|
||||
|
||||
static int emac_mdio_setup_aneg(struct mii_phy *phy, u32 advertise)
|
||||
{
|
||||
struct net_device *ndev = phy->dev;
|
||||
struct emac_instance *dev = netdev_priv(ndev);
|
||||
|
||||
dev->phy.autoneg = AUTONEG_ENABLE;
|
||||
dev->phy.speed = SPEED_1000;
|
||||
dev->phy.duplex = DUPLEX_FULL;
|
||||
dev->phy.advertising = advertise;
|
||||
phy->autoneg = AUTONEG_ENABLE;
|
||||
phy->speed = dev->phy.speed;
|
||||
phy->duplex = dev->phy.duplex;
|
||||
phy->advertising = advertise;
|
||||
return phy_start_aneg(dev->phy_dev);
|
||||
return emac_mdio_phy_start_aneg(phy, dev->phy_dev);
|
||||
}
|
||||
|
||||
static int emac_mdio_setup_forced(struct mii_phy *phy, int speed, int fd)
|
||||
|
@ -2481,13 +2503,10 @@ static int emac_mdio_setup_forced(struct mii_phy *phy, int speed, int fd)
|
|||
struct net_device *ndev = phy->dev;
|
||||
struct emac_instance *dev = netdev_priv(ndev);
|
||||
|
||||
dev->phy.autoneg = AUTONEG_DISABLE;
|
||||
dev->phy.speed = speed;
|
||||
dev->phy.duplex = fd;
|
||||
phy->autoneg = AUTONEG_DISABLE;
|
||||
phy->speed = speed;
|
||||
phy->duplex = fd;
|
||||
return phy_start_aneg(dev->phy_dev);
|
||||
return emac_mdio_phy_start_aneg(phy, dev->phy_dev);
|
||||
}
|
||||
|
||||
static int emac_mdio_poll_link(struct mii_phy *phy)
|
||||
|
@ -2509,16 +2528,17 @@ static int emac_mdio_read_link(struct mii_phy *phy)
|
|||
{
|
||||
struct net_device *ndev = phy->dev;
|
||||
struct emac_instance *dev = netdev_priv(ndev);
|
||||
struct phy_device *phy_dev = dev->phy_dev;
|
||||
int res;
|
||||
|
||||
res = phy_read_status(dev->phy_dev);
|
||||
res = phy_read_status(phy_dev);
|
||||
if (res)
|
||||
return res;
|
||||
|
||||
dev->phy.speed = phy->speed;
|
||||
dev->phy.duplex = phy->duplex;
|
||||
dev->phy.pause = phy->pause;
|
||||
dev->phy.asym_pause = phy->asym_pause;
|
||||
phy->speed = phy_dev->speed;
|
||||
phy->duplex = phy_dev->duplex;
|
||||
phy->pause = phy_dev->pause;
|
||||
phy->asym_pause = phy_dev->asym_pause;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -2528,13 +2548,6 @@ static int emac_mdio_init_phy(struct mii_phy *phy)
|
|||
struct emac_instance *dev = netdev_priv(ndev);
|
||||
|
||||
phy_start(dev->phy_dev);
|
||||
dev->phy.autoneg = phy->autoneg;
|
||||
dev->phy.speed = phy->speed;
|
||||
dev->phy.duplex = phy->duplex;
|
||||
dev->phy.advertising = phy->advertising;
|
||||
dev->phy.pause = phy->pause;
|
||||
dev->phy.asym_pause = phy->asym_pause;
|
||||
|
||||
return phy_init_hw(dev->phy_dev);
|
||||
}
|
||||
|
||||
|
|
|
@ -1468,6 +1468,11 @@ static void ibmvnic_netpoll_controller(struct net_device *dev)
|
|||
}
|
||||
#endif
|
||||
|
||||
static int ibmvnic_change_mtu(struct net_device *netdev, int new_mtu)
|
||||
{
|
||||
return -EOPNOTSUPP;
|
||||
}
|
||||
|
||||
static const struct net_device_ops ibmvnic_netdev_ops = {
|
||||
.ndo_open = ibmvnic_open,
|
||||
.ndo_stop = ibmvnic_close,
|
||||
|
@ -1479,6 +1484,7 @@ static const struct net_device_ops ibmvnic_netdev_ops = {
|
|||
#ifdef CONFIG_NET_POLL_CONTROLLER
|
||||
.ndo_poll_controller = ibmvnic_netpoll_controller,
|
||||
#endif
|
||||
.ndo_change_mtu = ibmvnic_change_mtu,
|
||||
};
|
||||
|
||||
/* ethtool functions */
|
||||
|
|
|
@ -399,6 +399,7 @@ struct i40e_pf {
|
|||
#define I40E_FLAG_RX_CSUM_ENABLED BIT_ULL(1)
|
||||
#define I40E_FLAG_MSI_ENABLED BIT_ULL(2)
|
||||
#define I40E_FLAG_MSIX_ENABLED BIT_ULL(3)
|
||||
#define I40E_FLAG_HW_ATR_EVICT_ENABLED BIT_ULL(4)
|
||||
#define I40E_FLAG_RSS_ENABLED BIT_ULL(6)
|
||||
#define I40E_FLAG_VMDQ_ENABLED BIT_ULL(7)
|
||||
#define I40E_FLAG_IWARP_ENABLED BIT_ULL(10)
|
||||
|
|
|
@ -224,7 +224,7 @@ static const struct i40e_priv_flags i40e_gstrings_priv_flags[] = {
|
|||
I40E_PRIV_FLAG("LinkPolling", I40E_FLAG_LINK_POLLING_ENABLED, 0),
|
||||
I40E_PRIV_FLAG("flow-director-atr", I40E_FLAG_FD_ATR_ENABLED, 0),
|
||||
I40E_PRIV_FLAG("veb-stats", I40E_FLAG_VEB_STATS_ENABLED, 0),
|
||||
I40E_PRIV_FLAG("hw-atr-eviction", I40E_FLAG_HW_ATR_EVICT_CAPABLE, 0),
|
||||
I40E_PRIV_FLAG("hw-atr-eviction", I40E_FLAG_HW_ATR_EVICT_ENABLED, 0),
|
||||
I40E_PRIV_FLAG("legacy-rx", I40E_FLAG_LEGACY_RX, 0),
|
||||
};
|
||||
|
||||
|
@ -4092,7 +4092,7 @@ flags_complete:
|
|||
|
||||
/* Only allow ATR evict on hardware that is capable of handling it */
|
||||
if (pf->flags & I40E_FLAG_HW_ATR_EVICT_CAPABLE)
|
||||
pf->flags &= ~I40E_FLAG_HW_ATR_EVICT_CAPABLE;
|
||||
pf->flags &= ~I40E_FLAG_HW_ATR_EVICT_ENABLED;
|
||||
|
||||
if (changed_flags & I40E_FLAG_TRUE_PROMISC_SUPPORT) {
|
||||
u16 sw_flags = 0, valid_flags = 0;
|
||||
|
|
|
@ -8821,11 +8821,12 @@ static int i40e_sw_init(struct i40e_pf *pf)
|
|||
(pf->hw.aq.api_min_ver > 4))) {
|
||||
/* Supported in FW API version higher than 1.4 */
|
||||
pf->flags |= I40E_FLAG_GENEVE_OFFLOAD_CAPABLE;
|
||||
pf->flags = I40E_FLAG_HW_ATR_EVICT_CAPABLE;
|
||||
} else {
|
||||
pf->flags = I40E_FLAG_HW_ATR_EVICT_CAPABLE;
|
||||
}
|
||||
|
||||
/* Enable HW ATR eviction if possible */
|
||||
if (pf->flags & I40E_FLAG_HW_ATR_EVICT_CAPABLE)
|
||||
pf->flags |= I40E_FLAG_HW_ATR_EVICT_ENABLED;
|
||||
|
||||
pf->eeprom_version = 0xDEAD;
|
||||
pf->lan_veb = I40E_NO_VEB;
|
||||
pf->lan_vsi = I40E_NO_VSI;
|
||||
|
|
|
@ -2341,7 +2341,7 @@ static void i40e_atr(struct i40e_ring *tx_ring, struct sk_buff *skb,
|
|||
/* Due to lack of space, no more new filters can be programmed */
|
||||
if (th->syn && (pf->flags & I40E_FLAG_FD_ATR_AUTO_DISABLED))
|
||||
return;
|
||||
if (pf->flags & I40E_FLAG_HW_ATR_EVICT_CAPABLE) {
|
||||
if (pf->flags & I40E_FLAG_HW_ATR_EVICT_ENABLED) {
|
||||
/* HW ATR eviction will take care of removing filters on FIN
|
||||
* and RST packets.
|
||||
*/
|
||||
|
@ -2403,7 +2403,7 @@ static void i40e_atr(struct i40e_ring *tx_ring, struct sk_buff *skb,
|
|||
I40E_TXD_FLTR_QW1_CNTINDEX_SHIFT) &
|
||||
I40E_TXD_FLTR_QW1_CNTINDEX_MASK;
|
||||
|
||||
if (pf->flags & I40E_FLAG_HW_ATR_EVICT_CAPABLE)
|
||||
if (pf->flags & I40E_FLAG_HW_ATR_EVICT_ENABLED)
|
||||
dtype_cmd |= I40E_TXD_FLTR_QW1_ATR_MASK;
|
||||
|
||||
fdir_desc->qindex_flex_ptype_vsi = cpu_to_le32(flex_ptype);
|
||||
|
|
|
@ -3017,10 +3017,12 @@ int i40e_ndo_set_vf_port_vlan(struct net_device *netdev, int vf_id,
|
|||
VLAN_VID_MASK));
|
||||
}
|
||||
|
||||
spin_unlock_bh(&vsi->mac_filter_hash_lock);
|
||||
if (vlan_id || qos)
|
||||
ret = i40e_vsi_add_pvid(vsi, vlanprio);
|
||||
else
|
||||
i40e_vsi_remove_pvid(vsi);
|
||||
spin_lock_bh(&vsi->mac_filter_hash_lock);
|
||||
|
||||
if (vlan_id) {
|
||||
dev_info(&pf->pdev->dev, "Setting VLAN %d, QOS 0x%x on VF %d\n",
|
||||
|
|
|
@ -3719,7 +3719,7 @@ static void mvpp2_bm_bufs_get_addrs(struct device *dev, struct mvpp2 *priv,
|
|||
dma_addr_t *dma_addr,
|
||||
phys_addr_t *phys_addr)
|
||||
{
|
||||
int cpu = smp_processor_id();
|
||||
int cpu = get_cpu();
|
||||
|
||||
*dma_addr = mvpp2_percpu_read(priv, cpu,
|
||||
MVPP2_BM_PHY_ALLOC_REG(bm_pool->id));
|
||||
|
@ -3740,6 +3740,8 @@ static void mvpp2_bm_bufs_get_addrs(struct device *dev, struct mvpp2 *priv,
|
|||
if (sizeof(phys_addr_t) == 8)
|
||||
*phys_addr |= (u64)phys_addr_highbits << 32;
|
||||
}
|
||||
|
||||
put_cpu();
|
||||
}
|
||||
|
||||
/* Free all buffers from the pool */
|
||||
|
@ -3920,18 +3922,12 @@ static inline u32 mvpp2_bm_cookie_pool_set(u32 cookie, int pool)
|
|||
return bm;
|
||||
}
|
||||
|
||||
/* Get pool number from a BM cookie */
|
||||
static inline int mvpp2_bm_cookie_pool_get(unsigned long cookie)
|
||||
{
|
||||
return (cookie >> MVPP2_BM_COOKIE_POOL_OFFS) & 0xFF;
|
||||
}
|
||||
|
||||
/* Release buffer to BM */
|
||||
static inline void mvpp2_bm_pool_put(struct mvpp2_port *port, int pool,
|
||||
dma_addr_t buf_dma_addr,
|
||||
phys_addr_t buf_phys_addr)
|
||||
{
|
||||
int cpu = smp_processor_id();
|
||||
int cpu = get_cpu();
|
||||
|
||||
if (port->priv->hw_version == MVPP22) {
|
||||
u32 val = 0;
|
||||
|
@ -3958,15 +3954,15 @@ static inline void mvpp2_bm_pool_put(struct mvpp2_port *port, int pool,
|
|||
MVPP2_BM_VIRT_RLS_REG, buf_phys_addr);
|
||||
mvpp2_percpu_write(port->priv, cpu,
|
||||
MVPP2_BM_PHY_RLS_REG(pool), buf_dma_addr);
|
||||
|
||||
put_cpu();
|
||||
}
|
||||
|
||||
/* Refill BM pool */
|
||||
static void mvpp2_pool_refill(struct mvpp2_port *port, u32 bm,
|
||||
static void mvpp2_pool_refill(struct mvpp2_port *port, int pool,
|
||||
dma_addr_t dma_addr,
|
||||
phys_addr_t phys_addr)
|
||||
{
|
||||
int pool = mvpp2_bm_cookie_pool_get(bm);
|
||||
|
||||
mvpp2_bm_pool_put(port, pool, dma_addr, phys_addr);
|
||||
}
|
||||
|
||||
|
@ -4186,8 +4182,6 @@ static void mvpp22_port_mii_set(struct mvpp2_port *port)
|
|||
{
|
||||
u32 val;
|
||||
|
||||
return;
|
||||
|
||||
/* Only GOP port 0 has an XLG MAC */
|
||||
if (port->gop_id == 0) {
|
||||
val = readl(port->base + MVPP22_XLG_CTRL3_REG);
|
||||
|
@ -4515,21 +4509,6 @@ static void mvpp2_rxq_offset_set(struct mvpp2_port *port,
|
|||
mvpp2_write(port->priv, MVPP2_RXQ_CONFIG_REG(prxq), val);
|
||||
}
|
||||
|
||||
/* Obtain BM cookie information from descriptor */
|
||||
static u32 mvpp2_bm_cookie_build(struct mvpp2_port *port,
|
||||
struct mvpp2_rx_desc *rx_desc)
|
||||
{
|
||||
int cpu = smp_processor_id();
|
||||
int pool;
|
||||
|
||||
pool = (mvpp2_rxdesc_status_get(port, rx_desc) &
|
||||
MVPP2_RXD_BM_POOL_ID_MASK) >>
|
||||
MVPP2_RXD_BM_POOL_ID_OFFS;
|
||||
|
||||
return ((pool & 0xFF) << MVPP2_BM_COOKIE_POOL_OFFS) |
|
||||
((cpu & 0xFF) << MVPP2_BM_COOKIE_CPU_OFFS);
|
||||
}
|
||||
|
||||
/* Tx descriptors helper methods */
|
||||
|
||||
/* Get pointer to next Tx descriptor to be processed (send) by HW */
|
||||
|
@ -4757,7 +4736,7 @@ static void mvpp2_txp_max_tx_size_set(struct mvpp2_port *port)
|
|||
static void mvpp2_rx_pkts_coal_set(struct mvpp2_port *port,
|
||||
struct mvpp2_rx_queue *rxq)
|
||||
{
|
||||
int cpu = smp_processor_id();
|
||||
int cpu = get_cpu();
|
||||
|
||||
if (rxq->pkts_coal > MVPP2_OCCUPIED_THRESH_MASK)
|
||||
rxq->pkts_coal = MVPP2_OCCUPIED_THRESH_MASK;
|
||||
|
@ -4765,6 +4744,8 @@ static void mvpp2_rx_pkts_coal_set(struct mvpp2_port *port,
|
|||
mvpp2_percpu_write(port->priv, cpu, MVPP2_RXQ_NUM_REG, rxq->id);
|
||||
mvpp2_percpu_write(port->priv, cpu, MVPP2_RXQ_THRESH_REG,
|
||||
rxq->pkts_coal);
|
||||
|
||||
put_cpu();
|
||||
}
|
||||
|
||||
static u32 mvpp2_usec_to_cycles(u32 usec, unsigned long clk_hz)
|
||||
|
@ -4945,7 +4926,7 @@ static int mvpp2_rxq_init(struct mvpp2_port *port,
|
|||
mvpp2_write(port->priv, MVPP2_RXQ_STATUS_REG(rxq->id), 0);
|
||||
|
||||
/* Set Rx descriptors queue starting address - indirect access */
|
||||
cpu = smp_processor_id();
|
||||
cpu = get_cpu();
|
||||
mvpp2_percpu_write(port->priv, cpu, MVPP2_RXQ_NUM_REG, rxq->id);
|
||||
if (port->priv->hw_version == MVPP21)
|
||||
rxq_dma = rxq->descs_dma;
|
||||
|
@ -4954,6 +4935,7 @@ static int mvpp2_rxq_init(struct mvpp2_port *port,
|
|||
mvpp2_percpu_write(port->priv, cpu, MVPP2_RXQ_DESC_ADDR_REG, rxq_dma);
|
||||
mvpp2_percpu_write(port->priv, cpu, MVPP2_RXQ_DESC_SIZE_REG, rxq->size);
|
||||
mvpp2_percpu_write(port->priv, cpu, MVPP2_RXQ_INDEX_REG, 0);
|
||||
put_cpu();
|
||||
|
||||
/* Set Offset */
|
||||
mvpp2_rxq_offset_set(port, rxq->id, NET_SKB_PAD);
|
||||
|
@ -4980,9 +4962,13 @@ static void mvpp2_rxq_drop_pkts(struct mvpp2_port *port,
|
|||
|
||||
for (i = 0; i < rx_received; i++) {
|
||||
struct mvpp2_rx_desc *rx_desc = mvpp2_rxq_next_desc_get(rxq);
|
||||
u32 bm = mvpp2_bm_cookie_build(port, rx_desc);
|
||||
u32 status = mvpp2_rxdesc_status_get(port, rx_desc);
|
||||
int pool;
|
||||
|
||||
mvpp2_pool_refill(port, bm,
|
||||
pool = (status & MVPP2_RXD_BM_POOL_ID_MASK) >>
|
||||
MVPP2_RXD_BM_POOL_ID_OFFS;
|
||||
|
||||
mvpp2_pool_refill(port, pool,
|
||||
mvpp2_rxdesc_dma_addr_get(port, rx_desc),
|
||||
mvpp2_rxdesc_cookie_get(port, rx_desc));
|
||||
}
|
||||
|
@ -5012,10 +4998,11 @@ static void mvpp2_rxq_deinit(struct mvpp2_port *port,
|
|||
* free descriptor number
|
||||
*/
|
||||
mvpp2_write(port->priv, MVPP2_RXQ_STATUS_REG(rxq->id), 0);
|
||||
cpu = smp_processor_id();
|
||||
cpu = get_cpu();
|
||||
mvpp2_percpu_write(port->priv, cpu, MVPP2_RXQ_NUM_REG, rxq->id);
|
||||
mvpp2_percpu_write(port->priv, cpu, MVPP2_RXQ_DESC_ADDR_REG, 0);
|
||||
mvpp2_percpu_write(port->priv, cpu, MVPP2_RXQ_DESC_SIZE_REG, 0);
|
||||
put_cpu();
|
||||
}
|
||||
|
||||
/* Create and initialize a Tx queue */
|
||||
|
@ -5038,7 +5025,7 @@ static int mvpp2_txq_init(struct mvpp2_port *port,
|
|||
txq->last_desc = txq->size - 1;
|
||||
|
||||
/* Set Tx descriptors queue starting address - indirect access */
|
||||
cpu = smp_processor_id();
|
||||
cpu = get_cpu();
|
||||
mvpp2_percpu_write(port->priv, cpu, MVPP2_TXQ_NUM_REG, txq->id);
|
||||
mvpp2_percpu_write(port->priv, cpu, MVPP2_TXQ_DESC_ADDR_REG,
|
||||
txq->descs_dma);
|
||||
|
@ -5063,6 +5050,7 @@ static int mvpp2_txq_init(struct mvpp2_port *port,
|
|||
mvpp2_percpu_write(port->priv, cpu, MVPP2_TXQ_PREF_BUF_REG,
|
||||
MVPP2_PREF_BUF_PTR(desc) | MVPP2_PREF_BUF_SIZE_16 |
|
||||
MVPP2_PREF_BUF_THRESH(desc_per_txq / 2));
|
||||
put_cpu();
|
||||
|
||||
/* WRR / EJP configuration - indirect access */
|
||||
tx_port_num = mvpp2_egress_port(port);
|
||||
|
@ -5133,10 +5121,11 @@ static void mvpp2_txq_deinit(struct mvpp2_port *port,
|
|||
mvpp2_write(port->priv, MVPP2_TXQ_SCHED_TOKEN_CNTR_REG(txq->id), 0);
|
||||
|
||||
/* Set Tx descriptors queue starting address and size */
|
||||
cpu = smp_processor_id();
|
||||
cpu = get_cpu();
|
||||
mvpp2_percpu_write(port->priv, cpu, MVPP2_TXQ_NUM_REG, txq->id);
|
||||
mvpp2_percpu_write(port->priv, cpu, MVPP2_TXQ_DESC_ADDR_REG, 0);
|
||||
mvpp2_percpu_write(port->priv, cpu, MVPP2_TXQ_DESC_SIZE_REG, 0);
|
||||
put_cpu();
|
||||
}
|
||||
|
||||
/* Cleanup Tx ports */
|
||||
|
@ -5146,7 +5135,7 @@ static void mvpp2_txq_clean(struct mvpp2_port *port, struct mvpp2_tx_queue *txq)
|
|||
int delay, pending, cpu;
|
||||
u32 val;
|
||||
|
||||
cpu = smp_processor_id();
|
||||
cpu = get_cpu();
|
||||
mvpp2_percpu_write(port->priv, cpu, MVPP2_TXQ_NUM_REG, txq->id);
|
||||
val = mvpp2_percpu_read(port->priv, cpu, MVPP2_TXQ_PREF_BUF_REG);
|
||||
val |= MVPP2_TXQ_DRAIN_EN_MASK;
|
||||
|
@ -5173,6 +5162,7 @@ static void mvpp2_txq_clean(struct mvpp2_port *port, struct mvpp2_tx_queue *txq)
|
|||
|
||||
val &= ~MVPP2_TXQ_DRAIN_EN_MASK;
|
||||
mvpp2_percpu_write(port->priv, cpu, MVPP2_TXQ_PREF_BUF_REG, val);
|
||||
put_cpu();
|
||||
|
||||
for_each_present_cpu(cpu) {
|
||||
txq_pcpu = per_cpu_ptr(txq->pcpu, cpu);
|
||||
|
@ -5420,7 +5410,7 @@ static void mvpp2_rx_csum(struct mvpp2_port *port, u32 status,
|
|||
|
||||
/* Reuse skb if possible, or allocate a new skb and add it to BM pool */
|
||||
static int mvpp2_rx_refill(struct mvpp2_port *port,
|
||||
struct mvpp2_bm_pool *bm_pool, u32 bm)
|
||||
struct mvpp2_bm_pool *bm_pool, int pool)
|
||||
{
|
||||
dma_addr_t dma_addr;
|
||||
phys_addr_t phys_addr;
|
||||
|
@ -5432,7 +5422,7 @@ static int mvpp2_rx_refill(struct mvpp2_port *port,
|
|||
if (!buf)
|
||||
return -ENOMEM;
|
||||
|
||||
mvpp2_pool_refill(port, bm, dma_addr, phys_addr);
|
||||
mvpp2_pool_refill(port, pool, dma_addr, phys_addr);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -5490,7 +5480,7 @@ static int mvpp2_rx(struct mvpp2_port *port, int rx_todo,
|
|||
unsigned int frag_size;
|
||||
dma_addr_t dma_addr;
|
||||
phys_addr_t phys_addr;
|
||||
u32 bm, rx_status;
|
||||
u32 rx_status;
|
||||
int pool, rx_bytes, err;
|
||||
void *data;
|
||||
|
||||
|
@ -5502,8 +5492,8 @@ static int mvpp2_rx(struct mvpp2_port *port, int rx_todo,
|
|||
phys_addr = mvpp2_rxdesc_cookie_get(port, rx_desc);
|
||||
data = (void *)phys_to_virt(phys_addr);
|
||||
|
||||
bm = mvpp2_bm_cookie_build(port, rx_desc);
|
||||
pool = mvpp2_bm_cookie_pool_get(bm);
|
||||
pool = (rx_status & MVPP2_RXD_BM_POOL_ID_MASK) >>
|
||||
MVPP2_RXD_BM_POOL_ID_OFFS;
|
||||
bm_pool = &port->priv->bm_pools[pool];
|
||||
|
||||
/* In case of an error, release the requested buffer pointer
|
||||
|
@ -5516,7 +5506,7 @@ err_drop_frame:
|
|||
dev->stats.rx_errors++;
|
||||
mvpp2_rx_error(port, rx_desc);
|
||||
/* Return the buffer to the pool */
|
||||
mvpp2_pool_refill(port, bm, dma_addr, phys_addr);
|
||||
mvpp2_pool_refill(port, pool, dma_addr, phys_addr);
|
||||
continue;
|
||||
}
|
||||
|
||||
|
@ -5531,7 +5521,7 @@ err_drop_frame:
|
|||
goto err_drop_frame;
|
||||
}
|
||||
|
||||
err = mvpp2_rx_refill(port, bm_pool, bm);
|
||||
err = mvpp2_rx_refill(port, bm_pool, pool);
|
||||
if (err) {
|
||||
netdev_err(port->dev, "failed to refill BM pools\n");
|
||||
goto err_drop_frame;
|
||||
|
|
|
@ -458,13 +458,15 @@ struct mlx5e_mpw_info {
|
|||
|
||||
struct mlx5e_rx_am_stats {
|
||||
int ppms; /* packets per msec */
|
||||
int bpms; /* bytes per msec */
|
||||
int epms; /* events per msec */
|
||||
};
|
||||
|
||||
struct mlx5e_rx_am_sample {
|
||||
ktime_t time;
|
||||
unsigned int pkt_ctr;
|
||||
u16 event_ctr;
|
||||
ktime_t time;
|
||||
u32 pkt_ctr;
|
||||
u32 byte_ctr;
|
||||
u16 event_ctr;
|
||||
};
|
||||
|
||||
struct mlx5e_rx_am { /* Adaptive Moderation */
|
||||
|
|
|
@ -183,28 +183,27 @@ static void mlx5e_am_exit_parking(struct mlx5e_rx_am *am)
|
|||
mlx5e_am_step(am);
|
||||
}
|
||||
|
||||
#define IS_SIGNIFICANT_DIFF(val, ref) \
|
||||
(((100 * abs((val) - (ref))) / (ref)) > 10) /* more than 10% difference */
|
||||
|
||||
static int mlx5e_am_stats_compare(struct mlx5e_rx_am_stats *curr,
|
||||
struct mlx5e_rx_am_stats *prev)
|
||||
{
|
||||
int diff;
|
||||
|
||||
if (!prev->ppms)
|
||||
return curr->ppms ? MLX5E_AM_STATS_BETTER :
|
||||
if (!prev->bpms)
|
||||
return curr->bpms ? MLX5E_AM_STATS_BETTER :
|
||||
MLX5E_AM_STATS_SAME;
|
||||
|
||||
diff = curr->ppms - prev->ppms;
|
||||
if (((100 * abs(diff)) / prev->ppms) > 10) /* more than 10% diff */
|
||||
return (diff > 0) ? MLX5E_AM_STATS_BETTER :
|
||||
MLX5E_AM_STATS_WORSE;
|
||||
if (IS_SIGNIFICANT_DIFF(curr->bpms, prev->bpms))
|
||||
return (curr->bpms > prev->bpms) ? MLX5E_AM_STATS_BETTER :
|
||||
MLX5E_AM_STATS_WORSE;
|
||||
|
||||
if (!prev->epms)
|
||||
return curr->epms ? MLX5E_AM_STATS_WORSE :
|
||||
MLX5E_AM_STATS_SAME;
|
||||
if (IS_SIGNIFICANT_DIFF(curr->ppms, prev->ppms))
|
||||
return (curr->ppms > prev->ppms) ? MLX5E_AM_STATS_BETTER :
|
||||
MLX5E_AM_STATS_WORSE;
|
||||
|
||||
diff = curr->epms - prev->epms;
|
||||
if (((100 * abs(diff)) / prev->epms) > 10) /* more than 10% diff */
|
||||
return (diff < 0) ? MLX5E_AM_STATS_BETTER :
|
||||
MLX5E_AM_STATS_WORSE;
|
||||
if (IS_SIGNIFICANT_DIFF(curr->epms, prev->epms))
|
||||
return (curr->epms < prev->epms) ? MLX5E_AM_STATS_BETTER :
|
||||
MLX5E_AM_STATS_WORSE;
|
||||
|
||||
return MLX5E_AM_STATS_SAME;
|
||||
}
|
||||
|
@ -266,10 +265,13 @@ static void mlx5e_am_sample(struct mlx5e_rq *rq,
|
|||
{
|
||||
s->time = ktime_get();
|
||||
s->pkt_ctr = rq->stats.packets;
|
||||
s->byte_ctr = rq->stats.bytes;
|
||||
s->event_ctr = rq->cq.event_ctr;
|
||||
}
|
||||
|
||||
#define MLX5E_AM_NEVENTS 64
|
||||
#define BITS_PER_TYPE(type) (sizeof(type) * BITS_PER_BYTE)
|
||||
#define BIT_GAP(bits, end, start) ((((end) - (start)) + BIT_ULL(bits)) & (BIT_ULL(bits) - 1))
|
||||
|
||||
static void mlx5e_am_calc_stats(struct mlx5e_rx_am_sample *start,
|
||||
struct mlx5e_rx_am_sample *end,
|
||||
|
@ -277,13 +279,17 @@ static void mlx5e_am_calc_stats(struct mlx5e_rx_am_sample *start,
|
|||
{
|
||||
/* u32 holds up to 71 minutes, should be enough */
|
||||
u32 delta_us = ktime_us_delta(end->time, start->time);
|
||||
unsigned int npkts = end->pkt_ctr - start->pkt_ctr;
|
||||
u32 npkts = BIT_GAP(BITS_PER_TYPE(u32), end->pkt_ctr, start->pkt_ctr);
|
||||
u32 nbytes = BIT_GAP(BITS_PER_TYPE(u32), end->byte_ctr,
|
||||
start->byte_ctr);
|
||||
|
||||
if (!delta_us)
|
||||
return;
|
||||
|
||||
curr_stats->ppms = (npkts * USEC_PER_MSEC) / delta_us;
|
||||
curr_stats->epms = (MLX5E_AM_NEVENTS * USEC_PER_MSEC) / delta_us;
|
||||
curr_stats->ppms = DIV_ROUND_UP(npkts * USEC_PER_MSEC, delta_us);
|
||||
curr_stats->bpms = DIV_ROUND_UP(nbytes * USEC_PER_MSEC, delta_us);
|
||||
curr_stats->epms = DIV_ROUND_UP(MLX5E_AM_NEVENTS * USEC_PER_MSEC,
|
||||
delta_us);
|
||||
}
|
||||
|
||||
void mlx5e_rx_am_work(struct work_struct *work)
|
||||
|
@ -308,7 +314,8 @@ void mlx5e_rx_am(struct mlx5e_rq *rq)
|
|||
|
||||
switch (am->state) {
|
||||
case MLX5E_AM_MEASURE_IN_PROGRESS:
|
||||
nevents = rq->cq.event_ctr - am->start_sample.event_ctr;
|
||||
nevents = BIT_GAP(BITS_PER_TYPE(u16), rq->cq.event_ctr,
|
||||
am->start_sample.event_ctr);
|
||||
if (nevents < MLX5E_AM_NEVENTS)
|
||||
break;
|
||||
mlx5e_am_sample(rq, &end_sample);
|
||||
|
|
|
@ -417,20 +417,13 @@ struct mlx5e_stats {
|
|||
};
|
||||
|
||||
static const struct counter_desc mlx5e_pme_status_desc[] = {
|
||||
{ "module_plug", 0 },
|
||||
{ "module_unplug", 8 },
|
||||
};
|
||||
|
||||
static const struct counter_desc mlx5e_pme_error_desc[] = {
|
||||
{ "module_pwr_budget_exd", 0 }, /* power budget exceed */
|
||||
{ "module_long_range", 8 }, /* long range for non MLNX cable */
|
||||
{ "module_bus_stuck", 16 }, /* bus stuck (I2C or data shorted) */
|
||||
{ "module_no_eeprom", 24 }, /* no eeprom/retry time out */
|
||||
{ "module_enforce_part", 32 }, /* enforce part number list */
|
||||
{ "module_unknown_id", 40 }, /* unknown identifier */
|
||||
{ "module_high_temp", 48 }, /* high temperature */
|
||||
{ "module_bus_stuck", 16 }, /* bus stuck (I2C or data shorted) */
|
||||
{ "module_high_temp", 48 }, /* high temperature */
|
||||
{ "module_bad_shorted", 56 }, /* bad or shorted cable/module */
|
||||
{ "module_unknown_status", 64 },
|
||||
};
|
||||
|
||||
#endif /* __MLX5_EN_STATS_H__ */
|
||||
|
|
|
@ -862,7 +862,7 @@ struct mlx5_flow_table *mlx5_create_vport_flow_table(struct mlx5_flow_namespace
|
|||
ft_attr.level = level;
|
||||
ft_attr.prio = prio;
|
||||
|
||||
return __mlx5_create_flow_table(ns, &ft_attr, FS_FT_OP_MOD_NORMAL, 0);
|
||||
return __mlx5_create_flow_table(ns, &ft_attr, FS_FT_OP_MOD_NORMAL, vport);
|
||||
}
|
||||
|
||||
struct mlx5_flow_table*
|
||||
|
|
|
@ -275,10 +275,8 @@ static void poll_health(unsigned long data)
|
|||
struct mlx5_core_health *health = &dev->priv.health;
|
||||
u32 count;
|
||||
|
||||
if (dev->state == MLX5_DEVICE_STATE_INTERNAL_ERROR) {
|
||||
mod_timer(&health->timer, get_next_poll_jiffies());
|
||||
return;
|
||||
}
|
||||
if (dev->state == MLX5_DEVICE_STATE_INTERNAL_ERROR)
|
||||
goto out;
|
||||
|
||||
count = ioread32be(health->health_counter);
|
||||
if (count == health->prev)
|
||||
|
@ -290,8 +288,6 @@ static void poll_health(unsigned long data)
|
|||
if (health->miss_counter == MAX_MISSES) {
|
||||
dev_err(&dev->pdev->dev, "device's health compromised - reached miss count\n");
|
||||
print_health_info(dev);
|
||||
} else {
|
||||
mod_timer(&health->timer, get_next_poll_jiffies());
|
||||
}
|
||||
|
||||
if (in_fatal(dev) && !health->sick) {
|
||||
|
@ -305,6 +301,9 @@ static void poll_health(unsigned long data)
|
|||
"new health works are not permitted at this stage\n");
|
||||
spin_unlock(&health->wq_lock);
|
||||
}
|
||||
|
||||
out:
|
||||
mod_timer(&health->timer, get_next_poll_jiffies());
|
||||
}
|
||||
|
||||
void mlx5_start_health_poll(struct mlx5_core_dev *dev)
|
||||
|
|
|
@ -537,8 +537,10 @@ static int handle_hca_cap(struct mlx5_core_dev *dev)
|
|||
/* disable cmdif checksum */
|
||||
MLX5_SET(cmd_hca_cap, set_hca_cap, cmdif_checksum, 0);
|
||||
|
||||
/* If the HCA supports 4K UARs use it */
|
||||
if (MLX5_CAP_GEN_MAX(dev, uar_4k))
|
||||
/* Enable 4K UAR only when HCA supports it and page size is bigger
|
||||
* than 4K.
|
||||
*/
|
||||
if (MLX5_CAP_GEN_MAX(dev, uar_4k) && PAGE_SIZE > 4096)
|
||||
MLX5_SET(cmd_hca_cap, set_hca_cap, uar_4k, 1);
|
||||
|
||||
MLX5_SET(cmd_hca_cap, set_hca_cap, log_uar_page_sz, PAGE_SHIFT - 12);
|
||||
|
|
|
@ -2956,7 +2956,7 @@ static u32 qed_grc_dump_ctx_data(struct qed_hwfn *p_hwfn,
|
|||
qed_wr(p_hwfn,
|
||||
p_ptt,
|
||||
s_storm_defs[storm_id].cm_ctx_wr_addr,
|
||||
BIT(9) | lid);
|
||||
(i << 9) | lid);
|
||||
*(dump_buf + offset) = qed_rd(p_hwfn,
|
||||
p_ptt,
|
||||
rd_reg_addr);
|
||||
|
|
|
@ -214,13 +214,13 @@ static int dwmac4_wrback_get_tx_timestamp_status(struct dma_desc *p)
|
|||
{
|
||||
/* Context type from W/B descriptor must be zero */
|
||||
if (le32_to_cpu(p->des3) & TDES3_CONTEXT_TYPE)
|
||||
return -EINVAL;
|
||||
return 0;
|
||||
|
||||
/* Tx Timestamp Status is 1 so des0 and des1'll have valid values */
|
||||
if (le32_to_cpu(p->des3) & TDES3_TIMESTAMP_STATUS)
|
||||
return 0;
|
||||
return 1;
|
||||
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline u64 dwmac4_get_timestamp(void *desc, u32 ats)
|
||||
|
@ -282,7 +282,10 @@ static int dwmac4_wrback_get_rx_timestamp_status(void *desc, u32 ats)
|
|||
}
|
||||
}
|
||||
exit:
|
||||
return ret;
|
||||
if (likely(ret == 0))
|
||||
return 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void dwmac4_rd_init_rx_desc(struct dma_desc *p, int disable_rx_ic,
|
||||
|
|
|
@ -434,14 +434,14 @@ static void stmmac_get_tx_hwtstamp(struct stmmac_priv *priv,
|
|||
return;
|
||||
|
||||
/* check tx tstamp status */
|
||||
if (!priv->hw->desc->get_tx_timestamp_status(p)) {
|
||||
if (priv->hw->desc->get_tx_timestamp_status(p)) {
|
||||
/* get the valid tstamp */
|
||||
ns = priv->hw->desc->get_timestamp(p, priv->adv_ts);
|
||||
|
||||
memset(&shhwtstamp, 0, sizeof(struct skb_shared_hwtstamps));
|
||||
shhwtstamp.hwtstamp = ns_to_ktime(ns);
|
||||
|
||||
netdev_info(priv->dev, "get valid TX hw timestamp %llu\n", ns);
|
||||
netdev_dbg(priv->dev, "get valid TX hw timestamp %llu\n", ns);
|
||||
/* pass tstamp to stack */
|
||||
skb_tstamp_tx(skb, &shhwtstamp);
|
||||
}
|
||||
|
@ -468,19 +468,19 @@ static void stmmac_get_rx_hwtstamp(struct stmmac_priv *priv, struct dma_desc *p,
|
|||
return;
|
||||
|
||||
/* Check if timestamp is available */
|
||||
if (!priv->hw->desc->get_rx_timestamp_status(p, priv->adv_ts)) {
|
||||
if (priv->hw->desc->get_rx_timestamp_status(p, priv->adv_ts)) {
|
||||
/* For GMAC4, the valid timestamp is from CTX next desc. */
|
||||
if (priv->plat->has_gmac4)
|
||||
ns = priv->hw->desc->get_timestamp(np, priv->adv_ts);
|
||||
else
|
||||
ns = priv->hw->desc->get_timestamp(p, priv->adv_ts);
|
||||
|
||||
netdev_info(priv->dev, "get valid RX hw timestamp %llu\n", ns);
|
||||
netdev_dbg(priv->dev, "get valid RX hw timestamp %llu\n", ns);
|
||||
shhwtstamp = skb_hwtstamps(skb);
|
||||
memset(shhwtstamp, 0, sizeof(struct skb_shared_hwtstamps));
|
||||
shhwtstamp->hwtstamp = ns_to_ktime(ns);
|
||||
} else {
|
||||
netdev_err(priv->dev, "cannot get RX hw timestamp\n");
|
||||
netdev_dbg(priv->dev, "cannot get RX hw timestamp\n");
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -546,7 +546,10 @@ static int stmmac_hwtstamp_ioctl(struct net_device *dev, struct ifreq *ifr)
|
|||
/* PTP v1, UDP, any kind of event packet */
|
||||
config.rx_filter = HWTSTAMP_FILTER_PTP_V1_L4_EVENT;
|
||||
/* take time stamp for all event messages */
|
||||
snap_type_sel = PTP_TCR_SNAPTYPSEL_1;
|
||||
if (priv->plat->has_gmac4)
|
||||
snap_type_sel = PTP_GMAC4_TCR_SNAPTYPSEL_1;
|
||||
else
|
||||
snap_type_sel = PTP_TCR_SNAPTYPSEL_1;
|
||||
|
||||
ptp_over_ipv4_udp = PTP_TCR_TSIPV4ENA;
|
||||
ptp_over_ipv6_udp = PTP_TCR_TSIPV6ENA;
|
||||
|
@ -578,7 +581,10 @@ static int stmmac_hwtstamp_ioctl(struct net_device *dev, struct ifreq *ifr)
|
|||
config.rx_filter = HWTSTAMP_FILTER_PTP_V2_L4_EVENT;
|
||||
ptp_v2 = PTP_TCR_TSVER2ENA;
|
||||
/* take time stamp for all event messages */
|
||||
snap_type_sel = PTP_TCR_SNAPTYPSEL_1;
|
||||
if (priv->plat->has_gmac4)
|
||||
snap_type_sel = PTP_GMAC4_TCR_SNAPTYPSEL_1;
|
||||
else
|
||||
snap_type_sel = PTP_TCR_SNAPTYPSEL_1;
|
||||
|
||||
ptp_over_ipv4_udp = PTP_TCR_TSIPV4ENA;
|
||||
ptp_over_ipv6_udp = PTP_TCR_TSIPV6ENA;
|
||||
|
@ -612,7 +618,10 @@ static int stmmac_hwtstamp_ioctl(struct net_device *dev, struct ifreq *ifr)
|
|||
config.rx_filter = HWTSTAMP_FILTER_PTP_V2_EVENT;
|
||||
ptp_v2 = PTP_TCR_TSVER2ENA;
|
||||
/* take time stamp for all event messages */
|
||||
snap_type_sel = PTP_TCR_SNAPTYPSEL_1;
|
||||
if (priv->plat->has_gmac4)
|
||||
snap_type_sel = PTP_GMAC4_TCR_SNAPTYPSEL_1;
|
||||
else
|
||||
snap_type_sel = PTP_TCR_SNAPTYPSEL_1;
|
||||
|
||||
ptp_over_ipv4_udp = PTP_TCR_TSIPV4ENA;
|
||||
ptp_over_ipv6_udp = PTP_TCR_TSIPV6ENA;
|
||||
|
|
|
@ -59,7 +59,8 @@
|
|||
/* Enable Snapshot for Messages Relevant to Master */
|
||||
#define PTP_TCR_TSMSTRENA BIT(15)
|
||||
/* Select PTP packets for Taking Snapshots */
|
||||
#define PTP_TCR_SNAPTYPSEL_1 GENMASK(17, 16)
|
||||
#define PTP_TCR_SNAPTYPSEL_1 BIT(16)
|
||||
#define PTP_GMAC4_TCR_SNAPTYPSEL_1 GENMASK(17, 16)
|
||||
/* Enable MAC address for PTP Frame Filtering */
|
||||
#define PTP_TCR_TSENMACADDR BIT(18)
|
||||
|
||||
|
|
|
@ -1007,7 +1007,7 @@ static void geneve_setup(struct net_device *dev)
|
|||
|
||||
dev->netdev_ops = &geneve_netdev_ops;
|
||||
dev->ethtool_ops = &geneve_ethtool_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
|
||||
SET_NETDEV_DEVTYPE(dev, &geneve_type);
|
||||
|
||||
|
|
|
@ -611,7 +611,7 @@ static const struct net_device_ops gtp_netdev_ops = {
|
|||
static void gtp_link_setup(struct net_device *dev)
|
||||
{
|
||||
dev->netdev_ops = >p_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
|
||||
dev->hard_header_len = 0;
|
||||
dev->addr_len = 0;
|
||||
|
|
|
@ -311,7 +311,7 @@ static void sp_setup(struct net_device *dev)
|
|||
{
|
||||
/* Finish setting up the DEVICE info. */
|
||||
dev->netdev_ops = &sp_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->mtu = SIXP_MTU;
|
||||
dev->hard_header_len = AX25_MAX_HEADER_LEN;
|
||||
dev->header_ops = &ax25_header_ops;
|
||||
|
|
|
@ -476,7 +476,7 @@ static const struct net_device_ops bpq_netdev_ops = {
|
|||
static void bpq_setup(struct net_device *dev)
|
||||
{
|
||||
dev->netdev_ops = &bpq_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
|
||||
memcpy(dev->broadcast, &ax25_bcast, AX25_ADDR_LEN);
|
||||
memcpy(dev->dev_addr, &ax25_defaddr, AX25_ADDR_LEN);
|
||||
|
|
|
@ -171,6 +171,8 @@ struct rndis_device {
|
|||
spinlock_t request_lock;
|
||||
struct list_head req_list;
|
||||
|
||||
struct work_struct mcast_work;
|
||||
|
||||
u8 hw_mac_adr[ETH_ALEN];
|
||||
u8 rss_key[NETVSC_HASH_KEYLEN];
|
||||
u16 ind_table[ITAB_NUM];
|
||||
|
@ -201,6 +203,7 @@ int rndis_filter_open(struct netvsc_device *nvdev);
|
|||
int rndis_filter_close(struct netvsc_device *nvdev);
|
||||
int rndis_filter_device_add(struct hv_device *dev,
|
||||
struct netvsc_device_info *info);
|
||||
void rndis_filter_update(struct netvsc_device *nvdev);
|
||||
void rndis_filter_device_remove(struct hv_device *dev,
|
||||
struct netvsc_device *nvdev);
|
||||
int rndis_filter_set_rss_param(struct rndis_device *rdev,
|
||||
|
@ -211,7 +214,6 @@ int rndis_filter_receive(struct net_device *ndev,
|
|||
struct vmbus_channel *channel,
|
||||
void *data, u32 buflen);
|
||||
|
||||
int rndis_filter_set_packet_filter(struct rndis_device *dev, u32 new_filter);
|
||||
int rndis_filter_set_device_mac(struct net_device *ndev, char *mac);
|
||||
|
||||
void netvsc_switch_datapath(struct net_device *nv_dev, bool vf);
|
||||
|
@ -696,7 +698,6 @@ struct net_device_context {
|
|||
/* list protection */
|
||||
spinlock_t lock;
|
||||
|
||||
struct work_struct work;
|
||||
u32 msg_enable; /* debug level */
|
||||
|
||||
u32 tx_checksum_mask;
|
||||
|
|
|
@ -56,37 +56,12 @@ static int debug = -1;
|
|||
module_param(debug, int, S_IRUGO);
|
||||
MODULE_PARM_DESC(debug, "Debug level (0=none,...,16=all)");
|
||||
|
||||
static void do_set_multicast(struct work_struct *w)
|
||||
{
|
||||
struct net_device_context *ndevctx =
|
||||
container_of(w, struct net_device_context, work);
|
||||
struct hv_device *device_obj = ndevctx->device_ctx;
|
||||
struct net_device *ndev = hv_get_drvdata(device_obj);
|
||||
struct netvsc_device *nvdev = rcu_dereference(ndevctx->nvdev);
|
||||
struct rndis_device *rdev;
|
||||
|
||||
if (!nvdev)
|
||||
return;
|
||||
|
||||
rdev = nvdev->extension;
|
||||
if (rdev == NULL)
|
||||
return;
|
||||
|
||||
if (ndev->flags & IFF_PROMISC)
|
||||
rndis_filter_set_packet_filter(rdev,
|
||||
NDIS_PACKET_TYPE_PROMISCUOUS);
|
||||
else
|
||||
rndis_filter_set_packet_filter(rdev,
|
||||
NDIS_PACKET_TYPE_BROADCAST |
|
||||
NDIS_PACKET_TYPE_ALL_MULTICAST |
|
||||
NDIS_PACKET_TYPE_DIRECTED);
|
||||
}
|
||||
|
||||
static void netvsc_set_multicast_list(struct net_device *net)
|
||||
{
|
||||
struct net_device_context *net_device_ctx = netdev_priv(net);
|
||||
struct netvsc_device *nvdev = rtnl_dereference(net_device_ctx->nvdev);
|
||||
|
||||
schedule_work(&net_device_ctx->work);
|
||||
rndis_filter_update(nvdev);
|
||||
}
|
||||
|
||||
static int netvsc_open(struct net_device *net)
|
||||
|
@ -123,8 +98,6 @@ static int netvsc_close(struct net_device *net)
|
|||
|
||||
netif_tx_disable(net);
|
||||
|
||||
/* Make sure netvsc_set_multicast_list doesn't re-enable filter! */
|
||||
cancel_work_sync(&net_device_ctx->work);
|
||||
ret = rndis_filter_close(nvdev);
|
||||
if (ret != 0) {
|
||||
netdev_err(net, "unable to close device (ret %d).\n", ret);
|
||||
|
@ -1028,7 +1001,7 @@ static const struct {
|
|||
static int netvsc_get_sset_count(struct net_device *dev, int string_set)
|
||||
{
|
||||
struct net_device_context *ndc = netdev_priv(dev);
|
||||
struct netvsc_device *nvdev = rcu_dereference(ndc->nvdev);
|
||||
struct netvsc_device *nvdev = rtnl_dereference(ndc->nvdev);
|
||||
|
||||
if (!nvdev)
|
||||
return -ENODEV;
|
||||
|
@ -1158,11 +1131,22 @@ netvsc_get_rxnfc(struct net_device *dev, struct ethtool_rxnfc *info,
|
|||
}
|
||||
|
||||
#ifdef CONFIG_NET_POLL_CONTROLLER
|
||||
static void netvsc_poll_controller(struct net_device *net)
|
||||
static void netvsc_poll_controller(struct net_device *dev)
|
||||
{
|
||||
/* As netvsc_start_xmit() works synchronous we don't have to
|
||||
* trigger anything here.
|
||||
*/
|
||||
struct net_device_context *ndc = netdev_priv(dev);
|
||||
struct netvsc_device *ndev;
|
||||
int i;
|
||||
|
||||
rcu_read_lock();
|
||||
ndev = rcu_dereference(ndc->nvdev);
|
||||
if (ndev) {
|
||||
for (i = 0; i < ndev->num_chn; i++) {
|
||||
struct netvsc_channel *nvchan = &ndev->chan_table[i];
|
||||
|
||||
napi_schedule(&nvchan->napi);
|
||||
}
|
||||
}
|
||||
rcu_read_unlock();
|
||||
}
|
||||
#endif
|
||||
|
||||
|
@ -1552,7 +1536,6 @@ static int netvsc_probe(struct hv_device *dev,
|
|||
hv_set_drvdata(dev, net);
|
||||
|
||||
INIT_DELAYED_WORK(&net_device_ctx->dwork, netvsc_link_change);
|
||||
INIT_WORK(&net_device_ctx->work, do_set_multicast);
|
||||
|
||||
spin_lock_init(&net_device_ctx->lock);
|
||||
INIT_LIST_HEAD(&net_device_ctx->reconfig_events);
|
||||
|
@ -1622,7 +1605,6 @@ static int netvsc_remove(struct hv_device *dev)
|
|||
netif_device_detach(net);
|
||||
|
||||
cancel_delayed_work_sync(&ndev_ctx->dwork);
|
||||
cancel_work_sync(&ndev_ctx->work);
|
||||
|
||||
/*
|
||||
* Call to the vsc driver to let it know that the device is being
|
||||
|
|
|
@ -31,6 +31,7 @@
|
|||
|
||||
#include "hyperv_net.h"
|
||||
|
||||
static void rndis_set_multicast(struct work_struct *w);
|
||||
|
||||
#define RNDIS_EXT_LEN PAGE_SIZE
|
||||
struct rndis_request {
|
||||
|
@ -76,6 +77,7 @@ static struct rndis_device *get_rndis_device(void)
|
|||
spin_lock_init(&device->request_lock);
|
||||
|
||||
INIT_LIST_HEAD(&device->req_list);
|
||||
INIT_WORK(&device->mcast_work, rndis_set_multicast);
|
||||
|
||||
device->state = RNDIS_DEV_UNINITIALIZED;
|
||||
|
||||
|
@ -815,7 +817,8 @@ static int rndis_filter_query_link_speed(struct rndis_device *dev)
|
|||
return ret;
|
||||
}
|
||||
|
||||
int rndis_filter_set_packet_filter(struct rndis_device *dev, u32 new_filter)
|
||||
static int rndis_filter_set_packet_filter(struct rndis_device *dev,
|
||||
u32 new_filter)
|
||||
{
|
||||
struct rndis_request *request;
|
||||
struct rndis_set_request *set;
|
||||
|
@ -846,6 +849,28 @@ int rndis_filter_set_packet_filter(struct rndis_device *dev, u32 new_filter)
|
|||
return ret;
|
||||
}
|
||||
|
||||
static void rndis_set_multicast(struct work_struct *w)
|
||||
{
|
||||
struct rndis_device *rdev
|
||||
= container_of(w, struct rndis_device, mcast_work);
|
||||
|
||||
if (rdev->ndev->flags & IFF_PROMISC)
|
||||
rndis_filter_set_packet_filter(rdev,
|
||||
NDIS_PACKET_TYPE_PROMISCUOUS);
|
||||
else
|
||||
rndis_filter_set_packet_filter(rdev,
|
||||
NDIS_PACKET_TYPE_BROADCAST |
|
||||
NDIS_PACKET_TYPE_ALL_MULTICAST |
|
||||
NDIS_PACKET_TYPE_DIRECTED);
|
||||
}
|
||||
|
||||
void rndis_filter_update(struct netvsc_device *nvdev)
|
||||
{
|
||||
struct rndis_device *rdev = nvdev->extension;
|
||||
|
||||
schedule_work(&rdev->mcast_work);
|
||||
}
|
||||
|
||||
static int rndis_filter_init_device(struct rndis_device *dev)
|
||||
{
|
||||
struct rndis_request *request;
|
||||
|
@ -973,6 +998,9 @@ static int rndis_filter_close_device(struct rndis_device *dev)
|
|||
if (dev->state != RNDIS_DEV_DATAINITIALIZED)
|
||||
return 0;
|
||||
|
||||
/* Make sure rndis_set_multicast doesn't re-enable filter! */
|
||||
cancel_work_sync(&dev->mcast_work);
|
||||
|
||||
ret = rndis_filter_set_packet_filter(dev, 0);
|
||||
if (ret == -ENODEV)
|
||||
ret = 0;
|
||||
|
|
|
@ -207,7 +207,6 @@ static void ifb_dev_free(struct net_device *dev)
|
|||
__skb_queue_purge(&txp->tq);
|
||||
}
|
||||
kfree(dp->tx_private);
|
||||
free_netdev(dev);
|
||||
}
|
||||
|
||||
static void ifb_setup(struct net_device *dev)
|
||||
|
@ -230,7 +229,8 @@ static void ifb_setup(struct net_device *dev)
|
|||
dev->priv_flags &= ~IFF_TX_SKB_SHARING;
|
||||
netif_keep_dst(dev);
|
||||
eth_hw_addr_random(dev);
|
||||
dev->destructor = ifb_dev_free;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->priv_destructor = ifb_dev_free;
|
||||
}
|
||||
|
||||
static netdev_tx_t ifb_xmit(struct sk_buff *skb, struct net_device *dev)
|
||||
|
|
|
@ -632,7 +632,7 @@ void ipvlan_link_setup(struct net_device *dev)
|
|||
dev->priv_flags &= ~(IFF_XMIT_DST_RELEASE | IFF_TX_SKB_SHARING);
|
||||
dev->priv_flags |= IFF_UNICAST_FLT | IFF_NO_QUEUE;
|
||||
dev->netdev_ops = &ipvlan_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->header_ops = &ipvlan_header_ops;
|
||||
dev->ethtool_ops = &ipvlan_ethtool_ops;
|
||||
}
|
||||
|
|
|
@ -159,7 +159,6 @@ static void loopback_dev_free(struct net_device *dev)
|
|||
{
|
||||
dev_net(dev)->loopback_dev = NULL;
|
||||
free_percpu(dev->lstats);
|
||||
free_netdev(dev);
|
||||
}
|
||||
|
||||
static const struct net_device_ops loopback_ops = {
|
||||
|
@ -196,7 +195,8 @@ static void loopback_setup(struct net_device *dev)
|
|||
dev->ethtool_ops = &loopback_ethtool_ops;
|
||||
dev->header_ops = ð_header_ops;
|
||||
dev->netdev_ops = &loopback_ops;
|
||||
dev->destructor = loopback_dev_free;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->priv_destructor = loopback_dev_free;
|
||||
}
|
||||
|
||||
/* Setup and register the loopback device. */
|
||||
|
|
|
@ -2996,7 +2996,6 @@ static void macsec_free_netdev(struct net_device *dev)
|
|||
free_percpu(macsec->secy.tx_sc.stats);
|
||||
|
||||
dev_put(real_dev);
|
||||
free_netdev(dev);
|
||||
}
|
||||
|
||||
static void macsec_setup(struct net_device *dev)
|
||||
|
@ -3006,7 +3005,8 @@ static void macsec_setup(struct net_device *dev)
|
|||
dev->max_mtu = ETH_MAX_MTU;
|
||||
dev->priv_flags |= IFF_NO_QUEUE;
|
||||
dev->netdev_ops = &macsec_netdev_ops;
|
||||
dev->destructor = macsec_free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->priv_destructor = macsec_free_netdev;
|
||||
SET_NETDEV_DEVTYPE(dev, &macsec_type);
|
||||
|
||||
eth_zero_addr(dev->broadcast);
|
||||
|
|
|
@ -1092,7 +1092,7 @@ void macvlan_common_setup(struct net_device *dev)
|
|||
netif_keep_dst(dev);
|
||||
dev->priv_flags |= IFF_UNICAST_FLT;
|
||||
dev->netdev_ops = &macvlan_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->header_ops = &macvlan_hard_header_ops;
|
||||
dev->ethtool_ops = &macvlan_ethtool_ops;
|
||||
}
|
||||
|
|
|
@ -358,7 +358,7 @@ static ssize_t enabled_store(struct config_item *item,
|
|||
if (err)
|
||||
goto out_unlock;
|
||||
|
||||
pr_info("netconsole: network logging started\n");
|
||||
pr_info("network logging started\n");
|
||||
} else { /* false */
|
||||
/* We need to disable the netconsole before cleaning it up
|
||||
* otherwise we might end up in write_msg() with
|
||||
|
|
|
@ -113,7 +113,7 @@ static void nlmon_setup(struct net_device *dev)
|
|||
|
||||
dev->netdev_ops = &nlmon_ops;
|
||||
dev->ethtool_ops = &nlmon_ethtool_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
|
||||
dev->features = NETIF_F_SG | NETIF_F_FRAGLIST |
|
||||
NETIF_F_HIGHDMA | NETIF_F_LLTX;
|
||||
|
|
|
@ -127,6 +127,7 @@ config MDIO_THUNDER
|
|||
tristate "ThunderX SOCs MDIO buses"
|
||||
depends on 64BIT
|
||||
depends on PCI
|
||||
depends on !(MDIO_DEVICE=y && PHYLIB=m)
|
||||
select MDIO_CAVIUM
|
||||
help
|
||||
This driver supports the MDIO interfaces found on Cavium
|
||||
|
|
|
@ -54,6 +54,8 @@ static const char *phy_speed_to_str(int speed)
|
|||
return "5Gbps";
|
||||
case SPEED_10000:
|
||||
return "10Gbps";
|
||||
case SPEED_14000:
|
||||
return "14Gbps";
|
||||
case SPEED_20000:
|
||||
return "20Gbps";
|
||||
case SPEED_25000:
|
||||
|
|
|
@ -629,7 +629,7 @@ static void sl_uninit(struct net_device *dev)
|
|||
static void sl_free_netdev(struct net_device *dev)
|
||||
{
|
||||
int i = dev->base_addr;
|
||||
free_netdev(dev);
|
||||
|
||||
slip_devs[i] = NULL;
|
||||
}
|
||||
|
||||
|
@ -651,7 +651,8 @@ static const struct net_device_ops sl_netdev_ops = {
|
|||
static void sl_setup(struct net_device *dev)
|
||||
{
|
||||
dev->netdev_ops = &sl_netdev_ops;
|
||||
dev->destructor = sl_free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->priv_destructor = sl_free_netdev;
|
||||
|
||||
dev->hard_header_len = 0;
|
||||
dev->addr_len = 0;
|
||||
|
@ -1369,8 +1370,6 @@ static void __exit slip_exit(void)
|
|||
if (sl->tty) {
|
||||
printk(KERN_ERR "%s: tty discipline still running\n",
|
||||
dev->name);
|
||||
/* Intentionally leak the control block. */
|
||||
dev->destructor = NULL;
|
||||
}
|
||||
|
||||
unregister_netdev(dev);
|
||||
|
|
|
@ -1643,7 +1643,6 @@ static void team_destructor(struct net_device *dev)
|
|||
struct team *team = netdev_priv(dev);
|
||||
|
||||
free_percpu(team->pcpu_stats);
|
||||
free_netdev(dev);
|
||||
}
|
||||
|
||||
static int team_open(struct net_device *dev)
|
||||
|
@ -2079,7 +2078,8 @@ static void team_setup(struct net_device *dev)
|
|||
|
||||
dev->netdev_ops = &team_netdev_ops;
|
||||
dev->ethtool_ops = &team_ethtool_ops;
|
||||
dev->destructor = team_destructor;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->priv_destructor = team_destructor;
|
||||
dev->priv_flags &= ~(IFF_XMIT_DST_RELEASE | IFF_TX_SKB_SHARING);
|
||||
dev->priv_flags |= IFF_NO_QUEUE;
|
||||
dev->priv_flags |= IFF_TEAM;
|
||||
|
|
|
@ -1560,7 +1560,6 @@ static void tun_free_netdev(struct net_device *dev)
|
|||
free_percpu(tun->pcpu_stats);
|
||||
tun_flow_uninit(tun);
|
||||
security_tun_dev_free_security(tun->security);
|
||||
free_netdev(dev);
|
||||
}
|
||||
|
||||
static void tun_setup(struct net_device *dev)
|
||||
|
@ -1571,7 +1570,8 @@ static void tun_setup(struct net_device *dev)
|
|||
tun->group = INVALID_GID;
|
||||
|
||||
dev->ethtool_ops = &tun_ethtool_ops;
|
||||
dev->destructor = tun_free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->priv_destructor = tun_free_netdev;
|
||||
/* We prefer our own queue length */
|
||||
dev->tx_queue_len = TUN_READQ_SIZE;
|
||||
}
|
||||
|
|
|
@ -298,7 +298,7 @@ static void usbpn_setup(struct net_device *dev)
|
|||
dev->addr_len = 1;
|
||||
dev->tx_queue_len = 3;
|
||||
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
}
|
||||
|
||||
/*
|
||||
|
|
|
@ -123,7 +123,7 @@ static void qmimux_setup(struct net_device *dev)
|
|||
dev->addr_len = 0;
|
||||
dev->flags = IFF_POINTOPOINT | IFF_NOARP | IFF_MULTICAST;
|
||||
dev->netdev_ops = &qmimux_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
}
|
||||
|
||||
static struct net_device *qmimux_find_dev(struct usbnet *dev, u8 mux_id)
|
||||
|
@ -1192,6 +1192,8 @@ static const struct usb_device_id products[] = {
|
|||
{QMI_FIXED_INTF(0x1199, 0x9056, 8)}, /* Sierra Wireless Modem */
|
||||
{QMI_FIXED_INTF(0x1199, 0x9057, 8)},
|
||||
{QMI_FIXED_INTF(0x1199, 0x9061, 8)}, /* Sierra Wireless Modem */
|
||||
{QMI_FIXED_INTF(0x1199, 0x9063, 8)}, /* Sierra Wireless EM7305 */
|
||||
{QMI_FIXED_INTF(0x1199, 0x9063, 10)}, /* Sierra Wireless EM7305 */
|
||||
{QMI_FIXED_INTF(0x1199, 0x9071, 8)}, /* Sierra Wireless MC74xx */
|
||||
{QMI_FIXED_INTF(0x1199, 0x9071, 10)}, /* Sierra Wireless MC74xx */
|
||||
{QMI_FIXED_INTF(0x1199, 0x9079, 8)}, /* Sierra Wireless EM74xx */
|
||||
|
@ -1206,6 +1208,8 @@ static const struct usb_device_id products[] = {
|
|||
{QMI_FIXED_INTF(0x1bc7, 0x1100, 3)}, /* Telit ME910 */
|
||||
{QMI_FIXED_INTF(0x1bc7, 0x1200, 5)}, /* Telit LE920 */
|
||||
{QMI_QUIRK_SET_DTR(0x1bc7, 0x1201, 2)}, /* Telit LE920, LE920A4 */
|
||||
{QMI_FIXED_INTF(0x1c9e, 0x9801, 3)}, /* Telewell TW-3G HSPA+ */
|
||||
{QMI_FIXED_INTF(0x1c9e, 0x9803, 4)}, /* Telewell TW-3G HSPA+ */
|
||||
{QMI_FIXED_INTF(0x1c9e, 0x9b01, 3)}, /* XS Stick W100-2 from 4G Systems */
|
||||
{QMI_FIXED_INTF(0x0b3c, 0xc000, 4)}, /* Olivetti Olicard 100 */
|
||||
{QMI_FIXED_INTF(0x0b3c, 0xc001, 4)}, /* Olivetti Olicard 120 */
|
||||
|
|
|
@ -4368,6 +4368,8 @@ static u8 rtl_get_version(struct usb_interface *intf)
|
|||
break;
|
||||
}
|
||||
|
||||
dev_dbg(&intf->dev, "Detected version 0x%04x\n", version);
|
||||
|
||||
return version;
|
||||
}
|
||||
|
||||
|
|
|
@ -222,7 +222,6 @@ static int veth_dev_init(struct net_device *dev)
|
|||
static void veth_dev_free(struct net_device *dev)
|
||||
{
|
||||
free_percpu(dev->vstats);
|
||||
free_netdev(dev);
|
||||
}
|
||||
|
||||
#ifdef CONFIG_NET_POLL_CONTROLLER
|
||||
|
@ -317,7 +316,8 @@ static void veth_setup(struct net_device *dev)
|
|||
NETIF_F_HW_VLAN_STAG_TX |
|
||||
NETIF_F_HW_VLAN_CTAG_RX |
|
||||
NETIF_F_HW_VLAN_STAG_RX);
|
||||
dev->destructor = veth_dev_free;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->priv_destructor = veth_dev_free;
|
||||
dev->max_mtu = ETH_MAX_MTU;
|
||||
|
||||
dev->hw_features = VETH_FEATURES;
|
||||
|
|
|
@ -36,12 +36,14 @@
|
|||
#include <net/addrconf.h>
|
||||
#include <net/l3mdev.h>
|
||||
#include <net/fib_rules.h>
|
||||
#include <net/netns/generic.h>
|
||||
|
||||
#define DRV_NAME "vrf"
|
||||
#define DRV_VERSION "1.0"
|
||||
|
||||
#define FIB_RULE_PREF 1000 /* default preference for FIB rules */
|
||||
static bool add_fib_rules = true;
|
||||
|
||||
static unsigned int vrf_net_id;
|
||||
|
||||
struct net_vrf {
|
||||
struct rtable __rcu *rth;
|
||||
|
@ -1348,7 +1350,7 @@ static void vrf_setup(struct net_device *dev)
|
|||
dev->netdev_ops = &vrf_netdev_ops;
|
||||
dev->l3mdev_ops = &vrf_l3mdev_ops;
|
||||
dev->ethtool_ops = &vrf_ethtool_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
|
||||
/* Fill in device structure with ethernet-generic values. */
|
||||
eth_hw_addr_random(dev);
|
||||
|
@ -1394,6 +1396,8 @@ static int vrf_newlink(struct net *src_net, struct net_device *dev,
|
|||
struct nlattr *tb[], struct nlattr *data[])
|
||||
{
|
||||
struct net_vrf *vrf = netdev_priv(dev);
|
||||
bool *add_fib_rules;
|
||||
struct net *net;
|
||||
int err;
|
||||
|
||||
if (!data || !data[IFLA_VRF_TABLE])
|
||||
|
@ -1409,13 +1413,15 @@ static int vrf_newlink(struct net *src_net, struct net_device *dev,
|
|||
if (err)
|
||||
goto out;
|
||||
|
||||
if (add_fib_rules) {
|
||||
net = dev_net(dev);
|
||||
add_fib_rules = net_generic(net, vrf_net_id);
|
||||
if (*add_fib_rules) {
|
||||
err = vrf_add_fib_rules(dev);
|
||||
if (err) {
|
||||
unregister_netdevice(dev);
|
||||
goto out;
|
||||
}
|
||||
add_fib_rules = false;
|
||||
*add_fib_rules = false;
|
||||
}
|
||||
|
||||
out:
|
||||
|
@ -1498,16 +1504,38 @@ static struct notifier_block vrf_notifier_block __read_mostly = {
|
|||
.notifier_call = vrf_device_event,
|
||||
};
|
||||
|
||||
/* Initialize per network namespace state */
|
||||
static int __net_init vrf_netns_init(struct net *net)
|
||||
{
|
||||
bool *add_fib_rules = net_generic(net, vrf_net_id);
|
||||
|
||||
*add_fib_rules = true;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static struct pernet_operations vrf_net_ops __net_initdata = {
|
||||
.init = vrf_netns_init,
|
||||
.id = &vrf_net_id,
|
||||
.size = sizeof(bool),
|
||||
};
|
||||
|
||||
static int __init vrf_init_module(void)
|
||||
{
|
||||
int rc;
|
||||
|
||||
register_netdevice_notifier(&vrf_notifier_block);
|
||||
|
||||
rc = rtnl_link_register(&vrf_link_ops);
|
||||
rc = register_pernet_subsys(&vrf_net_ops);
|
||||
if (rc < 0)
|
||||
goto error;
|
||||
|
||||
rc = rtnl_link_register(&vrf_link_ops);
|
||||
if (rc < 0) {
|
||||
unregister_pernet_subsys(&vrf_net_ops);
|
||||
goto error;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
error:
|
||||
|
|
|
@ -135,7 +135,7 @@ static void vsockmon_setup(struct net_device *dev)
|
|||
|
||||
dev->netdev_ops = &vsockmon_ops;
|
||||
dev->ethtool_ops = &vsockmon_ethtool_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
|
||||
dev->features = NETIF_F_SG | NETIF_F_FRAGLIST |
|
||||
NETIF_F_HIGHDMA | NETIF_F_LLTX;
|
||||
|
|
|
@ -2611,7 +2611,7 @@ static void vxlan_setup(struct net_device *dev)
|
|||
eth_hw_addr_random(dev);
|
||||
ether_setup(dev);
|
||||
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
SET_NETDEV_DEVTYPE(dev, &vxlan_type);
|
||||
|
||||
dev->features |= NETIF_F_LLTX;
|
||||
|
|
|
@ -475,7 +475,7 @@ static void dlci_setup(struct net_device *dev)
|
|||
dev->flags = 0;
|
||||
dev->header_ops = &dlci_header_ops;
|
||||
dev->netdev_ops = &dlci_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
|
||||
dlp->receive = dlci_receive;
|
||||
|
||||
|
|
|
@ -1106,7 +1106,7 @@ static int fr_add_pvc(struct net_device *frad, unsigned int dlci, int type)
|
|||
return -EIO;
|
||||
}
|
||||
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
*get_dev_p(pvc, type) = dev;
|
||||
if (!used) {
|
||||
state(hdlc)->dce_changed = 1;
|
||||
|
|
|
@ -306,7 +306,7 @@ static const struct net_device_ops lapbeth_netdev_ops = {
|
|||
static void lapbeth_setup(struct net_device *dev)
|
||||
{
|
||||
dev->netdev_ops = &lapbeth_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->type = ARPHRD_X25;
|
||||
dev->hard_header_len = 3;
|
||||
dev->mtu = 1000;
|
||||
|
|
|
@ -1287,7 +1287,7 @@ void init_netdev(struct net_device *dev)
|
|||
struct ath6kl *ar = ath6kl_priv(dev);
|
||||
|
||||
dev->netdev_ops = &ath6kl_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->watchdog_timeo = ATH6KL_TX_TIMEOUT;
|
||||
|
||||
dev->needed_headroom = ETH_HLEN;
|
||||
|
|
|
@ -5225,7 +5225,6 @@ void brcmf_cfg80211_free_netdev(struct net_device *ndev)
|
|||
|
||||
if (vif)
|
||||
brcmf_free_vif(vif);
|
||||
free_netdev(ndev);
|
||||
}
|
||||
|
||||
static bool brcmf_is_linkup(const struct brcmf_event_msg *e)
|
||||
|
|
|
@ -624,7 +624,8 @@ struct brcmf_if *brcmf_add_if(struct brcmf_pub *drvr, s32 bsscfgidx, s32 ifidx,
|
|||
if (!ndev)
|
||||
return ERR_PTR(-ENOMEM);
|
||||
|
||||
ndev->destructor = brcmf_cfg80211_free_netdev;
|
||||
ndev->needs_free_netdev = true;
|
||||
ndev->priv_destructor = brcmf_cfg80211_free_netdev;
|
||||
ifp = netdev_priv(ndev);
|
||||
ifp->ndev = ndev;
|
||||
/* store mapping ifidx to bsscfgidx */
|
||||
|
|
|
@ -73,7 +73,7 @@ struct net_device * hostap_add_interface(struct local_info *local,
|
|||
dev->mem_end = mdev->mem_end;
|
||||
|
||||
hostap_setup_dev(dev, local, type);
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
|
||||
sprintf(dev->name, "%s%s", prefix, name);
|
||||
if (!rtnl_locked)
|
||||
|
|
|
@ -2861,7 +2861,7 @@ static const struct net_device_ops hwsim_netdev_ops = {
|
|||
static void hwsim_mon_setup(struct net_device *dev)
|
||||
{
|
||||
dev->netdev_ops = &hwsim_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
ether_setup(dev);
|
||||
dev->priv_flags |= IFF_NO_QUEUE;
|
||||
dev->type = ARPHRD_IEEE80211_RADIOTAP;
|
||||
|
|
|
@ -1280,7 +1280,7 @@ void mwifiex_init_priv_params(struct mwifiex_private *priv,
|
|||
struct net_device *dev)
|
||||
{
|
||||
dev->netdev_ops = &mwifiex_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
/* Initialize private structure */
|
||||
priv->current_key_index = 0;
|
||||
priv->media_connected = false;
|
||||
|
|
|
@ -1954,7 +1954,6 @@ static void netiucv_free_netdevice(struct net_device *dev)
|
|||
privptr->conn = NULL; privptr->fsm = NULL;
|
||||
/* privptr gets freed by free_netdev() */
|
||||
}
|
||||
free_netdev(dev);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -1972,7 +1971,8 @@ static void netiucv_setup_netdevice(struct net_device *dev)
|
|||
dev->mtu = NETIUCV_MTU_DEFAULT;
|
||||
dev->min_mtu = 576;
|
||||
dev->max_mtu = NETIUCV_MTU_MAX;
|
||||
dev->destructor = netiucv_free_netdevice;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->priv_destructor = netiucv_free_netdevice;
|
||||
dev->hard_header_len = NETIUCV_HDRLEN;
|
||||
dev->addr_len = 0;
|
||||
dev->type = ARPHRD_SLIP;
|
||||
|
|
|
@ -152,7 +152,7 @@ static const struct net_device_ops mon_netdev_ops = {
|
|||
static void mon_setup(struct net_device *dev)
|
||||
{
|
||||
dev->netdev_ops = &mon_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
ether_setup(dev);
|
||||
dev->priv_flags |= IFF_NO_QUEUE;
|
||||
dev->type = ARPHRD_IEEE80211;
|
||||
|
|
|
@ -2667,7 +2667,8 @@ static int rtw_cfg80211_add_monitor_if (struct adapter *padapter, char *name, st
|
|||
mon_ndev->type = ARPHRD_IEEE80211_RADIOTAP;
|
||||
strncpy(mon_ndev->name, name, IFNAMSIZ);
|
||||
mon_ndev->name[IFNAMSIZ - 1] = 0;
|
||||
mon_ndev->destructor = rtw_ndev_destructor;
|
||||
mon_ndev->needs_free_netdev = true;
|
||||
mon_ndev->priv_destructor = rtw_ndev_destructor;
|
||||
|
||||
mon_ndev->netdev_ops = &rtw_cfg80211_monitor_if_ops;
|
||||
|
||||
|
|
|
@ -1207,8 +1207,6 @@ void rtw_ndev_destructor(struct net_device *ndev)
|
|||
|
||||
if (ndev->ieee80211_ptr)
|
||||
kfree((u8 *)ndev->ieee80211_ptr);
|
||||
|
||||
free_netdev(ndev);
|
||||
}
|
||||
|
||||
void rtw_dev_unload(struct adapter *padapter)
|
||||
|
|
|
@ -281,7 +281,7 @@ static void pn_net_setup(struct net_device *dev)
|
|||
dev->tx_queue_len = 1;
|
||||
|
||||
dev->netdev_ops = &pn_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->header_ops = &phonet_header_ops;
|
||||
}
|
||||
|
||||
|
|
|
@ -914,8 +914,7 @@ struct xfrmdev_ops {
|
|||
*
|
||||
* int (*ndo_change_mtu)(struct net_device *dev, int new_mtu);
|
||||
* Called when a user wants to change the Maximum Transfer Unit
|
||||
* of a device. If not defined, any request to change MTU will
|
||||
* will return an error.
|
||||
* of a device.
|
||||
*
|
||||
* void (*ndo_tx_timeout)(struct net_device *dev);
|
||||
* Callback used when the transmitter has not made any progress
|
||||
|
@ -1596,8 +1595,8 @@ enum netdev_priv_flags {
|
|||
* @rtnl_link_state: This enum represents the phases of creating
|
||||
* a new link
|
||||
*
|
||||
* @destructor: Called from unregister,
|
||||
* can be used to call free_netdev
|
||||
* @needs_free_netdev: Should unregister perform free_netdev?
|
||||
* @priv_destructor: Called from unregister
|
||||
* @npinfo: XXX: need comments on this one
|
||||
* @nd_net: Network namespace this network device is inside
|
||||
*
|
||||
|
@ -1858,7 +1857,8 @@ struct net_device {
|
|||
RTNL_LINK_INITIALIZING,
|
||||
} rtnl_link_state:16;
|
||||
|
||||
void (*destructor)(struct net_device *dev);
|
||||
bool needs_free_netdev;
|
||||
void (*priv_destructor)(struct net_device *dev);
|
||||
|
||||
#ifdef CONFIG_NETPOLL
|
||||
struct netpoll_info __rcu *npinfo;
|
||||
|
@ -4261,6 +4261,11 @@ static inline const char *netdev_name(const struct net_device *dev)
|
|||
return dev->name;
|
||||
}
|
||||
|
||||
static inline bool netdev_unregistering(const struct net_device *dev)
|
||||
{
|
||||
return dev->reg_state == NETREG_UNREGISTERING;
|
||||
}
|
||||
|
||||
static inline const char *netdev_reg_state(const struct net_device *dev)
|
||||
{
|
||||
switch (dev->reg_state) {
|
||||
|
|
|
@ -1486,8 +1486,10 @@ enum ethtool_link_mode_bit_indices {
|
|||
* it was forced up into this mode or autonegotiated.
|
||||
*/
|
||||
|
||||
/* The forced speed, in units of 1Mb. All values 0 to INT_MAX are legal. */
|
||||
/* Update drivers/net/phy/phy.c:phy_speed_to_str() when adding new values */
|
||||
/* The forced speed, in units of 1Mb. All values 0 to INT_MAX are legal.
|
||||
* Update drivers/net/phy/phy.c:phy_speed_to_str() and
|
||||
* drivers/net/bonding/bond_3ad.c:__get_link_speed() when adding new values.
|
||||
*/
|
||||
#define SPEED_10 10
|
||||
#define SPEED_100 100
|
||||
#define SPEED_1000 1000
|
||||
|
|
|
@ -343,6 +343,7 @@ enum ovs_key_attr {
|
|||
#define OVS_KEY_ATTR_MAX (__OVS_KEY_ATTR_MAX - 1)
|
||||
|
||||
enum ovs_tunnel_key_attr {
|
||||
/* OVS_TUNNEL_KEY_ATTR_NONE, standard nl API requires this attribute! */
|
||||
OVS_TUNNEL_KEY_ATTR_ID, /* be64 Tunnel ID */
|
||||
OVS_TUNNEL_KEY_ATTR_IPV4_SRC, /* be32 src IP address. */
|
||||
OVS_TUNNEL_KEY_ATTR_IPV4_DST, /* be32 dst IP address. */
|
||||
|
|
|
@ -813,7 +813,6 @@ static void vlan_dev_free(struct net_device *dev)
|
|||
|
||||
free_percpu(vlan->vlan_pcpu_stats);
|
||||
vlan->vlan_pcpu_stats = NULL;
|
||||
free_netdev(dev);
|
||||
}
|
||||
|
||||
void vlan_setup(struct net_device *dev)
|
||||
|
@ -826,7 +825,8 @@ void vlan_setup(struct net_device *dev)
|
|||
netif_keep_dst(dev);
|
||||
|
||||
dev->netdev_ops = &vlan_netdev_ops;
|
||||
dev->destructor = vlan_dev_free;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->priv_destructor = vlan_dev_free;
|
||||
dev->ethtool_ops = &vlan_ethtool_ops;
|
||||
|
||||
dev->min_mtu = 0;
|
||||
|
|
|
@ -1064,8 +1064,9 @@ bool batadv_dat_snoop_outgoing_arp_request(struct batadv_priv *bat_priv,
|
|||
|
||||
skb_new->protocol = eth_type_trans(skb_new, soft_iface);
|
||||
|
||||
soft_iface->stats.rx_packets++;
|
||||
soft_iface->stats.rx_bytes += skb->len + ETH_HLEN + hdr_size;
|
||||
batadv_inc_counter(bat_priv, BATADV_CNT_RX);
|
||||
batadv_add_counter(bat_priv, BATADV_CNT_RX_BYTES,
|
||||
skb->len + ETH_HLEN + hdr_size);
|
||||
|
||||
netif_rx(skb_new);
|
||||
batadv_dbg(BATADV_DBG_DAT, bat_priv, "ARP request replied locally\n");
|
||||
|
|
|
@ -987,7 +987,7 @@ int batadv_recv_unicast_packet(struct sk_buff *skb,
|
|||
batadv_dbg(BATADV_DBG_BLA, bat_priv,
|
||||
"recv_unicast_packet(): Dropped unicast pkt received from another backbone gw %pM.\n",
|
||||
orig_addr_gw);
|
||||
return NET_RX_DROP;
|
||||
goto free_skb;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1034,8 +1034,6 @@ static void batadv_softif_free(struct net_device *dev)
|
|||
* netdev and its private data (bat_priv)
|
||||
*/
|
||||
rcu_barrier();
|
||||
|
||||
free_netdev(dev);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -1047,7 +1045,8 @@ static void batadv_softif_init_early(struct net_device *dev)
|
|||
ether_setup(dev);
|
||||
|
||||
dev->netdev_ops = &batadv_netdev_ops;
|
||||
dev->destructor = batadv_softif_free;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->priv_destructor = batadv_softif_free;
|
||||
dev->features |= NETIF_F_HW_VLAN_CTAG_FILTER | NETIF_F_NETNS_LOCAL;
|
||||
dev->priv_flags |= IFF_NO_QUEUE;
|
||||
|
||||
|
|
|
@ -598,7 +598,7 @@ static void netdev_setup(struct net_device *dev)
|
|||
|
||||
dev->netdev_ops = &netdev_ops;
|
||||
dev->header_ops = &header_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
}
|
||||
|
||||
static struct device_type bt_type = {
|
||||
|
|
|
@ -379,7 +379,7 @@ void br_dev_setup(struct net_device *dev)
|
|||
ether_setup(dev);
|
||||
|
||||
dev->netdev_ops = &br_netdev_ops;
|
||||
dev->destructor = free_netdev;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->ethtool_ops = &br_ethtool_ops;
|
||||
SET_NETDEV_DEVTYPE(dev, &br_type);
|
||||
dev->priv_flags = IFF_EBRIDGE | IFF_NO_QUEUE;
|
||||
|
|
|
@ -754,6 +754,10 @@ static int caif_connect(struct socket *sock, struct sockaddr *uaddr,
|
|||
|
||||
lock_sock(sk);
|
||||
|
||||
err = -EINVAL;
|
||||
if (addr_len < offsetofend(struct sockaddr, sa_family))
|
||||
goto out;
|
||||
|
||||
err = -EAFNOSUPPORT;
|
||||
if (uaddr->sa_family != AF_CAIF)
|
||||
goto out;
|
||||
|
|
|
@ -81,11 +81,7 @@ static struct cfpkt *cfpkt_create_pfx(u16 len, u16 pfx)
|
|||
{
|
||||
struct sk_buff *skb;
|
||||
|
||||
if (likely(in_interrupt()))
|
||||
skb = alloc_skb(len + pfx, GFP_ATOMIC);
|
||||
else
|
||||
skb = alloc_skb(len + pfx, GFP_KERNEL);
|
||||
|
||||
skb = alloc_skb(len + pfx, GFP_ATOMIC);
|
||||
if (unlikely(skb == NULL))
|
||||
return NULL;
|
||||
|
||||
|
|
|
@ -392,14 +392,14 @@ static void chnl_net_destructor(struct net_device *dev)
|
|||
{
|
||||
struct chnl_net *priv = netdev_priv(dev);
|
||||
caif_free_client(&priv->chnl);
|
||||
free_netdev(dev);
|
||||
}
|
||||
|
||||
static void ipcaif_net_setup(struct net_device *dev)
|
||||
{
|
||||
struct chnl_net *priv;
|
||||
dev->netdev_ops = &netdev_ops;
|
||||
dev->destructor = chnl_net_destructor;
|
||||
dev->needs_free_netdev = true;
|
||||
dev->priv_destructor = chnl_net_destructor;
|
||||
dev->flags |= IFF_NOARP;
|
||||
dev->flags |= IFF_POINTOPOINT;
|
||||
dev->mtu = GPRS_PDP_MTU;
|
||||
|
|
|
@ -872,8 +872,7 @@ static int can_notifier(struct notifier_block *nb, unsigned long msg,
|
|||
|
||||
static int can_pernet_init(struct net *net)
|
||||
{
|
||||
net->can.can_rcvlists_lock =
|
||||
__SPIN_LOCK_UNLOCKED(net->can.can_rcvlists_lock);
|
||||
spin_lock_init(&net->can.can_rcvlists_lock);
|
||||
net->can.can_rx_alldev_list =
|
||||
kzalloc(sizeof(struct dev_rcv_lists), GFP_KERNEL);
|
||||
|
||||
|
|
|
@ -1253,8 +1253,9 @@ int dev_set_alias(struct net_device *dev, const char *alias, size_t len)
|
|||
if (!new_ifalias)
|
||||
return -ENOMEM;
|
||||
dev->ifalias = new_ifalias;
|
||||
memcpy(dev->ifalias, alias, len);
|
||||
dev->ifalias[len] = 0;
|
||||
|
||||
strlcpy(dev->ifalias, alias, len+1);
|
||||
return len;
|
||||
}
|
||||
|
||||
|
@ -4948,6 +4949,19 @@ __sum16 __skb_gro_checksum_complete(struct sk_buff *skb)
|
|||
}
|
||||
EXPORT_SYMBOL(__skb_gro_checksum_complete);
|
||||
|
||||
static void net_rps_send_ipi(struct softnet_data *remsd)
|
||||
{
|
||||
#ifdef CONFIG_RPS
|
||||
while (remsd) {
|
||||
struct softnet_data *next = remsd->rps_ipi_next;
|
||||
|
||||
if (cpu_online(remsd->cpu))
|
||||
smp_call_function_single_async(remsd->cpu, &remsd->csd);
|
||||
remsd = next;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
/*
|
||||
* net_rps_action_and_irq_enable sends any pending IPI's for rps.
|
||||
* Note: called with local irq disabled, but exits with local irq enabled.
|
||||
|
@ -4963,14 +4977,7 @@ static void net_rps_action_and_irq_enable(struct softnet_data *sd)
|
|||
local_irq_enable();
|
||||
|
||||
/* Send pending IPI's to kick RPS processing on remote cpus. */
|
||||
while (remsd) {
|
||||
struct softnet_data *next = remsd->rps_ipi_next;
|
||||
|
||||
if (cpu_online(remsd->cpu))
|
||||
smp_call_function_single_async(remsd->cpu,
|
||||
&remsd->csd);
|
||||
remsd = next;
|
||||
}
|
||||
net_rps_send_ipi(remsd);
|
||||
} else
|
||||
#endif
|
||||
local_irq_enable();
|
||||
|
@ -7501,6 +7508,8 @@ out:
|
|||
err_uninit:
|
||||
if (dev->netdev_ops->ndo_uninit)
|
||||
dev->netdev_ops->ndo_uninit(dev);
|
||||
if (dev->priv_destructor)
|
||||
dev->priv_destructor(dev);
|
||||
goto out;
|
||||
}
|
||||
EXPORT_SYMBOL(register_netdevice);
|
||||
|
@ -7708,8 +7717,10 @@ void netdev_run_todo(void)
|
|||
WARN_ON(rcu_access_pointer(dev->ip6_ptr));
|
||||
WARN_ON(dev->dn_ptr);
|
||||
|
||||
if (dev->destructor)
|
||||
dev->destructor(dev);
|
||||
if (dev->priv_destructor)
|
||||
dev->priv_destructor(dev);
|
||||
if (dev->needs_free_netdev)
|
||||
free_netdev(dev);
|
||||
|
||||
/* Report a network device has been unregistered */
|
||||
rtnl_lock();
|
||||
|
@ -8192,7 +8203,7 @@ static int dev_cpu_dead(unsigned int oldcpu)
|
|||
struct sk_buff **list_skb;
|
||||
struct sk_buff *skb;
|
||||
unsigned int cpu;
|
||||
struct softnet_data *sd, *oldsd;
|
||||
struct softnet_data *sd, *oldsd, *remsd = NULL;
|
||||
|
||||
local_irq_disable();
|
||||
cpu = smp_processor_id();
|
||||
|
@ -8233,6 +8244,13 @@ static int dev_cpu_dead(unsigned int oldcpu)
|
|||
raise_softirq_irqoff(NET_TX_SOFTIRQ);
|
||||
local_irq_enable();
|
||||
|
||||
#ifdef CONFIG_RPS
|
||||
remsd = oldsd->rps_ipi_list;
|
||||
oldsd->rps_ipi_list = NULL;
|
||||
#endif
|
||||
/* send out pending IPI's on offline CPU */
|
||||
net_rps_send_ipi(remsd);
|
||||
|
||||
/* Process offline CPU's input_pkt_queue */
|
||||
while ((skb = __skb_dequeue(&oldsd->process_queue))) {
|
||||
netif_rx_ni(skb);
|
||||
|
|
|
@ -469,6 +469,20 @@ static int dst_dev_event(struct notifier_block *this, unsigned long event,
|
|||
spin_lock_bh(&dst_garbage.lock);
|
||||
dst = dst_garbage.list;
|
||||
dst_garbage.list = NULL;
|
||||
/* The code in dst_ifdown places a hold on the loopback device.
|
||||
* If the gc entry processing is set to expire after a lengthy
|
||||
* interval, this hold can cause netdev_wait_allrefs() to hang
|
||||
* out and wait for a long time -- until the the loopback
|
||||
* interface is released. If we're really unlucky, it'll emit
|
||||
* pr_emerg messages to console too. Reset the interval here,
|
||||
* so dst cleanups occur in a more timely fashion.
|
||||
*/
|
||||
if (dst_garbage.timer_inc > DST_GC_INC) {
|
||||
dst_garbage.timer_inc = DST_GC_INC;
|
||||
dst_garbage.timer_expires = DST_GC_MIN;
|
||||
mod_delayed_work(system_wq, &dst_gc_work,
|
||||
dst_garbage.timer_expires);
|
||||
}
|
||||
spin_unlock_bh(&dst_garbage.lock);
|
||||
|
||||
if (last)
|
||||
|
|
|
@ -1124,6 +1124,8 @@ static noinline_for_stack int rtnl_fill_vfinfo(struct sk_buff *skb,
|
|||
struct ifla_vf_mac vf_mac;
|
||||
struct ifla_vf_info ivi;
|
||||
|
||||
memset(&ivi, 0, sizeof(ivi));
|
||||
|
||||
/* Not all SR-IOV capable drivers support the
|
||||
* spoofcheck and "RSS query enable" query. Preset to
|
||||
* -1 so the user space tool can detect that the driver
|
||||
|
@ -1132,7 +1134,6 @@ static noinline_for_stack int rtnl_fill_vfinfo(struct sk_buff *skb,
|
|||
ivi.spoofchk = -1;
|
||||
ivi.rss_query_en = -1;
|
||||
ivi.trusted = -1;
|
||||
memset(ivi.mac, 0, sizeof(ivi.mac));
|
||||
/* The default value for VF link state is "auto"
|
||||
* IFLA_VF_LINK_STATE_AUTO which equals zero
|
||||
*/
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue