linux/drivers/net/ethernet/atheros/atlx/atl2.c

// SPDX-License-Identifier: GPL-2.0-or-later
/*
 * Copyright(c) 2006 - 2007 Atheros Corporation. All rights reserved.
 * Copyright(c) 2007 - 2008 Chris Snook <[email protected]>
 *
 * Derived from Intel e1000 driver
 * Copyright(c) 1999 - 2005 Intel Corporation. All rights reserved.
 */

#include <linux/atomic.h>
#include <linux/crc32.h>
#include <linux/dma-mapping.h>
#include <linux/etherdevice.h>
#include <linux/ethtool.h>
#include <linux/hardirq.h>
#include <linux/if_vlan.h>
#include <linux/in.h>
#include <linux/interrupt.h>
#include <linux/ip.h>
#include <linux/irqflags.h>
#include <linux/irqreturn.h>
#include <linux/mii.h>
#include <linux/net.h>
#include <linux/netdevice.h>
#include <linux/pci.h>
#include <linux/pci_ids.h>
#include <linux/pm.h>
#include <linux/skbuff.h>
#include <linux/slab.h>
#include <linux/spinlock.h>
#include <linux/string.h>
#include <linux/tcp.h>
#include <linux/timer.h>
#include <linux/types.h>
#include <linux/workqueue.h>

#include "atl2.h"

static const char atl2_driver_name[] =;
static const struct ethtool_ops atl2_ethtool_ops;

MODULE_AUTHOR();
MODULE_DESCRIPTION();
MODULE_LICENSE();

/*
 * atl2_pci_tbl - PCI Device ID Table
 */
static const struct pci_device_id atl2_pci_tbl[] =;
MODULE_DEVICE_TABLE(pci, atl2_pci_tbl);

static void atl2_check_options(struct atl2_adapter *adapter);

/**
 * atl2_sw_init - Initialize general software structures (struct atl2_adapter)
 * @adapter: board private structure to initialize
 *
 * atl2_sw_init initializes the Adapter private data structure.
 * Fields are initialized based on PCI device information and
 * OS network device settings (MTU size).
 */
static int atl2_sw_init(struct atl2_adapter *adapter)
{}

/**
 * atl2_set_multi - Multicast and Promiscuous mode set
 * @netdev: network interface device structure
 *
 * The set_multi entry point is called whenever the multicast address
 * list or the network interface flags are updated.  This routine is
 * responsible for configuring the hardware for proper multicast,
 * promiscuous mode, and all-multi behavior.
 */
static void atl2_set_multi(struct net_device *netdev)
{}

static void init_ring_ptrs(struct atl2_adapter *adapter)
{}

/**
 * atl2_configure - Configure Transmit&Receive Unit after Reset
 * @adapter: board private structure
 *
 * Configure the Tx /Rx unit of the MAC after a reset.
 */
static int atl2_configure(struct atl2_adapter *adapter)
{}

/**
 * atl2_setup_ring_resources - allocate Tx / RX descriptor resources
 * @adapter: board private structure
 *
 * Return 0 on success, negative on failure
 */
static s32 atl2_setup_ring_resources(struct atl2_adapter *adapter)
{}

/**
 * atl2_irq_enable - Enable default interrupt generation settings
 * @adapter: board private structure
 */
static inline void atl2_irq_enable(struct atl2_adapter *adapter)
{}

/**
 * atl2_irq_disable - Mask off interrupt generation on the NIC
 * @adapter: board private structure
 */
static inline void atl2_irq_disable(struct atl2_adapter *adapter)
{}

static void __atl2_vlan_mode(netdev_features_t features, u32 *ctrl)
{}

static void atl2_vlan_mode(struct net_device *netdev,
	netdev_features_t features)
{}

static void atl2_restore_vlan(struct atl2_adapter *adapter)
{}

static netdev_features_t atl2_fix_features(struct net_device *netdev,
	netdev_features_t features)
{}

