/*
 * This function initializes the EMAC hardware.
 */
int keystone2_emac_initialize(struct eth_priv_t *eth_priv)
{
	int res;
	struct eth_device *dev;
	struct phy_device *phy_dev;

	dev = malloc(sizeof(struct eth_device));
	if (dev == NULL)
		return -1;

	memset(dev, 0, sizeof(struct eth_device));

	strcpy(dev->name, eth_priv->int_name);
	dev->priv = eth_priv;

	keystone2_eth_read_mac_addr(dev);

	dev->iobase		= 0;
	dev->init		= keystone2_eth_open;
	dev->halt		= keystone2_eth_close;
	dev->send		= keystone2_eth_send_packet;
	dev->recv		= keystone2_eth_rcv_packet;
#ifdef CONFIG_MCAST_TFTP
	dev->mcast		= keystone2_eth_bcast_addr;
#endif

	eth_register(dev);

	/* Register MDIO bus if it's not registered yet */
	if (!mdio_bus) {
		mdio_bus	= mdio_alloc();
		mdio_bus->read	= keystone2_mdio_read;
		mdio_bus->write	= keystone2_mdio_write;
		mdio_bus->reset	= keystone2_mdio_reset;
		mdio_bus->priv	= (void *)EMAC_MDIO_BASE_ADDR;
		sprintf(mdio_bus->name, "ethernet-mdio");

		res = mdio_register(mdio_bus);
		if (res)
			return res;
	}

#ifndef CONFIG_SOC_K2G
	keystone2_net_serdes_setup();
#endif

	/* Create phy device and bind it with driver */
#ifdef CONFIG_KSNET_MDIO_PHY_CONFIG_ENABLE
	phy_dev = phy_connect(mdio_bus, eth_priv->phy_addr,
			      dev, eth_priv->phy_if);
	phy_config(phy_dev);
#else
	phy_dev = phy_find_by_mask(mdio_bus, 1 << eth_priv->phy_addr,
				   eth_priv->phy_if);
	phy_dev->dev = dev;
#endif
	eth_priv->phy_dev = phy_dev;

	return 0;
}
Пример #2
0
static int ks2_eth_probe(struct udevice *dev)
{
	struct ks2_eth_priv *priv = dev_get_priv(dev);
	struct mii_dev *mdio_bus;
	int ret;

	priv->dev = dev;

	/* These clock enables has to be moved to common location */
	if (cpu_is_k2g())
		writel(KS2_ETHERNET_RGMII, KS2_ETHERNET_CFG);

	/* By default, select PA PLL clock as PA clock source */
#ifndef CONFIG_SOC_K2G
	if (psc_enable_module(KS2_LPSC_PA))
		return -EACCES;
#endif
	if (psc_enable_module(KS2_LPSC_CPGMAC))
		return -EACCES;
	if (psc_enable_module(KS2_LPSC_CRYPTO))
		return -EACCES;

	if (cpu_is_k2e() || cpu_is_k2l())
		pll_pa_clk_sel();


	priv->net_rx_buffs.buff_ptr = rx_buffs;
	priv->net_rx_buffs.num_buffs = RX_BUFF_NUMS;
	priv->net_rx_buffs.buff_len = RX_BUFF_LEN;

	if (priv->slave_port == 1) {
		/*
		 * Register MDIO bus for slave 0 only, other slave have
		 * to re-use the same
		 */
		mdio_bus = mdio_alloc();
		if (!mdio_bus) {
			error("MDIO alloc failed\n");
			return -ENOMEM;
		}
		priv->mdio_bus = mdio_bus;
		mdio_bus->read	= keystone2_mdio_read;
		mdio_bus->write	= keystone2_mdio_write;
		mdio_bus->reset	= keystone2_mdio_reset;
		mdio_bus->priv	= priv->mdio_base;
		sprintf(mdio_bus->name, "ethernet-mdio");

		ret = mdio_register(mdio_bus);
		if (ret) {
			error("MDIO bus register failed\n");
			return ret;
		}
	} else {
		/* Get the MDIO bus from slave 0 device */
		struct ks2_eth_priv *parent_priv;

		parent_priv = dev_get_priv(dev->parent);
		priv->mdio_bus = parent_priv->mdio_bus;
	}

#ifndef CONFIG_SOC_K2G
	keystone2_net_serdes_setup();
#endif

	priv->netcp_pktdma = &netcp_pktdma;

	if (priv->has_mdio) {
		priv->phydev = phy_connect(priv->mdio_bus, priv->phy_addr,
					   dev, priv->phy_if);
		phy_config(priv->phydev);
	}

	return 0;
}
Пример #3
0
/* Eth device open */
static int keystone2_eth_open(struct eth_device *dev, bd_t *bis)
{
	struct eth_priv_t *eth_priv = (struct eth_priv_t *)dev->priv;
	struct phy_device *phy_dev = eth_priv->phy_dev;

	debug("+ emac_open\n");

	net_rx_buffs.rx_flow	= eth_priv->rx_flow;

	sys_has_mdio =
		(eth_priv->sgmii_link_type == SGMII_LINK_MAC_PHY) ? 1 : 0;

	keystone2_net_serdes_setup();

	if (sys_has_mdio)
		keystone2_mdio_reset(mdio_bus);

	keystone_sgmii_config(phy_dev, eth_priv->slave_port - 1,
			      eth_priv->sgmii_link_type);

	udelay(10000);

	/* On chip switch configuration */
	ethss_config(target_get_switch_ctl(), SWITCH_MAX_PKT_SIZE);

	/* TODO: add error handling code */
	if (qm_init()) {
		printf("ERROR: qm_init()\n");
		return -1;
	}
	if (ksnav_init(&netcp_pktdma, &net_rx_buffs)) {
		qm_close();
		printf("ERROR: netcp_init()\n");
		return -1;
	}

	/*
	 * Streaming switch configuration. If not present this
	 * statement is defined to void in target.h.
	 * If present this is usually defined to a series of register writes
	 */
	hw_config_streaming_switch();

	if (sys_has_mdio) {
		keystone2_mdio_reset(mdio_bus);

		phy_startup(phy_dev);
		if (phy_dev->link == 0) {
			ksnav_close(&netcp_pktdma);
			qm_close();
			return -1;
		}
	}

	emac_gigabit_enable(dev);

	ethss_start();

	debug("- emac_open\n");

	emac_open = 1;

	return 0;
}