162306a36Sopenharmony_ci/* 262306a36Sopenharmony_ci * Linux driver for VMware's vmxnet3 ethernet NIC. 362306a36Sopenharmony_ci * 462306a36Sopenharmony_ci * Copyright (C) 2008-2022, VMware, Inc. All Rights Reserved. 562306a36Sopenharmony_ci * 662306a36Sopenharmony_ci * This program is free software; you can redistribute it and/or modify it 762306a36Sopenharmony_ci * under the terms of the GNU General Public License as published by the 862306a36Sopenharmony_ci * Free Software Foundation; version 2 of the License and no later version. 962306a36Sopenharmony_ci * 1062306a36Sopenharmony_ci * This program is distributed in the hope that it will be useful, but 1162306a36Sopenharmony_ci * WITHOUT ANY WARRANTY; without even the implied warranty of 1262306a36Sopenharmony_ci * MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE, GOOD TITLE or 1362306a36Sopenharmony_ci * NON INFRINGEMENT. See the GNU General Public License for more 1462306a36Sopenharmony_ci * details. 1562306a36Sopenharmony_ci * 1662306a36Sopenharmony_ci * You should have received a copy of the GNU General Public License 1762306a36Sopenharmony_ci * along with this program; if not, write to the Free Software 1862306a36Sopenharmony_ci * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 1962306a36Sopenharmony_ci * 2062306a36Sopenharmony_ci * The full GNU General Public License is included in this distribution in 2162306a36Sopenharmony_ci * the file called "COPYING". 2262306a36Sopenharmony_ci * 2362306a36Sopenharmony_ci * Maintained by: pv-drivers@vmware.com 2462306a36Sopenharmony_ci * 2562306a36Sopenharmony_ci */ 2662306a36Sopenharmony_ci 2762306a36Sopenharmony_ci#ifndef _VMXNET3_INT_H 2862306a36Sopenharmony_ci#define _VMXNET3_INT_H 2962306a36Sopenharmony_ci 3062306a36Sopenharmony_ci#include <linux/bitops.h> 3162306a36Sopenharmony_ci#include <linux/ethtool.h> 3262306a36Sopenharmony_ci#include <linux/delay.h> 3362306a36Sopenharmony_ci#include <linux/netdevice.h> 3462306a36Sopenharmony_ci#include <linux/pci.h> 3562306a36Sopenharmony_ci#include <linux/compiler.h> 3662306a36Sopenharmony_ci#include <linux/slab.h> 3762306a36Sopenharmony_ci#include <linux/spinlock.h> 3862306a36Sopenharmony_ci#include <linux/ioport.h> 3962306a36Sopenharmony_ci#include <linux/highmem.h> 4062306a36Sopenharmony_ci#include <linux/timer.h> 4162306a36Sopenharmony_ci#include <linux/skbuff.h> 4262306a36Sopenharmony_ci#include <linux/interrupt.h> 4362306a36Sopenharmony_ci#include <linux/workqueue.h> 4462306a36Sopenharmony_ci#include <linux/uaccess.h> 4562306a36Sopenharmony_ci#include <asm/dma.h> 4662306a36Sopenharmony_ci#include <asm/page.h> 4762306a36Sopenharmony_ci 4862306a36Sopenharmony_ci#include <linux/tcp.h> 4962306a36Sopenharmony_ci#include <linux/udp.h> 5062306a36Sopenharmony_ci#include <linux/ip.h> 5162306a36Sopenharmony_ci#include <linux/ipv6.h> 5262306a36Sopenharmony_ci#include <linux/in.h> 5362306a36Sopenharmony_ci#include <linux/etherdevice.h> 5462306a36Sopenharmony_ci#include <asm/checksum.h> 5562306a36Sopenharmony_ci#include <linux/if_vlan.h> 5662306a36Sopenharmony_ci#include <linux/if_arp.h> 5762306a36Sopenharmony_ci#include <linux/inetdevice.h> 5862306a36Sopenharmony_ci#include <linux/log2.h> 5962306a36Sopenharmony_ci#include <linux/bpf.h> 6062306a36Sopenharmony_ci#include <net/page_pool/helpers.h> 6162306a36Sopenharmony_ci#include <net/xdp.h> 6262306a36Sopenharmony_ci 6362306a36Sopenharmony_ci#include "vmxnet3_defs.h" 6462306a36Sopenharmony_ci 6562306a36Sopenharmony_ci#ifdef DEBUG 6662306a36Sopenharmony_ci# define VMXNET3_DRIVER_VERSION_REPORT VMXNET3_DRIVER_VERSION_STRING"-NAPI(debug)" 6762306a36Sopenharmony_ci#else 6862306a36Sopenharmony_ci# define VMXNET3_DRIVER_VERSION_REPORT VMXNET3_DRIVER_VERSION_STRING"-NAPI" 6962306a36Sopenharmony_ci#endif 7062306a36Sopenharmony_ci 7162306a36Sopenharmony_ci 7262306a36Sopenharmony_ci/* 7362306a36Sopenharmony_ci * Version numbers 7462306a36Sopenharmony_ci */ 7562306a36Sopenharmony_ci#define VMXNET3_DRIVER_VERSION_STRING "1.7.0.0-k" 7662306a36Sopenharmony_ci 7762306a36Sopenharmony_ci/* Each byte of this 32-bit integer encodes a version number in 7862306a36Sopenharmony_ci * VMXNET3_DRIVER_VERSION_STRING. 7962306a36Sopenharmony_ci */ 8062306a36Sopenharmony_ci#define VMXNET3_DRIVER_VERSION_NUM 0x01070000 8162306a36Sopenharmony_ci 8262306a36Sopenharmony_ci#if defined(CONFIG_PCI_MSI) 8362306a36Sopenharmony_ci /* RSS only makes sense if MSI-X is supported. */ 8462306a36Sopenharmony_ci #define VMXNET3_RSS 8562306a36Sopenharmony_ci#endif 8662306a36Sopenharmony_ci 8762306a36Sopenharmony_ci#define VMXNET3_REV_7 6 /* Vmxnet3 Rev. 7 */ 8862306a36Sopenharmony_ci#define VMXNET3_REV_6 5 /* Vmxnet3 Rev. 6 */ 8962306a36Sopenharmony_ci#define VMXNET3_REV_5 4 /* Vmxnet3 Rev. 5 */ 9062306a36Sopenharmony_ci#define VMXNET3_REV_4 3 /* Vmxnet3 Rev. 4 */ 9162306a36Sopenharmony_ci#define VMXNET3_REV_3 2 /* Vmxnet3 Rev. 3 */ 9262306a36Sopenharmony_ci#define VMXNET3_REV_2 1 /* Vmxnet3 Rev. 2 */ 9362306a36Sopenharmony_ci#define VMXNET3_REV_1 0 /* Vmxnet3 Rev. 1 */ 9462306a36Sopenharmony_ci 9562306a36Sopenharmony_ci/* 9662306a36Sopenharmony_ci * Capabilities 9762306a36Sopenharmony_ci */ 9862306a36Sopenharmony_ci 9962306a36Sopenharmony_cienum { 10062306a36Sopenharmony_ci VMNET_CAP_SG = 0x0001, /* Can do scatter-gather transmits. */ 10162306a36Sopenharmony_ci VMNET_CAP_IP4_CSUM = 0x0002, /* Can checksum only TCP/UDP over 10262306a36Sopenharmony_ci * IPv4 */ 10362306a36Sopenharmony_ci VMNET_CAP_HW_CSUM = 0x0004, /* Can checksum all packets. */ 10462306a36Sopenharmony_ci VMNET_CAP_HIGH_DMA = 0x0008, /* Can DMA to high memory. */ 10562306a36Sopenharmony_ci VMNET_CAP_TOE = 0x0010, /* Supports TCP/IP offload. */ 10662306a36Sopenharmony_ci VMNET_CAP_TSO = 0x0020, /* Supports TCP Segmentation 10762306a36Sopenharmony_ci * offload */ 10862306a36Sopenharmony_ci VMNET_CAP_SW_TSO = 0x0040, /* Supports SW TCP Segmentation */ 10962306a36Sopenharmony_ci VMNET_CAP_VMXNET_APROM = 0x0080, /* Vmxnet APROM support */ 11062306a36Sopenharmony_ci VMNET_CAP_HW_TX_VLAN = 0x0100, /* Can we do VLAN tagging in HW */ 11162306a36Sopenharmony_ci VMNET_CAP_HW_RX_VLAN = 0x0200, /* Can we do VLAN untagging in HW */ 11262306a36Sopenharmony_ci VMNET_CAP_SW_VLAN = 0x0400, /* VLAN tagging/untagging in SW */ 11362306a36Sopenharmony_ci VMNET_CAP_WAKE_PCKT_RCV = 0x0800, /* Can wake on network packet recv? */ 11462306a36Sopenharmony_ci VMNET_CAP_ENABLE_INT_INLINE = 0x1000, /* Enable Interrupt Inline */ 11562306a36Sopenharmony_ci VMNET_CAP_ENABLE_HEADER_COPY = 0x2000, /* copy header for vmkernel */ 11662306a36Sopenharmony_ci VMNET_CAP_TX_CHAIN = 0x4000, /* Guest can use multiple tx entries 11762306a36Sopenharmony_ci * for a pkt */ 11862306a36Sopenharmony_ci VMNET_CAP_RX_CHAIN = 0x8000, /* pkt can span multiple rx entries */ 11962306a36Sopenharmony_ci VMNET_CAP_LPD = 0x10000, /* large pkt delivery */ 12062306a36Sopenharmony_ci VMNET_CAP_BPF = 0x20000, /* BPF Support in VMXNET Virtual HW*/ 12162306a36Sopenharmony_ci VMNET_CAP_SG_SPAN_PAGES = 0x40000, /* Scatter-gather can span multiple*/ 12262306a36Sopenharmony_ci /* pages transmits */ 12362306a36Sopenharmony_ci VMNET_CAP_IP6_CSUM = 0x80000, /* Can do IPv6 csum offload. */ 12462306a36Sopenharmony_ci VMNET_CAP_TSO6 = 0x100000, /* TSO seg. offload for IPv6 pkts. */ 12562306a36Sopenharmony_ci VMNET_CAP_TSO256k = 0x200000, /* Can do TSO seg offload for */ 12662306a36Sopenharmony_ci /* pkts up to 256kB. */ 12762306a36Sopenharmony_ci VMNET_CAP_UPT = 0x400000 /* Support UPT */ 12862306a36Sopenharmony_ci}; 12962306a36Sopenharmony_ci 13062306a36Sopenharmony_ci/* 13162306a36Sopenharmony_ci * Maximum devices supported. 13262306a36Sopenharmony_ci */ 13362306a36Sopenharmony_ci#define MAX_ETHERNET_CARDS 10 13462306a36Sopenharmony_ci#define MAX_PCI_PASSTHRU_DEVICE 6 13562306a36Sopenharmony_ci 13662306a36Sopenharmony_cistruct vmxnet3_cmd_ring { 13762306a36Sopenharmony_ci union Vmxnet3_GenericDesc *base; 13862306a36Sopenharmony_ci u32 size; 13962306a36Sopenharmony_ci u32 next2fill; 14062306a36Sopenharmony_ci u32 next2comp; 14162306a36Sopenharmony_ci u8 gen; 14262306a36Sopenharmony_ci u8 isOutOfOrder; 14362306a36Sopenharmony_ci dma_addr_t basePA; 14462306a36Sopenharmony_ci}; 14562306a36Sopenharmony_ci 14662306a36Sopenharmony_cistatic inline void 14762306a36Sopenharmony_civmxnet3_cmd_ring_adv_next2fill(struct vmxnet3_cmd_ring *ring) 14862306a36Sopenharmony_ci{ 14962306a36Sopenharmony_ci ring->next2fill++; 15062306a36Sopenharmony_ci if (unlikely(ring->next2fill == ring->size)) { 15162306a36Sopenharmony_ci ring->next2fill = 0; 15262306a36Sopenharmony_ci VMXNET3_FLIP_RING_GEN(ring->gen); 15362306a36Sopenharmony_ci } 15462306a36Sopenharmony_ci} 15562306a36Sopenharmony_ci 15662306a36Sopenharmony_cistatic inline void 15762306a36Sopenharmony_civmxnet3_cmd_ring_adv_next2comp(struct vmxnet3_cmd_ring *ring) 15862306a36Sopenharmony_ci{ 15962306a36Sopenharmony_ci VMXNET3_INC_RING_IDX_ONLY(ring->next2comp, ring->size); 16062306a36Sopenharmony_ci} 16162306a36Sopenharmony_ci 16262306a36Sopenharmony_cistatic inline int 16362306a36Sopenharmony_civmxnet3_cmd_ring_desc_avail(struct vmxnet3_cmd_ring *ring) 16462306a36Sopenharmony_ci{ 16562306a36Sopenharmony_ci return (ring->next2comp > ring->next2fill ? 0 : ring->size) + 16662306a36Sopenharmony_ci ring->next2comp - ring->next2fill - 1; 16762306a36Sopenharmony_ci} 16862306a36Sopenharmony_ci 16962306a36Sopenharmony_cistruct vmxnet3_comp_ring { 17062306a36Sopenharmony_ci union Vmxnet3_GenericDesc *base; 17162306a36Sopenharmony_ci u32 size; 17262306a36Sopenharmony_ci u32 next2proc; 17362306a36Sopenharmony_ci u8 gen; 17462306a36Sopenharmony_ci u8 intr_idx; 17562306a36Sopenharmony_ci dma_addr_t basePA; 17662306a36Sopenharmony_ci}; 17762306a36Sopenharmony_ci 17862306a36Sopenharmony_cistatic inline void 17962306a36Sopenharmony_civmxnet3_comp_ring_adv_next2proc(struct vmxnet3_comp_ring *ring) 18062306a36Sopenharmony_ci{ 18162306a36Sopenharmony_ci ring->next2proc++; 18262306a36Sopenharmony_ci if (unlikely(ring->next2proc == ring->size)) { 18362306a36Sopenharmony_ci ring->next2proc = 0; 18462306a36Sopenharmony_ci VMXNET3_FLIP_RING_GEN(ring->gen); 18562306a36Sopenharmony_ci } 18662306a36Sopenharmony_ci} 18762306a36Sopenharmony_ci 18862306a36Sopenharmony_cistruct vmxnet3_tx_data_ring { 18962306a36Sopenharmony_ci struct Vmxnet3_TxDataDesc *base; 19062306a36Sopenharmony_ci u32 size; 19162306a36Sopenharmony_ci dma_addr_t basePA; 19262306a36Sopenharmony_ci}; 19362306a36Sopenharmony_ci 19462306a36Sopenharmony_ci#define VMXNET3_MAP_NONE 0 19562306a36Sopenharmony_ci#define VMXNET3_MAP_SINGLE BIT(0) 19662306a36Sopenharmony_ci#define VMXNET3_MAP_PAGE BIT(1) 19762306a36Sopenharmony_ci#define VMXNET3_MAP_XDP BIT(2) 19862306a36Sopenharmony_ci 19962306a36Sopenharmony_cistruct vmxnet3_tx_buf_info { 20062306a36Sopenharmony_ci u32 map_type; 20162306a36Sopenharmony_ci u16 len; 20262306a36Sopenharmony_ci u16 sop_idx; 20362306a36Sopenharmony_ci dma_addr_t dma_addr; 20462306a36Sopenharmony_ci union { 20562306a36Sopenharmony_ci struct sk_buff *skb; 20662306a36Sopenharmony_ci struct xdp_frame *xdpf; 20762306a36Sopenharmony_ci }; 20862306a36Sopenharmony_ci}; 20962306a36Sopenharmony_ci 21062306a36Sopenharmony_cistruct vmxnet3_tq_driver_stats { 21162306a36Sopenharmony_ci u64 drop_total; /* # of pkts dropped by the driver, the 21262306a36Sopenharmony_ci * counters below track droppings due to 21362306a36Sopenharmony_ci * different reasons 21462306a36Sopenharmony_ci */ 21562306a36Sopenharmony_ci u64 drop_too_many_frags; 21662306a36Sopenharmony_ci u64 drop_oversized_hdr; 21762306a36Sopenharmony_ci u64 drop_hdr_inspect_err; 21862306a36Sopenharmony_ci u64 drop_tso; 21962306a36Sopenharmony_ci 22062306a36Sopenharmony_ci u64 tx_ring_full; 22162306a36Sopenharmony_ci u64 linearized; /* # of pkts linearized */ 22262306a36Sopenharmony_ci u64 copy_skb_header; /* # of times we have to copy skb header */ 22362306a36Sopenharmony_ci u64 oversized_hdr; 22462306a36Sopenharmony_ci 22562306a36Sopenharmony_ci u64 xdp_xmit; 22662306a36Sopenharmony_ci u64 xdp_xmit_err; 22762306a36Sopenharmony_ci}; 22862306a36Sopenharmony_ci 22962306a36Sopenharmony_cistruct vmxnet3_tx_ctx { 23062306a36Sopenharmony_ci bool ipv4; 23162306a36Sopenharmony_ci bool ipv6; 23262306a36Sopenharmony_ci u16 mss; 23362306a36Sopenharmony_ci u32 l4_offset; /* only valid for pkts requesting tso or csum 23462306a36Sopenharmony_ci * offloading. For encap offload, it refers to 23562306a36Sopenharmony_ci * inner L4 offset i.e. it includes outer header 23662306a36Sopenharmony_ci * encap header and inner eth and ip header size 23762306a36Sopenharmony_ci */ 23862306a36Sopenharmony_ci 23962306a36Sopenharmony_ci u32 l4_hdr_size; /* only valid if mss != 0 24062306a36Sopenharmony_ci * Refers to inner L4 hdr size for encap 24162306a36Sopenharmony_ci * offload 24262306a36Sopenharmony_ci */ 24362306a36Sopenharmony_ci u32 copy_size; /* # of bytes copied into the data ring */ 24462306a36Sopenharmony_ci union Vmxnet3_GenericDesc *sop_txd; 24562306a36Sopenharmony_ci union Vmxnet3_GenericDesc *eop_txd; 24662306a36Sopenharmony_ci}; 24762306a36Sopenharmony_ci 24862306a36Sopenharmony_cistruct vmxnet3_tx_queue { 24962306a36Sopenharmony_ci char name[IFNAMSIZ+8]; /* To identify interrupt */ 25062306a36Sopenharmony_ci struct vmxnet3_adapter *adapter; 25162306a36Sopenharmony_ci spinlock_t tx_lock; 25262306a36Sopenharmony_ci struct vmxnet3_cmd_ring tx_ring; 25362306a36Sopenharmony_ci struct vmxnet3_tx_buf_info *buf_info; 25462306a36Sopenharmony_ci struct vmxnet3_tx_data_ring data_ring; 25562306a36Sopenharmony_ci struct vmxnet3_comp_ring comp_ring; 25662306a36Sopenharmony_ci struct Vmxnet3_TxQueueCtrl *shared; 25762306a36Sopenharmony_ci struct vmxnet3_tq_driver_stats stats; 25862306a36Sopenharmony_ci bool stopped; 25962306a36Sopenharmony_ci int num_stop; /* # of times the queue is 26062306a36Sopenharmony_ci * stopped */ 26162306a36Sopenharmony_ci int qid; 26262306a36Sopenharmony_ci u16 txdata_desc_size; 26362306a36Sopenharmony_ci} ____cacheline_aligned; 26462306a36Sopenharmony_ci 26562306a36Sopenharmony_cienum vmxnet3_rx_buf_type { 26662306a36Sopenharmony_ci VMXNET3_RX_BUF_NONE = 0, 26762306a36Sopenharmony_ci VMXNET3_RX_BUF_SKB = 1, 26862306a36Sopenharmony_ci VMXNET3_RX_BUF_PAGE = 2, 26962306a36Sopenharmony_ci VMXNET3_RX_BUF_XDP = 3, 27062306a36Sopenharmony_ci}; 27162306a36Sopenharmony_ci 27262306a36Sopenharmony_ci#define VMXNET3_RXD_COMP_PENDING 0 27362306a36Sopenharmony_ci#define VMXNET3_RXD_COMP_DONE 1 27462306a36Sopenharmony_ci 27562306a36Sopenharmony_cistruct vmxnet3_rx_buf_info { 27662306a36Sopenharmony_ci enum vmxnet3_rx_buf_type buf_type; 27762306a36Sopenharmony_ci u16 len; 27862306a36Sopenharmony_ci u8 comp_state; 27962306a36Sopenharmony_ci union { 28062306a36Sopenharmony_ci struct sk_buff *skb; 28162306a36Sopenharmony_ci struct page *page; 28262306a36Sopenharmony_ci }; 28362306a36Sopenharmony_ci dma_addr_t dma_addr; 28462306a36Sopenharmony_ci}; 28562306a36Sopenharmony_ci 28662306a36Sopenharmony_cistruct vmxnet3_rx_ctx { 28762306a36Sopenharmony_ci struct sk_buff *skb; 28862306a36Sopenharmony_ci u32 sop_idx; 28962306a36Sopenharmony_ci}; 29062306a36Sopenharmony_ci 29162306a36Sopenharmony_cistruct vmxnet3_rq_driver_stats { 29262306a36Sopenharmony_ci u64 drop_total; 29362306a36Sopenharmony_ci u64 drop_err; 29462306a36Sopenharmony_ci u64 drop_fcs; 29562306a36Sopenharmony_ci u64 rx_buf_alloc_failure; 29662306a36Sopenharmony_ci 29762306a36Sopenharmony_ci u64 xdp_packets; /* Total packets processed by XDP. */ 29862306a36Sopenharmony_ci u64 xdp_tx; 29962306a36Sopenharmony_ci u64 xdp_redirects; 30062306a36Sopenharmony_ci u64 xdp_drops; 30162306a36Sopenharmony_ci u64 xdp_aborted; 30262306a36Sopenharmony_ci}; 30362306a36Sopenharmony_ci 30462306a36Sopenharmony_cistruct vmxnet3_rx_data_ring { 30562306a36Sopenharmony_ci Vmxnet3_RxDataDesc *base; 30662306a36Sopenharmony_ci dma_addr_t basePA; 30762306a36Sopenharmony_ci u16 desc_size; 30862306a36Sopenharmony_ci}; 30962306a36Sopenharmony_ci 31062306a36Sopenharmony_cistruct vmxnet3_rx_queue { 31162306a36Sopenharmony_ci char name[IFNAMSIZ + 8]; /* To identify interrupt */ 31262306a36Sopenharmony_ci struct vmxnet3_adapter *adapter; 31362306a36Sopenharmony_ci struct napi_struct napi; 31462306a36Sopenharmony_ci struct vmxnet3_cmd_ring rx_ring[2]; 31562306a36Sopenharmony_ci struct vmxnet3_rx_data_ring data_ring; 31662306a36Sopenharmony_ci struct vmxnet3_comp_ring comp_ring; 31762306a36Sopenharmony_ci struct vmxnet3_rx_ctx rx_ctx; 31862306a36Sopenharmony_ci u32 qid; /* rqID in RCD for buffer from 1st ring */ 31962306a36Sopenharmony_ci u32 qid2; /* rqID in RCD for buffer from 2nd ring */ 32062306a36Sopenharmony_ci u32 dataRingQid; /* rqID in RCD for buffer from data ring */ 32162306a36Sopenharmony_ci struct vmxnet3_rx_buf_info *buf_info[2]; 32262306a36Sopenharmony_ci struct Vmxnet3_RxQueueCtrl *shared; 32362306a36Sopenharmony_ci struct vmxnet3_rq_driver_stats stats; 32462306a36Sopenharmony_ci struct page_pool *page_pool; 32562306a36Sopenharmony_ci struct xdp_rxq_info xdp_rxq; 32662306a36Sopenharmony_ci} ____cacheline_aligned; 32762306a36Sopenharmony_ci 32862306a36Sopenharmony_ci#define VMXNET3_DEVICE_MAX_TX_QUEUES 32 32962306a36Sopenharmony_ci#define VMXNET3_DEVICE_MAX_RX_QUEUES 32 /* Keep this value as a power of 2 */ 33062306a36Sopenharmony_ci 33162306a36Sopenharmony_ci#define VMXNET3_DEVICE_DEFAULT_TX_QUEUES 8 33262306a36Sopenharmony_ci#define VMXNET3_DEVICE_DEFAULT_RX_QUEUES 8 /* Keep this value as a power of 2 */ 33362306a36Sopenharmony_ci 33462306a36Sopenharmony_ci/* Should be less than UPT1_RSS_MAX_IND_TABLE_SIZE */ 33562306a36Sopenharmony_ci#define VMXNET3_RSS_IND_TABLE_SIZE (VMXNET3_DEVICE_MAX_RX_QUEUES * 4) 33662306a36Sopenharmony_ci 33762306a36Sopenharmony_ci#define VMXNET3_LINUX_MAX_MSIX_VECT (VMXNET3_DEVICE_MAX_TX_QUEUES + \ 33862306a36Sopenharmony_ci VMXNET3_DEVICE_MAX_RX_QUEUES + 1) 33962306a36Sopenharmony_ci#define VMXNET3_LINUX_MIN_MSIX_VECT 3 /* 1 for tx, 1 for rx pair and 1 for event */ 34062306a36Sopenharmony_ci 34162306a36Sopenharmony_ci 34262306a36Sopenharmony_cistruct vmxnet3_intr { 34362306a36Sopenharmony_ci enum vmxnet3_intr_mask_mode mask_mode; 34462306a36Sopenharmony_ci enum vmxnet3_intr_type type; /* MSI-X, MSI, or INTx? */ 34562306a36Sopenharmony_ci u8 num_intrs; /* # of intr vectors */ 34662306a36Sopenharmony_ci u8 event_intr_idx; /* idx of the intr vector for event */ 34762306a36Sopenharmony_ci u8 mod_levels[VMXNET3_LINUX_MAX_MSIX_VECT]; /* moderation level */ 34862306a36Sopenharmony_ci char event_msi_vector_name[IFNAMSIZ+17]; 34962306a36Sopenharmony_ci#ifdef CONFIG_PCI_MSI 35062306a36Sopenharmony_ci struct msix_entry msix_entries[VMXNET3_LINUX_MAX_MSIX_VECT]; 35162306a36Sopenharmony_ci#endif 35262306a36Sopenharmony_ci}; 35362306a36Sopenharmony_ci 35462306a36Sopenharmony_ci/* Interrupt sharing schemes, share_intr */ 35562306a36Sopenharmony_ci#define VMXNET3_INTR_BUDDYSHARE 0 /* Corresponding tx,rx queues share irq */ 35662306a36Sopenharmony_ci#define VMXNET3_INTR_TXSHARE 1 /* All tx queues share one irq */ 35762306a36Sopenharmony_ci#define VMXNET3_INTR_DONTSHARE 2 /* each queue has its own irq */ 35862306a36Sopenharmony_ci 35962306a36Sopenharmony_ci 36062306a36Sopenharmony_ci#define VMXNET3_STATE_BIT_RESETTING 0 36162306a36Sopenharmony_ci#define VMXNET3_STATE_BIT_QUIESCED 1 36262306a36Sopenharmony_cistruct vmxnet3_adapter { 36362306a36Sopenharmony_ci struct vmxnet3_tx_queue tx_queue[VMXNET3_DEVICE_MAX_TX_QUEUES]; 36462306a36Sopenharmony_ci struct vmxnet3_rx_queue rx_queue[VMXNET3_DEVICE_MAX_RX_QUEUES]; 36562306a36Sopenharmony_ci unsigned long active_vlans[BITS_TO_LONGS(VLAN_N_VID)]; 36662306a36Sopenharmony_ci struct vmxnet3_intr intr; 36762306a36Sopenharmony_ci spinlock_t cmd_lock; 36862306a36Sopenharmony_ci struct Vmxnet3_DriverShared *shared; 36962306a36Sopenharmony_ci struct Vmxnet3_PMConf *pm_conf; 37062306a36Sopenharmony_ci struct Vmxnet3_TxQueueDesc *tqd_start; /* all tx queue desc */ 37162306a36Sopenharmony_ci struct Vmxnet3_RxQueueDesc *rqd_start; /* all rx queue desc */ 37262306a36Sopenharmony_ci struct net_device *netdev; 37362306a36Sopenharmony_ci struct pci_dev *pdev; 37462306a36Sopenharmony_ci 37562306a36Sopenharmony_ci u8 __iomem *hw_addr0; /* for BAR 0 */ 37662306a36Sopenharmony_ci u8 __iomem *hw_addr1; /* for BAR 1 */ 37762306a36Sopenharmony_ci u8 version; 37862306a36Sopenharmony_ci 37962306a36Sopenharmony_ci#ifdef VMXNET3_RSS 38062306a36Sopenharmony_ci struct UPT1_RSSConf *rss_conf; 38162306a36Sopenharmony_ci bool rss; 38262306a36Sopenharmony_ci#endif 38362306a36Sopenharmony_ci u32 num_rx_queues; 38462306a36Sopenharmony_ci u32 num_tx_queues; 38562306a36Sopenharmony_ci 38662306a36Sopenharmony_ci /* rx buffer related */ 38762306a36Sopenharmony_ci unsigned skb_buf_size; 38862306a36Sopenharmony_ci int rx_buf_per_pkt; /* only apply to the 1st ring */ 38962306a36Sopenharmony_ci dma_addr_t shared_pa; 39062306a36Sopenharmony_ci dma_addr_t queue_desc_pa; 39162306a36Sopenharmony_ci dma_addr_t coal_conf_pa; 39262306a36Sopenharmony_ci 39362306a36Sopenharmony_ci /* Wake-on-LAN */ 39462306a36Sopenharmony_ci u32 wol; 39562306a36Sopenharmony_ci 39662306a36Sopenharmony_ci /* Link speed */ 39762306a36Sopenharmony_ci u32 link_speed; /* in mbps */ 39862306a36Sopenharmony_ci 39962306a36Sopenharmony_ci u64 tx_timeout_count; 40062306a36Sopenharmony_ci 40162306a36Sopenharmony_ci /* Ring sizes */ 40262306a36Sopenharmony_ci u32 tx_ring_size; 40362306a36Sopenharmony_ci u32 rx_ring_size; 40462306a36Sopenharmony_ci u32 rx_ring2_size; 40562306a36Sopenharmony_ci 40662306a36Sopenharmony_ci /* Size of buffer in the data ring */ 40762306a36Sopenharmony_ci u16 txdata_desc_size; 40862306a36Sopenharmony_ci u16 rxdata_desc_size; 40962306a36Sopenharmony_ci 41062306a36Sopenharmony_ci bool rxdataring_enabled; 41162306a36Sopenharmony_ci bool default_rss_fields; 41262306a36Sopenharmony_ci enum Vmxnet3_RSSField rss_fields; 41362306a36Sopenharmony_ci 41462306a36Sopenharmony_ci struct work_struct work; 41562306a36Sopenharmony_ci 41662306a36Sopenharmony_ci unsigned long state; /* VMXNET3_STATE_BIT_xxx */ 41762306a36Sopenharmony_ci 41862306a36Sopenharmony_ci int share_intr; 41962306a36Sopenharmony_ci 42062306a36Sopenharmony_ci struct Vmxnet3_CoalesceScheme *coal_conf; 42162306a36Sopenharmony_ci bool default_coal_mode; 42262306a36Sopenharmony_ci 42362306a36Sopenharmony_ci dma_addr_t adapter_pa; 42462306a36Sopenharmony_ci dma_addr_t pm_conf_pa; 42562306a36Sopenharmony_ci dma_addr_t rss_conf_pa; 42662306a36Sopenharmony_ci bool queuesExtEnabled; 42762306a36Sopenharmony_ci struct Vmxnet3_RingBufferSize ringBufSize; 42862306a36Sopenharmony_ci u32 devcap_supported[8]; 42962306a36Sopenharmony_ci u32 ptcap_supported[8]; 43062306a36Sopenharmony_ci u32 dev_caps[8]; 43162306a36Sopenharmony_ci u16 tx_prod_offset; 43262306a36Sopenharmony_ci u16 rx_prod_offset; 43362306a36Sopenharmony_ci u16 rx_prod2_offset; 43462306a36Sopenharmony_ci struct bpf_prog __rcu *xdp_bpf_prog; 43562306a36Sopenharmony_ci}; 43662306a36Sopenharmony_ci 43762306a36Sopenharmony_ci#define VMXNET3_WRITE_BAR0_REG(adapter, reg, val) \ 43862306a36Sopenharmony_ci writel((val), (adapter)->hw_addr0 + (reg)) 43962306a36Sopenharmony_ci#define VMXNET3_READ_BAR0_REG(adapter, reg) \ 44062306a36Sopenharmony_ci readl((adapter)->hw_addr0 + (reg)) 44162306a36Sopenharmony_ci 44262306a36Sopenharmony_ci#define VMXNET3_WRITE_BAR1_REG(adapter, reg, val) \ 44362306a36Sopenharmony_ci writel((val), (adapter)->hw_addr1 + (reg)) 44462306a36Sopenharmony_ci#define VMXNET3_READ_BAR1_REG(adapter, reg) \ 44562306a36Sopenharmony_ci readl((adapter)->hw_addr1 + (reg)) 44662306a36Sopenharmony_ci 44762306a36Sopenharmony_ci#define VMXNET3_WAKE_QUEUE_THRESHOLD(tq) (5) 44862306a36Sopenharmony_ci#define VMXNET3_RX_ALLOC_THRESHOLD(rq, ring_idx, adapter) \ 44962306a36Sopenharmony_ci ((rq)->rx_ring[ring_idx].size >> 3) 45062306a36Sopenharmony_ci 45162306a36Sopenharmony_ci#define VMXNET3_GET_ADDR_LO(dma) ((u32)(dma)) 45262306a36Sopenharmony_ci#define VMXNET3_GET_ADDR_HI(dma) ((u32)(((u64)(dma)) >> 32)) 45362306a36Sopenharmony_ci 45462306a36Sopenharmony_ci#define VMXNET3_VERSION_GE_2(adapter) \ 45562306a36Sopenharmony_ci (adapter->version >= VMXNET3_REV_2 + 1) 45662306a36Sopenharmony_ci#define VMXNET3_VERSION_GE_3(adapter) \ 45762306a36Sopenharmony_ci (adapter->version >= VMXNET3_REV_3 + 1) 45862306a36Sopenharmony_ci#define VMXNET3_VERSION_GE_4(adapter) \ 45962306a36Sopenharmony_ci (adapter->version >= VMXNET3_REV_4 + 1) 46062306a36Sopenharmony_ci#define VMXNET3_VERSION_GE_5(adapter) \ 46162306a36Sopenharmony_ci (adapter->version >= VMXNET3_REV_5 + 1) 46262306a36Sopenharmony_ci#define VMXNET3_VERSION_GE_6(adapter) \ 46362306a36Sopenharmony_ci (adapter->version >= VMXNET3_REV_6 + 1) 46462306a36Sopenharmony_ci#define VMXNET3_VERSION_GE_7(adapter) \ 46562306a36Sopenharmony_ci (adapter->version >= VMXNET3_REV_7 + 1) 46662306a36Sopenharmony_ci 46762306a36Sopenharmony_ci/* must be a multiple of VMXNET3_RING_SIZE_ALIGN */ 46862306a36Sopenharmony_ci#define VMXNET3_DEF_TX_RING_SIZE 512 46962306a36Sopenharmony_ci#define VMXNET3_DEF_RX_RING_SIZE 1024 47062306a36Sopenharmony_ci#define VMXNET3_DEF_RX_RING2_SIZE 512 47162306a36Sopenharmony_ci 47262306a36Sopenharmony_ci#define VMXNET3_DEF_RXDATA_DESC_SIZE 128 47362306a36Sopenharmony_ci 47462306a36Sopenharmony_ci#define VMXNET3_MAX_ETH_HDR_SIZE 22 47562306a36Sopenharmony_ci#define VMXNET3_MAX_SKB_BUF_SIZE (3*1024) 47662306a36Sopenharmony_ci 47762306a36Sopenharmony_ci#define VMXNET3_GET_RING_IDX(adapter, rqID) \ 47862306a36Sopenharmony_ci ((rqID >= adapter->num_rx_queues && \ 47962306a36Sopenharmony_ci rqID < 2 * adapter->num_rx_queues) ? 1 : 0) \ 48062306a36Sopenharmony_ci 48162306a36Sopenharmony_ci#define VMXNET3_RX_DATA_RING(adapter, rqID) \ 48262306a36Sopenharmony_ci (rqID >= 2 * adapter->num_rx_queues && \ 48362306a36Sopenharmony_ci rqID < 3 * adapter->num_rx_queues) \ 48462306a36Sopenharmony_ci 48562306a36Sopenharmony_ci#define VMXNET3_COAL_STATIC_DEFAULT_DEPTH 64 48662306a36Sopenharmony_ci 48762306a36Sopenharmony_ci#define VMXNET3_COAL_RBC_RATE(usecs) (1000000 / usecs) 48862306a36Sopenharmony_ci#define VMXNET3_COAL_RBC_USECS(rbc_rate) (1000000 / rbc_rate) 48962306a36Sopenharmony_ci#define VMXNET3_RSS_FIELDS_DEFAULT (VMXNET3_RSS_FIELDS_TCPIP4 | \ 49062306a36Sopenharmony_ci VMXNET3_RSS_FIELDS_TCPIP6) 49162306a36Sopenharmony_ci 49262306a36Sopenharmony_ciint 49362306a36Sopenharmony_civmxnet3_quiesce_dev(struct vmxnet3_adapter *adapter); 49462306a36Sopenharmony_ci 49562306a36Sopenharmony_ciint 49662306a36Sopenharmony_civmxnet3_activate_dev(struct vmxnet3_adapter *adapter); 49762306a36Sopenharmony_ci 49862306a36Sopenharmony_civoid 49962306a36Sopenharmony_civmxnet3_force_close(struct vmxnet3_adapter *adapter); 50062306a36Sopenharmony_ci 50162306a36Sopenharmony_civoid 50262306a36Sopenharmony_civmxnet3_reset_dev(struct vmxnet3_adapter *adapter); 50362306a36Sopenharmony_ci 50462306a36Sopenharmony_civoid 50562306a36Sopenharmony_civmxnet3_tq_destroy_all(struct vmxnet3_adapter *adapter); 50662306a36Sopenharmony_ci 50762306a36Sopenharmony_civoid 50862306a36Sopenharmony_civmxnet3_rq_destroy_all(struct vmxnet3_adapter *adapter); 50962306a36Sopenharmony_ci 51062306a36Sopenharmony_ciint 51162306a36Sopenharmony_civmxnet3_rq_create_all(struct vmxnet3_adapter *adapter); 51262306a36Sopenharmony_ci 51362306a36Sopenharmony_civoid 51462306a36Sopenharmony_civmxnet3_adjust_rx_ring_size(struct vmxnet3_adapter *adapter); 51562306a36Sopenharmony_ci 51662306a36Sopenharmony_cinetdev_features_t 51762306a36Sopenharmony_civmxnet3_fix_features(struct net_device *netdev, netdev_features_t features); 51862306a36Sopenharmony_ci 51962306a36Sopenharmony_cinetdev_features_t 52062306a36Sopenharmony_civmxnet3_features_check(struct sk_buff *skb, 52162306a36Sopenharmony_ci struct net_device *netdev, netdev_features_t features); 52262306a36Sopenharmony_ci 52362306a36Sopenharmony_ciint 52462306a36Sopenharmony_civmxnet3_set_features(struct net_device *netdev, netdev_features_t features); 52562306a36Sopenharmony_ci 52662306a36Sopenharmony_ciint 52762306a36Sopenharmony_civmxnet3_create_queues(struct vmxnet3_adapter *adapter, 52862306a36Sopenharmony_ci u32 tx_ring_size, u32 rx_ring_size, u32 rx_ring2_size, 52962306a36Sopenharmony_ci u16 txdata_desc_size, u16 rxdata_desc_size); 53062306a36Sopenharmony_ci 53162306a36Sopenharmony_civoid vmxnet3_set_ethtool_ops(struct net_device *netdev); 53262306a36Sopenharmony_ci 53362306a36Sopenharmony_civoid vmxnet3_get_stats64(struct net_device *dev, 53462306a36Sopenharmony_ci struct rtnl_link_stats64 *stats); 53562306a36Sopenharmony_cibool vmxnet3_check_ptcapability(u32 cap_supported, u32 cap); 53662306a36Sopenharmony_ci 53762306a36Sopenharmony_ciextern char vmxnet3_driver_name[]; 53862306a36Sopenharmony_ci#endif 539