/*
 * Copyright (c) 2013 Qualcomm Atheros, Inc.
 *
 * See file CREDITS for list of people who contributed to this
 * project.
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License as
 * published by the Free Software Foundation; either version 2 of
 * the License, or (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 * MA 02111-1307 USA
 */

#include <config.h>
#include <common.h>
#include <malloc.h>
#include <net.h>
#include <command.h>
#include <asm/io.h>
#include <asm/addrspace.h>
#include <asm/types.h>

#ifdef CONFIG_ATH_NAND_BR
#include <nand.h>
#endif

#include <atheros.h>
#include "qca-eth-955x.h"
#include "qca-eth-955x_phy.h"
#define SGMII_LINK_WAR_MAX_TRY 10

#if (CONFIG_COMMANDS & CFG_CMD_MII)
#include <miiphy.h>
#endif
#define ath_gmac_unit2mac(_unit)     ath_gmac_macs[(_unit)]
#define ath_gmac_name2mac(name)	   is_drqfn() ? ath_gmac_unit2mac(1):strcmp(name,"eth0") ? ath_gmac_unit2mac(1) : ath_gmac_unit2mac(0)

int ath_gmac_miiphy_read(char *devname, uint32_t phaddr, uint8_t reg, uint16_t *data);
int ath_gmac_miiphy_write(char *devname, uint32_t phaddr, uint8_t reg, uint16_t data);
extern void ath_sys_frequency(uint32_t *, uint32_t *, uint32_t *);

#ifndef CFG_ATH_GMAC_NMACS
#define CFG_ATH_GMAC_NMACS	1
#endif /* CFG_ATH_GMAC_NMACS */

ath_gmac_mac_t *ath_gmac_macs[CFG_ATH_GMAC_NMACS];


#ifdef CONFIG_VIR_PHY
extern int athr_vir_phy_setup(int unit);
extern int athr_vir_phy_is_up(int unit);
extern int athr_vir_phy_is_fdx(int unit);
extern int athr_vir_phy_speed(int unit);
extern void athr_vir_reg_init(void);
#endif

#ifdef  CONFIG_ATHRS17_PHY
extern void athrs17_reg_init(void);
extern void athrs17_reg_init_wan(void);
#endif


#ifdef CONFIG_ATHR_8033_PHY
extern int athrs_ar8033_reg_init(void *arg);
extern int athrs_ar8033_phy_setup(void  *arg);
extern int athrs_ar8033_phy_is_fdx(int ethUnit);
extern int athrs_ar8033_phy_is_link_alive(int phyUnit);
extern int athrs_ar8033_phy_is_up(int ethUnit);
extern int athrs_ar8033_phy_speed(int ethUnit,int phyUnit);
#endif

#ifdef CONFIG_ATH_NAND_BR

#define ATH_ETH_MAC_READ_SIZE 4096
extern unsigned long long
ath_nand_get_cal_offset(const char *ba);
#endif

static int
ath_gmac_send(struct eth_device *dev, volatile void *packet, int length)
{
	int i;

	ath_gmac_mac_t *mac = (ath_gmac_mac_t *)dev->priv;

	ath_gmac_desc_t *f = mac->fifo_tx[mac->next_tx];

	f->pkt_size = length;
	f->res1 = 0;
	f->pkt_start_addr = virt_to_phys(packet);

	ath_gmac_tx_give_to_dma(f);
	flush_cache((u32) packet, length);
	ath_gmac_reg_wr(mac, ATH_DMA_TX_DESC, virt_to_phys(f));
	ath_gmac_reg_wr(mac, ATH_DMA_TX_CTRL, ATH_TXE);

	for (i = 0; i < MAX_WAIT; i++) {
		udelay(10);
		if (!ath_gmac_tx_owned_by_dma(f))
			break;
	}
	if (i == MAX_WAIT)
		printf("Tx Timed out\n");

	f->pkt_start_addr = 0;
	f->pkt_size = 0;

	if (++mac->next_tx >= NO_OF_TX_FIFOS)
		mac->next_tx = 0;

	return (0);
}

static int ath_gmac_recv(struct eth_device *dev)
{
	int length;
	ath_gmac_desc_t *f;
	ath_gmac_mac_t *mac;
    	volatile int dmaed_pkt=0;
	int count = 0;

	mac = (ath_gmac_mac_t *)dev->priv;

	for (;;) {
	     f = mac->fifo_rx[mac->next_rx];
        if (ath_gmac_rx_owned_by_dma(f)) { 
	 /* check if the current Descriptor is_empty is 1,But the DMAed count is not-zero 
	    then move to desciprot where the packet is available */ 
	   dmaed_pkt = (ath_gmac_reg_rd(mac, 0x194) >> 16);
            if (!dmaed_pkt) {
	        break ;
              } else {  
                if (f->is_empty == 1) {
                    while ( count < NO_OF_RX_FIFOS ) {
                        if (++mac->next_rx >= NO_OF_RX_FIFOS) {
                            mac->next_rx = 0;
                        }
                        f = mac->fifo_rx[mac->next_rx];
                        /*
                         * Break on valid data in the desc by checking
                         *  empty bit.
                         */
                        if (!f->is_empty){
                            count = 0;
                            break;
                        }
                        count++;
                    }
               }
            } 
	} 
 
		length = f->pkt_size;

		NetReceive(NetRxPackets[mac->next_rx] , length - 4);
		flush_cache((u32) NetRxPackets[mac->next_rx] , PKTSIZE_ALIGN);

		ath_gmac_reg_wr(mac,0x194,1);
		ath_gmac_rx_give_to_dma(f);

		if (++mac->next_rx >= NO_OF_RX_FIFOS)
			mac->next_rx = 0;
	}

	if (!(ath_gmac_reg_rd(mac, ATH_DMA_RX_CTRL))) {
		ath_gmac_reg_wr(mac, ATH_DMA_RX_DESC, virt_to_phys(f));
		ath_gmac_reg_wr(mac, ATH_DMA_RX_CTRL, 1);
	}

	return (0);
}

