cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

fman_tgec.c (23548B)


      1/*
      2 * Copyright 2008-2015 Freescale Semiconductor Inc.
      3 *
      4 * Redistribution and use in source and binary forms, with or without
      5 * modification, are permitted provided that the following conditions are met:
      6 *     * Redistributions of source code must retain the above copyright
      7 *       notice, this list of conditions and the following disclaimer.
      8 *     * Redistributions in binary form must reproduce the above copyright
      9 *       notice, this list of conditions and the following disclaimer in the
     10 *       documentation and/or other materials provided with the distribution.
     11 *     * Neither the name of Freescale Semiconductor nor the
     12 *       names of its contributors may be used to endorse or promote products
     13 *       derived from this software without specific prior written permission.
     14 *
     15 *
     16 * ALTERNATIVELY, this software may be distributed under the terms of the
     17 * GNU General Public License ("GPL") as published by the Free Software
     18 * Foundation, either version 2 of that License or (at your option) any
     19 * later version.
     20 *
     21 * THIS SOFTWARE IS PROVIDED BY Freescale Semiconductor ``AS IS'' AND ANY
     22 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
     23 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
     24 * DISCLAIMED. IN NO EVENT SHALL Freescale Semiconductor BE LIABLE FOR ANY
     25 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
     26 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
     27 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
     28 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     29 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
     30 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     31 */
     32
     33#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
     34
     35#include "fman_tgec.h"
     36#include "fman.h"
     37
     38#include <linux/slab.h>
     39#include <linux/bitrev.h>
     40#include <linux/io.h>
     41#include <linux/crc32.h>
     42
     43/* Transmit Inter-Packet Gap Length Register (TX_IPG_LENGTH) */
     44#define TGEC_TX_IPG_LENGTH_MASK	0x000003ff
     45
     46/* Command and Configuration Register (COMMAND_CONFIG) */
     47#define CMD_CFG_EN_TIMESTAMP		0x00100000
     48#define CMD_CFG_NO_LEN_CHK		0x00020000
     49#define CMD_CFG_PAUSE_IGNORE		0x00000100
     50#define CMF_CFG_CRC_FWD			0x00000040
     51#define CMD_CFG_PROMIS_EN		0x00000010
     52#define CMD_CFG_RX_EN			0x00000002
     53#define CMD_CFG_TX_EN			0x00000001
     54
     55/* Interrupt Mask Register (IMASK) */
     56#define TGEC_IMASK_MDIO_SCAN_EVENT	0x00010000
     57#define TGEC_IMASK_MDIO_CMD_CMPL	0x00008000
     58#define TGEC_IMASK_REM_FAULT		0x00004000
     59#define TGEC_IMASK_LOC_FAULT		0x00002000
     60#define TGEC_IMASK_TX_ECC_ER		0x00001000
     61#define TGEC_IMASK_TX_FIFO_UNFL	0x00000800
     62#define TGEC_IMASK_TX_FIFO_OVFL	0x00000400
     63#define TGEC_IMASK_TX_ER		0x00000200
     64#define TGEC_IMASK_RX_FIFO_OVFL	0x00000100
     65#define TGEC_IMASK_RX_ECC_ER		0x00000080
     66#define TGEC_IMASK_RX_JAB_FRM		0x00000040
     67#define TGEC_IMASK_RX_OVRSZ_FRM	0x00000020
     68#define TGEC_IMASK_RX_RUNT_FRM		0x00000010
     69#define TGEC_IMASK_RX_FRAG_FRM		0x00000008
     70#define TGEC_IMASK_RX_LEN_ER		0x00000004
     71#define TGEC_IMASK_RX_CRC_ER		0x00000002
     72#define TGEC_IMASK_RX_ALIGN_ER		0x00000001
     73
     74/* Hashtable Control Register (HASHTABLE_CTRL) */
     75#define TGEC_HASH_MCAST_SHIFT		23
     76#define TGEC_HASH_MCAST_EN		0x00000200
     77#define TGEC_HASH_ADR_MSK		0x000001ff
     78
     79#define DEFAULT_TX_IPG_LENGTH			12
     80#define DEFAULT_MAX_FRAME_LENGTH		0x600
     81#define DEFAULT_PAUSE_QUANT			0xf000
     82
     83/* number of pattern match registers (entries) */
     84#define TGEC_NUM_OF_PADDRS          1
     85
     86/* Group address bit indication */
     87#define GROUP_ADDRESS               0x0000010000000000LL
     88
     89/* Hash table size (= 32 bits*8 regs) */
     90#define TGEC_HASH_TABLE_SIZE             512
     91
     92/* tGEC memory map */
     93struct tgec_regs {
     94	u32 tgec_id;		/* 0x000 Controller ID */
     95	u32 reserved001[1];	/* 0x004 */
     96	u32 command_config;	/* 0x008 Control and configuration */
     97	u32 mac_addr_0;		/* 0x00c Lower 32 bits of the MAC adr */
     98	u32 mac_addr_1;		/* 0x010 Upper 16 bits of the MAC adr */
     99	u32 maxfrm;		/* 0x014 Maximum frame length */
    100	u32 pause_quant;	/* 0x018 Pause quanta */
    101	u32 rx_fifo_sections;	/* 0x01c  */
    102	u32 tx_fifo_sections;	/* 0x020  */
    103	u32 rx_fifo_almost_f_e;	/* 0x024  */
    104	u32 tx_fifo_almost_f_e;	/* 0x028  */
    105	u32 hashtable_ctrl;	/* 0x02c Hash table control */
    106	u32 mdio_cfg_status;	/* 0x030  */
    107	u32 mdio_command;	/* 0x034  */
    108	u32 mdio_data;		/* 0x038  */
    109	u32 mdio_regaddr;	/* 0x03c  */
    110	u32 status;		/* 0x040  */
    111	u32 tx_ipg_len;		/* 0x044 Transmitter inter-packet-gap */
    112	u32 mac_addr_2;		/* 0x048 Lower 32 bits of 2nd MAC adr */
    113	u32 mac_addr_3;		/* 0x04c Upper 16 bits of 2nd MAC adr */
    114	u32 rx_fifo_ptr_rd;	/* 0x050  */
    115	u32 rx_fifo_ptr_wr;	/* 0x054  */
    116	u32 tx_fifo_ptr_rd;	/* 0x058  */
    117	u32 tx_fifo_ptr_wr;	/* 0x05c  */
    118	u32 imask;		/* 0x060 Interrupt mask */
    119	u32 ievent;		/* 0x064 Interrupt event */
    120	u32 udp_port;		/* 0x068 Defines a UDP Port number */
    121	u32 type_1588v2;	/* 0x06c Type field for 1588v2 */
    122	u32 reserved070[4];	/* 0x070 */
    123	/* 10Ge Statistics Counter */
    124	u32 tfrm_u;		/* 80 aFramesTransmittedOK */
    125	u32 tfrm_l;		/* 84 aFramesTransmittedOK */
    126	u32 rfrm_u;		/* 88 aFramesReceivedOK */
    127	u32 rfrm_l;		/* 8c aFramesReceivedOK */
    128	u32 rfcs_u;		/* 90 aFrameCheckSequenceErrors */
    129	u32 rfcs_l;		/* 94 aFrameCheckSequenceErrors */
    130	u32 raln_u;		/* 98 aAlignmentErrors */
    131	u32 raln_l;		/* 9c aAlignmentErrors */
    132	u32 txpf_u;		/* A0 aPAUSEMACCtrlFramesTransmitted */
    133	u32 txpf_l;		/* A4 aPAUSEMACCtrlFramesTransmitted */
    134	u32 rxpf_u;		/* A8 aPAUSEMACCtrlFramesReceived */
    135	u32 rxpf_l;		/* Ac aPAUSEMACCtrlFramesReceived */
    136	u32 rlong_u;		/* B0 aFrameTooLongErrors */
    137	u32 rlong_l;		/* B4 aFrameTooLongErrors */
    138	u32 rflr_u;		/* B8 aInRangeLengthErrors */
    139	u32 rflr_l;		/* Bc aInRangeLengthErrors */
    140	u32 tvlan_u;		/* C0 VLANTransmittedOK */
    141	u32 tvlan_l;		/* C4 VLANTransmittedOK */
    142	u32 rvlan_u;		/* C8 VLANReceivedOK */
    143	u32 rvlan_l;		/* Cc VLANReceivedOK */
    144	u32 toct_u;		/* D0 if_out_octets */
    145	u32 toct_l;		/* D4 if_out_octets */
    146	u32 roct_u;		/* D8 if_in_octets */
    147	u32 roct_l;		/* Dc if_in_octets */
    148	u32 ruca_u;		/* E0 if_in_ucast_pkts */
    149	u32 ruca_l;		/* E4 if_in_ucast_pkts */
    150	u32 rmca_u;		/* E8 ifInMulticastPkts */
    151	u32 rmca_l;		/* Ec ifInMulticastPkts */
    152	u32 rbca_u;		/* F0 ifInBroadcastPkts */
    153	u32 rbca_l;		/* F4 ifInBroadcastPkts */
    154	u32 terr_u;		/* F8 if_out_errors */
    155	u32 terr_l;		/* Fc if_out_errors */
    156	u32 reserved100[2];	/* 100-108 */
    157	u32 tuca_u;		/* 108 if_out_ucast_pkts */
    158	u32 tuca_l;		/* 10c if_out_ucast_pkts */
    159	u32 tmca_u;		/* 110 ifOutMulticastPkts */
    160	u32 tmca_l;		/* 114 ifOutMulticastPkts */
    161	u32 tbca_u;		/* 118 ifOutBroadcastPkts */
    162	u32 tbca_l;		/* 11c ifOutBroadcastPkts */
    163	u32 rdrp_u;		/* 120 etherStatsDropEvents */
    164	u32 rdrp_l;		/* 124 etherStatsDropEvents */
    165	u32 reoct_u;		/* 128 etherStatsOctets */
    166	u32 reoct_l;		/* 12c etherStatsOctets */
    167	u32 rpkt_u;		/* 130 etherStatsPkts */
    168	u32 rpkt_l;		/* 134 etherStatsPkts */
    169	u32 trund_u;		/* 138 etherStatsUndersizePkts */
    170	u32 trund_l;		/* 13c etherStatsUndersizePkts */
    171	u32 r64_u;		/* 140 etherStatsPkts64Octets */
    172	u32 r64_l;		/* 144 etherStatsPkts64Octets */
    173	u32 r127_u;		/* 148 etherStatsPkts65to127Octets */
    174	u32 r127_l;		/* 14c etherStatsPkts65to127Octets */
    175	u32 r255_u;		/* 150 etherStatsPkts128to255Octets */
    176	u32 r255_l;		/* 154 etherStatsPkts128to255Octets */
    177	u32 r511_u;		/* 158 etherStatsPkts256to511Octets */
    178	u32 r511_l;		/* 15c etherStatsPkts256to511Octets */
    179	u32 r1023_u;		/* 160 etherStatsPkts512to1023Octets */
    180	u32 r1023_l;		/* 164 etherStatsPkts512to1023Octets */
    181	u32 r1518_u;		/* 168 etherStatsPkts1024to1518Octets */
    182	u32 r1518_l;		/* 16c etherStatsPkts1024to1518Octets */
    183	u32 r1519x_u;		/* 170 etherStatsPkts1519toX */
    184	u32 r1519x_l;		/* 174 etherStatsPkts1519toX */
    185	u32 trovr_u;		/* 178 etherStatsOversizePkts */
    186	u32 trovr_l;		/* 17c etherStatsOversizePkts */
    187	u32 trjbr_u;		/* 180 etherStatsJabbers */
    188	u32 trjbr_l;		/* 184 etherStatsJabbers */
    189	u32 trfrg_u;		/* 188 etherStatsFragments */
    190	u32 trfrg_l;		/* 18C etherStatsFragments */
    191	u32 rerr_u;		/* 190 if_in_errors */
    192	u32 rerr_l;		/* 194 if_in_errors */
    193};
    194
    195struct tgec_cfg {
    196	bool pause_ignore;
    197	bool promiscuous_mode_enable;
    198	u16 max_frame_length;
    199	u16 pause_quant;
    200	u32 tx_ipg_length;
    201};
    202
    203struct fman_mac {
    204	/* Pointer to the memory mapped registers. */
    205	struct tgec_regs __iomem *regs;
    206	/* MAC address of device; */
    207	u64 addr;
    208	u16 max_speed;
    209	void *dev_id; /* device cookie used by the exception cbs */
    210	fman_mac_exception_cb *exception_cb;
    211	fman_mac_exception_cb *event_cb;
    212	/* pointer to driver's global address hash table  */
    213	struct eth_hash_t *multicast_addr_hash;
    214	/* pointer to driver's individual address hash table  */
    215	struct eth_hash_t *unicast_addr_hash;
    216	u8 mac_id;
    217	u32 exceptions;
    218	struct tgec_cfg *cfg;
    219	void *fm;
    220	struct fman_rev_info fm_rev_info;
    221	bool allmulti_enabled;
    222};
    223
    224static void set_mac_address(struct tgec_regs __iomem *regs, const u8 *adr)
    225{
    226	u32 tmp0, tmp1;
    227
    228	tmp0 = (u32)(adr[0] | adr[1] << 8 | adr[2] << 16 | adr[3] << 24);
    229	tmp1 = (u32)(adr[4] | adr[5] << 8);
    230	iowrite32be(tmp0, &regs->mac_addr_0);
    231	iowrite32be(tmp1, &regs->mac_addr_1);
    232}
    233
    234static void set_dflts(struct tgec_cfg *cfg)
    235{
    236	cfg->promiscuous_mode_enable = false;
    237	cfg->pause_ignore = false;
    238	cfg->tx_ipg_length = DEFAULT_TX_IPG_LENGTH;
    239	cfg->max_frame_length = DEFAULT_MAX_FRAME_LENGTH;
    240	cfg->pause_quant = DEFAULT_PAUSE_QUANT;
    241}
    242
    243static int init(struct tgec_regs __iomem *regs, struct tgec_cfg *cfg,
    244		u32 exception_mask)
    245{
    246	u32 tmp;
    247
    248	/* Config */
    249	tmp = CMF_CFG_CRC_FWD;
    250	if (cfg->promiscuous_mode_enable)
    251		tmp |= CMD_CFG_PROMIS_EN;
    252	if (cfg->pause_ignore)
    253		tmp |= CMD_CFG_PAUSE_IGNORE;
    254	/* Payload length check disable */
    255	tmp |= CMD_CFG_NO_LEN_CHK;
    256	iowrite32be(tmp, &regs->command_config);
    257
    258	/* Max Frame Length */
    259	iowrite32be((u32)cfg->max_frame_length, &regs->maxfrm);
    260	/* Pause Time */
    261	iowrite32be(cfg->pause_quant, &regs->pause_quant);
    262
    263	/* clear all pending events and set-up interrupts */
    264	iowrite32be(0xffffffff, &regs->ievent);
    265	iowrite32be(ioread32be(&regs->imask) | exception_mask, &regs->imask);
    266
    267	return 0;
    268}
    269
    270static int check_init_parameters(struct fman_mac *tgec)
    271{
    272	if (tgec->max_speed < SPEED_10000) {
    273		pr_err("10G MAC driver only support 10G speed\n");
    274		return -EINVAL;
    275	}
    276	if (!tgec->exception_cb) {
    277		pr_err("uninitialized exception_cb\n");
    278		return -EINVAL;
    279	}
    280	if (!tgec->event_cb) {
    281		pr_err("uninitialized event_cb\n");
    282		return -EINVAL;
    283	}
    284
    285	return 0;
    286}
    287
    288static int get_exception_flag(enum fman_mac_exceptions exception)
    289{
    290	u32 bit_mask;
    291
    292	switch (exception) {
    293	case FM_MAC_EX_10G_MDIO_SCAN_EVENT:
    294		bit_mask = TGEC_IMASK_MDIO_SCAN_EVENT;
    295		break;
    296	case FM_MAC_EX_10G_MDIO_CMD_CMPL:
    297		bit_mask = TGEC_IMASK_MDIO_CMD_CMPL;
    298		break;
    299	case FM_MAC_EX_10G_REM_FAULT:
    300		bit_mask = TGEC_IMASK_REM_FAULT;
    301		break;
    302	case FM_MAC_EX_10G_LOC_FAULT:
    303		bit_mask = TGEC_IMASK_LOC_FAULT;
    304		break;
    305	case FM_MAC_EX_10G_TX_ECC_ER:
    306		bit_mask = TGEC_IMASK_TX_ECC_ER;
    307		break;
    308	case FM_MAC_EX_10G_TX_FIFO_UNFL:
    309		bit_mask = TGEC_IMASK_TX_FIFO_UNFL;
    310		break;
    311	case FM_MAC_EX_10G_TX_FIFO_OVFL:
    312		bit_mask = TGEC_IMASK_TX_FIFO_OVFL;
    313		break;
    314	case FM_MAC_EX_10G_TX_ER:
    315		bit_mask = TGEC_IMASK_TX_ER;
    316		break;
    317	case FM_MAC_EX_10G_RX_FIFO_OVFL:
    318		bit_mask = TGEC_IMASK_RX_FIFO_OVFL;
    319		break;
    320	case FM_MAC_EX_10G_RX_ECC_ER:
    321		bit_mask = TGEC_IMASK_RX_ECC_ER;
    322		break;
    323	case FM_MAC_EX_10G_RX_JAB_FRM:
    324		bit_mask = TGEC_IMASK_RX_JAB_FRM;
    325		break;
    326	case FM_MAC_EX_10G_RX_OVRSZ_FRM:
    327		bit_mask = TGEC_IMASK_RX_OVRSZ_FRM;
    328		break;
    329	case FM_MAC_EX_10G_RX_RUNT_FRM:
    330		bit_mask = TGEC_IMASK_RX_RUNT_FRM;
    331		break;
    332	case FM_MAC_EX_10G_RX_FRAG_FRM:
    333		bit_mask = TGEC_IMASK_RX_FRAG_FRM;
    334		break;
    335	case FM_MAC_EX_10G_RX_LEN_ER:
    336		bit_mask = TGEC_IMASK_RX_LEN_ER;
    337		break;
    338	case FM_MAC_EX_10G_RX_CRC_ER:
    339		bit_mask = TGEC_IMASK_RX_CRC_ER;
    340		break;
    341	case FM_MAC_EX_10G_RX_ALIGN_ER:
    342		bit_mask = TGEC_IMASK_RX_ALIGN_ER;
    343		break;
    344	default:
    345		bit_mask = 0;
    346		break;
    347	}
    348
    349	return bit_mask;
    350}
    351
    352static void tgec_err_exception(void *handle)
    353{
    354	struct fman_mac *tgec = (struct fman_mac *)handle;
    355	struct tgec_regs __iomem *regs = tgec->regs;
    356	u32 event;
    357
    358	/* do not handle MDIO events */
    359	event = ioread32be(&regs->ievent) &
    360			   ~(TGEC_IMASK_MDIO_SCAN_EVENT |
    361			   TGEC_IMASK_MDIO_CMD_CMPL);
    362
    363	event &= ioread32be(&regs->imask);
    364
    365	iowrite32be(event, &regs->ievent);
    366
    367	if (event & TGEC_IMASK_REM_FAULT)
    368		tgec->exception_cb(tgec->dev_id, FM_MAC_EX_10G_REM_FAULT);
    369	if (event & TGEC_IMASK_LOC_FAULT)
    370		tgec->exception_cb(tgec->dev_id, FM_MAC_EX_10G_LOC_FAULT);
    371	if (event & TGEC_IMASK_TX_ECC_ER)
    372		tgec->exception_cb(tgec->dev_id, FM_MAC_EX_10G_TX_ECC_ER);
    373	if (event & TGEC_IMASK_TX_FIFO_UNFL)
    374		tgec->exception_cb(tgec->dev_id, FM_MAC_EX_10G_TX_FIFO_UNFL);
    375	if (event & TGEC_IMASK_TX_FIFO_OVFL)
    376		tgec->exception_cb(tgec->dev_id, FM_MAC_EX_10G_TX_FIFO_OVFL);
    377	if (event & TGEC_IMASK_TX_ER)
    378		tgec->exception_cb(tgec->dev_id, FM_MAC_EX_10G_TX_ER);
    379	if (event & TGEC_IMASK_RX_FIFO_OVFL)
    380		tgec->exception_cb(tgec->dev_id, FM_MAC_EX_10G_RX_FIFO_OVFL);
    381	if (event & TGEC_IMASK_RX_ECC_ER)
    382		tgec->exception_cb(tgec->dev_id, FM_MAC_EX_10G_RX_ECC_ER);
    383	if (event & TGEC_IMASK_RX_JAB_FRM)
    384		tgec->exception_cb(tgec->dev_id, FM_MAC_EX_10G_RX_JAB_FRM);
    385	if (event & TGEC_IMASK_RX_OVRSZ_FRM)
    386		tgec->exception_cb(tgec->dev_id, FM_MAC_EX_10G_RX_OVRSZ_FRM);
    387	if (event & TGEC_IMASK_RX_RUNT_FRM)
    388		tgec->exception_cb(tgec->dev_id, FM_MAC_EX_10G_RX_RUNT_FRM);
    389	if (event & TGEC_IMASK_RX_FRAG_FRM)
    390		tgec->exception_cb(tgec->dev_id, FM_MAC_EX_10G_RX_FRAG_FRM);
    391	if (event & TGEC_IMASK_RX_LEN_ER)
    392		tgec->exception_cb(tgec->dev_id, FM_MAC_EX_10G_RX_LEN_ER);
    393	if (event & TGEC_IMASK_RX_CRC_ER)
    394		tgec->exception_cb(tgec->dev_id, FM_MAC_EX_10G_RX_CRC_ER);
    395	if (event & TGEC_IMASK_RX_ALIGN_ER)
    396		tgec->exception_cb(tgec->dev_id, FM_MAC_EX_10G_RX_ALIGN_ER);
    397}
    398
    399static void free_init_resources(struct fman_mac *tgec)
    400{
    401	fman_unregister_intr(tgec->fm, FMAN_MOD_MAC, tgec->mac_id,
    402			     FMAN_INTR_TYPE_ERR);
    403
    404	/* release the driver's group hash table */
    405	free_hash_table(tgec->multicast_addr_hash);
    406	tgec->multicast_addr_hash = NULL;
    407
    408	/* release the driver's individual hash table */
    409	free_hash_table(tgec->unicast_addr_hash);
    410	tgec->unicast_addr_hash = NULL;
    411}
    412
    413static bool is_init_done(struct tgec_cfg *cfg)
    414{
    415	/* Checks if tGEC driver parameters were initialized */
    416	if (!cfg)
    417		return true;
    418
    419	return false;
    420}
    421
    422int tgec_enable(struct fman_mac *tgec, enum comm_mode mode)
    423{
    424	struct tgec_regs __iomem *regs = tgec->regs;
    425	u32 tmp;
    426
    427	if (!is_init_done(tgec->cfg))
    428		return -EINVAL;
    429
    430	tmp = ioread32be(&regs->command_config);
    431	if (mode & COMM_MODE_RX)
    432		tmp |= CMD_CFG_RX_EN;
    433	if (mode & COMM_MODE_TX)
    434		tmp |= CMD_CFG_TX_EN;
    435	iowrite32be(tmp, &regs->command_config);
    436
    437	return 0;
    438}
    439
    440int tgec_disable(struct fman_mac *tgec, enum comm_mode mode)
    441{
    442	struct tgec_regs __iomem *regs = tgec->regs;
    443	u32 tmp;
    444
    445	if (!is_init_done(tgec->cfg))
    446		return -EINVAL;
    447
    448	tmp = ioread32be(&regs->command_config);
    449	if (mode & COMM_MODE_RX)
    450		tmp &= ~CMD_CFG_RX_EN;
    451	if (mode & COMM_MODE_TX)
    452		tmp &= ~CMD_CFG_TX_EN;
    453	iowrite32be(tmp, &regs->command_config);
    454
    455	return 0;
    456}
    457
    458int tgec_set_promiscuous(struct fman_mac *tgec, bool new_val)
    459{
    460	struct tgec_regs __iomem *regs = tgec->regs;
    461	u32 tmp;
    462
    463	if (!is_init_done(tgec->cfg))
    464		return -EINVAL;
    465
    466	tmp = ioread32be(&regs->command_config);
    467	if (new_val)
    468		tmp |= CMD_CFG_PROMIS_EN;
    469	else
    470		tmp &= ~CMD_CFG_PROMIS_EN;
    471	iowrite32be(tmp, &regs->command_config);
    472
    473	return 0;
    474}
    475
    476int tgec_cfg_max_frame_len(struct fman_mac *tgec, u16 new_val)
    477{
    478	if (is_init_done(tgec->cfg))
    479		return -EINVAL;
    480
    481	tgec->cfg->max_frame_length = new_val;
    482
    483	return 0;
    484}
    485
    486int tgec_set_tx_pause_frames(struct fman_mac *tgec, u8 __maybe_unused priority,
    487			     u16 pause_time, u16 __maybe_unused thresh_time)
    488{
    489	struct tgec_regs __iomem *regs = tgec->regs;
    490
    491	if (!is_init_done(tgec->cfg))
    492		return -EINVAL;
    493
    494	iowrite32be((u32)pause_time, &regs->pause_quant);
    495
    496	return 0;
    497}
    498
    499int tgec_accept_rx_pause_frames(struct fman_mac *tgec, bool en)
    500{
    501	struct tgec_regs __iomem *regs = tgec->regs;
    502	u32 tmp;
    503
    504	if (!is_init_done(tgec->cfg))
    505		return -EINVAL;
    506
    507	tmp = ioread32be(&regs->command_config);
    508	if (!en)
    509		tmp |= CMD_CFG_PAUSE_IGNORE;
    510	else
    511		tmp &= ~CMD_CFG_PAUSE_IGNORE;
    512	iowrite32be(tmp, &regs->command_config);
    513
    514	return 0;
    515}
    516
    517int tgec_modify_mac_address(struct fman_mac *tgec, const enet_addr_t *p_enet_addr)
    518{
    519	if (!is_init_done(tgec->cfg))
    520		return -EINVAL;
    521
    522	tgec->addr = ENET_ADDR_TO_UINT64(*p_enet_addr);
    523	set_mac_address(tgec->regs, (const u8 *)(*p_enet_addr));
    524
    525	return 0;
    526}
    527
    528int tgec_add_hash_mac_address(struct fman_mac *tgec, enet_addr_t *eth_addr)
    529{
    530	struct tgec_regs __iomem *regs = tgec->regs;
    531	struct eth_hash_entry *hash_entry;
    532	u32 crc = 0xFFFFFFFF, hash;
    533	u64 addr;
    534
    535	if (!is_init_done(tgec->cfg))
    536		return -EINVAL;
    537
    538	addr = ENET_ADDR_TO_UINT64(*eth_addr);
    539
    540	if (!(addr & GROUP_ADDRESS)) {
    541		/* Unicast addresses not supported in hash */
    542		pr_err("Unicast Address\n");
    543		return -EINVAL;
    544	}
    545	/* CRC calculation */
    546	crc = crc32_le(crc, (u8 *)eth_addr, ETH_ALEN);
    547	crc = bitrev32(crc);
    548	/* Take 9 MSB bits */
    549	hash = (crc >> TGEC_HASH_MCAST_SHIFT) & TGEC_HASH_ADR_MSK;
    550
    551	/* Create element to be added to the driver hash table */
    552	hash_entry = kmalloc(sizeof(*hash_entry), GFP_ATOMIC);
    553	if (!hash_entry)
    554		return -ENOMEM;
    555	hash_entry->addr = addr;
    556	INIT_LIST_HEAD(&hash_entry->node);
    557
    558	list_add_tail(&hash_entry->node,
    559		      &tgec->multicast_addr_hash->lsts[hash]);
    560	iowrite32be((hash | TGEC_HASH_MCAST_EN), &regs->hashtable_ctrl);
    561
    562	return 0;
    563}
    564
    565int tgec_set_allmulti(struct fman_mac *tgec, bool enable)
    566{
    567	u32 entry;
    568	struct tgec_regs __iomem *regs = tgec->regs;
    569
    570	if (!is_init_done(tgec->cfg))
    571		return -EINVAL;
    572
    573	if (enable) {
    574		for (entry = 0; entry < TGEC_HASH_TABLE_SIZE; entry++)
    575			iowrite32be(entry | TGEC_HASH_MCAST_EN,
    576				    &regs->hashtable_ctrl);
    577	} else {
    578		for (entry = 0; entry < TGEC_HASH_TABLE_SIZE; entry++)
    579			iowrite32be(entry & ~TGEC_HASH_MCAST_EN,
    580				    &regs->hashtable_ctrl);
    581	}
    582
    583	tgec->allmulti_enabled = enable;
    584
    585	return 0;
    586}
    587
    588int tgec_set_tstamp(struct fman_mac *tgec, bool enable)
    589{
    590	struct tgec_regs __iomem *regs = tgec->regs;
    591	u32 tmp;
    592
    593	if (!is_init_done(tgec->cfg))
    594		return -EINVAL;
    595
    596	tmp = ioread32be(&regs->command_config);
    597
    598	if (enable)
    599		tmp |= CMD_CFG_EN_TIMESTAMP;
    600	else
    601		tmp &= ~CMD_CFG_EN_TIMESTAMP;
    602
    603	iowrite32be(tmp, &regs->command_config);
    604
    605	return 0;
    606}
    607
    608int tgec_del_hash_mac_address(struct fman_mac *tgec, enet_addr_t *eth_addr)
    609{
    610	struct tgec_regs __iomem *regs = tgec->regs;
    611	struct eth_hash_entry *hash_entry = NULL;
    612	struct list_head *pos;
    613	u32 crc = 0xFFFFFFFF, hash;
    614	u64 addr;
    615
    616	if (!is_init_done(tgec->cfg))
    617		return -EINVAL;
    618
    619	addr = ((*(u64 *)eth_addr) >> 16);
    620
    621	/* CRC calculation */
    622	crc = crc32_le(crc, (u8 *)eth_addr, ETH_ALEN);
    623	crc = bitrev32(crc);
    624	/* Take 9 MSB bits */
    625	hash = (crc >> TGEC_HASH_MCAST_SHIFT) & TGEC_HASH_ADR_MSK;
    626
    627	list_for_each(pos, &tgec->multicast_addr_hash->lsts[hash]) {
    628		hash_entry = ETH_HASH_ENTRY_OBJ(pos);
    629		if (hash_entry && hash_entry->addr == addr) {
    630			list_del_init(&hash_entry->node);
    631			kfree(hash_entry);
    632			break;
    633		}
    634	}
    635
    636	if (!tgec->allmulti_enabled) {
    637		if (list_empty(&tgec->multicast_addr_hash->lsts[hash]))
    638			iowrite32be((hash & ~TGEC_HASH_MCAST_EN),
    639				    &regs->hashtable_ctrl);
    640	}
    641
    642	return 0;
    643}
    644
    645int tgec_get_version(struct fman_mac *tgec, u32 *mac_version)
    646{
    647	struct tgec_regs __iomem *regs = tgec->regs;
    648
    649	if (!is_init_done(tgec->cfg))
    650		return -EINVAL;
    651
    652	*mac_version = ioread32be(&regs->tgec_id);
    653
    654	return 0;
    655}
    656
    657int tgec_set_exception(struct fman_mac *tgec,
    658		       enum fman_mac_exceptions exception, bool enable)
    659{
    660	struct tgec_regs __iomem *regs = tgec->regs;
    661	u32 bit_mask = 0;
    662
    663	if (!is_init_done(tgec->cfg))
    664		return -EINVAL;
    665
    666	bit_mask = get_exception_flag(exception);
    667	if (bit_mask) {
    668		if (enable)
    669			tgec->exceptions |= bit_mask;
    670		else
    671			tgec->exceptions &= ~bit_mask;
    672	} else {
    673		pr_err("Undefined exception\n");
    674		return -EINVAL;
    675	}
    676	if (enable)
    677		iowrite32be(ioread32be(&regs->imask) | bit_mask, &regs->imask);
    678	else
    679		iowrite32be(ioread32be(&regs->imask) & ~bit_mask, &regs->imask);
    680
    681	return 0;
    682}
    683
    684int tgec_init(struct fman_mac *tgec)
    685{
    686	struct tgec_cfg *cfg;
    687	enet_addr_t eth_addr;
    688	int err;
    689
    690	if (is_init_done(tgec->cfg))
    691		return -EINVAL;
    692
    693	if (DEFAULT_RESET_ON_INIT &&
    694	    (fman_reset_mac(tgec->fm, tgec->mac_id) != 0)) {
    695		pr_err("Can't reset MAC!\n");
    696		return -EINVAL;
    697	}
    698
    699	err = check_init_parameters(tgec);
    700	if (err)
    701		return err;
    702
    703	cfg = tgec->cfg;
    704
    705	if (tgec->addr) {
    706		MAKE_ENET_ADDR_FROM_UINT64(tgec->addr, eth_addr);
    707		set_mac_address(tgec->regs, (const u8 *)eth_addr);
    708	}
    709
    710	/* interrupts */
    711	/* FM_10G_REM_N_LCL_FLT_EX_10GMAC_ERRATA_SW005 Errata workaround */
    712	if (tgec->fm_rev_info.major <= 2)
    713		tgec->exceptions &= ~(TGEC_IMASK_REM_FAULT |
    714				      TGEC_IMASK_LOC_FAULT);
    715
    716	err = init(tgec->regs, cfg, tgec->exceptions);
    717	if (err) {
    718		free_init_resources(tgec);
    719		pr_err("TGEC version doesn't support this i/f mode\n");
    720		return err;
    721	}
    722
    723	/* Max Frame Length */
    724	err = fman_set_mac_max_frame(tgec->fm, tgec->mac_id,
    725				     cfg->max_frame_length);
    726	if (err) {
    727		pr_err("Setting max frame length FAILED\n");
    728		free_init_resources(tgec);
    729		return -EINVAL;
    730	}
    731
    732	/* FM_TX_FIFO_CORRUPTION_ERRATA_10GMAC_A007 Errata workaround */
    733	if (tgec->fm_rev_info.major == 2) {
    734		struct tgec_regs __iomem *regs = tgec->regs;
    735		u32 tmp;
    736
    737		/* restore the default tx ipg Length */
    738		tmp = (ioread32be(&regs->tx_ipg_len) &
    739		       ~TGEC_TX_IPG_LENGTH_MASK) | 12;
    740
    741		iowrite32be(tmp, &regs->tx_ipg_len);
    742	}
    743
    744	tgec->multicast_addr_hash = alloc_hash_table(TGEC_HASH_TABLE_SIZE);
    745	if (!tgec->multicast_addr_hash) {
    746		free_init_resources(tgec);
    747		pr_err("allocation hash table is FAILED\n");
    748		return -ENOMEM;
    749	}
    750
    751	tgec->unicast_addr_hash = alloc_hash_table(TGEC_HASH_TABLE_SIZE);
    752	if (!tgec->unicast_addr_hash) {
    753		free_init_resources(tgec);
    754		pr_err("allocation hash table is FAILED\n");
    755		return -ENOMEM;
    756	}
    757
    758	fman_register_intr(tgec->fm, FMAN_MOD_MAC, tgec->mac_id,
    759			   FMAN_INTR_TYPE_ERR, tgec_err_exception, tgec);
    760
    761	kfree(cfg);
    762	tgec->cfg = NULL;
    763
    764	return 0;
    765}
    766
    767int tgec_free(struct fman_mac *tgec)
    768{
    769	free_init_resources(tgec);
    770
    771	kfree(tgec->cfg);
    772	kfree(tgec);
    773
    774	return 0;
    775}
    776
    777struct fman_mac *tgec_config(struct fman_mac_params *params)
    778{
    779	struct fman_mac *tgec;
    780	struct tgec_cfg *cfg;
    781	void __iomem *base_addr;
    782
    783	base_addr = params->base_addr;
    784	/* allocate memory for the UCC GETH data structure. */
    785	tgec = kzalloc(sizeof(*tgec), GFP_KERNEL);
    786	if (!tgec)
    787		return NULL;
    788
    789	/* allocate memory for the 10G MAC driver parameters data structure. */
    790	cfg = kzalloc(sizeof(*cfg), GFP_KERNEL);
    791	if (!cfg) {
    792		tgec_free(tgec);
    793		return NULL;
    794	}
    795
    796	/* Plant parameter structure pointer */
    797	tgec->cfg = cfg;
    798
    799	set_dflts(cfg);
    800
    801	tgec->regs = base_addr;
    802	tgec->addr = ENET_ADDR_TO_UINT64(params->addr);
    803	tgec->max_speed = params->max_speed;
    804	tgec->mac_id = params->mac_id;
    805	tgec->exceptions = (TGEC_IMASK_MDIO_SCAN_EVENT	|
    806			    TGEC_IMASK_REM_FAULT	|
    807			    TGEC_IMASK_LOC_FAULT	|
    808			    TGEC_IMASK_TX_ECC_ER	|
    809			    TGEC_IMASK_TX_FIFO_UNFL	|
    810			    TGEC_IMASK_TX_FIFO_OVFL	|
    811			    TGEC_IMASK_TX_ER		|
    812			    TGEC_IMASK_RX_FIFO_OVFL	|
    813			    TGEC_IMASK_RX_ECC_ER	|
    814			    TGEC_IMASK_RX_JAB_FRM	|
    815			    TGEC_IMASK_RX_OVRSZ_FRM	|
    816			    TGEC_IMASK_RX_RUNT_FRM	|
    817			    TGEC_IMASK_RX_FRAG_FRM	|
    818			    TGEC_IMASK_RX_CRC_ER	|
    819			    TGEC_IMASK_RX_ALIGN_ER);
    820	tgec->exception_cb = params->exception_cb;
    821	tgec->event_cb = params->event_cb;
    822	tgec->dev_id = params->dev_id;
    823	tgec->fm = params->fm;
    824
    825	/* Save FMan revision */
    826	fman_get_revision(tgec->fm, &tgec->fm_rev_info);
    827
    828	return tgec;
    829}