static int atl2_set_features(struct net_device *netdev,
	netdev_features_t features)
{}

static void atl2_intr_rx(struct atl2_adapter *adapter)
{}

static void atl2_intr_tx(struct atl2_adapter *adapter)
{}

static void atl2_check_for_link(struct atl2_adapter *adapter)
{}

static inline void atl2_clear_phy_int(struct atl2_adapter *adapter)
{}

/**
 * atl2_intr - Interrupt Handler
 * @irq: interrupt number
 * @data: pointer to a network interface device structure
 */
static irqreturn_t atl2_intr(int irq, void *data)
{}

static int atl2_request_irq(struct atl2_adapter *adapter)
{}

/**
 * atl2_free_ring_resources - Free Tx / RX descriptor Resources
 * @adapter: board private structure
 *
 * Free all transmit software resources
 */
static void atl2_free_ring_resources(struct atl2_adapter *adapter)
{}

/**
 * atl2_open - Called when a network interface is made active
 * @netdev: network interface device structure
 *
 * Returns 0 on success, negative value on failure
 *
 * The open entry point is called when a network interface is made
 * active by the system (IFF_UP).  At this point all resources needed
 * for transmit and receive operations are allocated, the interrupt
 * handler is registered with the OS, the watchdog timer is started,
 * and the stack is notified that the interface is ready.
 */
static int atl2_open(struct net_device *netdev)
{}

static void atl2_down(struct atl2_adapter *adapter)
{}

static void atl2_free_irq(struct atl2_adapter *adapter)
{}

/**
 * atl2_close - Disables a network interface
 * @netdev: network interface device structure
 *
 * Returns 0, this is not allowed to fail
 *
 * The close entry point is called when an interface is de-activated
 * by the OS.  The hardware is still under the drivers control, but
 * needs to be disabled.  A global MAC reset is issued to stop the
 * hardware, and all transmit and receive resources are freed.
 */
static int atl2_close(struct net_device *netdev)
{}

static inline int TxsFreeUnit(struct atl2_adapter *adapter)
{}

static inline int TxdFreeBytes(struct atl2_adapter *adapter)
{}

static netdev_tx_t atl2_xmit_frame(struct sk_buff *skb,
					 struct net_device *netdev)
{}

/**
 * atl2_change_mtu - Change the Maximum Transfer Unit
 * @netdev: network interface device structure
 * @new_mtu: new value for maximum frame size
 *
 * Returns 0 on success, negative on failure
 */
static int atl2_change_mtu(struct net_device *netdev, int new_mtu)
{}

/**
 * atl2_set_mac - Change the Ethernet Address of the NIC
 * @netdev: network interface device structure
 * @p: pointer to an address structure
 *
 * Returns 0 on success, negative on failure
 */
static int atl2_set_mac(struct net_device *netdev, void *p)
{}

static int atl2_mii_ioctl(struct net_device *netdev, struct ifreq *ifr, int cmd)
{}

static int atl2_ioctl(struct net_device *netdev, struct ifreq *ifr, int cmd)
{}

/**
 * atl2_tx_timeout - Respond to a Tx Hang
 * @netdev: network interface device structure
 * @txqueue: index of the hanging transmit queue
 */
static void atl2_tx_timeout(struct net_device *netdev, unsigned int txqueue)
{}

/**
 * atl2_watchdog - Timer Call-back
 * @t: timer list containing a pointer to netdev cast into an unsigned long
 */
static void atl2_watchdog(struct timer_list *t)
{}

/**
 * atl2_phy_config - Timer Call-back
 * @t: timer list containing a pointer to netdev cast into an unsigned long
 */
static void atl2_phy_config(struct timer_list *t)
{}

static int atl2_up(struct atl2_adapter *adapter)
{}

static void atl2_reinit_locked(struct atl2_adapter *adapter)
{}

static void atl2_reset_task(struct work_struct *work)
{}

