mirror of
https://github.com/AsahiLinux/u-boot
synced 2024-11-25 22:20:45 +00:00
Merge branch 'master' of git://git.denx.de/u-boot-net
This commit is contained in:
commit
1a1326d2da
27 changed files with 718 additions and 377 deletions
|
@ -41,9 +41,11 @@ static int extract_range(char *input, int *plo, int *phi)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int mdio_write_ranges(struct mii_dev *bus, int addrlo,
|
||||
static int mdio_write_ranges(struct phy_device *phydev, struct mii_dev *bus,
|
||||
int addrlo,
|
||||
int addrhi, int devadlo, int devadhi,
|
||||
int reglo, int reghi, unsigned short data)
|
||||
int reglo, int reghi, unsigned short data,
|
||||
int extended)
|
||||
{
|
||||
int addr, devad, reg;
|
||||
int err = 0;
|
||||
|
@ -51,7 +53,12 @@ static int mdio_write_ranges(struct mii_dev *bus, int addrlo,
|
|||
for (addr = addrlo; addr <= addrhi; addr++) {
|
||||
for (devad = devadlo; devad <= devadhi; devad++) {
|
||||
for (reg = reglo; reg <= reghi; reg++) {
|
||||
err = bus->write(bus, addr, devad, reg, data);
|
||||
if (!extended)
|
||||
err = bus->write(bus, addr, devad,
|
||||
reg, data);
|
||||
else
|
||||
err = phydev->drv->writeext(phydev,
|
||||
addr, devad, reg, data);
|
||||
|
||||
if (err)
|
||||
goto err_out;
|
||||
|
@ -63,9 +70,10 @@ err_out:
|
|||
return err;
|
||||
}
|
||||
|
||||
static int mdio_read_ranges(struct mii_dev *bus, int addrlo,
|
||||
static int mdio_read_ranges(struct phy_device *phydev, struct mii_dev *bus,
|
||||
int addrlo,
|
||||
int addrhi, int devadlo, int devadhi,
|
||||
int reglo, int reghi)
|
||||
int reglo, int reghi, int extended)
|
||||
{
|
||||
int addr, devad, reg;
|
||||
|
||||
|
@ -77,7 +85,12 @@ static int mdio_read_ranges(struct mii_dev *bus, int addrlo,
|
|||
for (reg = reglo; reg <= reghi; reg++) {
|
||||
int val;
|
||||
|
||||
val = bus->read(bus, addr, devad, reg);
|
||||
if (!extended)
|
||||
val = bus->read(bus, addr, devad, reg);
|
||||
else
|
||||
val = phydev->drv->readext(phydev, addr,
|
||||
devad, reg);
|
||||
|
||||
if (val < 0) {
|
||||
printf("Error\n");
|
||||
|
||||
|
@ -126,9 +139,10 @@ static int extract_reg_range(char *input, int *devadlo, int *devadhi,
|
|||
}
|
||||
|
||||
static int extract_phy_range(char *const argv[], int argc, struct mii_dev **bus,
|
||||
struct phy_device **phydev,
|
||||
int *addrlo, int *addrhi)
|
||||
{
|
||||
struct phy_device *phydev;
|
||||
struct phy_device *dev = *phydev;
|
||||
|
||||
if ((argc < 1) || (argc > 2))
|
||||
return -1;
|
||||
|
@ -154,11 +168,11 @@ static int extract_phy_range(char *const argv[], int argc, struct mii_dev **bus,
|
|||
* device by the given name. If none are found, we call
|
||||
* extract_range() on the string, and see if it's an address range.
|
||||
*/
|
||||
phydev = mdio_phydev_for_ethname(argv[0]);
|
||||
dev = mdio_phydev_for_ethname(argv[0]);
|
||||
|
||||
if (phydev) {
|
||||
*addrlo = *addrhi = phydev->addr;
|
||||
*bus = phydev->bus;
|
||||
if (dev) {
|
||||
*addrlo = *addrhi = dev->addr;
|
||||
*bus = dev->bus;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -175,6 +189,8 @@ static int do_mdio(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
|
|||
unsigned short data;
|
||||
int pos = argc - 1;
|
||||
struct mii_dev *bus;
|
||||
struct phy_device *phydev = NULL;
|
||||
int extended = 0;
|
||||
|
||||
if (argc < 2)
|
||||
return CMD_RET_USAGE;
|
||||
|
@ -197,6 +213,29 @@ static int do_mdio(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
|
|||
if (flag & CMD_FLAG_REPEAT)
|
||||
op[0] = last_op[0];
|
||||
|
||||
if (strlen(argv[1]) > 1) {
|
||||
op[1] = argv[1][1];
|
||||
if (op[1] == 'x') {
|
||||
phydev = mdio_phydev_for_ethname(argv[2]);
|
||||
|
||||
if (phydev) {
|
||||
addrlo = phydev->addr;
|
||||
addrhi = addrlo;
|
||||
bus = phydev->bus;
|
||||
extended = 1;
|
||||
} else {
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (!phydev->drv ||
|
||||
(!phydev->drv->writeext && (op[0] == 'w')) ||
|
||||
(!phydev->drv->readext && (op[0] == 'r'))) {
|
||||
puts("PHY does not have extended functions\n");
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
switch (op[0]) {
|
||||
case 'w':
|
||||
if (pos > 1)
|
||||
|
@ -210,7 +249,7 @@ static int do_mdio(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
|
|||
default:
|
||||
if (pos > 1)
|
||||
if (extract_phy_range(&(argv[2]), pos - 1, &bus,
|
||||
&addrlo, &addrhi))
|
||||
&phydev, &addrlo, &addrhi))
|
||||
return -1;
|
||||
|
||||
break;
|
||||
|
@ -227,13 +266,13 @@ static int do_mdio(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
|
|||
|
||||
switch (op[0]) {
|
||||
case 'w':
|
||||
mdio_write_ranges(bus, addrlo, addrhi, devadlo, devadhi,
|
||||
reglo, reghi, data);
|
||||
mdio_write_ranges(phydev, bus, addrlo, addrhi, devadlo, devadhi,
|
||||
reglo, reghi, data, extended);
|
||||
break;
|
||||
|
||||
case 'r':
|
||||
mdio_read_ranges(bus, addrlo, addrhi, devadlo, devadhi,
|
||||
reglo, reghi);
|
||||
mdio_read_ranges(phydev, bus, addrlo, addrhi, devadlo, devadhi,
|
||||
reglo, reghi, extended);
|
||||
break;
|
||||
}
|
||||
|
||||
|
@ -262,6 +301,10 @@ U_BOOT_CMD(
|
|||
"read PHY's register at <devad>.<reg>\n"
|
||||
"mdio write <phydev> [<devad>.]<reg> <data> - "
|
||||
"write PHY's register at <devad>.<reg>\n"
|
||||
"mdio rx <phydev> [<devad>.]<reg> - "
|
||||
"read PHY's extended register at <devad>.<reg>\n"
|
||||
"mdio wx <phydev> [<devad>.]<reg> <data> - "
|
||||
"write PHY's extended register at <devad>.<reg>\n"
|
||||
"<phydev> may be:\n"
|
||||
" <busname> <addr>\n"
|
||||
" <addr>\n"
|
||||
|
|
|
@ -78,9 +78,9 @@ static const MII_field_desc_t reg_3_desc_tbl[] = {
|
|||
|
||||
static const MII_field_desc_t reg_4_desc_tbl[] = {
|
||||
{ 15, 15, 0x01, "next page able" },
|
||||
{ 14, 14, 0x01, "reserved" },
|
||||
{ 14, 14, 0x01, "(reserved)" },
|
||||
{ 13, 13, 0x01, "remote fault" },
|
||||
{ 12, 12, 0x01, "reserved" },
|
||||
{ 12, 12, 0x01, "(reserved)" },
|
||||
{ 11, 11, 0x01, "asymmetric pause" },
|
||||
{ 10, 10, 0x01, "pause enable" },
|
||||
{ 9, 9, 0x01, "100BASE-T4 able" },
|
||||
|
|
|
@ -96,7 +96,7 @@ static int mac_reset(struct eth_device *dev)
|
|||
ulong start;
|
||||
int timeout = CONFIG_MACRESET_TIMEOUT;
|
||||
|
||||
writel(DMAMAC_SRST, &dma_p->busmode);
|
||||
writel(readl(&dma_p->busmode) | DMAMAC_SRST, &dma_p->busmode);
|
||||
|
||||
if (priv->interface != PHY_INTERFACE_MODE_RGMII)
|
||||
writel(MII_PORTSELECT, &mac_p->conf);
|
||||
|
|
|
@ -112,7 +112,7 @@ struct dmamacdescr {
|
|||
u32 dmamac_cntl;
|
||||
void *dmamac_addr;
|
||||
struct dmamacdescr *dmamac_next;
|
||||
};
|
||||
} __aligned(16);
|
||||
|
||||
/*
|
||||
* txrx_status definitions
|
||||
|
@ -224,8 +224,7 @@ struct dw_eth_dev {
|
|||
u32 tx_currdescnum;
|
||||
u32 rx_currdescnum;
|
||||
u32 phy_configured;
|
||||
int link_printed;
|
||||
u32 padding;
|
||||
u32 link_printed;
|
||||
|
||||
struct dmamacdescr tx_mac_descrtable[CONFIG_TX_DESCR_NUM];
|
||||
struct dmamacdescr rx_mac_descrtable[CONFIG_RX_DESCR_NUM];
|
||||
|
@ -237,7 +236,7 @@ struct dw_eth_dev {
|
|||
struct eth_dma_regs *dma_regs_p;
|
||||
|
||||
struct eth_device *dev;
|
||||
} __attribute__ ((aligned(8)));
|
||||
};
|
||||
|
||||
/* Speed specific definitions */
|
||||
#define SPEED_10M 1
|
||||
|
|
|
@ -342,6 +342,15 @@ static int dm9000_init(struct eth_device *dev, bd_t *bd)
|
|||
DM9000_iow(DM9000_ISR, ISR_ROOS | ISR_ROS | ISR_PTS | ISR_PRS);
|
||||
|
||||
printf("MAC: %pM\n", dev->enetaddr);
|
||||
if (!is_valid_ether_addr(dev->enetaddr)) {
|
||||
#ifdef CONFIG_RANDOM_MACADDR
|
||||
printf("Bad MAC address (uninitialized EEPROM?), randomizing\n");
|
||||
eth_random_enetaddr(dev->enetaddr);
|
||||
printf("MAC: %pM\n", dev->enetaddr);
|
||||
#else
|
||||
printf("WARNING: Bad MAC address (uninitialized EEPROM?)\n");
|
||||
#endif
|
||||
}
|
||||
|
||||
/* fill device MAC address registers */
|
||||
for (i = 0, oft = DM9000_PAR; i < 6; i++, oft++)
|
||||
|
|
|
@ -114,12 +114,13 @@ static int e1000_write_phy_reg(struct e1000_hw *hw, uint32_t reg_addr,
|
|||
static int32_t e1000_phy_hw_reset(struct e1000_hw *hw);
|
||||
static int e1000_phy_reset(struct e1000_hw *hw);
|
||||
static int e1000_detect_gig_phy(struct e1000_hw *hw);
|
||||
static void e1000_put_hw_eeprom_semaphore(struct e1000_hw *hw);
|
||||
static void e1000_set_media_type(struct e1000_hw *hw);
|
||||
|
||||
static int32_t e1000_swfw_sync_acquire(struct e1000_hw *hw, uint16_t mask);
|
||||
static int32_t e1000_check_phy_reset_block(struct e1000_hw *hw);
|
||||
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
static void e1000_put_hw_eeprom_semaphore(struct e1000_hw *hw);
|
||||
static int32_t e1000_read_eeprom(struct e1000_hw *hw, uint16_t offset,
|
||||
uint16_t words,
|
||||
uint16_t *data);
|
||||
|
@ -885,6 +886,7 @@ static int e1000_validate_eeprom_checksum(struct e1000_hw *hw)
|
|||
|
||||
return -E1000_ERR_EEPROM;
|
||||
}
|
||||
#endif /* CONFIG_E1000_NO_NVM */
|
||||
|
||||
/*****************************************************************************
|
||||
* Set PHY to class A mode
|
||||
|
@ -897,6 +899,7 @@ static int e1000_validate_eeprom_checksum(struct e1000_hw *hw)
|
|||
static int32_t
|
||||
e1000_set_phy_mode(struct e1000_hw *hw)
|
||||
{
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
int32_t ret_val;
|
||||
uint16_t eeprom_data;
|
||||
|
||||
|
@ -923,10 +926,11 @@ e1000_set_phy_mode(struct e1000_hw *hw)
|
|||
hw->phy_reset_disable = false;
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
return E1000_SUCCESS;
|
||||
}
|
||||
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
/***************************************************************************
|
||||
*
|
||||
* Obtaining software semaphore bit (SMBI) before resetting PHY.
|
||||
|
@ -965,6 +969,7 @@ e1000_get_software_semaphore(struct e1000_hw *hw)
|
|||
|
||||
return E1000_SUCCESS;
|
||||
}
|
||||
#endif
|
||||
|
||||
/***************************************************************************
|
||||
* This function clears HW semaphore bits.
|
||||
|
@ -977,6 +982,7 @@ e1000_get_software_semaphore(struct e1000_hw *hw)
|
|||
static void
|
||||
e1000_put_hw_eeprom_semaphore(struct e1000_hw *hw)
|
||||
{
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
uint32_t swsm;
|
||||
|
||||
DEBUGFUNC();
|
||||
|
@ -991,6 +997,7 @@ e1000_put_hw_eeprom_semaphore(struct e1000_hw *hw)
|
|||
} else
|
||||
swsm &= ~(E1000_SWSM_SWESMBI);
|
||||
E1000_WRITE_REG(hw, SWSM, swsm);
|
||||
#endif
|
||||
}
|
||||
|
||||
/***************************************************************************
|
||||
|
@ -1007,6 +1014,7 @@ e1000_put_hw_eeprom_semaphore(struct e1000_hw *hw)
|
|||
static int32_t
|
||||
e1000_get_hw_eeprom_semaphore(struct e1000_hw *hw)
|
||||
{
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
int32_t timeout;
|
||||
uint32_t swsm;
|
||||
|
||||
|
@ -1043,7 +1051,7 @@ e1000_get_hw_eeprom_semaphore(struct e1000_hw *hw)
|
|||
"SWESMBI bit is set.\n");
|
||||
return -E1000_ERR_EEPROM;
|
||||
}
|
||||
|
||||
#endif
|
||||
return E1000_SUCCESS;
|
||||
}
|
||||
|
||||
|
@ -1097,6 +1105,7 @@ static bool e1000_is_second_port(struct e1000_hw *hw)
|
|||
}
|
||||
}
|
||||
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
/******************************************************************************
|
||||
* Reads the adapter's MAC address from the EEPROM and inverts the LSB for the
|
||||
* second function of dual function devices
|
||||
|
@ -1136,6 +1145,7 @@ e1000_read_mac_addr(struct eth_device *nic)
|
|||
#endif
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
/******************************************************************************
|
||||
* Initializes receive address filters.
|
||||
|
@ -1764,9 +1774,11 @@ static int
|
|||
e1000_setup_link(struct eth_device *nic)
|
||||
{
|
||||
struct e1000_hw *hw = nic->priv;
|
||||
uint32_t ctrl_ext;
|
||||
int32_t ret_val;
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
uint32_t ctrl_ext;
|
||||
uint16_t eeprom_data;
|
||||
#endif
|
||||
|
||||
DEBUGFUNC();
|
||||
|
||||
|
@ -1775,6 +1787,7 @@ e1000_setup_link(struct eth_device *nic)
|
|||
if (e1000_check_phy_reset_block(hw))
|
||||
return E1000_SUCCESS;
|
||||
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
/* Read and store word 0x0F of the EEPROM. This word contains bits
|
||||
* that determine the hardware's default PAUSE (flow control) mode,
|
||||
* a bit that determines whether the HW defaults to enabling or
|
||||
|
@ -1788,7 +1801,7 @@ e1000_setup_link(struct eth_device *nic)
|
|||
DEBUGOUT("EEPROM Read Error\n");
|
||||
return -E1000_ERR_EEPROM;
|
||||
}
|
||||
|
||||
#endif
|
||||
if (hw->fc == e1000_fc_default) {
|
||||
switch (hw->mac_type) {
|
||||
case e1000_ich8lan:
|
||||
|
@ -1797,6 +1810,7 @@ e1000_setup_link(struct eth_device *nic)
|
|||
hw->fc = e1000_fc_full;
|
||||
break;
|
||||
default:
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
ret_val = e1000_read_eeprom(hw,
|
||||
EEPROM_INIT_CONTROL2_REG, 1, &eeprom_data);
|
||||
if (ret_val) {
|
||||
|
@ -1809,6 +1823,7 @@ e1000_setup_link(struct eth_device *nic)
|
|||
EEPROM_WORD0F_ASM_DIR)
|
||||
hw->fc = e1000_fc_tx_pause;
|
||||
else
|
||||
#endif
|
||||
hw->fc = e1000_fc_full;
|
||||
break;
|
||||
}
|
||||
|
@ -1828,6 +1843,7 @@ e1000_setup_link(struct eth_device *nic)
|
|||
|
||||
DEBUGOUT("After fix-ups FlowControl is now = %x\n", hw->fc);
|
||||
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
/* Take the 4 bits from EEPROM word 0x0F that determine the initial
|
||||
* polarity value for the SW controlled pins, and setup the
|
||||
* Extended Device Control reg with that info.
|
||||
|
@ -1840,6 +1856,7 @@ e1000_setup_link(struct eth_device *nic)
|
|||
SWDPIO__EXT_SHIFT);
|
||||
E1000_WRITE_REG(hw, CTRL_EXT, ctrl_ext);
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Call the necessary subroutine to configure the link. */
|
||||
ret_val = (hw->media_type == e1000_media_type_fiber) ?
|
||||
|
@ -5196,6 +5213,7 @@ e1000_initialize(bd_t * bis)
|
|||
e1000_reset_hw(hw);
|
||||
list_add_tail(&hw->list_node, &e1000_hw_list);
|
||||
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
/* Validate the EEPROM and get chipset information */
|
||||
#if !defined(CONFIG_MVBC_1G)
|
||||
if (e1000_init_eeprom_params(hw)) {
|
||||
|
@ -5206,11 +5224,17 @@ e1000_initialize(bd_t * bis)
|
|||
continue;
|
||||
#endif
|
||||
e1000_read_mac_addr(nic);
|
||||
#endif
|
||||
e1000_get_bus_type(hw);
|
||||
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
printf("e1000: %02x:%02x:%02x:%02x:%02x:%02x\n ",
|
||||
nic->enetaddr[0], nic->enetaddr[1], nic->enetaddr[2],
|
||||
nic->enetaddr[3], nic->enetaddr[4], nic->enetaddr[5]);
|
||||
#else
|
||||
memset(nic->enetaddr, 0, 6);
|
||||
printf("e1000: no NVM\n");
|
||||
#endif
|
||||
|
||||
/* Set up the function pointers and register the device */
|
||||
nic->init = e1000_init;
|
||||
|
|
|
@ -63,11 +63,14 @@ struct e1000_hw_stats;
|
|||
|
||||
/* Internal E1000 helper functions */
|
||||
struct e1000_hw *e1000_find_card(unsigned int cardnum);
|
||||
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
int32_t e1000_acquire_eeprom(struct e1000_hw *hw);
|
||||
void e1000_standby_eeprom(struct e1000_hw *hw);
|
||||
void e1000_release_eeprom(struct e1000_hw *hw);
|
||||
void e1000_raise_ee_clk(struct e1000_hw *hw, uint32_t *eecd);
|
||||
void e1000_lower_ee_clk(struct e1000_hw *hw, uint32_t *eecd);
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_E1000_SPI
|
||||
int do_e1000_spi(cmd_tbl_t *cmdtp, struct e1000_hw *hw,
|
||||
|
@ -1019,6 +1022,7 @@ struct e1000_hw_stats {
|
|||
uint64_t tsctfc;
|
||||
};
|
||||
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
struct e1000_eeprom_info {
|
||||
e1000_eeprom_type type;
|
||||
uint16_t word_size;
|
||||
|
@ -1029,6 +1033,7 @@ e1000_eeprom_type type;
|
|||
bool use_eerd;
|
||||
bool use_eewr;
|
||||
};
|
||||
#endif
|
||||
|
||||
typedef enum {
|
||||
e1000_smart_speed_default = 0,
|
||||
|
@ -1081,10 +1086,14 @@ struct e1000_hw {
|
|||
uint32_t io_base;
|
||||
#endif
|
||||
uint32_t asf_firmware_present;
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
uint32_t eeprom_semaphore_present;
|
||||
#endif
|
||||
uint32_t swfw_sync_present;
|
||||
uint32_t swfwhw_semaphore_present;
|
||||
#ifndef CONFIG_E1000_NO_NVM
|
||||
struct e1000_eeprom_info eeprom;
|
||||
#endif
|
||||
e1000_ms_type master_slave;
|
||||
e1000_ms_type original_master_slave;
|
||||
e1000_ffe_config ffe_config_state;
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
* Copyright 2009-2010 Freescale Semiconductor, Inc.
|
||||
* Copyright 2009-2010, 2013 Freescale Semiconductor, Inc.
|
||||
* Jun-jie Zhang <b18070@freescale.com>
|
||||
* Mingkai Hu <Mingkai.hu@freescale.com>
|
||||
*
|
||||
|
@ -13,7 +13,7 @@
|
|||
#include <asm/errno.h>
|
||||
#include <asm/fsl_enet.h>
|
||||
|
||||
void tsec_local_mdio_write(struct tsec_mii_mng *phyregs, int port_addr,
|
||||
void tsec_local_mdio_write(struct tsec_mii_mng __iomem *phyregs, int port_addr,
|
||||
int dev_addr, int regnum, int value)
|
||||
{
|
||||
int timeout = 1000000;
|
||||
|
@ -26,7 +26,7 @@ void tsec_local_mdio_write(struct tsec_mii_mng *phyregs, int port_addr,
|
|||
;
|
||||
}
|
||||
|
||||
int tsec_local_mdio_read(struct tsec_mii_mng *phyregs, int port_addr,
|
||||
int tsec_local_mdio_read(struct tsec_mii_mng __iomem *phyregs, int port_addr,
|
||||
int dev_addr, int regnum)
|
||||
{
|
||||
int value;
|
||||
|
@ -57,7 +57,8 @@ int tsec_local_mdio_read(struct tsec_mii_mng *phyregs, int port_addr,
|
|||
|
||||
static int fsl_pq_mdio_reset(struct mii_dev *bus)
|
||||
{
|
||||
struct tsec_mii_mng *regs = bus->priv;
|
||||
struct tsec_mii_mng __iomem *regs =
|
||||
(struct tsec_mii_mng __iomem *)bus->priv;
|
||||
|
||||
/* Reset MII (due to new addresses) */
|
||||
out_be32(®s->miimcfg, MIIMCFG_RESET_MGMT);
|
||||
|
@ -72,7 +73,8 @@ static int fsl_pq_mdio_reset(struct mii_dev *bus)
|
|||
|
||||
int tsec_phy_read(struct mii_dev *bus, int addr, int dev_addr, int regnum)
|
||||
{
|
||||
struct tsec_mii_mng *phyregs = bus->priv;
|
||||
struct tsec_mii_mng __iomem *phyregs =
|
||||
(struct tsec_mii_mng __iomem *)bus->priv;
|
||||
|
||||
return tsec_local_mdio_read(phyregs, addr, dev_addr, regnum);
|
||||
}
|
||||
|
@ -80,7 +82,8 @@ int tsec_phy_read(struct mii_dev *bus, int addr, int dev_addr, int regnum)
|
|||
int tsec_phy_write(struct mii_dev *bus, int addr, int dev_addr, int regnum,
|
||||
u16 value)
|
||||
{
|
||||
struct tsec_mii_mng *phyregs = bus->priv;
|
||||
struct tsec_mii_mng __iomem *phyregs =
|
||||
(struct tsec_mii_mng __iomem *)bus->priv;
|
||||
|
||||
tsec_local_mdio_write(phyregs, addr, dev_addr, regnum, value);
|
||||
|
||||
|
@ -101,7 +104,7 @@ int fsl_pq_mdio_init(bd_t *bis, struct fsl_pq_mdio_info *info)
|
|||
bus->reset = fsl_pq_mdio_reset;
|
||||
sprintf(bus->name, info->name);
|
||||
|
||||
bus->priv = info->regs;
|
||||
bus->priv = (void *)info->regs;
|
||||
|
||||
return mdio_register(bus);
|
||||
}
|
||||
|
|
|
@ -420,8 +420,9 @@ static int mvgbe_init(struct eth_device *dev)
|
|||
{
|
||||
struct mvgbe_device *dmvgbe = to_mvgbe(dev);
|
||||
struct mvgbe_registers *regs = dmvgbe->regs;
|
||||
#if (defined (CONFIG_MII) || defined (CONFIG_CMD_MII)) \
|
||||
&& defined (CONFIG_SYS_FAULT_ECHO_LINK_DOWN)
|
||||
#if (defined(CONFIG_MII) || defined(CONFIG_CMD_MII)) && \
|
||||
!defined(CONFIG_PHYLIB) && \
|
||||
defined(CONFIG_SYS_FAULT_ECHO_LINK_DOWN)
|
||||
int i;
|
||||
#endif
|
||||
/* setup RX rings */
|
||||
|
|
|
@ -40,7 +40,7 @@ static int ar8035_config(struct phy_device *phydev)
|
|||
static struct phy_driver AR8021_driver = {
|
||||
.name = "AR8021",
|
||||
.uid = 0x4dd040,
|
||||
.mask = 0xfffff0,
|
||||
.mask = 0x4fffff,
|
||||
.features = PHY_GBIT_FEATURES,
|
||||
.config = ar8021_config,
|
||||
.startup = genphy_startup,
|
||||
|
@ -48,11 +48,11 @@ static struct phy_driver AR8021_driver = {
|
|||
};
|
||||
|
||||
static struct phy_driver AR8031_driver = {
|
||||
.name = "AR8031",
|
||||
.name = "AR8031/AR8033",
|
||||
.uid = 0x4dd074,
|
||||
.mask = 0xfffff0,
|
||||
.mask = 0x4fffff,
|
||||
.features = PHY_GBIT_FEATURES,
|
||||
.config = genphy_config,
|
||||
.config = ar8021_config,
|
||||
.startup = genphy_startup,
|
||||
.shutdown = genphy_shutdown,
|
||||
};
|
||||
|
|
|
@ -100,6 +100,19 @@ int ksz9021_phy_extended_read(struct phy_device *phydev, int regnum)
|
|||
return phy_read(phydev, MDIO_DEVAD_NONE, MII_KSZ9021_EXTENDED_DATAR);
|
||||
}
|
||||
|
||||
|
||||
static int ksz9021_phy_extread(struct phy_device *phydev, int addr, int devaddr,
|
||||
int regnum)
|
||||
{
|
||||
return ksz9021_phy_extended_read(phydev, regnum);
|
||||
}
|
||||
|
||||
static int ksz9021_phy_extwrite(struct phy_device *phydev, int addr,
|
||||
int devaddr, int regnum, u16 val)
|
||||
{
|
||||
return ksz9021_phy_extended_write(phydev, regnum, val);
|
||||
}
|
||||
|
||||
/* Micrel ksz9021 */
|
||||
static int ksz9021_config(struct phy_device *phydev)
|
||||
{
|
||||
|
@ -131,6 +144,8 @@ static struct phy_driver ksz9021_driver = {
|
|||
.config = &ksz9021_config,
|
||||
.startup = &ksz90xx_startup,
|
||||
.shutdown = &genphy_shutdown,
|
||||
.writeext = &ksz9021_phy_extwrite,
|
||||
.readext = &ksz9021_phy_extread,
|
||||
};
|
||||
#endif
|
||||
|
||||
|
@ -171,14 +186,31 @@ int ksz9031_phy_extended_read(struct phy_device *phydev, int devaddr,
|
|||
return phy_read(phydev, MDIO_DEVAD_NONE, MII_KSZ9031_MMD_REG_DATA);
|
||||
}
|
||||
|
||||
static int ksz9031_phy_extread(struct phy_device *phydev, int addr, int devaddr,
|
||||
int regnum)
|
||||
{
|
||||
return ksz9031_phy_extended_read(phydev, devaddr, regnum,
|
||||
MII_KSZ9031_MOD_DATA_NO_POST_INC);
|
||||
};
|
||||
|
||||
static int ksz9031_phy_extwrite(struct phy_device *phydev, int addr,
|
||||
int devaddr, int regnum, u16 val)
|
||||
{
|
||||
return ksz9031_phy_extended_write(phydev, devaddr, regnum,
|
||||
MII_KSZ9031_MOD_DATA_POST_INC_RW, val);
|
||||
};
|
||||
|
||||
|
||||
static struct phy_driver ksz9031_driver = {
|
||||
.name = "Micrel ksz9031",
|
||||
.uid = 0x221620,
|
||||
.mask = 0xfffffe,
|
||||
.mask = 0xfffff0,
|
||||
.features = PHY_GBIT_FEATURES,
|
||||
.config = &genphy_config,
|
||||
.startup = &ksz90xx_startup,
|
||||
.shutdown = &genphy_shutdown,
|
||||
.writeext = &ksz9031_phy_extwrite,
|
||||
.readext = &ksz9031_phy_extread,
|
||||
};
|
||||
|
||||
int phy_micrel_init(void)
|
||||
|
|
|
@ -275,13 +275,14 @@ int genphy_parse_link(struct phy_device *phydev)
|
|||
int mii_reg = phy_read(phydev, MDIO_DEVAD_NONE, MII_BMSR);
|
||||
|
||||
/* We're using autonegotiation */
|
||||
if (mii_reg & BMSR_ANEGCAPABLE) {
|
||||
if (phydev->supported & SUPPORTED_Autoneg) {
|
||||
u32 lpa = 0;
|
||||
int gblpa = 0;
|
||||
u32 estatus = 0;
|
||||
|
||||
/* Check for gigabit capability */
|
||||
if (mii_reg & BMSR_ERCAP) {
|
||||
if (phydev->supported & (SUPPORTED_1000baseT_Full |
|
||||
SUPPORTED_1000baseT_Half)) {
|
||||
/* We want a list of states supported by
|
||||
* both PHYs in the link
|
||||
*/
|
||||
|
|
|
@ -102,7 +102,7 @@ static int rtl8211x_startup(struct phy_device *phydev)
|
|||
static struct phy_driver RTL8211B_driver = {
|
||||
.name = "RealTek RTL8211B",
|
||||
.uid = 0x1cc910,
|
||||
.mask = 0xfffff0,
|
||||
.mask = 0xffffff,
|
||||
.features = PHY_GBIT_FEATURES,
|
||||
.config = &rtl8211x_config,
|
||||
.startup = &rtl8211x_startup,
|
||||
|
@ -113,7 +113,7 @@ static struct phy_driver RTL8211B_driver = {
|
|||
static struct phy_driver RTL8211E_driver = {
|
||||
.name = "RealTek RTL8211E",
|
||||
.uid = 0x1cc915,
|
||||
.mask = 0xfffff0,
|
||||
.mask = 0xffffff,
|
||||
.features = PHY_GBIT_FEATURES,
|
||||
.config = &rtl8211x_config,
|
||||
.startup = &rtl8211x_startup,
|
||||
|
@ -124,7 +124,7 @@ static struct phy_driver RTL8211E_driver = {
|
|||
static struct phy_driver RTL8211DN_driver = {
|
||||
.name = "RealTek RTL8211DN",
|
||||
.uid = 0x1cc914,
|
||||
.mask = 0xfffff0,
|
||||
.mask = 0xffffff,
|
||||
.features = PHY_GBIT_FEATURES,
|
||||
.config = &rtl8211x_config,
|
||||
.startup = &rtl8211x_startup,
|
||||
|
|
|
@ -12,6 +12,7 @@
|
|||
*/
|
||||
#include <miiphy.h>
|
||||
|
||||
/* This code does not check the partner abilities. */
|
||||
static int smsc_parse_status(struct phy_device *phydev)
|
||||
{
|
||||
int mii_reg;
|
||||
|
@ -64,7 +65,7 @@ static struct phy_driver lan8710_driver = {
|
|||
.mask = 0xffff0,
|
||||
.features = PHY_BASIC_FEATURES,
|
||||
.config = &genphy_config_aneg,
|
||||
.startup = &smsc_startup,
|
||||
.startup = &genphy_startup,
|
||||
.shutdown = &genphy_shutdown,
|
||||
};
|
||||
|
||||
|
|
|
@ -49,6 +49,15 @@
|
|||
#define MIIM_VSC8574_18G_QSGMII 0x80e0
|
||||
#define MIIM_VSC8574_18G_CMDSTAT 0x8000
|
||||
|
||||
/* Vitesse VSC8514 control register */
|
||||
#define MIIM_VSC8514_GENERAL18 0x12
|
||||
#define MIIM_VSC8514_GENERAL19 0x13
|
||||
#define MIIM_VSC8514_GENERAL23 0x17
|
||||
|
||||
/* Vitesse VSC8514 gerenal purpose register 18 */
|
||||
#define MIIM_VSC8514_18G_QSGMII 0x80e0
|
||||
#define MIIM_VSC8514_18G_CMDSTAT 0x8000
|
||||
|
||||
/* CIS8201 */
|
||||
static int vitesse_config(struct phy_device *phydev)
|
||||
{
|
||||
|
@ -148,7 +157,7 @@ static int vsc8601_config(struct phy_device *phydev)
|
|||
static int vsc8574_config(struct phy_device *phydev)
|
||||
{
|
||||
u32 val;
|
||||
/* configure regiser 19G for MAC */
|
||||
/* configure register 19G for MAC */
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, PHY_EXT_PAGE_ACCESS,
|
||||
PHY_EXT_PAGE_ACCESS_GENERAL);
|
||||
|
||||
|
@ -188,6 +197,53 @@ static int vsc8574_config(struct phy_device *phydev)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int vsc8514_config(struct phy_device *phydev)
|
||||
{
|
||||
u32 val;
|
||||
int timeout = 1000000;
|
||||
|
||||
/* configure register to access 19G */
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, PHY_EXT_PAGE_ACCESS,
|
||||
PHY_EXT_PAGE_ACCESS_GENERAL);
|
||||
|
||||
val = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_VSC8514_GENERAL19);
|
||||
if (phydev->interface == PHY_INTERFACE_MODE_QSGMII) {
|
||||
/* set bit 15:14 to '01' for QSGMII mode */
|
||||
val = (val & 0x3fff) | (1 << 14);
|
||||
phy_write(phydev, MDIO_DEVAD_NONE,
|
||||
MIIM_VSC8514_GENERAL19, val);
|
||||
/* Enable 4 ports MAC QSGMII */
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, MIIM_VSC8514_GENERAL18,
|
||||
MIIM_VSC8514_18G_QSGMII);
|
||||
} else {
|
||||
/*TODO Add SGMII functionality once spec sheet
|
||||
* for VSC8514 defines complete functionality
|
||||
*/
|
||||
}
|
||||
|
||||
val = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_VSC8514_GENERAL18);
|
||||
/* When bit 15 is cleared the command has completed */
|
||||
while ((val & MIIM_VSC8514_18G_CMDSTAT) && timeout--)
|
||||
val = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_VSC8514_GENERAL18);
|
||||
|
||||
if (0 == timeout) {
|
||||
printf("PHY 8514 config failed\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, PHY_EXT_PAGE_ACCESS, 0);
|
||||
|
||||
/* configure register to access 23 */
|
||||
val = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_VSC8514_GENERAL23);
|
||||
/* set bits 10:8 to '000' */
|
||||
val = (val & 0xf8ff);
|
||||
phy_write(phydev, MDIO_DEVAD_NONE, MIIM_VSC8514_GENERAL23, val);
|
||||
|
||||
genphy_config_aneg(phydev);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static struct phy_driver VSC8211_driver = {
|
||||
.name = "Vitesse VSC8211",
|
||||
.uid = 0xfc4b0,
|
||||
|
@ -238,6 +294,16 @@ static struct phy_driver VSC8574_driver = {
|
|||
.shutdown = &genphy_shutdown,
|
||||
};
|
||||
|
||||
static struct phy_driver VSC8514_driver = {
|
||||
.name = "Vitesse VSC8514",
|
||||
.uid = 0x70570,
|
||||
.mask = 0xffff0,
|
||||
.features = PHY_GBIT_FEATURES,
|
||||
.config = &vsc8514_config,
|
||||
.startup = &vitesse_startup,
|
||||
.shutdown = &genphy_shutdown,
|
||||
};
|
||||
|
||||
static struct phy_driver VSC8601_driver = {
|
||||
.name = "Vitesse VSC8601",
|
||||
.uid = 0x70420,
|
||||
|
@ -298,6 +364,7 @@ int phy_vitesse_init(void)
|
|||
phy_register(&VSC8211_driver);
|
||||
phy_register(&VSC8221_driver);
|
||||
phy_register(&VSC8574_driver);
|
||||
phy_register(&VSC8514_driver);
|
||||
phy_register(&VSC8662_driver);
|
||||
phy_register(&cis8201_driver);
|
||||
phy_register(&cis8204_driver);
|
||||
|
|
|
@ -188,7 +188,7 @@ static int rtl_transmit(struct eth_device *dev, void *packet, int length);
|
|||
static int rtl_poll(struct eth_device *dev);
|
||||
static void rtl_disable(struct eth_device *dev);
|
||||
#ifdef CONFIG_MCAST_TFTP/* This driver already accepts all b/mcast */
|
||||
static int rtl_bcast_addr (struct eth_device *dev, u8 bcast_mac, u8 set)
|
||||
static int rtl_bcast_addr(struct eth_device *dev, const u8 *bcast_mac, u8 set)
|
||||
{
|
||||
return (0);
|
||||
}
|
||||
|
|
|
@ -246,6 +246,8 @@ static struct {
|
|||
{"RTL-8169sc/8110sc", 0x18, 0xff7e1880,},
|
||||
{"RTL-8168b/8111sb", 0x30, 0xff7e1880,},
|
||||
{"RTL-8168b/8111sb", 0x38, 0xff7e1880,},
|
||||
{"RTL-8168d/8111d", 0x28, 0xff7e1880,},
|
||||
{"RTL-8168evl/8111evl", 0x2e, 0xff7e1880,},
|
||||
{"RTL-8101e", 0x34, 0xff7e1880,},
|
||||
{"RTL-8100e", 0x32, 0xff7e1880,},
|
||||
};
|
||||
|
@ -314,6 +316,7 @@ static const unsigned int rtl8169_rx_config =
|
|||
|
||||
static struct pci_device_id supported[] = {
|
||||
{PCI_VENDOR_ID_REALTEK, 0x8167},
|
||||
{PCI_VENDOR_ID_REALTEK, 0x8168},
|
||||
{PCI_VENDOR_ID_REALTEK, 0x8169},
|
||||
{}
|
||||
};
|
||||
|
@ -394,6 +397,50 @@ match:
|
|||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Cache maintenance functions. These are simple wrappers around the more
|
||||
* general purpose flush_cache() and invalidate_dcache_range() functions.
|
||||
*/
|
||||
|
||||
static void rtl_inval_rx_desc(struct RxDesc *desc)
|
||||
{
|
||||
unsigned long start = (unsigned long)desc & ~(ARCH_DMA_MINALIGN - 1);
|
||||
unsigned long end = ALIGN(start + sizeof(*desc), ARCH_DMA_MINALIGN);
|
||||
|
||||
invalidate_dcache_range(start, end);
|
||||
}
|
||||
|
||||
static void rtl_flush_rx_desc(struct RxDesc *desc)
|
||||
{
|
||||
flush_cache((unsigned long)desc, sizeof(*desc));
|
||||
}
|
||||
|
||||
static void rtl_inval_tx_desc(struct TxDesc *desc)
|
||||
{
|
||||
unsigned long start = (unsigned long)desc & ~(ARCH_DMA_MINALIGN - 1);
|
||||
unsigned long end = ALIGN(start + sizeof(*desc), ARCH_DMA_MINALIGN);
|
||||
|
||||
invalidate_dcache_range(start, end);
|
||||
}
|
||||
|
||||
static void rtl_flush_tx_desc(struct TxDesc *desc)
|
||||
{
|
||||
flush_cache((unsigned long)desc, sizeof(*desc));
|
||||
}
|
||||
|
||||
static void rtl_inval_buffer(void *buf, size_t size)
|
||||
{
|
||||
unsigned long start = (unsigned long)buf & ~(ARCH_DMA_MINALIGN - 1);
|
||||
unsigned long end = ALIGN(start + size, ARCH_DMA_MINALIGN);
|
||||
|
||||
invalidate_dcache_range(start, end);
|
||||
}
|
||||
|
||||
static void rtl_flush_buffer(void *buf, size_t size)
|
||||
{
|
||||
flush_cache((unsigned long)buf, size);
|
||||
}
|
||||
|
||||
/**************************************************************************
|
||||
RECV - Receive a frame
|
||||
***************************************************************************/
|
||||
|
@ -411,14 +458,16 @@ static int rtl_recv(struct eth_device *dev)
|
|||
ioaddr = dev->iobase;
|
||||
|
||||
cur_rx = tpc->cur_rx;
|
||||
flush_cache((unsigned long)&tpc->RxDescArray[cur_rx],
|
||||
sizeof(struct RxDesc));
|
||||
|
||||
rtl_inval_rx_desc(&tpc->RxDescArray[cur_rx]);
|
||||
|
||||
if ((le32_to_cpu(tpc->RxDescArray[cur_rx].status) & OWNbit) == 0) {
|
||||
if (!(le32_to_cpu(tpc->RxDescArray[cur_rx].status) & RxRES)) {
|
||||
unsigned char rxdata[RX_BUF_LEN];
|
||||
length = (int) (le32_to_cpu(tpc->RxDescArray[cur_rx].
|
||||
status) & 0x00001FFF) - 4;
|
||||
|
||||
rtl_inval_buffer(tpc->RxBufferRing[cur_rx], length);
|
||||
memcpy(rxdata, tpc->RxBufferRing[cur_rx], length);
|
||||
NetReceive(rxdata, length);
|
||||
|
||||
|
@ -430,8 +479,7 @@ static int rtl_recv(struct eth_device *dev)
|
|||
cpu_to_le32(OWNbit + RX_BUF_SIZE);
|
||||
tpc->RxDescArray[cur_rx].buf_addr =
|
||||
cpu_to_le32(bus_to_phys(tpc->RxBufferRing[cur_rx]));
|
||||
flush_cache((unsigned long)tpc->RxBufferRing[cur_rx],
|
||||
RX_BUF_SIZE);
|
||||
rtl_flush_rx_desc(&tpc->RxDescArray[cur_rx]);
|
||||
} else {
|
||||
puts("Error Rx");
|
||||
}
|
||||
|
@ -473,7 +521,7 @@ static int rtl_send(struct eth_device *dev, void *packet, int length)
|
|||
/* point to the current txb incase multiple tx_rings are used */
|
||||
ptxb = tpc->Tx_skbuff[entry * MAX_ETH_FRAME_SIZE];
|
||||
memcpy(ptxb, (char *)packet, (int)length);
|
||||
flush_cache((unsigned long)ptxb, length);
|
||||
rtl_flush_buffer(ptxb, length);
|
||||
|
||||
while (len < ETH_ZLEN)
|
||||
ptxb[len++] = '\0';
|
||||
|
@ -489,20 +537,20 @@ static int rtl_send(struct eth_device *dev, void *packet, int length)
|
|||
cpu_to_le32((OWNbit | EORbit | FSbit | LSbit) |
|
||||
((len > ETH_ZLEN) ? len : ETH_ZLEN));
|
||||
}
|
||||
rtl_flush_tx_desc(&tpc->TxDescArray[entry]);
|
||||
RTL_W8(TxPoll, 0x40); /* set polling bit */
|
||||
|
||||
tpc->cur_tx++;
|
||||
to = currticks() + TX_TIMEOUT;
|
||||
do {
|
||||
flush_cache((unsigned long)&tpc->TxDescArray[entry],
|
||||
sizeof(struct TxDesc));
|
||||
rtl_inval_tx_desc(&tpc->TxDescArray[entry]);
|
||||
} while ((le32_to_cpu(tpc->TxDescArray[entry].status) & OWNbit)
|
||||
&& (currticks() < to)); /* wait */
|
||||
|
||||
if (currticks() >= to) {
|
||||
#ifdef DEBUG_RTL8169_TX
|
||||
puts ("tx timeout/error\n");
|
||||
printf ("%s elapsed time : %d\n", __FUNCTION__, currticks()-stime);
|
||||
puts("tx timeout/error\n");
|
||||
printf("%s elapsed time : %lu\n", __func__, currticks()-stime);
|
||||
#endif
|
||||
ret = 0;
|
||||
} else {
|
||||
|
@ -604,7 +652,7 @@ static void rtl8169_hw_start(struct eth_device *dev)
|
|||
RTL_W16(MultiIntr, RTL_R16(MultiIntr) & 0xF000);
|
||||
|
||||
#ifdef DEBUG_RTL8169
|
||||
printf ("%s elapsed time : %d\n", __FUNCTION__, currticks()-stime);
|
||||
printf("%s elapsed time : %lu\n", __func__, currticks()-stime);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
@ -638,11 +686,11 @@ static void rtl8169_init_ring(struct eth_device *dev)
|
|||
tpc->RxBufferRing[i] = &rxb[i * RX_BUF_SIZE];
|
||||
tpc->RxDescArray[i].buf_addr =
|
||||
cpu_to_le32(bus_to_phys(tpc->RxBufferRing[i]));
|
||||
flush_cache((unsigned long)tpc->RxBufferRing[i], RX_BUF_SIZE);
|
||||
rtl_flush_rx_desc(&tpc->RxDescArray[i]);
|
||||
}
|
||||
|
||||
#ifdef DEBUG_RTL8169
|
||||
printf ("%s elapsed time : %d\n", __FUNCTION__, currticks()-stime);
|
||||
printf("%s elapsed time : %lu\n", __func__, currticks()-stime);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
@ -683,7 +731,7 @@ static int rtl_reset(struct eth_device *dev, bd_t *bis)
|
|||
txb[5] = dev->enetaddr[5];
|
||||
|
||||
#ifdef DEBUG_RTL8169
|
||||
printf ("%s elapsed time : %d\n", __FUNCTION__, currticks()-stime);
|
||||
printf("%s elapsed time : %lu\n", __func__, currticks()-stime);
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
@ -869,11 +917,25 @@ int rtl8169_initialize(bd_t *bis)
|
|||
int idx=0;
|
||||
|
||||
while(1){
|
||||
unsigned int region;
|
||||
u16 device;
|
||||
|
||||
/* Find RTL8169 */
|
||||
if ((devno = pci_find_devices(supported, idx++)) < 0)
|
||||
break;
|
||||
|
||||
pci_read_config_dword(devno, PCI_BASE_ADDRESS_1, &iobase);
|
||||
pci_read_config_word(devno, PCI_DEVICE_ID, &device);
|
||||
switch (device) {
|
||||
case 0x8168:
|
||||
region = 2;
|
||||
break;
|
||||
|
||||
default:
|
||||
region = 1;
|
||||
break;
|
||||
}
|
||||
|
||||
pci_read_config_dword(devno, PCI_BASE_ADDRESS_0 + (region * 4), &iobase);
|
||||
iobase &= ~0xf;
|
||||
|
||||
debug ("rtl8169: REALTEK RTL8169 @0x%x\n", iobase);
|
||||
|
|
|
@ -4,6 +4,7 @@
|
|||
* Copyright (C) 2008, 2011 Renesas Solutions Corp.
|
||||
* Copyright (c) 2008, 2011 Nobuhiro Iwamatsu
|
||||
* Copyright (c) 2007 Carlos Munoz <carlos@kenati.com>
|
||||
* Copyright (C) 2013 Renesas Electronics Corporation
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-2.0+
|
||||
*/
|
||||
|
@ -25,13 +26,31 @@
|
|||
#ifndef CONFIG_SH_ETHER_PHY_ADDR
|
||||
# error "Please define CONFIG_SH_ETHER_PHY_ADDR"
|
||||
#endif
|
||||
#ifdef CONFIG_SH_ETHER_CACHE_WRITEBACK
|
||||
#define flush_cache_wback(addr, len) \
|
||||
dcache_wback_range((u32)addr, (u32)(addr + len - 1))
|
||||
|
||||
#if defined(CONFIG_SH_ETHER_CACHE_WRITEBACK) && !defined(CONFIG_SYS_DCACHE_OFF)
|
||||
#define flush_cache_wback(addr, len) \
|
||||
flush_dcache_range((u32)addr, (u32)(addr + len - 1))
|
||||
#else
|
||||
#define flush_cache_wback(...)
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_SH_ETHER_CACHE_INVALIDATE) && defined(CONFIG_ARM)
|
||||
#define invalidate_cache(addr, len) \
|
||||
{ \
|
||||
u32 line_size = CONFIG_SH_ETHER_ALIGNE_SIZE; \
|
||||
u32 start, end; \
|
||||
\
|
||||
start = (u32)addr; \
|
||||
end = start + len; \
|
||||
start &= ~(line_size - 1); \
|
||||
end = ((end + line_size - 1) & ~(line_size - 1)); \
|
||||
\
|
||||
invalidate_dcache_range(start, end); \
|
||||
}
|
||||
#else
|
||||
#define invalidate_cache(...)
|
||||
#endif
|
||||
|
||||
#define TIMEOUT_CNT 1000
|
||||
|
||||
int sh_eth_send(struct eth_device *dev, void *packet, int len)
|
||||
|
@ -69,8 +88,11 @@ int sh_eth_send(struct eth_device *dev, void *packet, int len)
|
|||
|
||||
/* Wait until packet is transmitted */
|
||||
timeout = TIMEOUT_CNT;
|
||||
while (port_info->tx_desc_cur->td0 & TD_TACT && timeout--)
|
||||
do {
|
||||
invalidate_cache(port_info->tx_desc_cur,
|
||||
sizeof(struct tx_desc_s));
|
||||
udelay(100);
|
||||
} while (port_info->tx_desc_cur->td0 & TD_TACT && timeout--);
|
||||
|
||||
if (timeout < 0) {
|
||||
printf(SHETHER_NAME ": transmit timeout\n");
|
||||
|
@ -94,12 +116,14 @@ int sh_eth_recv(struct eth_device *dev)
|
|||
uchar *packet;
|
||||
|
||||
/* Check if the rx descriptor is ready */
|
||||
invalidate_cache(port_info->rx_desc_cur, sizeof(struct rx_desc_s));
|
||||
if (!(port_info->rx_desc_cur->rd0 & RD_RACT)) {
|
||||
/* Check for errors */
|
||||
if (!(port_info->rx_desc_cur->rd0 & RD_RFE)) {
|
||||
len = port_info->rx_desc_cur->rd1 & 0xffff;
|
||||
packet = (uchar *)
|
||||
ADDR_TO_P2(port_info->rx_desc_cur->rd2);
|
||||
invalidate_cache(packet, len);
|
||||
NetReceive(packet, len);
|
||||
}
|
||||
|
||||
|
@ -108,7 +132,6 @@ int sh_eth_recv(struct eth_device *dev)
|
|||
port_info->rx_desc_cur->rd0 = RD_RACT | RD_RDLE;
|
||||
else
|
||||
port_info->rx_desc_cur->rd0 = RD_RACT;
|
||||
|
||||
/* Point to the next descriptor */
|
||||
port_info->rx_desc_cur++;
|
||||
if (port_info->rx_desc_cur >=
|
||||
|
@ -237,15 +260,17 @@ static int sh_eth_rx_desc_init(struct sh_eth_dev *eth)
|
|||
* Allocate rx data buffers. They must be 32 bytes aligned and in
|
||||
* P2 area
|
||||
*/
|
||||
port_info->rx_buf_malloc = malloc(NUM_RX_DESC * MAX_BUF_SIZE + 31);
|
||||
port_info->rx_buf_malloc = malloc(
|
||||
NUM_RX_DESC * MAX_BUF_SIZE + RX_BUF_ALIGNE_SIZE - 1);
|
||||
if (!port_info->rx_buf_malloc) {
|
||||
printf(SHETHER_NAME ": malloc failed\n");
|
||||
ret = -ENOMEM;
|
||||
goto err_buf_malloc;
|
||||
}
|
||||
|
||||
tmp_addr = (u32)(((int)port_info->rx_buf_malloc + (32 - 1)) &
|
||||
~(32 - 1));
|
||||
tmp_addr = (u32)(((int)port_info->rx_buf_malloc
|
||||
+ (RX_BUF_ALIGNE_SIZE - 1)) &
|
||||
~(RX_BUF_ALIGNE_SIZE - 1));
|
||||
port_info->rx_buf_base = (u8 *)ADDR_TO_P2(tmp_addr);
|
||||
|
||||
/* Initialize all descriptors */
|
||||
|
@ -351,8 +376,9 @@ static int sh_eth_config(struct sh_eth_dev *eth, bd_t *bd)
|
|||
struct phy_device *phy;
|
||||
|
||||
/* Configure e-dmac registers */
|
||||
sh_eth_write(eth, (sh_eth_read(eth, EDMR) & ~EMDR_DESC_R) | EDMR_EL,
|
||||
EDMR);
|
||||
sh_eth_write(eth, (sh_eth_read(eth, EDMR) & ~EMDR_DESC_R) |
|
||||
(EMDR_DESC | EDMR_EL), EDMR);
|
||||
|
||||
sh_eth_write(eth, 0, EESIPR);
|
||||
sh_eth_write(eth, 0, TRSCER);
|
||||
sh_eth_write(eth, 0, TFTR);
|
||||
|
@ -384,6 +410,8 @@ static int sh_eth_config(struct sh_eth_dev *eth, bd_t *bd)
|
|||
|
||||
#if defined(CONFIG_CPU_SH7734) || defined(CONFIG_R8A7740)
|
||||
sh_eth_write(eth, CONFIG_SH_ETHER_SH7734_MII, RMII_MII);
|
||||
#elif defined(CONFIG_R8A7790) || defined(CONFIG_R8A7791)
|
||||
sh_eth_write(eth, sh_eth_read(eth, RMIIMR) | 0x1, RMIIMR);
|
||||
#endif
|
||||
/* Configure phy */
|
||||
ret = sh_eth_phy_config(eth);
|
||||
|
@ -407,7 +435,8 @@ static int sh_eth_config(struct sh_eth_dev *eth, bd_t *bd)
|
|||
sh_eth_write(eth, GECMR_100B, GECMR);
|
||||
#elif defined(CONFIG_CPU_SH7757) || defined(CONFIG_CPU_SH7752)
|
||||
sh_eth_write(eth, 1, RTRATE);
|
||||
#elif defined(CONFIG_CPU_SH7724)
|
||||
#elif defined(CONFIG_CPU_SH7724) || defined(CONFIG_R8A7790) || \
|
||||
defined(CONFIG_R8A7791)
|
||||
val = ECMR_RTM;
|
||||
#endif
|
||||
} else if (phy->speed == 10) {
|
||||
|
|
|
@ -31,6 +31,11 @@
|
|||
#define ADDR_TO_P2(addr) (addr)
|
||||
#endif /* defined(CONFIG_SH) */
|
||||
|
||||
/* base padding size is 16 */
|
||||
#ifndef CONFIG_SH_ETHER_ALIGNE_SIZE
|
||||
#define CONFIG_SH_ETHER_ALIGNE_SIZE 16
|
||||
#endif
|
||||
|
||||
/* Number of supported ports */
|
||||
#define MAX_PORT_NUM 2
|
||||
|
||||
|
@ -45,15 +50,16 @@
|
|||
|
||||
/* The size of the tx descriptor is determined by how much padding is used.
|
||||
4, 20, or 52 bytes of padding can be used */
|
||||
#define TX_DESC_PADDING 4
|
||||
#define TX_DESC_SIZE (12 + TX_DESC_PADDING)
|
||||
#define TX_DESC_PADDING (CONFIG_SH_ETHER_ALIGNE_SIZE - 12)
|
||||
/* same as CONFIG_SH_ETHER_ALIGNE_SIZE */
|
||||
#define TX_DESC_SIZE (12 + TX_DESC_PADDING)
|
||||
|
||||
/* Tx descriptor. We always use 3 bytes of padding */
|
||||
struct tx_desc_s {
|
||||
volatile u32 td0;
|
||||
u32 td1;
|
||||
u32 td2; /* Buffer start */
|
||||
u32 padding;
|
||||
u8 padding[TX_DESC_PADDING]; /* aligned cache line size */
|
||||
};
|
||||
|
||||
/* There is no limitation in the number of rx descriptors */
|
||||
|
@ -61,15 +67,18 @@ struct tx_desc_s {
|
|||
|
||||
/* The size of the rx descriptor is determined by how much padding is used.
|
||||
4, 20, or 52 bytes of padding can be used */
|
||||
#define RX_DESC_PADDING 4
|
||||
#define RX_DESC_PADDING (CONFIG_SH_ETHER_ALIGNE_SIZE - 12)
|
||||
/* same as CONFIG_SH_ETHER_ALIGNE_SIZE */
|
||||
#define RX_DESC_SIZE (12 + RX_DESC_PADDING)
|
||||
/* aligned cache line size */
|
||||
#define RX_BUF_ALIGNE_SIZE (CONFIG_SH_ETHER_ALIGNE_SIZE > 32 ? 64 : 32)
|
||||
|
||||
/* Rx descriptor. We always use 4 bytes of padding */
|
||||
struct rx_desc_s {
|
||||
volatile u32 rd0;
|
||||
volatile u32 rd1;
|
||||
u32 rd2; /* Buffer start */
|
||||
u32 padding;
|
||||
u8 padding[TX_DESC_PADDING]; /* aligned cache line size */
|
||||
};
|
||||
|
||||
struct sh_eth_info {
|
||||
|
@ -157,6 +166,7 @@ enum {
|
|||
TLFRCR,
|
||||
CERCR,
|
||||
CEECR,
|
||||
RMIIMR, /* R8A7790 */
|
||||
MAFCR,
|
||||
RTRATE,
|
||||
CSMR,
|
||||
|
@ -263,6 +273,7 @@ static const u16 sh_eth_offset_fast_sh4[SH_ETH_MAX_REGISTER_OFFSET] = {
|
|||
[RMCR] = 0x0058,
|
||||
[TFUCR] = 0x0064,
|
||||
[RFOCR] = 0x0068,
|
||||
[RMIIMR] = 0x006C,
|
||||
[FCFTR] = 0x0070,
|
||||
[RPADIR] = 0x0078,
|
||||
[TRIMD] = 0x007c,
|
||||
|
@ -290,6 +301,9 @@ static const u16 sh_eth_offset_fast_sh4[SH_ETH_MAX_REGISTER_OFFSET] = {
|
|||
#elif defined(CONFIG_R8A7740)
|
||||
#define SH_ETH_TYPE_GETHER
|
||||
#define BASE_IO_ADDR 0xE9A00000
|
||||
#elif defined(CONFIG_R8A7790) || defined(CONFIG_R8A7791)
|
||||
#define SH_ETH_TYPE_ETHER
|
||||
#define BASE_IO_ADDR 0xEE700200
|
||||
#endif
|
||||
|
||||
/*
|
||||
|
@ -320,6 +334,14 @@ enum DMAC_M_BIT {
|
|||
#endif
|
||||
};
|
||||
|
||||
#if CONFIG_SH_ETHER_ALIGNE_SIZE == 64
|
||||
# define EMDR_DESC EDMR_DL1
|
||||
#elif CONFIG_SH_ETHER_ALIGNE_SIZE == 32
|
||||
# define EMDR_DESC EDMR_DL0
|
||||
#elif CONFIG_SH_ETHER_ALIGNE_SIZE == 16 /* Default */
|
||||
# define EMDR_DESC 0
|
||||
#endif
|
||||
|
||||
/* RFLR */
|
||||
#define RFLR_RFL_MIN 0x05EE /* Recv Frame length 1518 byte */
|
||||
|
||||
|
@ -485,6 +507,8 @@ enum FELIC_MODE_BIT {
|
|||
ECMR_PRM = 0x00000001,
|
||||
#ifdef CONFIG_CPU_SH7724
|
||||
ECMR_RTM = 0x00000010,
|
||||
#elif defined(CONFIG_R8A7790) || defined(CONFIG_R8A7791)
|
||||
ECMR_RTM = 0x00000004,
|
||||
#endif
|
||||
|
||||
};
|
||||
|
|
|
@ -5,7 +5,7 @@
|
|||
* terms of the GNU Public License, Version 2, incorporated
|
||||
* herein by reference.
|
||||
*
|
||||
* Copyright 2004-2011 Freescale Semiconductor, Inc.
|
||||
* Copyright 2004-2011, 2013 Freescale Semiconductor, Inc.
|
||||
* (C) Copyright 2003, Motorola, Inc.
|
||||
* author Andy Fleming
|
||||
*
|
||||
|
@ -25,21 +25,13 @@ DECLARE_GLOBAL_DATA_PTR;
|
|||
|
||||
#define TX_BUF_CNT 2
|
||||
|
||||
static uint rxIdx; /* index of the current RX buffer */
|
||||
static uint txIdx; /* index of the current TX buffer */
|
||||
|
||||
typedef volatile struct rtxbd {
|
||||
txbd8_t txbd[TX_BUF_CNT];
|
||||
rxbd8_t rxbd[PKTBUFSRX];
|
||||
} RTXBD;
|
||||
|
||||
#define MAXCONTROLLERS (8)
|
||||
|
||||
static struct tsec_private *privlist[MAXCONTROLLERS];
|
||||
static int num_tsecs = 0;
|
||||
static uint rx_idx; /* index of the current RX buffer */
|
||||
static uint tx_idx; /* index of the current TX buffer */
|
||||
|
||||
#ifdef __GNUC__
|
||||
static RTXBD rtx __attribute__ ((aligned(8)));
|
||||
static struct txbd8 __iomem txbd[TX_BUF_CNT] __aligned(8);
|
||||
static struct rxbd8 __iomem rxbd[PKTBUFSRX] __aligned(8);
|
||||
|
||||
#else
|
||||
#error "rtx must be 64-bit aligned"
|
||||
#endif
|
||||
|
@ -57,7 +49,7 @@ static struct tsec_info_struct tsec_info[] = {
|
|||
#endif
|
||||
#ifdef CONFIG_MPC85XX_FEC
|
||||
{
|
||||
.regs = (tsec_t *)(TSEC_BASE_ADDR + 0x2000),
|
||||
.regs = TSEC_GET_REGS(2, 0x2000),
|
||||
.devname = CONFIG_MPC85XX_FEC_NAME,
|
||||
.phyaddr = FEC_PHY_ADDR,
|
||||
.flags = FEC_FLAGS,
|
||||
|
@ -113,32 +105,31 @@ static void tsec_configure_serdes(struct tsec_private *priv)
|
|||
* result.
|
||||
* 2) Use the 8 most significant bits as a hash into a 256-entry
|
||||
* table. The table is controlled through 8 32-bit registers:
|
||||
* gaddr0-7. gaddr0's MSB is entry 0, and gaddr7's LSB is
|
||||
* gaddr7. This means that the 3 most significant bits in the
|
||||
* gaddr0-7. gaddr0's MSB is entry 0, and gaddr7's LSB is entry
|
||||
* 255. This means that the 3 most significant bits in the
|
||||
* hash index which gaddr register to use, and the 5 other bits
|
||||
* indicate which bit (assuming an IBM numbering scheme, which
|
||||
* for PowerPC (tm) is usually the case) in the tregister holds
|
||||
* for PowerPC (tm) is usually the case) in the register holds
|
||||
* the entry. */
|
||||
static int
|
||||
tsec_mcast_addr (struct eth_device *dev, u8 mcast_mac, u8 set)
|
||||
tsec_mcast_addr(struct eth_device *dev, const u8 *mcast_mac, u8 set)
|
||||
{
|
||||
struct tsec_private *priv = privlist[1];
|
||||
volatile tsec_t *regs = priv->regs;
|
||||
volatile u32 *reg_array, value;
|
||||
u8 result, whichbit, whichreg;
|
||||
struct tsec_private *priv = (struct tsec_private *)dev->priv;
|
||||
struct tsec __iomem *regs = priv->regs;
|
||||
u32 result, value;
|
||||
u8 whichbit, whichreg;
|
||||
|
||||
result = (u8)((ether_crc(MAC_ADDR_LEN,mcast_mac) >> 24) & 0xff);
|
||||
whichbit = result & 0x1f; /* the 5 LSB = which bit to set */
|
||||
whichreg = result >> 5; /* the 3 MSB = which reg to set it in */
|
||||
value = (1 << (31-whichbit));
|
||||
result = ether_crc(MAC_ADDR_LEN, mcast_mac);
|
||||
whichbit = (result >> 24) & 0x1f; /* the 5 LSB = which bit to set */
|
||||
whichreg = result >> 29; /* the 3 MSB = which reg to set it in */
|
||||
|
||||
reg_array = &(regs->hash.gaddr0);
|
||||
value = 1 << (31-whichbit);
|
||||
|
||||
if (set)
|
||||
setbits_be32(®s->hash.gaddr0 + whichreg, value);
|
||||
else
|
||||
clrbits_be32(®s->hash.gaddr0 + whichreg, value);
|
||||
|
||||
if (set) {
|
||||
reg_array[whichreg] |= value;
|
||||
} else {
|
||||
reg_array[whichreg] &= ~value;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
#endif /* Multicast TFTP ? */
|
||||
|
@ -147,7 +138,7 @@ tsec_mcast_addr (struct eth_device *dev, u8 mcast_mac, u8 set)
|
|||
* those we don't care about (unless zero is bad, in which case,
|
||||
* choose a more appropriate value)
|
||||
*/
|
||||
static void init_registers(tsec_t *regs)
|
||||
static void init_registers(struct tsec __iomem *regs)
|
||||
{
|
||||
/* Clear IEVENT */
|
||||
out_be32(®s->ievent, IEVENT_INIT_CLEAR);
|
||||
|
@ -175,7 +166,7 @@ static void init_registers(tsec_t *regs)
|
|||
out_be32(®s->rctrl, 0x00000000);
|
||||
|
||||
/* Init RMON mib registers */
|
||||
memset((void *)&(regs->rmon), 0, sizeof(rmon_mib_t));
|
||||
memset((void *)®s->rmon, 0, sizeof(regs->rmon));
|
||||
|
||||
out_be32(®s->rmon.cam1, 0xffffffff);
|
||||
out_be32(®s->rmon.cam2, 0xffffffff);
|
||||
|
@ -194,7 +185,7 @@ static void init_registers(tsec_t *regs)
|
|||
*/
|
||||
static void adjust_link(struct tsec_private *priv, struct phy_device *phydev)
|
||||
{
|
||||
tsec_t *regs = priv->regs;
|
||||
struct tsec __iomem *regs = priv->regs;
|
||||
u32 ecntrl, maccfg2;
|
||||
|
||||
if (!phydev->link) {
|
||||
|
@ -248,7 +239,7 @@ static void adjust_link(struct tsec_private *priv, struct phy_device *phydev)
|
|||
void redundant_init(struct eth_device *dev)
|
||||
{
|
||||
struct tsec_private *priv = dev->priv;
|
||||
tsec_t *regs = priv->regs;
|
||||
struct tsec __iomem *regs = priv->regs;
|
||||
uint t, count = 0;
|
||||
int fail = 1;
|
||||
static const u8 pkt[] = {
|
||||
|
@ -281,23 +272,26 @@ void redundant_init(struct eth_device *dev)
|
|||
clrbits_be32(®s->dmactrl, DMACTRL_GRS | DMACTRL_GTS);
|
||||
|
||||
do {
|
||||
uint16_t status;
|
||||
tsec_send(dev, (void *)pkt, sizeof(pkt));
|
||||
|
||||
/* Wait for buffer to be received */
|
||||
for (t = 0; rtx.rxbd[rxIdx].status & RXBD_EMPTY; t++) {
|
||||
for (t = 0; in_be16(&rxbd[rx_idx].status) & RXBD_EMPTY; t++) {
|
||||
if (t >= 10 * TOUT_LOOP) {
|
||||
printf("%s: tsec: rx error\n", dev->name);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (!memcmp(pkt, (void *)NetRxPackets[rxIdx], sizeof(pkt)))
|
||||
if (!memcmp(pkt, (void *)NetRxPackets[rx_idx], sizeof(pkt)))
|
||||
fail = 0;
|
||||
|
||||
rtx.rxbd[rxIdx].length = 0;
|
||||
rtx.rxbd[rxIdx].status =
|
||||
RXBD_EMPTY | (((rxIdx + 1) == PKTBUFSRX) ? RXBD_WRAP : 0);
|
||||
rxIdx = (rxIdx + 1) % PKTBUFSRX;
|
||||
out_be16(&rxbd[rx_idx].length, 0);
|
||||
status = RXBD_EMPTY;
|
||||
if ((rx_idx + 1) == PKTBUFSRX)
|
||||
status |= RXBD_WRAP;
|
||||
out_be16(&rxbd[rx_idx].status, status);
|
||||
rx_idx = (rx_idx + 1) % PKTBUFSRX;
|
||||
|
||||
if (in_be32(®s->ievent) & IEVENT_BSY) {
|
||||
out_be32(®s->ievent, IEVENT_BSY);
|
||||
|
@ -325,36 +319,39 @@ void redundant_init(struct eth_device *dev)
|
|||
*/
|
||||
static void startup_tsec(struct eth_device *dev)
|
||||
{
|
||||
int i;
|
||||
struct tsec_private *priv = (struct tsec_private *)dev->priv;
|
||||
tsec_t *regs = priv->regs;
|
||||
struct tsec __iomem *regs = priv->regs;
|
||||
uint16_t status;
|
||||
int i;
|
||||
|
||||
/* reset the indices to zero */
|
||||
rxIdx = 0;
|
||||
txIdx = 0;
|
||||
rx_idx = 0;
|
||||
tx_idx = 0;
|
||||
#ifdef CONFIG_SYS_FSL_ERRATUM_NMG_ETSEC129
|
||||
uint svr;
|
||||
#endif
|
||||
|
||||
/* Point to the buffer descriptors */
|
||||
out_be32(®s->tbase, (unsigned int)(&rtx.txbd[txIdx]));
|
||||
out_be32(®s->rbase, (unsigned int)(&rtx.rxbd[rxIdx]));
|
||||
out_be32(®s->tbase, (u32)&txbd[0]);
|
||||
out_be32(®s->rbase, (u32)&rxbd[0]);
|
||||
|
||||
/* Initialize the Rx Buffer descriptors */
|
||||
for (i = 0; i < PKTBUFSRX; i++) {
|
||||
rtx.rxbd[i].status = RXBD_EMPTY;
|
||||
rtx.rxbd[i].length = 0;
|
||||
rtx.rxbd[i].bufPtr = (uint) NetRxPackets[i];
|
||||
out_be16(&rxbd[i].status, RXBD_EMPTY);
|
||||
out_be16(&rxbd[i].length, 0);
|
||||
out_be32(&rxbd[i].bufptr, (u32)NetRxPackets[i]);
|
||||
}
|
||||
rtx.rxbd[PKTBUFSRX - 1].status |= RXBD_WRAP;
|
||||
status = in_be16(&rxbd[PKTBUFSRX - 1].status);
|
||||
out_be16(&rxbd[PKTBUFSRX - 1].status, status | RXBD_WRAP);
|
||||
|
||||
/* Initialize the TX Buffer Descriptors */
|
||||
for (i = 0; i < TX_BUF_CNT; i++) {
|
||||
rtx.txbd[i].status = 0;
|
||||
rtx.txbd[i].length = 0;
|
||||
rtx.txbd[i].bufPtr = 0;
|
||||
out_be16(&txbd[i].status, 0);
|
||||
out_be16(&txbd[i].length, 0);
|
||||
out_be32(&txbd[i].bufptr, 0);
|
||||
}
|
||||
rtx.txbd[TX_BUF_CNT - 1].status |= TXBD_WRAP;
|
||||
status = in_be16(&txbd[TX_BUF_CNT - 1].status);
|
||||
out_be16(&txbd[TX_BUF_CNT - 1].status, status | TXBD_WRAP);
|
||||
|
||||
#ifdef CONFIG_SYS_FSL_ERRATUM_NMG_ETSEC129
|
||||
svr = get_svr();
|
||||
|
@ -378,66 +375,67 @@ static void startup_tsec(struct eth_device *dev)
|
|||
*/
|
||||
static int tsec_send(struct eth_device *dev, void *packet, int length)
|
||||
{
|
||||
int i;
|
||||
int result = 0;
|
||||
struct tsec_private *priv = (struct tsec_private *)dev->priv;
|
||||
tsec_t *regs = priv->regs;
|
||||
struct tsec __iomem *regs = priv->regs;
|
||||
uint16_t status;
|
||||
int result = 0;
|
||||
int i;
|
||||
|
||||
/* Find an empty buffer descriptor */
|
||||
for (i = 0; rtx.txbd[txIdx].status & TXBD_READY; i++) {
|
||||
for (i = 0; in_be16(&txbd[tx_idx].status) & TXBD_READY; i++) {
|
||||
if (i >= TOUT_LOOP) {
|
||||
debug("%s: tsec: tx buffers full\n", dev->name);
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
rtx.txbd[txIdx].bufPtr = (uint) packet;
|
||||
rtx.txbd[txIdx].length = length;
|
||||
rtx.txbd[txIdx].status |=
|
||||
(TXBD_READY | TXBD_LAST | TXBD_CRC | TXBD_INTERRUPT);
|
||||
out_be32(&txbd[tx_idx].bufptr, (u32)packet);
|
||||
out_be16(&txbd[tx_idx].length, length);
|
||||
status = in_be16(&txbd[tx_idx].status);
|
||||
out_be16(&txbd[tx_idx].status, status |
|
||||
(TXBD_READY | TXBD_LAST | TXBD_CRC | TXBD_INTERRUPT));
|
||||
|
||||
/* Tell the DMA to go */
|
||||
out_be32(®s->tstat, TSTAT_CLEAR_THALT);
|
||||
|
||||
/* Wait for buffer to be transmitted */
|
||||
for (i = 0; rtx.txbd[txIdx].status & TXBD_READY; i++) {
|
||||
for (i = 0; in_be16(&txbd[tx_idx].status) & TXBD_READY; i++) {
|
||||
if (i >= TOUT_LOOP) {
|
||||
debug("%s: tsec: tx error\n", dev->name);
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
txIdx = (txIdx + 1) % TX_BUF_CNT;
|
||||
result = rtx.txbd[txIdx].status & TXBD_STATS;
|
||||
tx_idx = (tx_idx + 1) % TX_BUF_CNT;
|
||||
result = in_be16(&txbd[tx_idx].status) & TXBD_STATS;
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
static int tsec_recv(struct eth_device *dev)
|
||||
{
|
||||
int length;
|
||||
struct tsec_private *priv = (struct tsec_private *)dev->priv;
|
||||
tsec_t *regs = priv->regs;
|
||||
struct tsec __iomem *regs = priv->regs;
|
||||
|
||||
while (!(rtx.rxbd[rxIdx].status & RXBD_EMPTY)) {
|
||||
|
||||
length = rtx.rxbd[rxIdx].length;
|
||||
while (!(in_be16(&rxbd[rx_idx].status) & RXBD_EMPTY)) {
|
||||
int length = in_be16(&rxbd[rx_idx].length);
|
||||
uint16_t status = in_be16(&rxbd[rx_idx].status);
|
||||
|
||||
/* Send the packet up if there were no errors */
|
||||
if (!(rtx.rxbd[rxIdx].status & RXBD_STATS)) {
|
||||
NetReceive(NetRxPackets[rxIdx], length - 4);
|
||||
} else {
|
||||
printf("Got error %x\n",
|
||||
(rtx.rxbd[rxIdx].status & RXBD_STATS));
|
||||
}
|
||||
if (!(status & RXBD_STATS))
|
||||
NetReceive(NetRxPackets[rx_idx], length - 4);
|
||||
else
|
||||
printf("Got error %x\n", (status & RXBD_STATS));
|
||||
|
||||
rtx.rxbd[rxIdx].length = 0;
|
||||
out_be16(&rxbd[rx_idx].length, 0);
|
||||
|
||||
status = RXBD_EMPTY;
|
||||
/* Set the wrap bit if this is the last element in the list */
|
||||
rtx.rxbd[rxIdx].status =
|
||||
RXBD_EMPTY | (((rxIdx + 1) == PKTBUFSRX) ? RXBD_WRAP : 0);
|
||||
if ((rx_idx + 1) == PKTBUFSRX)
|
||||
status |= RXBD_WRAP;
|
||||
out_be16(&rxbd[rx_idx].status, status);
|
||||
|
||||
rxIdx = (rxIdx + 1) % PKTBUFSRX;
|
||||
rx_idx = (rx_idx + 1) % PKTBUFSRX;
|
||||
}
|
||||
|
||||
if (in_be32(®s->ievent) & IEVENT_BSY) {
|
||||
|
@ -453,7 +451,7 @@ static int tsec_recv(struct eth_device *dev)
|
|||
static void tsec_halt(struct eth_device *dev)
|
||||
{
|
||||
struct tsec_private *priv = (struct tsec_private *)dev->priv;
|
||||
tsec_t *regs = priv->regs;
|
||||
struct tsec __iomem *regs = priv->regs;
|
||||
|
||||
clrbits_be32(®s->dmactrl, DMACTRL_GRS | DMACTRL_GTS);
|
||||
setbits_be32(®s->dmactrl, DMACTRL_GRS | DMACTRL_GTS);
|
||||
|
@ -475,11 +473,9 @@ static void tsec_halt(struct eth_device *dev)
|
|||
*/
|
||||
static int tsec_init(struct eth_device *dev, bd_t * bd)
|
||||
{
|
||||
uint tempval;
|
||||
char tmpbuf[MAC_ADDR_LEN];
|
||||
int i;
|
||||
struct tsec_private *priv = (struct tsec_private *)dev->priv;
|
||||
tsec_t *regs = priv->regs;
|
||||
struct tsec __iomem *regs = priv->regs;
|
||||
u32 tempval;
|
||||
int ret;
|
||||
|
||||
/* Make sure the controller is stopped */
|
||||
|
@ -492,16 +488,16 @@ static int tsec_init(struct eth_device *dev, bd_t * bd)
|
|||
out_be32(®s->ecntrl, ECNTRL_INIT_SETTINGS);
|
||||
|
||||
/* Copy the station address into the address registers.
|
||||
* Backwards, because little endian MACS are dumb */
|
||||
for (i = 0; i < MAC_ADDR_LEN; i++)
|
||||
tmpbuf[MAC_ADDR_LEN - 1 - i] = dev->enetaddr[i];
|
||||
|
||||
tempval = (tmpbuf[0] << 24) | (tmpbuf[1] << 16) | (tmpbuf[2] << 8) |
|
||||
tmpbuf[3];
|
||||
* For a station address of 0x12345678ABCD in transmission
|
||||
* order (BE), MACnADDR1 is set to 0xCDAB7856 and
|
||||
* MACnADDR2 is set to 0x34120000.
|
||||
*/
|
||||
tempval = (dev->enetaddr[5] << 24) | (dev->enetaddr[4] << 16) |
|
||||
(dev->enetaddr[3] << 8) | dev->enetaddr[2];
|
||||
|
||||
out_be32(®s->macstnaddr1, tempval);
|
||||
|
||||
tempval = *((uint *) (tmpbuf + 4));
|
||||
tempval = (dev->enetaddr[1] << 24) | (dev->enetaddr[0] << 16);
|
||||
|
||||
out_be32(®s->macstnaddr2, tempval);
|
||||
|
||||
|
@ -527,7 +523,7 @@ static int tsec_init(struct eth_device *dev, bd_t * bd)
|
|||
|
||||
static phy_interface_t tsec_get_interface(struct tsec_private *priv)
|
||||
{
|
||||
tsec_t *regs = priv->regs;
|
||||
struct tsec __iomem *regs = priv->regs;
|
||||
u32 ecntrl;
|
||||
|
||||
ecntrl = in_be32(®s->ecntrl);
|
||||
|
@ -576,7 +572,7 @@ static int init_phy(struct eth_device *dev)
|
|||
{
|
||||
struct tsec_private *priv = (struct tsec_private *)dev->priv;
|
||||
struct phy_device *phydev;
|
||||
tsec_t *regs = priv->regs;
|
||||
struct tsec __iomem *regs = priv->regs;
|
||||
u32 supported = (SUPPORTED_10baseT_Half |
|
||||
SUPPORTED_10baseT_Full |
|
||||
SUPPORTED_100baseT_Half |
|
||||
|
@ -626,7 +622,6 @@ static int tsec_initialize(bd_t *bis, struct tsec_info_struct *tsec_info)
|
|||
if (NULL == priv)
|
||||
return 0;
|
||||
|
||||
privlist[num_tsecs++] = priv;
|
||||
priv->regs = tsec_info->regs;
|
||||
priv->phyregs_sgmii = tsec_info->miiregs_sgmii;
|
||||
|
||||
|
@ -684,7 +679,7 @@ int tsec_standard_init(bd_t *bis)
|
|||
{
|
||||
struct fsl_pq_mdio_info info;
|
||||
|
||||
info.regs = (struct tsec_mii_mng *)CONFIG_SYS_MDIO_BASE_ADDR;
|
||||
info.regs = TSEC_GET_MDIO_REGS_BASE(1);
|
||||
info.name = DEFAULT_MII_NAME;
|
||||
|
||||
fsl_pq_mdio_init(bis, &info);
|
||||
|
|
|
@ -43,11 +43,6 @@
|
|||
#define ZYNQ_GEM_TXBUF_WRAP_MASK 0x40000000
|
||||
#define ZYNQ_GEM_TXBUF_LAST_MASK 0x00008000 /* Last buffer */
|
||||
|
||||
#define ZYNQ_GEM_TXSR_HRESPNOK_MASK 0x00000100 /* Transmit hresp not OK */
|
||||
#define ZYNQ_GEM_TXSR_URUN_MASK 0x00000040 /* Transmit underrun */
|
||||
/* Transmit buffs exhausted mid frame */
|
||||
#define ZYNQ_GEM_TXSR_BUFEXH_MASK 0x00000010
|
||||
|
||||
#define ZYNQ_GEM_NWCTRL_TXEN_MASK 0x00000008 /* Enable transmit */
|
||||
#define ZYNQ_GEM_NWCTRL_RXEN_MASK 0x00000004 /* Enable receive */
|
||||
#define ZYNQ_GEM_NWCTRL_MDEN_MASK 0x00000010 /* Enable MDIO port */
|
||||
|
@ -90,6 +85,11 @@
|
|||
*/
|
||||
#define PHY_DETECT_MASK 0x1808
|
||||
|
||||
/* TX BD status masks */
|
||||
#define ZYNQ_GEM_TXBUF_FRMLEN_MASK 0x000007ff
|
||||
#define ZYNQ_GEM_TXBUF_EXHAUSTED 0x08000000
|
||||
#define ZYNQ_GEM_TXBUF_UNDERRUN 0x10000000
|
||||
|
||||
/* Device registers */
|
||||
struct zynq_gem_regs {
|
||||
u32 nwctrl; /* Network Control reg */
|
||||
|
@ -123,12 +123,18 @@ struct emac_bd {
|
|||
};
|
||||
|
||||
#define RX_BUF 3
|
||||
/* Page table entries are set to 1MB, or multiples of 1MB
|
||||
* (not < 1MB). driver uses less bd's so use 1MB bdspace.
|
||||
*/
|
||||
#define BD_SPACE 0x100000
|
||||
/* BD separation space */
|
||||
#define BD_SEPRN_SPACE 64
|
||||
|
||||
/* Initialized, rxbd_current, rx_first_buf must be 0 after init */
|
||||
struct zynq_gem_priv {
|
||||
struct emac_bd tx_bd;
|
||||
struct emac_bd rx_bd[RX_BUF];
|
||||
char rxbuffers[RX_BUF * PKTSIZE_ALIGN];
|
||||
struct emac_bd *tx_bd;
|
||||
struct emac_bd *rx_bd;
|
||||
char *rxbuffers;
|
||||
u32 rxbd_current;
|
||||
u32 rx_first_buf;
|
||||
int phyaddr;
|
||||
|
@ -299,20 +305,18 @@ static int zynq_gem_init(struct eth_device *dev, bd_t * bis)
|
|||
readl(®s->stat[i]);
|
||||
|
||||
/* Setup RxBD space */
|
||||
memset(&(priv->rx_bd), 0, sizeof(priv->rx_bd));
|
||||
/* Create the RxBD ring */
|
||||
memset(&(priv->rxbuffers), 0, sizeof(priv->rxbuffers));
|
||||
memset(priv->rx_bd, 0, RX_BUF * sizeof(struct emac_bd));
|
||||
|
||||
for (i = 0; i < RX_BUF; i++) {
|
||||
priv->rx_bd[i].status = 0xF0000000;
|
||||
priv->rx_bd[i].addr =
|
||||
(u32)((char *)&(priv->rxbuffers) +
|
||||
((u32)(priv->rxbuffers) +
|
||||
(i * PKTSIZE_ALIGN));
|
||||
}
|
||||
/* WRAP bit to last BD */
|
||||
priv->rx_bd[--i].addr |= ZYNQ_GEM_RXBUF_WRAP_MASK;
|
||||
/* Write RxBDs to IP */
|
||||
writel((u32)&(priv->rx_bd), ®s->rxqbase);
|
||||
writel((u32)priv->rx_bd, ®s->rxqbase);
|
||||
|
||||
/* Setup for DMA Configuration register */
|
||||
writel(ZYNQ_GEM_DMACR_INIT, ®s->dmacr);
|
||||
|
@ -368,32 +372,35 @@ static int zynq_gem_init(struct eth_device *dev, bd_t * bis)
|
|||
|
||||
static int zynq_gem_send(struct eth_device *dev, void *ptr, int len)
|
||||
{
|
||||
u32 status;
|
||||
u32 addr, size;
|
||||
struct zynq_gem_priv *priv = dev->priv;
|
||||
struct zynq_gem_regs *regs = (struct zynq_gem_regs *)dev->iobase;
|
||||
const u32 mask = ZYNQ_GEM_TXSR_HRESPNOK_MASK | \
|
||||
ZYNQ_GEM_TXSR_URUN_MASK | ZYNQ_GEM_TXSR_BUFEXH_MASK;
|
||||
|
||||
/* setup BD */
|
||||
writel((u32)&(priv->tx_bd), ®s->txqbase);
|
||||
writel((u32)priv->tx_bd, ®s->txqbase);
|
||||
|
||||
/* Setup Tx BD */
|
||||
memset((void *)&(priv->tx_bd), 0, sizeof(struct emac_bd));
|
||||
memset(priv->tx_bd, 0, sizeof(struct emac_bd));
|
||||
|
||||
priv->tx_bd.addr = (u32)ptr;
|
||||
priv->tx_bd.status = len | ZYNQ_GEM_TXBUF_LAST_MASK;
|
||||
priv->tx_bd->addr = (u32)ptr;
|
||||
priv->tx_bd->status = (len & ZYNQ_GEM_TXBUF_FRMLEN_MASK) |
|
||||
ZYNQ_GEM_TXBUF_LAST_MASK;
|
||||
|
||||
addr = (u32) ptr;
|
||||
addr &= ~(ARCH_DMA_MINALIGN - 1);
|
||||
size = roundup(len, ARCH_DMA_MINALIGN);
|
||||
flush_dcache_range(addr, addr + size);
|
||||
barrier();
|
||||
|
||||
/* Start transmit */
|
||||
setbits_le32(®s->nwctrl, ZYNQ_GEM_NWCTRL_STARTTX_MASK);
|
||||
|
||||
/* Read the stat register to know if the packet has been transmitted */
|
||||
status = readl(®s->txsr);
|
||||
if (status & mask)
|
||||
printf("Something has gone wrong here!? Status is 0x%x.\n",
|
||||
status);
|
||||
/* Read TX BD status */
|
||||
if (priv->tx_bd->status & ZYNQ_GEM_TXBUF_UNDERRUN)
|
||||
printf("TX underrun\n");
|
||||
if (priv->tx_bd->status & ZYNQ_GEM_TXBUF_EXHAUSTED)
|
||||
printf("TX buffers exhausted in mid frame\n");
|
||||
|
||||
/* Clear Tx status register before leaving . */
|
||||
writel(status, ®s->txsr);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -416,8 +423,12 @@ static int zynq_gem_recv(struct eth_device *dev)
|
|||
|
||||
frame_len = current_bd->status & ZYNQ_GEM_RXBUF_LEN_MASK;
|
||||
if (frame_len) {
|
||||
NetReceive((u8 *) (current_bd->addr &
|
||||
ZYNQ_GEM_RXBUF_ADD_MASK), frame_len);
|
||||
u32 addr = current_bd->addr & ZYNQ_GEM_RXBUF_ADD_MASK;
|
||||
addr &= ~(ARCH_DMA_MINALIGN - 1);
|
||||
u32 size = roundup(frame_len, ARCH_DMA_MINALIGN);
|
||||
invalidate_dcache_range(addr, addr + size);
|
||||
|
||||
NetReceive((u8 *)addr, frame_len);
|
||||
|
||||
if (current_bd->status & ZYNQ_GEM_RXBUF_SOF_MASK)
|
||||
priv->rx_first_buf = priv->rxbd_current;
|
||||
|
@ -471,6 +482,7 @@ int zynq_gem_initialize(bd_t *bis, int base_addr, int phy_addr, u32 emio)
|
|||
{
|
||||
struct eth_device *dev;
|
||||
struct zynq_gem_priv *priv;
|
||||
void *bd_space;
|
||||
|
||||
dev = calloc(1, sizeof(*dev));
|
||||
if (dev == NULL)
|
||||
|
@ -483,6 +495,18 @@ int zynq_gem_initialize(bd_t *bis, int base_addr, int phy_addr, u32 emio)
|
|||
}
|
||||
priv = dev->priv;
|
||||
|
||||
/* Align rxbuffers to ARCH_DMA_MINALIGN */
|
||||
priv->rxbuffers = memalign(ARCH_DMA_MINALIGN, RX_BUF * PKTSIZE_ALIGN);
|
||||
memset(priv->rxbuffers, 0, RX_BUF * PKTSIZE_ALIGN);
|
||||
|
||||
/* Align bd_space to 1MB */
|
||||
bd_space = memalign(1 << MMU_SECTION_SHIFT, BD_SPACE);
|
||||
mmu_set_region_dcache_behaviour((u32)bd_space, BD_SPACE, DCACHE_OFF);
|
||||
|
||||
/* Initialize the bd spaces for tx and rx bd's */
|
||||
priv->tx_bd = (struct emac_bd *)bd_space;
|
||||
priv->rx_bd = (struct emac_bd *)((u32)bd_space + BD_SEPRN_SPACE);
|
||||
|
||||
priv->phyaddr = phy_addr;
|
||||
priv->emio = emio;
|
||||
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
* Copyright 2009-2012 Freescale Semiconductor, Inc.
|
||||
* Copyright 2009-2012, 2013 Freescale Semiconductor, Inc.
|
||||
* Jun-jie Zhang <b18070@freescale.com>
|
||||
* Mingkai Hu <Mingkai.hu@freescale.com>
|
||||
*
|
||||
|
@ -31,9 +31,9 @@
|
|||
#define MIIMIND_BUSY 0x00000001
|
||||
#define MIIMIND_NOTVALID 0x00000004
|
||||
|
||||
void tsec_local_mdio_write(struct tsec_mii_mng *phyregs, int port_addr,
|
||||
void tsec_local_mdio_write(struct tsec_mii_mng __iomem *phyregs, int port_addr,
|
||||
int dev_addr, int reg, int value);
|
||||
int tsec_local_mdio_read(struct tsec_mii_mng *phyregs, int port_addr,
|
||||
int tsec_local_mdio_read(struct tsec_mii_mng __iomem *phyregs, int port_addr,
|
||||
int dev_addr, int regnum);
|
||||
int tsec_phy_read(struct mii_dev *bus, int addr, int dev_addr, int regnum);
|
||||
int tsec_phy_write(struct mii_dev *bus, int addr, int dev_addr, int regnum,
|
||||
|
@ -44,7 +44,7 @@ int memac_mdio_read(struct mii_dev *bus, int port_addr, int dev_addr,
|
|||
int regnum);
|
||||
|
||||
struct fsl_pq_mdio_info {
|
||||
struct tsec_mii_mng *regs;
|
||||
struct tsec_mii_mng __iomem *regs;
|
||||
char *name;
|
||||
};
|
||||
int fsl_pq_mdio_init(bd_t *bis, struct fsl_pq_mdio_info *info);
|
||||
|
|
|
@ -15,6 +15,11 @@
|
|||
#define MII_KSZ9031_MOD_DATA_POST_INC_RW 0x8000
|
||||
#define MII_KSZ9031_MOD_DATA_POST_INC_W 0xC000
|
||||
|
||||
#define MII_KSZ9031_EXT_RGMII_CTRL_SIG_SKEW 0x4
|
||||
#define MII_KSZ9031_EXT_RGMII_RX_DATA_SKEW 0x5
|
||||
#define MII_KSZ9031_EXT_RGMII_TX_DATA_SKEW 0x6
|
||||
#define MII_KSZ9031_EXT_RGMII_CLOCK_SKEW 0x8
|
||||
|
||||
struct phy_device;
|
||||
int ksz9021_phy_extended_write(struct phy_device *phydev, int regnum, u16 val);
|
||||
int ksz9021_phy_extended_read(struct phy_device *phydev, int regnum);
|
||||
|
|
|
@ -89,7 +89,7 @@ struct eth_device {
|
|||
int (*recv) (struct eth_device *);
|
||||
void (*halt) (struct eth_device *);
|
||||
#ifdef CONFIG_MCAST_TFTP
|
||||
int (*mcast) (struct eth_device *, u32 ip, u8 set);
|
||||
int (*mcast) (struct eth_device *, const u8 *enetaddr, u8 set);
|
||||
#endif
|
||||
int (*write_hwaddr) (struct eth_device *);
|
||||
struct eth_device *next;
|
||||
|
|
|
@ -125,6 +125,9 @@ struct phy_driver {
|
|||
/* Called when bringing down the controller */
|
||||
int (*shutdown)(struct phy_device *phydev);
|
||||
|
||||
int (*readext)(struct phy_device *phydev, int addr, int devad, int reg);
|
||||
int (*writeext)(struct phy_device *phydev, int addr, int devad, int reg,
|
||||
u16 val);
|
||||
struct list_head list;
|
||||
};
|
||||
|
||||
|
|
333
include/tsec.h
333
include/tsec.h
|
@ -7,7 +7,7 @@
|
|||
* terms of the GNU Public License, Version 2, incorporated
|
||||
* herein by reference.
|
||||
*
|
||||
* Copyright 2004, 2007, 2009, 2011 Freescale Semiconductor, Inc.
|
||||
* Copyright 2004, 2007, 2009, 2011, 2013 Freescale Semiconductor, Inc.
|
||||
* (C) Copyright 2003, Motorola, Inc.
|
||||
* maintained by Xianghua Xiao (x.xiao@motorola.com)
|
||||
* author Andy Fleming
|
||||
|
@ -27,13 +27,26 @@
|
|||
|
||||
#define CONFIG_SYS_MDIO_BASE_ADDR (MDIO_BASE_ADDR + 0x520)
|
||||
|
||||
#define TSEC_GET_REGS(num, offset) \
|
||||
(struct tsec __iomem *)\
|
||||
(TSEC_BASE_ADDR + (((num) - 1) * (offset)))
|
||||
|
||||
#define TSEC_GET_REGS_BASE(num) \
|
||||
TSEC_GET_REGS((num), TSEC_SIZE)
|
||||
|
||||
#define TSEC_GET_MDIO_REGS(num, offset) \
|
||||
(struct tsec_mii_mng __iomem *)\
|
||||
(CONFIG_SYS_MDIO_BASE_ADDR + ((num) - 1) * (offset))
|
||||
|
||||
#define TSEC_GET_MDIO_REGS_BASE(num) \
|
||||
TSEC_GET_MDIO_REGS((num), TSEC_MDIO_OFFSET)
|
||||
|
||||
#define DEFAULT_MII_NAME "FSL_MDIO"
|
||||
|
||||
#define STD_TSEC_INFO(num) \
|
||||
{ \
|
||||
.regs = (tsec_t *)(TSEC_BASE_ADDR + ((num - 1) * TSEC_SIZE)), \
|
||||
.miiregs_sgmii = (struct tsec_mii_mng *)(CONFIG_SYS_MDIO_BASE_ADDR \
|
||||
+ (num - 1) * TSEC_MDIO_OFFSET), \
|
||||
.regs = TSEC_GET_REGS_BASE(num), \
|
||||
.miiregs_sgmii = TSEC_GET_MDIO_REGS_BASE(num), \
|
||||
.devname = CONFIG_TSEC##num##_NAME, \
|
||||
.phyaddr = TSEC##num##_PHY_ADDR, \
|
||||
.flags = TSEC##num##_FLAGS, \
|
||||
|
@ -42,9 +55,8 @@
|
|||
|
||||
#define SET_STD_TSEC_INFO(x, num) \
|
||||
{ \
|
||||
x.regs = (tsec_t *)(TSEC_BASE_ADDR + ((num - 1) * TSEC_SIZE)); \
|
||||
x.miiregs_sgmii = (struct tsec_mii_mng *)(CONFIG_SYS_MDIO_BASE_ADDR \
|
||||
+ (num - 1) * TSEC_MDIO_OFFSET); \
|
||||
x.regs = TSEC_GET_REGS_BASE(num); \
|
||||
x.miiregs_sgmii = TSEC_GET_MDIO_REGS_BASE(num); \
|
||||
x.devname = CONFIG_TSEC##num##_NAME; \
|
||||
x.phyaddr = TSEC##num##_PHY_ADDR; \
|
||||
x.flags = TSEC##num##_FLAGS;\
|
||||
|
@ -186,195 +198,190 @@
|
|||
#define RXBD_TRUNCATED 0x0001
|
||||
#define RXBD_STATS 0x003f
|
||||
|
||||
typedef struct txbd8
|
||||
{
|
||||
ushort status; /* Status Fields */
|
||||
ushort length; /* Buffer length */
|
||||
uint bufPtr; /* Buffer Pointer */
|
||||
} txbd8_t;
|
||||
struct txbd8 {
|
||||
uint16_t status; /* Status Fields */
|
||||
uint16_t length; /* Buffer length */
|
||||
uint32_t bufptr; /* Buffer Pointer */
|
||||
};
|
||||
|
||||
typedef struct rxbd8
|
||||
{
|
||||
ushort status; /* Status Fields */
|
||||
ushort length; /* Buffer Length */
|
||||
uint bufPtr; /* Buffer Pointer */
|
||||
} rxbd8_t;
|
||||
struct rxbd8 {
|
||||
uint16_t status; /* Status Fields */
|
||||
uint16_t length; /* Buffer Length */
|
||||
uint32_t bufptr; /* Buffer Pointer */
|
||||
};
|
||||
|
||||
typedef struct rmon_mib
|
||||
{
|
||||
struct tsec_rmon_mib {
|
||||
/* Transmit and Receive Counters */
|
||||
uint tr64; /* Transmit and Receive 64-byte Frame Counter */
|
||||
uint tr127; /* Transmit and Receive 65-127 byte Frame Counter */
|
||||
uint tr255; /* Transmit and Receive 128-255 byte Frame Counter */
|
||||
uint tr511; /* Transmit and Receive 256-511 byte Frame Counter */
|
||||
uint tr1k; /* Transmit and Receive 512-1023 byte Frame Counter */
|
||||
uint trmax; /* Transmit and Receive 1024-1518 byte Frame Counter */
|
||||
uint trmgv; /* Transmit and Receive 1519-1522 byte Good VLAN Frame */
|
||||
u32 tr64; /* Tx/Rx 64-byte Frame Counter */
|
||||
u32 tr127; /* Tx/Rx 65-127 byte Frame Counter */
|
||||
u32 tr255; /* Tx/Rx 128-255 byte Frame Counter */
|
||||
u32 tr511; /* Tx/Rx 256-511 byte Frame Counter */
|
||||
u32 tr1k; /* Tx/Rx 512-1023 byte Frame Counter */
|
||||
u32 trmax; /* Tx/Rx 1024-1518 byte Frame Counter */
|
||||
u32 trmgv; /* Tx/Rx 1519-1522 byte Good VLAN Frame */
|
||||
/* Receive Counters */
|
||||
uint rbyt; /* Receive Byte Counter */
|
||||
uint rpkt; /* Receive Packet Counter */
|
||||
uint rfcs; /* Receive FCS Error Counter */
|
||||
uint rmca; /* Receive Multicast Packet (Counter) */
|
||||
uint rbca; /* Receive Broadcast Packet */
|
||||
uint rxcf; /* Receive Control Frame Packet */
|
||||
uint rxpf; /* Receive Pause Frame Packet */
|
||||
uint rxuo; /* Receive Unknown OP Code */
|
||||
uint raln; /* Receive Alignment Error */
|
||||
uint rflr; /* Receive Frame Length Error */
|
||||
uint rcde; /* Receive Code Error */
|
||||
uint rcse; /* Receive Carrier Sense Error */
|
||||
uint rund; /* Receive Undersize Packet */
|
||||
uint rovr; /* Receive Oversize Packet */
|
||||
uint rfrg; /* Receive Fragments */
|
||||
uint rjbr; /* Receive Jabber */
|
||||
uint rdrp; /* Receive Drop */
|
||||
u32 rbyt; /* Receive Byte Counter */
|
||||
u32 rpkt; /* Receive Packet Counter */
|
||||
u32 rfcs; /* Receive FCS Error Counter */
|
||||
u32 rmca; /* Receive Multicast Packet (Counter) */
|
||||
u32 rbca; /* Receive Broadcast Packet */
|
||||
u32 rxcf; /* Receive Control Frame Packet */
|
||||
u32 rxpf; /* Receive Pause Frame Packet */
|
||||
u32 rxuo; /* Receive Unknown OP Code */
|
||||
u32 raln; /* Receive Alignment Error */
|
||||
u32 rflr; /* Receive Frame Length Error */
|
||||
u32 rcde; /* Receive Code Error */
|
||||
u32 rcse; /* Receive Carrier Sense Error */
|
||||
u32 rund; /* Receive Undersize Packet */
|
||||
u32 rovr; /* Receive Oversize Packet */
|
||||
u32 rfrg; /* Receive Fragments */
|
||||
u32 rjbr; /* Receive Jabber */
|
||||
u32 rdrp; /* Receive Drop */
|
||||
/* Transmit Counters */
|
||||
uint tbyt; /* Transmit Byte Counter */
|
||||
uint tpkt; /* Transmit Packet */
|
||||
uint tmca; /* Transmit Multicast Packet */
|
||||
uint tbca; /* Transmit Broadcast Packet */
|
||||
uint txpf; /* Transmit Pause Control Frame */
|
||||
uint tdfr; /* Transmit Deferral Packet */
|
||||
uint tedf; /* Transmit Excessive Deferral Packet */
|
||||
uint tscl; /* Transmit Single Collision Packet */
|
||||
u32 tbyt; /* Transmit Byte Counter */
|
||||
u32 tpkt; /* Transmit Packet */
|
||||
u32 tmca; /* Transmit Multicast Packet */
|
||||
u32 tbca; /* Transmit Broadcast Packet */
|
||||
u32 txpf; /* Transmit Pause Control Frame */
|
||||
u32 tdfr; /* Transmit Deferral Packet */
|
||||
u32 tedf; /* Transmit Excessive Deferral Packet */
|
||||
u32 tscl; /* Transmit Single Collision Packet */
|
||||
/* (0x2_n700) */
|
||||
uint tmcl; /* Transmit Multiple Collision Packet */
|
||||
uint tlcl; /* Transmit Late Collision Packet */
|
||||
uint txcl; /* Transmit Excessive Collision Packet */
|
||||
uint tncl; /* Transmit Total Collision */
|
||||
u32 tmcl; /* Transmit Multiple Collision Packet */
|
||||
u32 tlcl; /* Transmit Late Collision Packet */
|
||||
u32 txcl; /* Transmit Excessive Collision Packet */
|
||||
u32 tncl; /* Transmit Total Collision */
|
||||
|
||||
uint res2;
|
||||
u32 res2;
|
||||
|
||||
uint tdrp; /* Transmit Drop Frame */
|
||||
uint tjbr; /* Transmit Jabber Frame */
|
||||
uint tfcs; /* Transmit FCS Error */
|
||||
uint txcf; /* Transmit Control Frame */
|
||||
uint tovr; /* Transmit Oversize Frame */
|
||||
uint tund; /* Transmit Undersize Frame */
|
||||
uint tfrg; /* Transmit Fragments Frame */
|
||||
u32 tdrp; /* Transmit Drop Frame */
|
||||
u32 tjbr; /* Transmit Jabber Frame */
|
||||
u32 tfcs; /* Transmit FCS Error */
|
||||
u32 txcf; /* Transmit Control Frame */
|
||||
u32 tovr; /* Transmit Oversize Frame */
|
||||
u32 tund; /* Transmit Undersize Frame */
|
||||
u32 tfrg; /* Transmit Fragments Frame */
|
||||
/* General Registers */
|
||||
uint car1; /* Carry Register One */
|
||||
uint car2; /* Carry Register Two */
|
||||
uint cam1; /* Carry Register One Mask */
|
||||
uint cam2; /* Carry Register Two Mask */
|
||||
} rmon_mib_t;
|
||||
u32 car1; /* Carry Register One */
|
||||
u32 car2; /* Carry Register Two */
|
||||
u32 cam1; /* Carry Register One Mask */
|
||||
u32 cam2; /* Carry Register Two Mask */
|
||||
};
|
||||
|
||||
typedef struct tsec_hash_regs
|
||||
{
|
||||
uint iaddr0; /* Individual Address Register 0 */
|
||||
uint iaddr1; /* Individual Address Register 1 */
|
||||
uint iaddr2; /* Individual Address Register 2 */
|
||||
uint iaddr3; /* Individual Address Register 3 */
|
||||
uint iaddr4; /* Individual Address Register 4 */
|
||||
uint iaddr5; /* Individual Address Register 5 */
|
||||
uint iaddr6; /* Individual Address Register 6 */
|
||||
uint iaddr7; /* Individual Address Register 7 */
|
||||
uint res1[24];
|
||||
uint gaddr0; /* Group Address Register 0 */
|
||||
uint gaddr1; /* Group Address Register 1 */
|
||||
uint gaddr2; /* Group Address Register 2 */
|
||||
uint gaddr3; /* Group Address Register 3 */
|
||||
uint gaddr4; /* Group Address Register 4 */
|
||||
uint gaddr5; /* Group Address Register 5 */
|
||||
uint gaddr6; /* Group Address Register 6 */
|
||||
uint gaddr7; /* Group Address Register 7 */
|
||||
uint res2[24];
|
||||
} tsec_hash_t;
|
||||
struct tsec_hash_regs {
|
||||
u32 iaddr0; /* Individual Address Register 0 */
|
||||
u32 iaddr1; /* Individual Address Register 1 */
|
||||
u32 iaddr2; /* Individual Address Register 2 */
|
||||
u32 iaddr3; /* Individual Address Register 3 */
|
||||
u32 iaddr4; /* Individual Address Register 4 */
|
||||
u32 iaddr5; /* Individual Address Register 5 */
|
||||
u32 iaddr6; /* Individual Address Register 6 */
|
||||
u32 iaddr7; /* Individual Address Register 7 */
|
||||
u32 res1[24];
|
||||
u32 gaddr0; /* Group Address Register 0 */
|
||||
u32 gaddr1; /* Group Address Register 1 */
|
||||
u32 gaddr2; /* Group Address Register 2 */
|
||||
u32 gaddr3; /* Group Address Register 3 */
|
||||
u32 gaddr4; /* Group Address Register 4 */
|
||||
u32 gaddr5; /* Group Address Register 5 */
|
||||
u32 gaddr6; /* Group Address Register 6 */
|
||||
u32 gaddr7; /* Group Address Register 7 */
|
||||
u32 res2[24];
|
||||
};
|
||||
|
||||
typedef struct tsec
|
||||
{
|
||||
struct tsec {
|
||||
/* General Control and Status Registers (0x2_n000) */
|
||||
uint res000[4];
|
||||
u32 res000[4];
|
||||
|
||||
uint ievent; /* Interrupt Event */
|
||||
uint imask; /* Interrupt Mask */
|
||||
uint edis; /* Error Disabled */
|
||||
uint res01c;
|
||||
uint ecntrl; /* Ethernet Control */
|
||||
uint minflr; /* Minimum Frame Length */
|
||||
uint ptv; /* Pause Time Value */
|
||||
uint dmactrl; /* DMA Control */
|
||||
uint tbipa; /* TBI PHY Address */
|
||||
u32 ievent; /* Interrupt Event */
|
||||
u32 imask; /* Interrupt Mask */
|
||||
u32 edis; /* Error Disabled */
|
||||
u32 res01c;
|
||||
u32 ecntrl; /* Ethernet Control */
|
||||
u32 minflr; /* Minimum Frame Length */
|
||||
u32 ptv; /* Pause Time Value */
|
||||
u32 dmactrl; /* DMA Control */
|
||||
u32 tbipa; /* TBI PHY Address */
|
||||
|
||||
uint res034[3];
|
||||
uint res040[48];
|
||||
u32 res034[3];
|
||||
u32 res040[48];
|
||||
|
||||
/* Transmit Control and Status Registers (0x2_n100) */
|
||||
uint tctrl; /* Transmit Control */
|
||||
uint tstat; /* Transmit Status */
|
||||
uint res108;
|
||||
uint tbdlen; /* Tx BD Data Length */
|
||||
uint res110[5];
|
||||
uint ctbptr; /* Current TxBD Pointer */
|
||||
uint res128[23];
|
||||
uint tbptr; /* TxBD Pointer */
|
||||
uint res188[30];
|
||||
u32 tctrl; /* Transmit Control */
|
||||
u32 tstat; /* Transmit Status */
|
||||
u32 res108;
|
||||
u32 tbdlen; /* Tx BD Data Length */
|
||||
u32 res110[5];
|
||||
u32 ctbptr; /* Current TxBD Pointer */
|
||||
u32 res128[23];
|
||||
u32 tbptr; /* TxBD Pointer */
|
||||
u32 res188[30];
|
||||
/* (0x2_n200) */
|
||||
uint res200;
|
||||
uint tbase; /* TxBD Base Address */
|
||||
uint res208[42];
|
||||
uint ostbd; /* Out of Sequence TxBD */
|
||||
uint ostbdp; /* Out of Sequence Tx Data Buffer Pointer */
|
||||
uint res2b8[18];
|
||||
u32 res200;
|
||||
u32 tbase; /* TxBD Base Address */
|
||||
u32 res208[42];
|
||||
u32 ostbd; /* Out of Sequence TxBD */
|
||||
u32 ostbdp; /* Out of Sequence Tx Data Buffer Pointer */
|
||||
u32 res2b8[18];
|
||||
|
||||
/* Receive Control and Status Registers (0x2_n300) */
|
||||
uint rctrl; /* Receive Control */
|
||||
uint rstat; /* Receive Status */
|
||||
uint res308;
|
||||
uint rbdlen; /* RxBD Data Length */
|
||||
uint res310[4];
|
||||
uint res320;
|
||||
uint crbptr; /* Current Receive Buffer Pointer */
|
||||
uint res328[6];
|
||||
uint mrblr; /* Maximum Receive Buffer Length */
|
||||
uint res344[16];
|
||||
uint rbptr; /* RxBD Pointer */
|
||||
uint res388[30];
|
||||
u32 rctrl; /* Receive Control */
|
||||
u32 rstat; /* Receive Status */
|
||||
u32 res308;
|
||||
u32 rbdlen; /* RxBD Data Length */
|
||||
u32 res310[4];
|
||||
u32 res320;
|
||||
u32 crbptr; /* Current Receive Buffer Pointer */
|
||||
u32 res328[6];
|
||||
u32 mrblr; /* Maximum Receive Buffer Length */
|
||||
u32 res344[16];
|
||||
u32 rbptr; /* RxBD Pointer */
|
||||
u32 res388[30];
|
||||
/* (0x2_n400) */
|
||||
uint res400;
|
||||
uint rbase; /* RxBD Base Address */
|
||||
uint res408[62];
|
||||
u32 res400;
|
||||
u32 rbase; /* RxBD Base Address */
|
||||
u32 res408[62];
|
||||
|
||||
/* MAC Registers (0x2_n500) */
|
||||
uint maccfg1; /* MAC Configuration #1 */
|
||||
uint maccfg2; /* MAC Configuration #2 */
|
||||
uint ipgifg; /* Inter Packet Gap/Inter Frame Gap */
|
||||
uint hafdup; /* Half-duplex */
|
||||
uint maxfrm; /* Maximum Frame */
|
||||
uint res514;
|
||||
uint res518;
|
||||
u32 maccfg1; /* MAC Configuration #1 */
|
||||
u32 maccfg2; /* MAC Configuration #2 */
|
||||
u32 ipgifg; /* Inter Packet Gap/Inter Frame Gap */
|
||||
u32 hafdup; /* Half-duplex */
|
||||
u32 maxfrm; /* Maximum Frame */
|
||||
u32 res514;
|
||||
u32 res518;
|
||||
|
||||
uint res51c;
|
||||
u32 res51c;
|
||||
|
||||
uint resmdio[6];
|
||||
u32 resmdio[6];
|
||||
|
||||
uint res538;
|
||||
u32 res538;
|
||||
|
||||
uint ifstat; /* Interface Status */
|
||||
uint macstnaddr1; /* Station Address, part 1 */
|
||||
uint macstnaddr2; /* Station Address, part 2 */
|
||||
uint res548[46];
|
||||
u32 ifstat; /* Interface Status */
|
||||
u32 macstnaddr1; /* Station Address, part 1 */
|
||||
u32 macstnaddr2; /* Station Address, part 2 */
|
||||
u32 res548[46];
|
||||
|
||||
/* (0x2_n600) */
|
||||
uint res600[32];
|
||||
u32 res600[32];
|
||||
|
||||
/* RMON MIB Registers (0x2_n680-0x2_n73c) */
|
||||
rmon_mib_t rmon;
|
||||
uint res740[48];
|
||||
struct tsec_rmon_mib rmon;
|
||||
u32 res740[48];
|
||||
|
||||
/* Hash Function Registers (0x2_n800) */
|
||||
tsec_hash_t hash;
|
||||
struct tsec_hash_regs hash;
|
||||
|
||||
uint res900[128];
|
||||
u32 res900[128];
|
||||
|
||||
/* Pattern Registers (0x2_nb00) */
|
||||
uint resb00[62];
|
||||
uint attr; /* Default Attribute Register */
|
||||
uint attreli; /* Default Attribute Extract Length and Index */
|
||||
u32 resb00[62];
|
||||
u32 attr; /* Default Attribute Register */
|
||||
u32 attreli; /* Default Attribute Extract Length and Index */
|
||||
|
||||
/* TSEC Future Expansion Space (0x2_nc00-0x2_nffc) */
|
||||
uint resc00[256];
|
||||
} tsec_t;
|
||||
u32 resc00[256];
|
||||
};
|
||||
|
||||
#define TSEC_GIGABIT (1 << 0)
|
||||
|
||||
|
@ -383,8 +390,8 @@ typedef struct tsec
|
|||
#define TSEC_SGMII (1 << 2) /* MAC-PHY interface uses SGMII */
|
||||
|
||||
struct tsec_private {
|
||||
tsec_t *regs;
|
||||
struct tsec_mii_mng *phyregs_sgmii;
|
||||
struct tsec __iomem *regs;
|
||||
struct tsec_mii_mng __iomem *phyregs_sgmii;
|
||||
struct phy_device *phydev;
|
||||
phy_interface_t interface;
|
||||
struct mii_dev *bus;
|
||||
|
@ -394,8 +401,8 @@ struct tsec_private {
|
|||
};
|
||||
|
||||
struct tsec_info_struct {
|
||||
tsec_t *regs;
|
||||
struct tsec_mii_mng *miiregs_sgmii;
|
||||
struct tsec __iomem *regs;
|
||||
struct tsec_mii_mng __iomem *miiregs_sgmii;
|
||||
char *devname;
|
||||
char *mii_devname;
|
||||
phy_interface_t interface;
|
||||
|
|
|
@ -281,7 +281,7 @@ static void update_block_number(void)
|
|||
* number of 0 this means that there was a wrap
|
||||
* around of the (16 bit) counter.
|
||||
*/
|
||||
if (TftpBlock == 0) {
|
||||
if (TftpBlock == 0 && TftpLastBlock != 0) {
|
||||
TftpBlockWrap++;
|
||||
TftpBlockWrapOffset += TftpBlkSize * TFTP_SEQUENCE_SIZE;
|
||||
TftpTimeoutCount = 0; /* we've done well, reset thhe timeout */
|
||||
|
@ -849,6 +849,9 @@ TftpStartServer(void)
|
|||
|
||||
TftpState = STATE_RECV_WRQ;
|
||||
net_set_udp_handler(TftpHandler);
|
||||
|
||||
/* zero out server ether in case the server ip has changed */
|
||||
memset(NetServerEther, 0, 6);
|
||||
}
|
||||
#endif /* CONFIG_CMD_TFTPSRV */
|
||||
|
||||
|
|
Loading…
Reference in a new issue