void ath_gmac_mii_setup(ath_gmac_mac_t *mac)
{
	u32 mgmt_cfg_val;

	ath_reg_wr(SWITCH_CLOCK_SPARE_ADDRESS, 0x520);

	if ((is_s17()  && mac->mac_unit == 0) || is_drqfn()) {
		printf("Scorpion  ----> S17 PHY *\n");
		mgmt_cfg_val = 7;
#ifndef ATH_RGMII_CAL
		ath_reg_wr(ATH_ETH_CFG, ETH_CFG_ETH_RXDV_DELAY_SET(3) |
					ETH_CFG_ETH_RXD_DELAY_SET(3)|
					ETH_CFG_RGMII_GE0_SET(1));

		ath_reg_wr(ETH_XMII_ADDRESS, ETH_XMII_TX_INVERT_SET(1) |
                			     ETH_XMII_RX_DELAY_SET(2)  |
                			     ETH_XMII_TX_DELAY_SET(1)  |
					     ETH_XMII_GIGE_SET(1));
#else
        rgmii_cal_alg()
#endif
		udelay(1000);
		ath_gmac_reg_wr(mac, ATH_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
		ath_gmac_reg_wr(mac, ATH_MAC_MII_MGMT_CFG, mgmt_cfg_val);
		return;
	}

	if (is_ar8033 () && mac->mac_unit == 1) {
        	printf("Scorpion ---->8033 PHY*\n");

		mgmt_cfg_val = 7;
		ath_gmac_reg_wr(mac, ATH_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
		ath_gmac_reg_wr(mac, ATH_MAC_MII_MGMT_CFG, mgmt_cfg_val);
		return;


        }
        if (is_vir_phy()) {
        	printf("Scorpion ---->VIR PHY*\n");
		
		ath_reg_wr(ATH_ETH_CFG, ETH_CFG_ETH_RXDV_DELAY_SET(3) |
					ETH_CFG_ETH_RXD_DELAY_SET(3)|
					ETH_CFG_RGMII_GE0_SET(1));
		ath_reg_wr(ETH_XMII_ADDRESS, ETH_XMII_TX_INVERT_SET(1) |
                			     ETH_XMII_RX_DELAY_SET(2)  |
                			     ETH_XMII_TX_DELAY_SET(1)  |
					     ETH_XMII_GIGE_SET(1));
		udelay(1000);
		ath_gmac_reg_wr(mac, ATH_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
		ath_gmac_reg_wr(mac, ATH_MAC_MII_MGMT_CFG, mgmt_cfg_val);
		
                return;
	}



}

void
athrs_sgmii_res_cal(void)
{
	unsigned int read_data, read_data_otp, otp_value, otp_per_val, rbias_per;
	unsigned int read_data_spi;
	unsigned int *address_spi = (unsigned int *)0xbffffffc;
	unsigned int rbias_pos_or_neg, res_cal_val;
	unsigned int sgmii_pos, sgmii_res_cal_value;
	unsigned int reversed_sgmii_value, use_value;

	ath_reg_wr(OTP_INTF2_ADDRESS, 0x7d);
	ath_reg_wr(OTP_LDO_CONTROL_ADDRESS, 0x0);

	while (ath_reg_rd(OTP_LDO_STATUS_ADDRESS) & OTP_LDO_STATUS_POWER_ON_MASK);

	read_data = ath_reg_rd(OTP_MEM_0_ADDRESS + 4);

	while (!(ath_reg_rd(OTP_STATUS0_ADDRESS) & OTP_STATUS0_EFUSE_READ_DATA_VALID_MASK));

	read_data_otp = ath_reg_rd(OTP_STATUS1_ADDRESS);

	if (read_data_otp & 0x1fff) {
		read_data = read_data_otp;
	} else {
		read_data_spi = *(address_spi);
		if ((read_data_spi & 0xffff0000) == 0x5ca10000) {
			read_data = read_data_spi;
		} else {
			read_data = read_data_otp;
		}
	}

	if (read_data & 0x00001000) {
		otp_value = (read_data & 0xfc0) >> 6;
	} else {
		otp_value = read_data & 0x3f;
	}

	if (otp_value > 31) {
		otp_per_val = 63 - otp_value;
		rbias_pos_or_neg = 1;
	} else {
		otp_per_val = otp_value;
		rbias_pos_or_neg = 0;
	}

	rbias_per = otp_per_val * 15;

	if (rbias_pos_or_neg == 1) {
		res_cal_val = (rbias_per + 34) / 21;
		sgmii_pos = 1;
	} else {
		if (rbias_per > 34) {
			res_cal_val = (rbias_per - 34) / 21;
			sgmii_pos = 0;
		} else {
			res_cal_val = (34 - rbias_per) / 21;
			sgmii_pos = 1;
		}
	}

	if (sgmii_pos == 1) {
		sgmii_res_cal_value = 8 + res_cal_val;
	} else {
		sgmii_res_cal_value = 8 - res_cal_val;
	}

	reversed_sgmii_value = 0;
	use_value = 0x8;
	reversed_sgmii_value = reversed_sgmii_value | ((sgmii_res_cal_value & use_value) >> 3);
	use_value = 0x4;
	reversed_sgmii_value = reversed_sgmii_value | ((sgmii_res_cal_value & use_value) >> 1);
	use_value = 0x2;
	reversed_sgmii_value = reversed_sgmii_value | ((sgmii_res_cal_value & use_value) << 1);
	use_value = 0x1;
	reversed_sgmii_value = reversed_sgmii_value | ((sgmii_res_cal_value & use_value) << 3);

	reversed_sgmii_value &= 0xf;

	printf("%s: cal value = 0x%x\n", __func__, reversed_sgmii_value);

	// To Check the locking of the SGMII PLL

	read_data = (ath_reg_rd(SGMII_SERDES_ADDRESS) &
				~SGMII_SERDES_RES_CALIBRATION_MASK) |
			SGMII_SERDES_RES_CALIBRATION_SET(reversed_sgmii_value);

	ath_reg_wr(SGMII_SERDES_ADDRESS, read_data);


	ath_reg_wr(ETH_SGMII_SERDES_ADDRESS,
			ETH_SGMII_SERDES_EN_LOCK_DETECT_MASK |
			ETH_SGMII_SERDES_PLL_REFCLK_SEL_MASK |
			ETH_SGMII_SERDES_EN_PLL_MASK);

	ath_reg_rmw_set(SGMII_SERDES_ADDRESS,
			SGMII_SERDES_CDR_BW_SET(3) |
			SGMII_SERDES_TX_DR_CTRL_SET(1) |
			SGMII_SERDES_PLL_BW_SET(1) |
			SGMII_SERDES_EN_SIGNAL_DETECT_SET(1) |
			SGMII_SERDES_FIBER_SDO_SET(1) |
			SGMII_SERDES_VCO_REG_SET(3));

	ath_reg_rmw_clear(RST_RESET_ADDRESS, RST_RESET_ETH_SGMII_ARESET_MASK);
	udelay(25);
	ath_reg_rmw_clear(RST_RESET_ADDRESS, RST_RESET_ETH_SGMII_RESET_MASK);

	while (!(ath_reg_rd(SGMII_SERDES_ADDRESS) & SGMII_SERDES_LOCK_DETECT_STATUS_MASK));
}


static void athr_gmac_sgmii_setup()
{
	int status = 0, count = 0;

#ifdef ATH_SGMII_FORCED_MODE
        ath_reg_wr(MR_AN_CONTROL_ADDRESS, MR_AN_CONTROL_SPEED_SEL1_SET(1) |
                                           MR_AN_CONTROL_PHY_RESET_SET(1)  |
                                           MR_AN_CONTROL_DUPLEX_MODE_SET(1));
        udelay(10);

        ath_reg_wr(SGMII_CONFIG_ADDRESS, SGMII_CONFIG_MODE_CTRL_SET(2)   |
                                          SGMII_CONFIG_FORCE_SPEED_SET(1) |
                                          SGMII_CONFIG_SPEED_SET(2));

        printf ("SGMII in forced mode\n");
#else

	ath_reg_wr(SGMII_CONFIG_ADDRESS, SGMII_CONFIG_MODE_CTRL_SET(2));

	ath_reg_wr(MR_AN_CONTROL_ADDRESS, MR_AN_CONTROL_AN_ENABLE_SET(1)
                                      |MR_AN_CONTROL_PHY_RESET_SET(1));

	ath_reg_wr(MR_AN_CONTROL_ADDRESS, MR_AN_CONTROL_AN_ENABLE_SET(1));
#endif
/*
 * SGMII reset sequence suggested by systems team.
 */

	ath_reg_wr(SGMII_RESET_ADDRESS, SGMII_RESET_RX_CLK_N_RESET);

	ath_reg_wr(SGMII_RESET_ADDRESS, SGMII_RESET_HW_RX_125M_N_SET(1));

	ath_reg_wr(SGMII_RESET_ADDRESS, SGMII_RESET_HW_RX_125M_N_SET(1)
                                    |SGMII_RESET_RX_125M_N_SET(1));

	ath_reg_wr(SGMII_RESET_ADDRESS, SGMII_RESET_HW_RX_125M_N_SET(1)
                                    |SGMII_RESET_TX_125M_N_SET(1)
                                    |SGMII_RESET_RX_125M_N_SET(1));

	ath_reg_wr(SGMII_RESET_ADDRESS, SGMII_RESET_HW_RX_125M_N_SET(1)
                                    |SGMII_RESET_TX_125M_N_SET(1)
                                    |SGMII_RESET_RX_125M_N_SET(1)
                                    |SGMII_RESET_RX_CLK_N_SET(1));

	ath_reg_wr(SGMII_RESET_ADDRESS, SGMII_RESET_HW_RX_125M_N_SET(1)
                                    |SGMII_RESET_TX_125M_N_SET(1)
                                    |SGMII_RESET_RX_125M_N_SET(1)
                                    |SGMII_RESET_RX_CLK_N_SET(1)
                                    |SGMII_RESET_TX_CLK_N_SET(1));

        ath_reg_rmw_clear(MR_AN_CONTROL_ADDRESS, MR_AN_CONTROL_PHY_RESET_SET(1));
	/*
	 * WAR::Across resets SGMII link status goes to weird
	 * state.
	 * if 0xb8070058 (SGMII_DEBUG register) reads other then 0x1f or 0x10
	 * for sure we are in bad  state.
	 * Issue a PHY reset in MR_AN_CONTROL_ADDRESS to keep going.
	 */
	status = (ath_reg_rd(SGMII_DEBUG_ADDRESS) & 0xff);
	while (!(status == 0xf || status == 0x10)) {

		ath_reg_rmw_set(MR_AN_CONTROL_ADDRESS, MR_AN_CONTROL_PHY_RESET_SET(1));
		udelay(100);
		ath_reg_rmw_clear(MR_AN_CONTROL_ADDRESS, MR_AN_CONTROL_PHY_RESET_SET(1));
		if (count++ == SGMII_LINK_WAR_MAX_TRY) {
			printf ("Max resets limit reached exiting...\n");
			break;
	    	}
		status = (ath_reg_rd(SGMII_DEBUG_ADDRESS) & 0xff);
	}

	printf("%s SGMII done\n",__func__);

}

static void ath_gmac_hw_start(ath_gmac_mac_t *mac)
{


#ifndef ATH_RGMII_CAL /* Moved after mii_setup since these registers are touched in RGMII cal code */
	if(mac->mac_unit)
	{
		ath_gmac_reg_rmw_set(mac, ATH_MAC_CFG2, (ATH_MAC_CFG2_PAD_CRC_EN |
					ATH_MAC_CFG2_LEN_CHECK | ATH_MAC_CFG2_IF_1000));
	} else {


		ath_gmac_reg_rmw_set(mac, ATH_MAC_CFG2, (ATH_MAC_CFG2_PAD_CRC_EN |
					ATH_MAC_CFG2_LEN_CHECK | ATH_MAC_CFG2_IF_10_100));
	}
	ath_gmac_reg_wr(mac, ATH_MAC_FIFO_CFG_0, 0x1f00);
#endif


#ifdef ATH_RGMII_CAL
	if(mac->mac_unit)
	{
		ath_gmac_reg_rmw_set(mac, ATH_MAC_CFG2, (ATH_MAC_CFG2_PAD_CRC_EN |
					ATH_MAC_CFG2_LEN_CHECK | ATH_MAC_CFG2_IF_1000));
	} else {


		ath_gmac_reg_rmw_set(mac, ATH_MAC_CFG2, (ATH_MAC_CFG2_PAD_CRC_EN |
					ATH_MAC_CFG2_LEN_CHECK | ATH_MAC_CFG2_IF_10_100));
	}
	ath_gmac_reg_wr(mac, ATH_MAC_FIFO_CFG_0, 0x1f00);
#endif

	ath_gmac_reg_wr(mac, ATH_MAC_FIFO_CFG_1, 0x10ffff);
	ath_gmac_reg_wr(mac, ATH_MAC_FIFO_CFG_2, 0xAAA0555);

	ath_gmac_reg_rmw_set(mac, ATH_MAC_FIFO_CFG_4, 0x3ffff);
	/*
	 * Setting Drop CRC Errors, Pause Frames,Length Error frames
	 * and Multi/Broad cast frames.
	 */

	ath_gmac_reg_wr(mac, ATH_MAC_FIFO_CFG_5, 0x7eccf);

	ath_gmac_reg_wr(mac, ATH_MAC_FIFO_CFG_3, 0x1f00140);

	printf(": cfg1 %#x cfg2 %#x\n", ath_gmac_reg_rd(mac, ATH_MAC_CFG1),
			ath_gmac_reg_rd(mac, ATH_MAC_CFG2));


}

static int ath_gmac_check_link(ath_gmac_mac_t *mac)
{
	int link, duplex, speed;

	ath_gmac_phy_link(mac->mac_unit, &link);
	ath_gmac_phy_duplex(mac->mac_unit, &duplex);
	ath_gmac_phy_speed(mac->mac_unit, &speed);

	mac->link = link;

	if(!mac->link) {
		printf("%s link down\n",mac->dev->name);
		return 0;
	}

	switch (speed)
	{
		case _1000BASET:
			ath_gmac_set_mac_if(mac, 1);
			ath_gmac_reg_rmw_set(mac, ATH_MAC_FIFO_CFG_5, (1 << 19));

			if (is_ar8033() && mac->mac_unit == 1) {
				ath_reg_wr(ETH_SGMII_ADDRESS, ETH_SGMII_GIGE_SET(1) |
                                           ETH_SGMII_CLK_SEL_SET(1));
			}
	
			break;

		case _100BASET:
			ath_gmac_set_mac_if(mac, 0);
			ath_gmac_set_mac_speed(mac, 1);
			ath_gmac_reg_rmw_clear(mac, ATH_MAC_FIFO_CFG_5, (1 << 19));

                        if (is_ar8033() && mac->mac_unit == 1) {
                        	ath_reg_wr(ETH_SGMII_ADDRESS, ETH_SGMII_PHASE0_COUNT_SET(1) |
                                           ETH_SGMII_PHASE1_COUNT_SET(1));
			}

			break;

		case _10BASET:
			ath_gmac_set_mac_if(mac, 0);
			ath_gmac_set_mac_speed(mac, 0);
			ath_gmac_reg_rmw_clear(mac, ATH_MAC_FIFO_CFG_5, (1 << 19));

			if (is_ar8033() && mac->mac_unit == 1) {
				ath_reg_wr(ETH_SGMII_ADDRESS, ETH_SGMII_PHASE0_COUNT_SET(19) |
                                           ETH_SGMII_PHASE1_COUNT_SET(19));
			}

			break;

		default:
			printf("Invalid speed detected\n");
			return 0;
	}

	if (mac->link && (duplex == mac->duplex) && (speed == mac->speed))
		return 1;

	mac->duplex = duplex;
	mac->speed = speed;

	printf("dup %d speed %d\n", duplex, speed);

	ath_gmac_set_mac_duplex(mac,duplex);

	return 1;
}

/*
 * For every command we re-setup the ring and start with clean h/w rx state
 */
static int ath_gmac_clean_rx(struct eth_device *dev, bd_t * bd)
{

	int i;
	ath_gmac_desc_t *fr;
	ath_gmac_mac_t *mac = (ath_gmac_mac_t*)dev->priv;

	if (!ath_gmac_check_link(mac))
		return 0;

	mac->next_rx = 0;

        ath_gmac_reg_wr(mac, ATH_MAC_FIFO_CFG_0, 0x1f00); 
        ath_gmac_reg_wr(mac, ATH_MAC_CFG1, (ATH_MAC_CFG1_RX_EN | ATH_MAC_CFG1_TX_EN));

	for (i = 0; i < NO_OF_RX_FIFOS; i++) {
		fr = mac->fifo_rx[i];
		fr->pkt_start_addr = virt_to_phys(NetRxPackets[i]);
		flush_cache((u32) NetRxPackets[i], PKTSIZE_ALIGN);
		ath_gmac_rx_give_to_dma(fr);
	}

	ath_gmac_reg_wr(mac, ATH_DMA_RX_DESC, virt_to_phys(mac->fifo_rx[0]));
	ath_gmac_reg_wr(mac, ATH_DMA_RX_CTRL, ATH_RXE);	/* rx start */
	udelay(1000 * 1000);


	return 1;

}

static int ath_gmac_alloc_fifo(int ndesc, ath_gmac_desc_t ** fifo)
{
	int i;
	u32 size;
	uchar *p = NULL;

	size = sizeof(ath_gmac_desc_t) * ndesc;
	size += CFG_CACHELINE_SIZE - 1;

	if ((p = malloc(size)) == NULL) {
		printf("Cant allocate fifos\n");
		return -1;
	}

	p = (uchar *) (((u32) p + CFG_CACHELINE_SIZE - 1) &
			~(CFG_CACHELINE_SIZE - 1));
	p = UNCACHED_SDRAM(p);

	for (i = 0; i < ndesc; i++)
		fifo[i] = (ath_gmac_desc_t *) p + i;

	return 0;
}

static int ath_gmac_setup_fifos(ath_gmac_mac_t *mac)
{
	int i;

	if (ath_gmac_alloc_fifo(NO_OF_TX_FIFOS, mac->fifo_tx))
		return 1;

	for (i = 0; i < NO_OF_TX_FIFOS; i++) {
		mac->fifo_tx[i]->next_desc = (i == NO_OF_TX_FIFOS - 1) ?
			virt_to_phys(mac->fifo_tx[0]) : virt_to_phys(mac->fifo_tx[i + 1]);
		ath_gmac_tx_own(mac->fifo_tx[i]);
	}

	if (ath_gmac_alloc_fifo(NO_OF_RX_FIFOS, mac->fifo_rx))
		return 1;

	for (i = 0; i < NO_OF_RX_FIFOS; i++) {
		mac->fifo_rx[i]->next_desc = (i == NO_OF_RX_FIFOS - 1) ?
			virt_to_phys(mac->fifo_rx[0]) : virt_to_phys(mac->fifo_rx[i + 1]);
	}

	return (1);
}

static void ath_gmac_halt(struct eth_device *dev)
{
	ath_gmac_mac_t *mac = (ath_gmac_mac_t *)dev->priv;
        ath_gmac_reg_rmw_clear(mac, ATH_MAC_CFG1,(ATH_MAC_CFG1_RX_EN | ATH_MAC_CFG1_TX_EN));
        ath_gmac_reg_wr(mac,ATH_MAC_FIFO_CFG_0,0x1f1f);
	ath_gmac_reg_wr(mac,ATH_DMA_RX_CTRL, 0);
	while (ath_gmac_reg_rd(mac, ATH_DMA_RX_CTRL));
}

#ifdef CONFIG_ATH_NAND_BR

unsigned char *
ath_eth_mac_addr(unsigned char *sectorBuff)
{
	ulong   off, size;
	nand_info_t *nand;
	unsigned char ret;

	/*
	 * caldata partition is of 128k
	 */
	nand = &nand_info[nand_curr_device];
	size = ATH_ETH_MAC_READ_SIZE; /* To read 4k setting size as 4k */

	/*
	 * Get the Offset of Caldata partition
	 */
	off = ath_nand_get_cal_offset(getenv("bootargs"));
	if(off == ATH_CAL_OFF_INVAL) {
		printf("Invalid CAL offset \n");
		return NULL;
	}
	/*
	 * Get the values from flash, and program into the MAC address
	 * registers
	 */
	ret = nand_read(nand, (loff_t)off, &size, (u_char *)sectorBuff);
	printf(" %d bytes %s: %s\n", size,
			"read", ret ? "ERROR" : "OK");
	if(ret != 0 ) {
		return NULL;
	}

	return sectorBuff;
}

#else  /* CONFIG_ATH_NAND_BR */

unsigned char *
ath_gmac_mac_addr_loc(void)
{
	extern flash_info_t flash_info[];

#ifdef BOARDCAL
	/*
	 ** BOARDCAL environmental variable has the address of the cal sector
	 */

	return ((unsigned char *)BOARDCAL);

#else
	/* MAC address is store in the 2nd 4k of last sector */
	return ((unsigned char *)
			(KSEG1ADDR(ATH_SPI_BASE) + (4 * 1024) +
			 flash_info[0].size - (64 * 1024) /* sector_size */ ));
#endif
}

#endif  /* CONFIG_ATH_NAND_BR */

static void ath_gmac_get_ethaddr(struct eth_device *dev)
{
	unsigned char *eeprom;
	unsigned char *mac = dev->enetaddr;
#ifndef CONFIG_ATH_EMULATION

#ifdef CONFIG_ATH_NAND_BR
	unsigned char sectorBuff[ATH_ETH_MAC_READ_SIZE];

	eeprom = ath_eth_mac_addr(sectorBuff);
	if(eeprom == NULL) {
		/* mac address will be set to default mac address */
		mac[0] = 0xff;
	}
	else {
#else  /* CONFIG_ATH_NAND_BR */
		eeprom = ath_gmac_mac_addr_loc();
#endif  /* CONFIG_ATH_NAND_BR */

		if (strcmp(dev->name, "eth0") == 0) {
			memcpy(mac, eeprom, 6);
		} else if (strcmp(dev->name, "eth1") == 0) {
			eeprom += 6;
			memcpy(mac, eeprom, 6);
		} else {
			printf("%s: unknown ethernet device %s\n", __func__, dev->name);
			return;
		}
#ifdef CONFIG_ATH_NAND_BR
	}
#endif  /* CONFIG_ATH_NAND_BR */
	/* Use fixed address if the above address is invalid */
	if (mac[0] != 0x00 || (mac[0] == 0xff && mac[5] == 0xff))
#else
	if (1)
#endif
	{
			mac[0] = 0x00;
			mac[1] = 0x03;
			mac[2] = 0x7f;
			mac[3] = 0x09;
			mac[4] = 0x0b;
			mac[5] = 0xad;
			printf("No valid address in Flash. Using fixed address\n");
		} else {
			printf("Fetching MAC Address from 0x%p\n", __func__, eeprom);
		}
}

void
athr_mgmt_init(void)
{

#ifdef CONFIG_MGMT_INIT
	uint32_t rddata;

	rddata = ath_reg_rd(GPIO_IN_ENABLE3_ADDRESS)&
		~GPIO_IN_ENABLE3_MII_GE1_MDI_MASK;
	rddata |= GPIO_IN_ENABLE3_MII_GE1_MDI_SET(19);
	ath_reg_wr(GPIO_IN_ENABLE3_ADDRESS, rddata);

	ath_reg_rmw_clear(GPIO_OE_ADDRESS, (1 << 19));

	ath_reg_rmw_clear(GPIO_OE_ADDRESS, (1 << 17));


	rddata = ath_reg_rd(GPIO_OUT_FUNCTION4_ADDRESS) &
		~ (GPIO_OUT_FUNCTION4_ENABLE_GPIO_19_MASK |
		GPIO_OUT_FUNCTION4_ENABLE_GPIO_17_MASK);

	rddata |= GPIO_OUT_FUNCTION4_ENABLE_GPIO_19_SET(0x20) |
	GPIO_OUT_FUNCTION4_ENABLE_GPIO_17_SET(0x21);

	ath_reg_wr(GPIO_OUT_FUNCTION4_ADDRESS, rddata);
#endif
	printf ("%s ::done\n",__func__);
}


int ath_gmac_enet_initialize(bd_t * bis)
{
	struct eth_device *dev[CFG_ATH_GMAC_NMACS];
	u32 mask, mac_h, mac_l;
	int i;

	printf("%s...\n", __func__);

	athrs_sgmii_res_cal();

	for (i = 0;i < CFG_ATH_GMAC_NMACS;i++) {

		if ((dev[i] = (struct eth_device *) malloc(sizeof (struct eth_device))) == NULL) {
			puts("malloc failed\n");
			return 0;
		}

		if ((ath_gmac_macs[i] = (ath_gmac_mac_t *) malloc(sizeof (ath_gmac_mac_t))) == NULL) {
			puts("malloc failed\n");
			return 0;
		}

		memset(ath_gmac_macs[i], 0, sizeof(ath_gmac_macs[i]));
		memset(dev[i], 0, sizeof(dev[i]));

		sprintf(dev[i]->name, "eth%d", i);
		ath_gmac_get_ethaddr(dev[i]);

		ath_gmac_macs[i]->mac_unit = i;
		ath_gmac_macs[i]->mac_base = i ? ATH_GE1_BASE : ATH_GE0_BASE ;
		ath_gmac_macs[i]->dev = dev[i];

		dev[i]->iobase = 0;
		dev[i]->init = ath_gmac_clean_rx;
		dev[i]->halt = ath_gmac_halt;
		dev[i]->send = ath_gmac_send;
		dev[i]->recv = ath_gmac_recv;
		dev[i]->priv = (void *)ath_gmac_macs[i];
	}

#if !defined(CONFIG_ATH_NAND_BR)
	ath_reg_rmw_set(RST_RESET_ADDRESS,  RST_RESET_ETH_SGMII_ARESET_SET(1));
	udelay(1000 * 100);
	ath_reg_rmw_clear(RST_RESET_ADDRESS, RST_RESET_ETH_SGMII_ARESET_SET(1));
	udelay(100);
#endif
	ath_reg_rmw_set(RST_RESET_ADDRESS, RST_RESET_ETH_SGMII_RESET_SET(1) | RST_RESET_EXTERNAL_RESET_SET(1));
	udelay(1000 * 100);
	ath_reg_rmw_clear(RST_RESET_ADDRESS, RST_RESET_ETH_SGMII_RESET_SET(1) | RST_RESET_EXTERNAL_RESET_SET(1));
	udelay(1000 * 100);

	for (i = 0;i < CFG_ATH_GMAC_NMACS;i++) {

		ath_gmac_reg_rmw_set(ath_gmac_macs[i], ATH_MAC_CFG1, ATH_MAC_CFG1_SOFT_RST
				| ATH_MAC_CFG1_RX_RST | ATH_MAC_CFG1_TX_RST);

		if(!i) {
			mask = (ATH_RESET_GE0_MAC | ATH_RESET_GE1_MAC);

			mask = mask | ATH_RESET_GE0_MDIO | ATH_RESET_GE1_MDIO;

			printf("%s: reset mask:%x \n", __func__, mask);

			ath_reg_rmw_set(RST_RESET_ADDRESS, mask);
			udelay(1000 * 100);

			ath_reg_rmw_clear(RST_RESET_ADDRESS, mask);
			udelay(1000 * 100);

			udelay(10 * 1000);
		}
#if defined(CONFIG_MGMT_INIT) && defined (CONFIG_ATHR_SWITCH_ONLY_MODE) || defined ATH_MDC_GPIO
		if (!i)
			athr_mgmt_init();

		if (ath_gmac_macs[i]->mac_unit == 0)
                        continue;
#endif
		eth_register(dev[i]);
#if(CONFIG_COMMANDS & CFG_CMD_MII)
		miiphy_register(dev[i]->name, ath_gmac_miiphy_read, ath_gmac_miiphy_write);
#endif
		ath_gmac_mii_setup(ath_gmac_macs[i]);

		/* if using header for register configuration, we have to     */
		/* configure s26 register after frame transmission is enabled */

		if (ath_gmac_macs[i]->mac_unit == 0) { /* WAN Phy */
#ifdef  CONFIG_ATHRS17_PHY
			athrs17_reg_init();
#endif

#ifdef CONFIG_VIR_PHY
			printf("VIRPhy reg init \n");
			athr_vir_reg_init();
#endif

		} else {
#ifdef CONFIG_ATHR_8033_PHY
			printf("AR8033 PHY init \n");
			athrs_ar8033_reg_init(NULL);

#endif

#if defined(CONFIG_MGMT_INIT) && defined (CONFIG_ATHR_SWITCH_ONLY_MODE)
			athrs17_reg_init();
#elif defined (CONFIG_ATHRS17_PHY) && !defined(CFG_DUAL_PHY_SUPPORT)
			athrs17_reg_init_wan();
#endif
		}
#ifdef CONFIG_ATHRS_GMAC_SGMII
	/*
         * MAC unit 1 or drqfn package call sgmii setup.
	 */
	if (i == 1 || is_drqfn())
		athr_gmac_sgmii_setup();
#endif
		ath_gmac_hw_start(ath_gmac_macs[i]);
		ath_gmac_setup_fifos(ath_gmac_macs[i]);



		udelay(100 * 1000);

		{
			unsigned char *mac = dev[i]->enetaddr;

			printf("%s: %02x:%02x:%02x:%02x:%02x:%02x\n", dev[i]->name,
					mac[0] & 0xff, mac[1] & 0xff, mac[2] & 0xff,
					mac[3] & 0xff, mac[4] & 0xff, mac[5] & 0xff);
		}
		mac_l = (dev[i]->enetaddr[4] << 8) | (dev[i]->enetaddr[5]);
		mac_h = (dev[i]->enetaddr[0] << 24) | (dev[i]->enetaddr[1] << 16) |
			(dev[i]->enetaddr[2] << 8) | (dev[i]->enetaddr[3] << 0);

		ath_gmac_reg_wr(ath_gmac_macs[i], ATH_GE_MAC_ADDR1, mac_l);
		ath_gmac_reg_wr(ath_gmac_macs[i], ATH_GE_MAC_ADDR2, mac_h);


	ath_gmac_phy_setup(ath_gmac_macs[i]->mac_unit);
		printf("%s up\n",dev[i]->name);
	}


	return 1;
}

#if (CONFIG_COMMANDS & CFG_CMD_MII)
int
ath_gmac_miiphy_read(char *devname, uint32_t phy_addr, uint8_t reg, uint16_t *data)
{
	ath_gmac_mac_t *mac   = ath_gmac_name2mac(devname);
	uint16_t      addr  = (phy_addr << ATH_ADDR_SHIFT) | reg, val;
	volatile int           rddata;
	uint16_t      ii = 0xFFFF;




	/*
	 * Check for previous transactions are complete. Added to avoid
	 * race condition while running at higher frequencies.
	 */
	do
	{
		udelay(5);
		rddata = ath_gmac_reg_rd(mac, ATH_MII_MGMT_IND) & 0x1;
	}while(rddata && --ii);

	if (ii == 0)
		printf("ERROR:%s:%d transaction failed\n",__func__,__LINE__);


	ath_gmac_reg_wr(mac, ATH_MII_MGMT_CMD, 0x0);
	ath_gmac_reg_wr(mac, ATH_MII_MGMT_ADDRESS, addr);
	ath_gmac_reg_wr(mac, ATH_MII_MGMT_CMD, ATH_MGMT_CMD_READ);

	do
	{
		udelay(5);
		rddata = ath_gmac_reg_rd(mac, ATH_MII_MGMT_IND) & 0x1;
	}while(rddata && --ii);

	if(ii==0)
		printf("Error!!! Leave ath_gmac_miiphy_read without polling correct status!\n");

	val = ath_gmac_reg_rd(mac, ATH_MII_MGMT_STATUS);
	ath_gmac_reg_wr(mac, ATH_MII_MGMT_CMD, 0x0);

        if (data != NULL)
	    *data = val; 
	return val;
}

int
ath_gmac_miiphy_write(char *devname, uint32_t phy_addr, uint8_t reg, uint16_t data)
{
	ath_gmac_mac_t *mac   = ath_gmac_name2mac(devname);
	uint16_t      addr  = (phy_addr << ATH_ADDR_SHIFT) | reg;
	volatile int rddata;
	uint16_t      ii = 0xFFFF;


	/*
	 * Check for previous transactions are complete. Added to avoid
	 * race condition while running at higher frequencies.
	 */
	do {
		udelay(5);
		rddata = ath_gmac_reg_rd(mac, ATH_MII_MGMT_IND) & 0x1;
	} while (rddata && --ii);

	if (ii == 0)
		printf("ERROR:%s:%d transaction failed\n",__func__,__LINE__);

	ath_gmac_reg_wr(mac, ATH_MII_MGMT_ADDRESS, addr);
	ath_gmac_reg_wr(mac, ATH_MII_MGMT_CTRL, data);

	do {
		rddata = ath_gmac_reg_rd(mac, ATH_MII_MGMT_IND) & 0x1;
	} while (rddata && --ii);

	if (ii == 0)
		printf("Error!!! Leave ath_gmac_miiphy_write without polling correct status!\n");
	return 0; 
}
#endif		/* CONFIG_COMMANDS & CFG_CMD_MII */