static void atl2_setup_mac_ctrl(struct atl2_adapter *adapter)
{}

static int atl2_check_link(struct atl2_adapter *adapter)
{}

/**
 * atl2_link_chg_task - deal with link change event Out of interrupt context
 * @work: pointer to work struct with private info
 */
static void atl2_link_chg_task(struct work_struct *work)
{}

static void atl2_setup_pcicmd(struct pci_dev *pdev)
{}

#ifdef CONFIG_NET_POLL_CONTROLLER
static void atl2_poll_controller(struct net_device *netdev)
{}
#endif


static const struct net_device_ops atl2_netdev_ops =;

/**
 * atl2_probe - Device Initialization Routine
 * @pdev: PCI device information struct
 * @ent: entry in atl2_pci_tbl
 *
 * Returns 0 on success, negative on failure
 *
 * atl2_probe initializes an adapter identified by a pci_dev structure.
 * The OS initialization, configuring of the adapter private structure,
 * and a hardware reset occur.
 */
static int atl2_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
{}

/**
 * atl2_remove - Device Removal Routine
 * @pdev: PCI device information struct
 *
 * atl2_remove is called by the PCI subsystem to alert the driver
 * that it should release a PCI device.  The could be caused by a
 * Hot-Plug event, or because the driver is going to be removed from
 * memory.
 */
/* FIXME: write the original MAC address back in case it was changed from a
 * BIOS-set value, as in atl1 -- CHS */
static void atl2_remove(struct pci_dev *pdev)
{}

static int atl2_suspend(struct pci_dev *pdev, pm_message_t state)
{}

#ifdef CONFIG_PM
static int atl2_resume(struct pci_dev *pdev)
{}
#endif

static void atl2_shutdown(struct pci_dev *pdev)
{}

static struct pci_driver atl2_driver =;

module_pci_driver();

static void atl2_read_pci_cfg(struct atl2_hw *hw, u32 reg, u16 *value)
{}

static void atl2_write_pci_cfg(struct atl2_hw *hw, u32 reg, u16 *value)
{}

static int atl2_get_link_ksettings(struct net_device *netdev,
				   struct ethtool_link_ksettings *cmd)
{}

static int atl2_set_link_ksettings(struct net_device *netdev,
				   const struct ethtool_link_ksettings *cmd)
{}

static u32 atl2_get_msglevel(struct net_device *netdev)
{}

/*
 * It's sane for this to be empty, but we might want to take advantage of this.
 */
static void atl2_set_msglevel(struct net_device *netdev, u32 data)
{}

static int atl2_get_regs_len(struct net_device *netdev)
{}

static void atl2_get_regs(struct net_device *netdev,
	struct ethtool_regs *regs, void *p)
{}

static int atl2_get_eeprom_len(struct net_device *netdev)
{}

static int atl2_get_eeprom(struct net_device *netdev,
	struct ethtool_eeprom *eeprom, u8 *bytes)
{}

static int atl2_set_eeprom(struct net_device *netdev,
	struct ethtool_eeprom *eeprom, u8 *bytes)
{}

static void atl2_get_drvinfo(struct net_device *netdev,
	struct ethtool_drvinfo *drvinfo)
{}

static void atl2_get_wol(struct net_device *netdev,
	struct ethtool_wolinfo *wol)
{}

static int atl2_set_wol(struct net_device *netdev, struct ethtool_wolinfo *wol)
{}

static int atl2_nway_reset(struct net_device *netdev)
{}

static const struct ethtool_ops atl2_ethtool_ops =;

#define LBYTESWAP(a)
#define LONGSWAP(a)
#define SHORTSWAP(a)

/*
 * Reset the transmit and receive units; mask and clear all interrupts.
 *
 * hw - Struct containing variables accessed by shared code
 * return : 0  or  idle status (if error)
 */
static s32 atl2_reset_hw(struct atl2_hw *hw)
{}

