/** * Put an RGMII interface in loopback mode. Internal packets sent * out will be received back again on the same port. Externally * received packets will echo back out. * * @param port IPD port number to loop. */ void cvmx_helper_rgmii_internal_loopback(int port) { int interface = (port >> 4) & 1; int index = port & 0xf; uint64_t tmp; cvmx_gmxx_prtx_cfg_t gmx_cfg; gmx_cfg.u64 = 0; gmx_cfg.s.duplex = 1; gmx_cfg.s.slottime = 1; gmx_cfg.s.speed = 1; cvmx_write_csr(CVMX_GMXX_TXX_CLK(index, interface), 1); cvmx_write_csr(CVMX_GMXX_TXX_SLOT(index, interface), 0x200); cvmx_write_csr(CVMX_GMXX_TXX_BURST(index, interface), 0x2000); cvmx_write_csr(CVMX_GMXX_PRTX_CFG(index, interface), gmx_cfg.u64); tmp = cvmx_read_csr(CVMX_ASXX_PRT_LOOP(interface)); cvmx_write_csr(CVMX_ASXX_PRT_LOOP(interface), (1 << index) | tmp); tmp = cvmx_read_csr(CVMX_ASXX_TX_PRT_EN(interface)); cvmx_write_csr(CVMX_ASXX_TX_PRT_EN(interface), (1 << index) | tmp); tmp = cvmx_read_csr(CVMX_ASXX_RX_PRT_EN(interface)); cvmx_write_csr(CVMX_ASXX_RX_PRT_EN(interface), (1 << index) | tmp); gmx_cfg.s.en = 1; cvmx_write_csr(CVMX_GMXX_PRTX_CFG(index, interface), gmx_cfg.u64); }
/** * Return the link state of an IPD/PKO port as returned by * auto negotiation. The result of this function may not match * Octeon's link config if auto negotiation has changed since * the last call to cvmx_helper_link_set(). * * @ipd_port: IPD/PKO port to query * * Returns Link state */ cvmx_helper_link_info_t __cvmx_helper_rgmii_link_get(int ipd_port) { int interface = cvmx_helper_get_interface_num(ipd_port); int index = cvmx_helper_get_interface_index_num(ipd_port); union cvmx_asxx_prt_loop asxx_prt_loop; asxx_prt_loop.u64 = cvmx_read_csr(CVMX_ASXX_PRT_LOOP(interface)); if (asxx_prt_loop.s.int_loop & (1 << index)) { /* Force 1Gbps full duplex on internal loopback */ cvmx_helper_link_info_t result; result.u64 = 0; result.s.full_duplex = 1; result.s.link_up = 1; result.s.speed = 1000; return result; } else return __cvmx_helper_board_link_get(ipd_port); }