#define CUSTOM_SPI_CS_SETUP
#define CUSTOM_SPI_CLK_HI
#define CUSTOM_SPI_CLK_LO
#define CUSTOM_SPI_CS_HOLD
#define CUSTOM_SPI_CS_HI

static struct atl2_spi_flash_dev flash_table[] =;

static bool atl2_spi_read(struct atl2_hw *hw, u32 addr, u32 *buf)
{}

/*
 * get_permanent_address
 * return 0 if get valid mac address,
 */
static int get_permanent_address(struct atl2_hw *hw)
{}

/*
 * Reads the adapter's MAC address from the EEPROM
 *
 * hw - Struct containing variables accessed by shared code
 */
static s32 atl2_read_mac_addr(struct atl2_hw *hw)
{}

/*
 * Hashes an address to determine its location in the multicast table
 *
 * hw - Struct containing variables accessed by shared code
 * mc_addr - the multicast address to hash
 *
 * atl2_hash_mc_addr
 *  purpose
 *      set hash value for a multicast address
 *      hash calcu processing :
 *          1. calcu 32bit CRC for multicast address
 *          2. reverse crc with MSB to LSB
 */
static u32 atl2_hash_mc_addr(struct atl2_hw *hw, u8 *mc_addr)
{}

/*
 * Sets the bit in the multicast table corresponding to the hash value.
 *
 * hw - Struct containing variables accessed by shared code
 * hash_value - Multicast address hash value
 */
static void atl2_hash_set(struct atl2_hw *hw, u32 hash_value)
{}

/*
 * atl2_init_pcie - init PCIE module
 */
static void atl2_init_pcie(struct atl2_hw *hw)
{}

static void atl2_init_flash_opcode(struct atl2_hw *hw)
{}

/********************************************************************
* Performs basic configuration of the adapter.
*
* hw - Struct containing variables accessed by shared code
* Assumes that the controller has previously been reset and is in a
* post-reset uninitialized state. Initializes multicast table,
* and  Calls routines to setup link
* Leaves the transmit and receive units disabled and uninitialized.
********************************************************************/
static s32 atl2_init_hw(struct atl2_hw *hw)
{}

/*
 * Detects the current speed and duplex settings of the hardware.
 *
 * hw - Struct containing variables accessed by shared code
 * speed - Speed of the connection
 * duplex - Duplex setting of the connection
 */
static s32 atl2_get_speed_and_duplex(struct atl2_hw *hw, u16 *speed,
	u16 *duplex)
{}

/*
 * Reads the value from a PHY register
 * hw - Struct containing variables accessed by shared code
 * reg_addr - address of the PHY register to read
 */
static s32 atl2_read_phy_reg(struct atl2_hw *hw, u16 reg_addr, u16 *phy_data)
{}

/*
 * Writes a value to a PHY register
 * hw - Struct containing variables accessed by shared code
 * reg_addr - address of the PHY register to write
 * data - data to write to the PHY
 */
static s32 atl2_write_phy_reg(struct atl2_hw *hw, u32 reg_addr, u16 phy_data)
{}

/*
 * Configures PHY autoneg and flow control advertisement settings
 *
 * hw - Struct containing variables accessed by shared code
 */
static s32 atl2_phy_setup_autoneg_adv(struct atl2_hw *hw)
{}

/*
 * Resets the PHY and make all config validate
 *
 * hw - Struct containing variables accessed by shared code
 *
 * Sets bit 15 and 12 of the MII Control regiser (for F001 bug)
 */
static s32 atl2_phy_commit(struct atl2_hw *hw)
{}

static s32 atl2_phy_init(struct atl2_hw *hw)
{}

static void atl2_set_mac_addr(struct atl2_hw *hw)
{}

/*
 * check_eeprom_exist
 * return 0 if eeprom exist
 */
static int atl2_check_eeprom_exist(struct atl2_hw *hw)
{}

/* FIXME: This doesn't look right. -- CHS */
static bool atl2_write_eeprom(struct atl2_hw *hw, u32 offset, u32 value)
{}

static bool atl2_read_eeprom(struct atl2_hw *hw, u32 Offset, u32 *pValue)
{}

static void atl2_force_ps(struct atl2_hw *hw)
{}

/* This is the only thing that needs to be changed to adjust the
 * maximum number of ports that the driver can manage.
 */
#define ATL2_MAX_NIC

#define OPTION_UNSET
#define OPTION_DISABLED
#define OPTION_ENABLED

/* All parameters are treated the same, as an integer array of values.
 * This macro just reduces the need to repeat the same declaration code
 * over and over (plus this helps to avoid typo bugs).
 */
#define ATL2_PARAM_INIT
#ifndef module_param_array
/* Module Parameters are always initialized to -1, so that the driver
 * can tell the difference between no user specified value or the
 * user asking for the default value.
 * The true default values are loaded in when atl2_check_options is called.
 *
 * This is a GCC extension to ANSI C.
 * See the item "Labeled Elements in Initializers" in the section
 * "Extensions to the C Language Family" of the GCC documentation.
 */

#define ATL2_PARAM
#else
#define ATL2_PARAM(X, desc)
#endif

/*
 * Transmit Memory Size
 * Valid Range: 64-2048
 * Default Value: 128
 */
#define ATL2_MIN_TX_MEMSIZE
#define ATL2_MAX_TX_MEMSIZE
#define ATL2_DEFAULT_TX_MEMSIZE
ATL2_PARAM(TxMemSize, "Bytes of Transmit Memory");

/*
 * Receive Memory Block Count
 * Valid Range: 16-512
 * Default Value: 128
 */
#define ATL2_MIN_RXD_COUNT
#define ATL2_MAX_RXD_COUNT
#define ATL2_DEFAULT_RXD_COUNT
ATL2_PARAM(RxMemBlock, "Number of receive memory block");

/*
 * User Specified MediaType Override
 *
 * Valid Range: 0-5
 *  - 0    - auto-negotiate at all supported speeds
 *  - 1    - only link at 1000Mbps Full Duplex
 *  - 2    - only link at 100Mbps Full Duplex
 *  - 3    - only link at 100Mbps Half Duplex
 *  - 4    - only link at 10Mbps Full Duplex
 *  - 5    - only link at 10Mbps Half Duplex
 * Default Value: 0
 */
ATL2_PARAM(MediaType, "MediaType Select");

/*
 * Interrupt Moderate Timer in units of 2048 ns (~2 us)
 * Valid Range: 10-65535
 * Default Value: 45000(90ms)
 */
#define INT_MOD_DEFAULT_CNT
#define INT_MOD_MAX_CNT
#define INT_MOD_MIN_CNT
ATL2_PARAM(IntModTimer, "Interrupt Moderator Timer");

/*
 * FlashVendor
 * Valid Range: 0-2
 * 0 - Atmel
 * 1 - SST
 * 2 - ST
 */
ATL2_PARAM(FlashVendor, "SPI Flash Vendor");

#define AUTONEG_ADV_DEFAULT
#define AUTONEG_ADV_MASK
#define FLOW_CONTROL_DEFAULT

#define FLASH_VENDOR_DEFAULT
#define FLASH_VENDOR_MIN
#define FLASH_VENDOR_MAX

struct atl2_option {};

static int atl2_validate_option(int *value, struct atl2_option *opt)
{}

/**
 * atl2_check_options - Range Checking for Command Line Parameters
 * @adapter: board private structure
 *
 * This routine checks all command line parameters for valid user
 * input.  If an invalid value is given, or if no user specified
 * value exists, a default value is used.  The final value is stored
 * in a variable in the adapter structure.
 */
static void atl2_check_options(struct atl2_adapter *adapter)
{}