183d290c5STom Rini // SPDX-License-Identifier: GPL-2.0+ 2c517771aSPrabhakar Kushwaha /* 3a6f2a6eaSYogesh Gaur * Copyright 2014-2016 Freescale Semiconductor, Inc. 42557c5a9SYogesh Gaur * Copyright 2017 NXP 5c517771aSPrabhakar Kushwaha */ 6c517771aSPrabhakar Kushwaha 7c517771aSPrabhakar Kushwaha #include <common.h> 8c517771aSPrabhakar Kushwaha #include <asm/io.h> 9c517771aSPrabhakar Kushwaha #include <asm/types.h> 10c517771aSPrabhakar Kushwaha #include <malloc.h> 11c517771aSPrabhakar Kushwaha #include <net.h> 12c517771aSPrabhakar Kushwaha #include <hwconfig.h> 13c517771aSPrabhakar Kushwaha #include <phy.h> 14c517771aSPrabhakar Kushwaha #include <linux/compat.h> 15c919ab9eSPrabhakar Kushwaha #include <fsl-mc/fsl_dpmac.h> 16c517771aSPrabhakar Kushwaha 176c2b520aSPrabhakar Kushwaha #include <fsl-mc/ldpaa_wriop.h> 18c517771aSPrabhakar Kushwaha #include "ldpaa_eth.h" 19c517771aSPrabhakar Kushwaha 206c2b520aSPrabhakar Kushwaha #ifdef CONFIG_PHYLIB 21c517771aSPrabhakar Kushwaha static int init_phy(struct eth_device *dev) 22c517771aSPrabhakar Kushwaha { 236c2b520aSPrabhakar Kushwaha struct ldpaa_eth_priv *priv = (struct ldpaa_eth_priv *)dev->priv; 246c2b520aSPrabhakar Kushwaha struct phy_device *phydev = NULL; 256c2b520aSPrabhakar Kushwaha struct mii_dev *bus; 26c517771aSPrabhakar Kushwaha 276c2b520aSPrabhakar Kushwaha bus = wriop_get_mdio(priv->dpmac_id); 286c2b520aSPrabhakar Kushwaha if (bus == NULL) 29c517771aSPrabhakar Kushwaha return 0; 306c2b520aSPrabhakar Kushwaha 316c2b520aSPrabhakar Kushwaha phydev = phy_connect(bus, wriop_get_phy_address(priv->dpmac_id), 326c2b520aSPrabhakar Kushwaha dev, wriop_get_enet_if(priv->dpmac_id)); 336c2b520aSPrabhakar Kushwaha if (!phydev) { 346c2b520aSPrabhakar Kushwaha printf("Failed to connect\n"); 356c2b520aSPrabhakar Kushwaha return -1; 36c517771aSPrabhakar Kushwaha } 37c517771aSPrabhakar Kushwaha 386c2b520aSPrabhakar Kushwaha priv->phydev = phydev; 396c2b520aSPrabhakar Kushwaha 406c2b520aSPrabhakar Kushwaha return phy_config(phydev); 416c2b520aSPrabhakar Kushwaha } 426c2b520aSPrabhakar Kushwaha #endif 436c2b520aSPrabhakar Kushwaha 445038d3e5SPrabhakar Kushwaha #ifdef DEBUG 452557c5a9SYogesh Gaur 462557c5a9SYogesh Gaur #define DPNI_STATS_PER_PAGE 6 472557c5a9SYogesh Gaur 482557c5a9SYogesh Gaur static const char *dpni_statistics[][DPNI_STATS_PER_PAGE] = { 492557c5a9SYogesh Gaur { 502557c5a9SYogesh Gaur "DPNI_CNT_ING_ALL_FRAMES", 512557c5a9SYogesh Gaur "DPNI_CNT_ING_ALL_BYTES", 522557c5a9SYogesh Gaur "DPNI_CNT_ING_MCAST_FRAMES", 532557c5a9SYogesh Gaur "DPNI_CNT_ING_MCAST_BYTES", 542557c5a9SYogesh Gaur "DPNI_CNT_ING_BCAST_FRAMES", 552557c5a9SYogesh Gaur "DPNI_CNT_ING_BCAST_BYTES", 562557c5a9SYogesh Gaur }, { 572557c5a9SYogesh Gaur "DPNI_CNT_EGR_ALL_FRAMES", 582557c5a9SYogesh Gaur "DPNI_CNT_EGR_ALL_BYTES", 592557c5a9SYogesh Gaur "DPNI_CNT_EGR_MCAST_FRAMES", 602557c5a9SYogesh Gaur "DPNI_CNT_EGR_MCAST_BYTES", 612557c5a9SYogesh Gaur "DPNI_CNT_EGR_BCAST_FRAMES", 622557c5a9SYogesh Gaur "DPNI_CNT_EGR_BCAST_BYTES", 632557c5a9SYogesh Gaur }, { 642557c5a9SYogesh Gaur "DPNI_CNT_ING_FILTERED_FRAMES", 652557c5a9SYogesh Gaur "DPNI_CNT_ING_DISCARDED_FRAMES", 662557c5a9SYogesh Gaur "DPNI_CNT_ING_NOBUFFER_DISCARDS", 672557c5a9SYogesh Gaur "DPNI_CNT_EGR_DISCARDED_FRAMES", 682557c5a9SYogesh Gaur "DPNI_CNT_EGR_CNF_FRAMES", 692557c5a9SYogesh Gaur "" 702557c5a9SYogesh Gaur }, 712557c5a9SYogesh Gaur }; 722557c5a9SYogesh Gaur 732557c5a9SYogesh Gaur static void print_dpni_stats(const char *strings[], 742557c5a9SYogesh Gaur struct dpni_statistics dpni_stats) 752557c5a9SYogesh Gaur { 762557c5a9SYogesh Gaur uint64_t *stat; 772557c5a9SYogesh Gaur int i; 782557c5a9SYogesh Gaur 792557c5a9SYogesh Gaur stat = (uint64_t *)&dpni_stats; 802557c5a9SYogesh Gaur for (i = 0; i < DPNI_STATS_PER_PAGE; i++) { 812557c5a9SYogesh Gaur if (strcmp(strings[i], "\0") == 0) 822557c5a9SYogesh Gaur break; 832557c5a9SYogesh Gaur printf("%s= %llu\n", strings[i], *stat); 842557c5a9SYogesh Gaur stat++; 852557c5a9SYogesh Gaur } 862557c5a9SYogesh Gaur } 872557c5a9SYogesh Gaur 885038d3e5SPrabhakar Kushwaha static void ldpaa_eth_get_dpni_counter(void) 895038d3e5SPrabhakar Kushwaha { 905038d3e5SPrabhakar Kushwaha int err = 0; 912557c5a9SYogesh Gaur unsigned int page = 0; 922557c5a9SYogesh Gaur struct dpni_statistics dpni_stats; 935038d3e5SPrabhakar Kushwaha 942557c5a9SYogesh Gaur printf("DPNI counters ..\n"); 952557c5a9SYogesh Gaur for (page = 0; page < 3; page++) { 962557c5a9SYogesh Gaur err = dpni_get_statistics(dflt_mc_io, MC_CMD_NO_FLAGS, 972557c5a9SYogesh Gaur dflt_dpni->dpni_handle, page, 982557c5a9SYogesh Gaur &dpni_stats); 995038d3e5SPrabhakar Kushwaha if (err < 0) { 1002557c5a9SYogesh Gaur printf("dpni_get_statistics: failed:"); 1012557c5a9SYogesh Gaur printf("%d for page[%d]\n", err, page); 1025038d3e5SPrabhakar Kushwaha return; 1035038d3e5SPrabhakar Kushwaha } 1042557c5a9SYogesh Gaur print_dpni_stats(dpni_statistics[page], dpni_stats); 1055038d3e5SPrabhakar Kushwaha } 1065038d3e5SPrabhakar Kushwaha } 10744b2036eSPrabhakar Kushwaha 10844b2036eSPrabhakar Kushwaha static void ldpaa_eth_get_dpmac_counter(struct eth_device *net_dev) 10944b2036eSPrabhakar Kushwaha { 11044b2036eSPrabhakar Kushwaha struct ldpaa_eth_priv *priv = (struct ldpaa_eth_priv *)net_dev->priv; 11144b2036eSPrabhakar Kushwaha int err = 0; 11244b2036eSPrabhakar Kushwaha u64 value; 11344b2036eSPrabhakar Kushwaha 11444b2036eSPrabhakar Kushwaha err = dpmac_get_counter(dflt_mc_io, MC_CMD_NO_FLAGS, 11544b2036eSPrabhakar Kushwaha priv->dpmac_handle, 11644b2036eSPrabhakar Kushwaha DPMAC_CNT_ING_BYTE, 11744b2036eSPrabhakar Kushwaha &value); 11844b2036eSPrabhakar Kushwaha if (err < 0) { 11944b2036eSPrabhakar Kushwaha printf("dpmac_get_counter: DPMAC_CNT_ING_BYTE failed\n"); 12044b2036eSPrabhakar Kushwaha return; 12144b2036eSPrabhakar Kushwaha } 1222557c5a9SYogesh Gaur printf("\nDPMAC counters ..\n"); 12344b2036eSPrabhakar Kushwaha printf("DPMAC_CNT_ING_BYTE=%lld\n", value); 12444b2036eSPrabhakar Kushwaha 12544b2036eSPrabhakar Kushwaha err = dpmac_get_counter(dflt_mc_io, MC_CMD_NO_FLAGS, 12644b2036eSPrabhakar Kushwaha priv->dpmac_handle, 12744b2036eSPrabhakar Kushwaha DPMAC_CNT_ING_FRAME_DISCARD, 12844b2036eSPrabhakar Kushwaha &value); 12944b2036eSPrabhakar Kushwaha if (err < 0) { 13044b2036eSPrabhakar Kushwaha printf("dpmac_get_counter: DPMAC_CNT_ING_FRAME_DISCARD failed\n"); 13144b2036eSPrabhakar Kushwaha return; 13244b2036eSPrabhakar Kushwaha } 13344b2036eSPrabhakar Kushwaha printf("DPMAC_CNT_ING_FRAME_DISCARD=%lld\n", value); 13444b2036eSPrabhakar Kushwaha 13544b2036eSPrabhakar Kushwaha err = dpmac_get_counter(dflt_mc_io, MC_CMD_NO_FLAGS, 13644b2036eSPrabhakar Kushwaha priv->dpmac_handle, 13744b2036eSPrabhakar Kushwaha DPMAC_CNT_ING_ALIGN_ERR, 13844b2036eSPrabhakar Kushwaha &value); 13944b2036eSPrabhakar Kushwaha if (err < 0) { 14044b2036eSPrabhakar Kushwaha printf("dpmac_get_counter: DPMAC_CNT_ING_ALIGN_ERR failed\n"); 14144b2036eSPrabhakar Kushwaha return; 14244b2036eSPrabhakar Kushwaha } 14344b2036eSPrabhakar Kushwaha printf("DPMAC_CNT_ING_ALIGN_ERR =%lld\n", value); 14444b2036eSPrabhakar Kushwaha 14544b2036eSPrabhakar Kushwaha err = dpmac_get_counter(dflt_mc_io, MC_CMD_NO_FLAGS, 14644b2036eSPrabhakar Kushwaha priv->dpmac_handle, 14744b2036eSPrabhakar Kushwaha DPMAC_CNT_ING_BYTE, 14844b2036eSPrabhakar Kushwaha &value); 14944b2036eSPrabhakar Kushwaha if (err < 0) { 15044b2036eSPrabhakar Kushwaha printf("dpmac_get_counter: DPMAC_CNT_ING_BYTE failed\n"); 15144b2036eSPrabhakar Kushwaha return; 15244b2036eSPrabhakar Kushwaha } 15344b2036eSPrabhakar Kushwaha printf("DPMAC_CNT_ING_BYTE=%lld\n", value); 15444b2036eSPrabhakar Kushwaha 15544b2036eSPrabhakar Kushwaha err = dpmac_get_counter(dflt_mc_io, MC_CMD_NO_FLAGS, 15644b2036eSPrabhakar Kushwaha priv->dpmac_handle, 15744b2036eSPrabhakar Kushwaha DPMAC_CNT_ING_ERR_FRAME, 15844b2036eSPrabhakar Kushwaha &value); 15944b2036eSPrabhakar Kushwaha if (err < 0) { 16044b2036eSPrabhakar Kushwaha printf("dpmac_get_counter: DPMAC_CNT_ING_ERR_FRAME failed\n"); 16144b2036eSPrabhakar Kushwaha return; 16244b2036eSPrabhakar Kushwaha } 16344b2036eSPrabhakar Kushwaha printf("DPMAC_CNT_ING_ERR_FRAME=%lld\n", value); 16444b2036eSPrabhakar Kushwaha 16544b2036eSPrabhakar Kushwaha err = dpmac_get_counter(dflt_mc_io, MC_CMD_NO_FLAGS, 16644b2036eSPrabhakar Kushwaha priv->dpmac_handle, 16744b2036eSPrabhakar Kushwaha DPMAC_CNT_EGR_BYTE , 16844b2036eSPrabhakar Kushwaha &value); 16944b2036eSPrabhakar Kushwaha if (err < 0) { 17044b2036eSPrabhakar Kushwaha printf("dpmac_get_counter: DPMAC_CNT_EGR_BYTE failed\n"); 17144b2036eSPrabhakar Kushwaha return; 17244b2036eSPrabhakar Kushwaha } 17344b2036eSPrabhakar Kushwaha printf("DPMAC_CNT_EGR_BYTE =%lld\n", value); 17444b2036eSPrabhakar Kushwaha 17544b2036eSPrabhakar Kushwaha err = dpmac_get_counter(dflt_mc_io, MC_CMD_NO_FLAGS, 17644b2036eSPrabhakar Kushwaha priv->dpmac_handle, 17744b2036eSPrabhakar Kushwaha DPMAC_CNT_EGR_ERR_FRAME , 17844b2036eSPrabhakar Kushwaha &value); 17944b2036eSPrabhakar Kushwaha if (err < 0) { 18044b2036eSPrabhakar Kushwaha printf("dpmac_get_counter: DPMAC_CNT_EGR_ERR_FRAME failed\n"); 18144b2036eSPrabhakar Kushwaha return; 18244b2036eSPrabhakar Kushwaha } 18344b2036eSPrabhakar Kushwaha printf("DPMAC_CNT_EGR_ERR_FRAME =%lld\n", value); 18444b2036eSPrabhakar Kushwaha } 1855038d3e5SPrabhakar Kushwaha #endif 1865038d3e5SPrabhakar Kushwaha 187c517771aSPrabhakar Kushwaha static void ldpaa_eth_rx(struct ldpaa_eth_priv *priv, 188c517771aSPrabhakar Kushwaha const struct dpaa_fd *fd) 189c517771aSPrabhakar Kushwaha { 190c517771aSPrabhakar Kushwaha u64 fd_addr; 191c517771aSPrabhakar Kushwaha uint16_t fd_offset; 192c517771aSPrabhakar Kushwaha uint32_t fd_length; 193c517771aSPrabhakar Kushwaha struct ldpaa_fas *fas; 194c517771aSPrabhakar Kushwaha uint32_t status, err; 19556c57cf7SPrabhakar Kushwaha u32 timeo = (CONFIG_SYS_HZ * 2) / 1000; 19656c57cf7SPrabhakar Kushwaha u32 time_start; 197c517771aSPrabhakar Kushwaha struct qbman_release_desc releasedesc; 198c517771aSPrabhakar Kushwaha struct qbman_swp *swp = dflt_dpio->sw_portal; 199c517771aSPrabhakar Kushwaha 200c517771aSPrabhakar Kushwaha fd_addr = ldpaa_fd_get_addr(fd); 201c517771aSPrabhakar Kushwaha fd_offset = ldpaa_fd_get_offset(fd); 202c517771aSPrabhakar Kushwaha fd_length = ldpaa_fd_get_len(fd); 203c517771aSPrabhakar Kushwaha 204c517771aSPrabhakar Kushwaha debug("Rx frame:data addr=0x%p size=0x%x\n", (u64 *)fd_addr, fd_length); 205c517771aSPrabhakar Kushwaha 206c517771aSPrabhakar Kushwaha if (fd->simple.frc & LDPAA_FD_FRC_FASV) { 207c517771aSPrabhakar Kushwaha /* Read the frame annotation status word and check for errors */ 208c517771aSPrabhakar Kushwaha fas = (struct ldpaa_fas *) 209c517771aSPrabhakar Kushwaha ((uint8_t *)(fd_addr) + 210c919ab9eSPrabhakar Kushwaha dflt_dpni->buf_layout.private_data_size); 211c517771aSPrabhakar Kushwaha status = le32_to_cpu(fas->status); 212c517771aSPrabhakar Kushwaha if (status & LDPAA_ETH_RX_ERR_MASK) { 213c517771aSPrabhakar Kushwaha printf("Rx frame error(s): 0x%08x\n", 214c517771aSPrabhakar Kushwaha status & LDPAA_ETH_RX_ERR_MASK); 215c517771aSPrabhakar Kushwaha goto error; 216c517771aSPrabhakar Kushwaha } else if (status & LDPAA_ETH_RX_UNSUPP_MASK) { 217c517771aSPrabhakar Kushwaha printf("Unsupported feature in bitmask: 0x%08x\n", 218c517771aSPrabhakar Kushwaha status & LDPAA_ETH_RX_UNSUPP_MASK); 219c517771aSPrabhakar Kushwaha goto error; 220c517771aSPrabhakar Kushwaha } 221c517771aSPrabhakar Kushwaha } 222c517771aSPrabhakar Kushwaha 223c517771aSPrabhakar Kushwaha debug("Rx frame: To Upper layer\n"); 224c517771aSPrabhakar Kushwaha net_process_received_packet((uint8_t *)(fd_addr) + fd_offset, 225c517771aSPrabhakar Kushwaha fd_length); 226c517771aSPrabhakar Kushwaha 227c517771aSPrabhakar Kushwaha error: 2285753b0f1SPrabhakar Kushwaha flush_dcache_range(fd_addr, fd_addr + LDPAA_ETH_RX_BUFFER_SIZE); 229c517771aSPrabhakar Kushwaha qbman_release_desc_clear(&releasedesc); 230c517771aSPrabhakar Kushwaha qbman_release_desc_set_bpid(&releasedesc, dflt_dpbp->dpbp_attr.bpid); 23156c57cf7SPrabhakar Kushwaha time_start = get_timer(0); 232c517771aSPrabhakar Kushwaha do { 233c517771aSPrabhakar Kushwaha /* Release buffer into the QBMAN */ 234c517771aSPrabhakar Kushwaha err = qbman_swp_release(swp, &releasedesc, &fd_addr, 1); 23556c57cf7SPrabhakar Kushwaha } while (get_timer(time_start) < timeo && err == -EBUSY); 23656c57cf7SPrabhakar Kushwaha 23756c57cf7SPrabhakar Kushwaha if (err == -EBUSY) 23856c57cf7SPrabhakar Kushwaha printf("Rx frame: QBMAN buffer release fails\n"); 23956c57cf7SPrabhakar Kushwaha 240c517771aSPrabhakar Kushwaha return; 241c517771aSPrabhakar Kushwaha } 242c517771aSPrabhakar Kushwaha 243c517771aSPrabhakar Kushwaha static int ldpaa_eth_pull_dequeue_rx(struct eth_device *dev) 244c517771aSPrabhakar Kushwaha { 245c517771aSPrabhakar Kushwaha struct ldpaa_eth_priv *priv = (struct ldpaa_eth_priv *)dev->priv; 246c517771aSPrabhakar Kushwaha const struct ldpaa_dq *dq; 247c517771aSPrabhakar Kushwaha const struct dpaa_fd *fd; 248b4c3a35dSPrabhakar Kushwaha int i = 5, err = 0, status; 249b4c3a35dSPrabhakar Kushwaha u32 timeo = (CONFIG_SYS_HZ * 2) / 1000; 250b4c3a35dSPrabhakar Kushwaha u32 time_start; 251c517771aSPrabhakar Kushwaha static struct qbman_pull_desc pulldesc; 252c517771aSPrabhakar Kushwaha struct qbman_swp *swp = dflt_dpio->sw_portal; 253c517771aSPrabhakar Kushwaha 2545753b0f1SPrabhakar Kushwaha while (--i) { 255c517771aSPrabhakar Kushwaha qbman_pull_desc_clear(&pulldesc); 256c517771aSPrabhakar Kushwaha qbman_pull_desc_set_numframes(&pulldesc, 1); 257c517771aSPrabhakar Kushwaha qbman_pull_desc_set_fq(&pulldesc, priv->rx_dflt_fqid); 258c517771aSPrabhakar Kushwaha 259c517771aSPrabhakar Kushwaha err = qbman_swp_pull(swp, &pulldesc); 260c517771aSPrabhakar Kushwaha if (err < 0) { 261c517771aSPrabhakar Kushwaha printf("Dequeue frames error:0x%08x\n", err); 262c517771aSPrabhakar Kushwaha continue; 263c517771aSPrabhakar Kushwaha } 264c517771aSPrabhakar Kushwaha 265b4c3a35dSPrabhakar Kushwaha time_start = get_timer(0); 2665753b0f1SPrabhakar Kushwaha 267b4c3a35dSPrabhakar Kushwaha do { 268b4c3a35dSPrabhakar Kushwaha dq = qbman_swp_dqrr_next(swp); 269b4c3a35dSPrabhakar Kushwaha } while (get_timer(time_start) < timeo && !dq); 2705753b0f1SPrabhakar Kushwaha 271c517771aSPrabhakar Kushwaha if (dq) { 272c517771aSPrabhakar Kushwaha /* Check for valid frame. If not sent a consume 273c517771aSPrabhakar Kushwaha * confirmation to QBMAN otherwise give it to NADK 274c517771aSPrabhakar Kushwaha * application and then send consume confirmation to 275c517771aSPrabhakar Kushwaha * QBMAN. 276c517771aSPrabhakar Kushwaha */ 277c517771aSPrabhakar Kushwaha status = (uint8_t)ldpaa_dq_flags(dq); 278c517771aSPrabhakar Kushwaha if ((status & LDPAA_DQ_STAT_VALIDFRAME) == 0) { 279c517771aSPrabhakar Kushwaha debug("Dequeue RX frames:"); 280c517771aSPrabhakar Kushwaha debug("No frame delivered\n"); 281c517771aSPrabhakar Kushwaha 282c517771aSPrabhakar Kushwaha qbman_swp_dqrr_consume(swp, dq); 2830c7c87a4SPrabhakar Kushwaha continue; 284c517771aSPrabhakar Kushwaha } 285c517771aSPrabhakar Kushwaha 286c517771aSPrabhakar Kushwaha fd = ldpaa_dq_fd(dq); 287c517771aSPrabhakar Kushwaha 288c517771aSPrabhakar Kushwaha /* Obtain FD and process it */ 289c517771aSPrabhakar Kushwaha ldpaa_eth_rx(priv, fd); 290c517771aSPrabhakar Kushwaha qbman_swp_dqrr_consume(swp, dq); 291c517771aSPrabhakar Kushwaha break; 292b4c3a35dSPrabhakar Kushwaha } else { 293b4c3a35dSPrabhakar Kushwaha err = -ENODATA; 294b4c3a35dSPrabhakar Kushwaha debug("No DQRR entries\n"); 295b4c3a35dSPrabhakar Kushwaha break; 296c517771aSPrabhakar Kushwaha } 297c517771aSPrabhakar Kushwaha } 298c517771aSPrabhakar Kushwaha 299c517771aSPrabhakar Kushwaha return err; 300c517771aSPrabhakar Kushwaha } 301c517771aSPrabhakar Kushwaha 302c517771aSPrabhakar Kushwaha static int ldpaa_eth_tx(struct eth_device *net_dev, void *buf, int len) 303c517771aSPrabhakar Kushwaha { 304c517771aSPrabhakar Kushwaha struct ldpaa_eth_priv *priv = (struct ldpaa_eth_priv *)net_dev->priv; 305c517771aSPrabhakar Kushwaha struct dpaa_fd fd; 306c517771aSPrabhakar Kushwaha u64 buffer_start; 307c517771aSPrabhakar Kushwaha int data_offset, err; 308e48df52bSPrabhakar Kushwaha u32 timeo = (CONFIG_SYS_HZ * 10) / 1000; 309e48df52bSPrabhakar Kushwaha u32 time_start; 310c517771aSPrabhakar Kushwaha struct qbman_swp *swp = dflt_dpio->sw_portal; 311c517771aSPrabhakar Kushwaha struct qbman_eq_desc ed; 312e48df52bSPrabhakar Kushwaha struct qbman_release_desc releasedesc; 313c517771aSPrabhakar Kushwaha 314c517771aSPrabhakar Kushwaha /* Setup the FD fields */ 315c517771aSPrabhakar Kushwaha memset(&fd, 0, sizeof(fd)); 316c517771aSPrabhakar Kushwaha 317c517771aSPrabhakar Kushwaha data_offset = priv->tx_data_offset; 318c517771aSPrabhakar Kushwaha 319c517771aSPrabhakar Kushwaha do { 320c517771aSPrabhakar Kushwaha err = qbman_swp_acquire(dflt_dpio->sw_portal, 321c517771aSPrabhakar Kushwaha dflt_dpbp->dpbp_attr.bpid, 322c517771aSPrabhakar Kushwaha &buffer_start, 1); 323c517771aSPrabhakar Kushwaha } while (err == -EBUSY); 324c517771aSPrabhakar Kushwaha 3255e9445daSAshish Kumar if (err <= 0) { 326c517771aSPrabhakar Kushwaha printf("qbman_swp_acquire() failed\n"); 327c517771aSPrabhakar Kushwaha return -ENOMEM; 328c517771aSPrabhakar Kushwaha } 329c517771aSPrabhakar Kushwaha 330c517771aSPrabhakar Kushwaha debug("TX data: malloc buffer start=0x%p\n", (u64 *)buffer_start); 331c517771aSPrabhakar Kushwaha 332c517771aSPrabhakar Kushwaha memcpy(((uint8_t *)(buffer_start) + data_offset), buf, len); 333c517771aSPrabhakar Kushwaha 3345753b0f1SPrabhakar Kushwaha flush_dcache_range(buffer_start, buffer_start + 3355753b0f1SPrabhakar Kushwaha LDPAA_ETH_RX_BUFFER_SIZE); 336c517771aSPrabhakar Kushwaha 337c517771aSPrabhakar Kushwaha ldpaa_fd_set_addr(&fd, (u64)buffer_start); 338c517771aSPrabhakar Kushwaha ldpaa_fd_set_offset(&fd, (uint16_t)(data_offset)); 339c517771aSPrabhakar Kushwaha ldpaa_fd_set_bpid(&fd, dflt_dpbp->dpbp_attr.bpid); 340c517771aSPrabhakar Kushwaha ldpaa_fd_set_len(&fd, len); 341c517771aSPrabhakar Kushwaha 342c517771aSPrabhakar Kushwaha fd.simple.ctrl = LDPAA_FD_CTRL_ASAL | LDPAA_FD_CTRL_PTA | 343c517771aSPrabhakar Kushwaha LDPAA_FD_CTRL_PTV1; 344c517771aSPrabhakar Kushwaha 345c517771aSPrabhakar Kushwaha qbman_eq_desc_clear(&ed); 346c517771aSPrabhakar Kushwaha qbman_eq_desc_set_no_orp(&ed, 0); 347c517771aSPrabhakar Kushwaha qbman_eq_desc_set_qd(&ed, priv->tx_qdid, priv->tx_flow_id, 0); 348e48df52bSPrabhakar Kushwaha 349e48df52bSPrabhakar Kushwaha time_start = get_timer(0); 350e48df52bSPrabhakar Kushwaha 351e48df52bSPrabhakar Kushwaha while (get_timer(time_start) < timeo) { 352e48df52bSPrabhakar Kushwaha err = qbman_swp_enqueue(swp, &ed, 353e48df52bSPrabhakar Kushwaha (const struct qbman_fd *)(&fd)); 354e48df52bSPrabhakar Kushwaha if (err != -EBUSY) 355e48df52bSPrabhakar Kushwaha break; 356e48df52bSPrabhakar Kushwaha } 357e48df52bSPrabhakar Kushwaha 358e48df52bSPrabhakar Kushwaha if (err < 0) { 359c517771aSPrabhakar Kushwaha printf("error enqueueing Tx frame\n"); 360e48df52bSPrabhakar Kushwaha goto error; 361e48df52bSPrabhakar Kushwaha } 362c517771aSPrabhakar Kushwaha 363c517771aSPrabhakar Kushwaha return err; 364e48df52bSPrabhakar Kushwaha 365e48df52bSPrabhakar Kushwaha error: 366e48df52bSPrabhakar Kushwaha qbman_release_desc_clear(&releasedesc); 367e48df52bSPrabhakar Kushwaha qbman_release_desc_set_bpid(&releasedesc, dflt_dpbp->dpbp_attr.bpid); 368e48df52bSPrabhakar Kushwaha time_start = get_timer(0); 369e48df52bSPrabhakar Kushwaha do { 370e48df52bSPrabhakar Kushwaha /* Release buffer into the QBMAN */ 371e48df52bSPrabhakar Kushwaha err = qbman_swp_release(swp, &releasedesc, &buffer_start, 1); 372e48df52bSPrabhakar Kushwaha } while (get_timer(time_start) < timeo && err == -EBUSY); 373e48df52bSPrabhakar Kushwaha 374e48df52bSPrabhakar Kushwaha if (err == -EBUSY) 375e48df52bSPrabhakar Kushwaha printf("TX data: QBMAN buffer release fails\n"); 376e48df52bSPrabhakar Kushwaha 377e48df52bSPrabhakar Kushwaha return err; 378c517771aSPrabhakar Kushwaha } 379c517771aSPrabhakar Kushwaha 380c517771aSPrabhakar Kushwaha static int ldpaa_eth_open(struct eth_device *net_dev, bd_t *bd) 381c517771aSPrabhakar Kushwaha { 382c517771aSPrabhakar Kushwaha struct ldpaa_eth_priv *priv = (struct ldpaa_eth_priv *)net_dev->priv; 383c919ab9eSPrabhakar Kushwaha struct dpmac_link_state dpmac_link_state = { 0 }; 3845038d3e5SPrabhakar Kushwaha #ifdef DEBUG 3855038d3e5SPrabhakar Kushwaha struct dpni_link_state link_state; 3865038d3e5SPrabhakar Kushwaha #endif 3876c2b520aSPrabhakar Kushwaha int err = 0; 3886c2b520aSPrabhakar Kushwaha struct mii_dev *bus; 3896c2b520aSPrabhakar Kushwaha phy_interface_t enet_if; 3902557c5a9SYogesh Gaur struct dpni_queue d_queue; 391c517771aSPrabhakar Kushwaha 392c517771aSPrabhakar Kushwaha if (net_dev->state == ETH_STATE_ACTIVE) 393c517771aSPrabhakar Kushwaha return 0; 394c517771aSPrabhakar Kushwaha 395c919ab9eSPrabhakar Kushwaha if (get_mc_boot_status() != 0) { 396c919ab9eSPrabhakar Kushwaha printf("ERROR (MC is not booted)\n"); 397c919ab9eSPrabhakar Kushwaha return -ENODEV; 398c919ab9eSPrabhakar Kushwaha } 399c919ab9eSPrabhakar Kushwaha 400c919ab9eSPrabhakar Kushwaha if (get_dpl_apply_status() == 0) { 401c919ab9eSPrabhakar Kushwaha printf("ERROR (DPL is deployed. No device available)\n"); 402c919ab9eSPrabhakar Kushwaha return -ENODEV; 403c919ab9eSPrabhakar Kushwaha } 4046c2b520aSPrabhakar Kushwaha 405c919ab9eSPrabhakar Kushwaha /* DPMAC initialization */ 406c919ab9eSPrabhakar Kushwaha err = ldpaa_dpmac_setup(priv); 407c919ab9eSPrabhakar Kushwaha if (err < 0) 408c919ab9eSPrabhakar Kushwaha goto err_dpmac_setup; 409c919ab9eSPrabhakar Kushwaha 4106c2b520aSPrabhakar Kushwaha #ifdef CONFIG_PHYLIB 411b7401d09SPriyanka Jain if (priv->phydev) { 4126c2b520aSPrabhakar Kushwaha err = phy_startup(priv->phydev); 4136c2b520aSPrabhakar Kushwaha if (err) { 4146c2b520aSPrabhakar Kushwaha printf("%s: Could not initialize\n", 4156c2b520aSPrabhakar Kushwaha priv->phydev->dev->name); 416*afd6c6b4SPankaj Bansal goto err_dpmac_bind; 4176c2b520aSPrabhakar Kushwaha } 418b7401d09SPriyanka Jain } 4196c2b520aSPrabhakar Kushwaha #else 4206c2b520aSPrabhakar Kushwaha priv->phydev = (struct phy_device *)malloc(sizeof(struct phy_device)); 4216c2b520aSPrabhakar Kushwaha memset(priv->phydev, 0, sizeof(struct phy_device)); 4226c2b520aSPrabhakar Kushwaha 4236c2b520aSPrabhakar Kushwaha priv->phydev->speed = SPEED_1000; 4246c2b520aSPrabhakar Kushwaha priv->phydev->link = 1; 4256c2b520aSPrabhakar Kushwaha priv->phydev->duplex = DUPLEX_FULL; 4266c2b520aSPrabhakar Kushwaha #endif 4276c2b520aSPrabhakar Kushwaha 4286c2b520aSPrabhakar Kushwaha bus = wriop_get_mdio(priv->dpmac_id); 4296c2b520aSPrabhakar Kushwaha enet_if = wriop_get_enet_if(priv->dpmac_id); 4306c2b520aSPrabhakar Kushwaha if ((bus == NULL) && 4316c2b520aSPrabhakar Kushwaha (enet_if == PHY_INTERFACE_MODE_XGMII)) { 4326c2b520aSPrabhakar Kushwaha priv->phydev = (struct phy_device *) 4336c2b520aSPrabhakar Kushwaha malloc(sizeof(struct phy_device)); 4346c2b520aSPrabhakar Kushwaha memset(priv->phydev, 0, sizeof(struct phy_device)); 4356c2b520aSPrabhakar Kushwaha 4366c2b520aSPrabhakar Kushwaha priv->phydev->speed = SPEED_10000; 4376c2b520aSPrabhakar Kushwaha priv->phydev->link = 1; 4386c2b520aSPrabhakar Kushwaha priv->phydev->duplex = DUPLEX_FULL; 4396c2b520aSPrabhakar Kushwaha } 4406c2b520aSPrabhakar Kushwaha 4416c2b520aSPrabhakar Kushwaha if (!priv->phydev->link) { 4426c2b520aSPrabhakar Kushwaha printf("%s: No link.\n", priv->phydev->dev->name); 4436c2b520aSPrabhakar Kushwaha err = -1; 444*afd6c6b4SPankaj Bansal goto err_dpmac_bind; 4456c2b520aSPrabhakar Kushwaha } 4466c2b520aSPrabhakar Kushwaha 447c919ab9eSPrabhakar Kushwaha /* DPMAC binding DPNI */ 448c919ab9eSPrabhakar Kushwaha err = ldpaa_dpmac_bind(priv); 449c919ab9eSPrabhakar Kushwaha if (err) 450*afd6c6b4SPankaj Bansal goto err_dpmac_bind; 451c919ab9eSPrabhakar Kushwaha 452c517771aSPrabhakar Kushwaha /* DPNI initialization */ 453c517771aSPrabhakar Kushwaha err = ldpaa_dpni_setup(priv); 454c517771aSPrabhakar Kushwaha if (err < 0) 455c517771aSPrabhakar Kushwaha goto err_dpni_setup; 456c517771aSPrabhakar Kushwaha 457c517771aSPrabhakar Kushwaha err = ldpaa_dpbp_setup(); 458c517771aSPrabhakar Kushwaha if (err < 0) 459c517771aSPrabhakar Kushwaha goto err_dpbp_setup; 460c517771aSPrabhakar Kushwaha 461c517771aSPrabhakar Kushwaha /* DPNI binding DPBP */ 462c517771aSPrabhakar Kushwaha err = ldpaa_dpni_bind(priv); 463c517771aSPrabhakar Kushwaha if (err) 464c919ab9eSPrabhakar Kushwaha goto err_dpni_bind; 465c517771aSPrabhakar Kushwaha 4667b2edb8bSPrabhakar Kushwaha err = dpni_add_mac_addr(dflt_mc_io, MC_CMD_NO_FLAGS, 467c919ab9eSPrabhakar Kushwaha dflt_dpni->dpni_handle, net_dev->enetaddr); 468c517771aSPrabhakar Kushwaha if (err) { 4697b2edb8bSPrabhakar Kushwaha printf("dpni_add_mac_addr() failed\n"); 470c517771aSPrabhakar Kushwaha return err; 471c517771aSPrabhakar Kushwaha } 472c517771aSPrabhakar Kushwaha 473c919ab9eSPrabhakar Kushwaha err = dpni_enable(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpni->dpni_handle); 474c517771aSPrabhakar Kushwaha if (err < 0) { 475c517771aSPrabhakar Kushwaha printf("dpni_enable() failed\n"); 476c517771aSPrabhakar Kushwaha return err; 477c517771aSPrabhakar Kushwaha } 478c517771aSPrabhakar Kushwaha 4796c2b520aSPrabhakar Kushwaha dpmac_link_state.rate = priv->phydev->speed; 4806c2b520aSPrabhakar Kushwaha 4816c2b520aSPrabhakar Kushwaha if (priv->phydev->autoneg == AUTONEG_DISABLE) 4826c2b520aSPrabhakar Kushwaha dpmac_link_state.options &= ~DPMAC_LINK_OPT_AUTONEG; 4836c2b520aSPrabhakar Kushwaha else 4846c2b520aSPrabhakar Kushwaha dpmac_link_state.options |= DPMAC_LINK_OPT_AUTONEG; 4856c2b520aSPrabhakar Kushwaha 4866c2b520aSPrabhakar Kushwaha if (priv->phydev->duplex == DUPLEX_HALF) 4876c2b520aSPrabhakar Kushwaha dpmac_link_state.options |= DPMAC_LINK_OPT_HALF_DUPLEX; 4886c2b520aSPrabhakar Kushwaha 4896c2b520aSPrabhakar Kushwaha dpmac_link_state.up = priv->phydev->link; 4906c2b520aSPrabhakar Kushwaha 491c919ab9eSPrabhakar Kushwaha err = dpmac_set_link_state(dflt_mc_io, MC_CMD_NO_FLAGS, 492c919ab9eSPrabhakar Kushwaha priv->dpmac_handle, &dpmac_link_state); 493c919ab9eSPrabhakar Kushwaha if (err < 0) { 494c919ab9eSPrabhakar Kushwaha printf("dpmac_set_link_state() failed\n"); 495c919ab9eSPrabhakar Kushwaha return err; 496c919ab9eSPrabhakar Kushwaha } 4975038d3e5SPrabhakar Kushwaha 4985038d3e5SPrabhakar Kushwaha #ifdef DEBUG 4992557c5a9SYogesh Gaur printf("DPMAC link status: %d - ", dpmac_link_state.up); 5002557c5a9SYogesh Gaur dpmac_link_state.up == 0 ? printf("down\n") : 5012557c5a9SYogesh Gaur dpmac_link_state.up == 1 ? printf("up\n") : printf("error state\n"); 5022557c5a9SYogesh Gaur 5035038d3e5SPrabhakar Kushwaha err = dpni_get_link_state(dflt_mc_io, MC_CMD_NO_FLAGS, 5045038d3e5SPrabhakar Kushwaha dflt_dpni->dpni_handle, &link_state); 5055038d3e5SPrabhakar Kushwaha if (err < 0) { 5065038d3e5SPrabhakar Kushwaha printf("dpni_get_link_state() failed\n"); 5075038d3e5SPrabhakar Kushwaha return err; 5085038d3e5SPrabhakar Kushwaha } 5095038d3e5SPrabhakar Kushwaha 5102557c5a9SYogesh Gaur printf("DPNI link status: %d - ", link_state.up); 5115038d3e5SPrabhakar Kushwaha link_state.up == 0 ? printf("down\n") : 5125038d3e5SPrabhakar Kushwaha link_state.up == 1 ? printf("up\n") : printf("error state\n"); 5135038d3e5SPrabhakar Kushwaha #endif 5145038d3e5SPrabhakar Kushwaha 5152557c5a9SYogesh Gaur memset(&d_queue, 0, sizeof(struct dpni_queue)); 5162557c5a9SYogesh Gaur err = dpni_get_queue(dflt_mc_io, MC_CMD_NO_FLAGS, 5172557c5a9SYogesh Gaur dflt_dpni->dpni_handle, DPNI_QUEUE_RX, 5182557c5a9SYogesh Gaur 0, 0, &d_queue); 519c517771aSPrabhakar Kushwaha if (err) { 5202557c5a9SYogesh Gaur printf("dpni_get_queue failed\n"); 5212557c5a9SYogesh Gaur goto err_get_queue; 522c517771aSPrabhakar Kushwaha } 523c517771aSPrabhakar Kushwaha 5242557c5a9SYogesh Gaur priv->rx_dflt_fqid = d_queue.fqid; 525c517771aSPrabhakar Kushwaha 526c919ab9eSPrabhakar Kushwaha err = dpni_get_qdid(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpni->dpni_handle, 52787457d11SPrabhakar Kushwaha &priv->tx_qdid); 528c517771aSPrabhakar Kushwaha if (err) { 529c517771aSPrabhakar Kushwaha printf("dpni_get_qdid() failed\n"); 530c517771aSPrabhakar Kushwaha goto err_qdid; 531c517771aSPrabhakar Kushwaha } 532c517771aSPrabhakar Kushwaha 5336c2b520aSPrabhakar Kushwaha return priv->phydev->link; 534c517771aSPrabhakar Kushwaha 535c517771aSPrabhakar Kushwaha err_qdid: 5362557c5a9SYogesh Gaur err_get_queue: 537c919ab9eSPrabhakar Kushwaha dpni_disable(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpni->dpni_handle); 538c919ab9eSPrabhakar Kushwaha err_dpni_bind: 539c517771aSPrabhakar Kushwaha ldpaa_dpbp_free(); 540c517771aSPrabhakar Kushwaha err_dpbp_setup: 541c919ab9eSPrabhakar Kushwaha dpni_close(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpni->dpni_handle); 542c517771aSPrabhakar Kushwaha err_dpni_setup: 543*afd6c6b4SPankaj Bansal err_dpmac_bind: 5442557c5a9SYogesh Gaur dpmac_close(dflt_mc_io, MC_CMD_NO_FLAGS, priv->dpmac_handle); 5452557c5a9SYogesh Gaur dpmac_destroy(dflt_mc_io, 5462557c5a9SYogesh Gaur dflt_dprc_handle, 5472557c5a9SYogesh Gaur MC_CMD_NO_FLAGS, priv->dpmac_id); 548c919ab9eSPrabhakar Kushwaha err_dpmac_setup: 549c517771aSPrabhakar Kushwaha return err; 550c517771aSPrabhakar Kushwaha } 551c517771aSPrabhakar Kushwaha 552c517771aSPrabhakar Kushwaha static void ldpaa_eth_stop(struct eth_device *net_dev) 553c517771aSPrabhakar Kushwaha { 554c517771aSPrabhakar Kushwaha struct ldpaa_eth_priv *priv = (struct ldpaa_eth_priv *)net_dev->priv; 555c517771aSPrabhakar Kushwaha int err = 0; 5566c2b520aSPrabhakar Kushwaha #ifdef CONFIG_PHYLIB 5576c2b520aSPrabhakar Kushwaha struct mii_dev *bus = wriop_get_mdio(priv->dpmac_id); 5586c2b520aSPrabhakar Kushwaha #endif 559c517771aSPrabhakar Kushwaha 5605753b0f1SPrabhakar Kushwaha if ((net_dev->state == ETH_STATE_PASSIVE) || 5615753b0f1SPrabhakar Kushwaha (net_dev->state == ETH_STATE_INIT)) 562c517771aSPrabhakar Kushwaha return; 563c919ab9eSPrabhakar Kushwaha 5645038d3e5SPrabhakar Kushwaha #ifdef DEBUG 5655038d3e5SPrabhakar Kushwaha ldpaa_eth_get_dpni_counter(); 56644b2036eSPrabhakar Kushwaha ldpaa_eth_get_dpmac_counter(net_dev); 5675038d3e5SPrabhakar Kushwaha #endif 5685038d3e5SPrabhakar Kushwaha 569c919ab9eSPrabhakar Kushwaha err = dprc_disconnect(dflt_mc_io, MC_CMD_NO_FLAGS, 570c919ab9eSPrabhakar Kushwaha dflt_dprc_handle, &dpmac_endpoint); 571c919ab9eSPrabhakar Kushwaha if (err < 0) 572c919ab9eSPrabhakar Kushwaha printf("dprc_disconnect() failed dpmac_endpoint\n"); 573c919ab9eSPrabhakar Kushwaha 5742557c5a9SYogesh Gaur err = dpmac_close(dflt_mc_io, MC_CMD_NO_FLAGS, priv->dpmac_handle); 5752557c5a9SYogesh Gaur if (err < 0) 5762557c5a9SYogesh Gaur printf("dpmac_close() failed\n"); 5772557c5a9SYogesh Gaur 5782557c5a9SYogesh Gaur err = dpmac_destroy(dflt_mc_io, 5792557c5a9SYogesh Gaur dflt_dprc_handle, 5802557c5a9SYogesh Gaur MC_CMD_NO_FLAGS, 5812557c5a9SYogesh Gaur priv->dpmac_id); 582c919ab9eSPrabhakar Kushwaha if (err < 0) 583c919ab9eSPrabhakar Kushwaha printf("dpmac_destroy() failed\n"); 584c919ab9eSPrabhakar Kushwaha 585c517771aSPrabhakar Kushwaha /* Stop Tx and Rx traffic */ 586c919ab9eSPrabhakar Kushwaha err = dpni_disable(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpni->dpni_handle); 587c517771aSPrabhakar Kushwaha if (err < 0) 588c517771aSPrabhakar Kushwaha printf("dpni_disable() failed\n"); 589c517771aSPrabhakar Kushwaha 590c517771aSPrabhakar Kushwaha #ifdef CONFIG_PHYLIB 5916c2b520aSPrabhakar Kushwaha if (priv->phydev && bus != NULL) 592c517771aSPrabhakar Kushwaha phy_shutdown(priv->phydev); 593a5fe87e8SPrabhakar Kushwaha else { 5946c2b520aSPrabhakar Kushwaha free(priv->phydev); 595a5fe87e8SPrabhakar Kushwaha priv->phydev = NULL; 596a5fe87e8SPrabhakar Kushwaha } 597c517771aSPrabhakar Kushwaha #endif 598c517771aSPrabhakar Kushwaha 5992557c5a9SYogesh Gaur /* Free DPBP handle and reset. */ 600c517771aSPrabhakar Kushwaha ldpaa_dpbp_free(); 6012557c5a9SYogesh Gaur 602c919ab9eSPrabhakar Kushwaha dpni_reset(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpni->dpni_handle); 6032557c5a9SYogesh Gaur if (err < 0) 6042557c5a9SYogesh Gaur printf("dpni_reset() failed\n"); 6052557c5a9SYogesh Gaur 606c919ab9eSPrabhakar Kushwaha dpni_close(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpni->dpni_handle); 6072557c5a9SYogesh Gaur if (err < 0) 6082557c5a9SYogesh Gaur printf("dpni_close() failed\n"); 609c517771aSPrabhakar Kushwaha } 610c517771aSPrabhakar Kushwaha 611c517771aSPrabhakar Kushwaha static void ldpaa_dpbp_drain_cnt(int count) 612c517771aSPrabhakar Kushwaha { 613c517771aSPrabhakar Kushwaha uint64_t buf_array[7]; 614c517771aSPrabhakar Kushwaha void *addr; 615c517771aSPrabhakar Kushwaha int ret, i; 616c517771aSPrabhakar Kushwaha 617c517771aSPrabhakar Kushwaha BUG_ON(count > 7); 618c517771aSPrabhakar Kushwaha 619c517771aSPrabhakar Kushwaha do { 620c517771aSPrabhakar Kushwaha ret = qbman_swp_acquire(dflt_dpio->sw_portal, 621c517771aSPrabhakar Kushwaha dflt_dpbp->dpbp_attr.bpid, 622c517771aSPrabhakar Kushwaha buf_array, count); 623c517771aSPrabhakar Kushwaha if (ret < 0) { 624c517771aSPrabhakar Kushwaha printf("qbman_swp_acquire() failed\n"); 625c517771aSPrabhakar Kushwaha return; 626c517771aSPrabhakar Kushwaha } 627c517771aSPrabhakar Kushwaha for (i = 0; i < ret; i++) { 628c517771aSPrabhakar Kushwaha addr = (void *)buf_array[i]; 629c517771aSPrabhakar Kushwaha debug("Free: buffer addr =0x%p\n", addr); 630c517771aSPrabhakar Kushwaha free(addr); 631c517771aSPrabhakar Kushwaha } 632c517771aSPrabhakar Kushwaha } while (ret); 633c517771aSPrabhakar Kushwaha } 634c517771aSPrabhakar Kushwaha 635c517771aSPrabhakar Kushwaha static void ldpaa_dpbp_drain(void) 636c517771aSPrabhakar Kushwaha { 637c517771aSPrabhakar Kushwaha int i; 638c517771aSPrabhakar Kushwaha for (i = 0; i < LDPAA_ETH_NUM_BUFS; i += 7) 639c517771aSPrabhakar Kushwaha ldpaa_dpbp_drain_cnt(7); 640c517771aSPrabhakar Kushwaha } 641c517771aSPrabhakar Kushwaha 642c517771aSPrabhakar Kushwaha static int ldpaa_bp_add_7(uint16_t bpid) 643c517771aSPrabhakar Kushwaha { 644c517771aSPrabhakar Kushwaha uint64_t buf_array[7]; 645c517771aSPrabhakar Kushwaha u8 *addr; 646c517771aSPrabhakar Kushwaha int i; 647c517771aSPrabhakar Kushwaha struct qbman_release_desc rd; 648c517771aSPrabhakar Kushwaha 649c517771aSPrabhakar Kushwaha for (i = 0; i < 7; i++) { 65014480454SPrabhakar Kushwaha addr = memalign(LDPAA_ETH_BUF_ALIGN, LDPAA_ETH_RX_BUFFER_SIZE); 651c517771aSPrabhakar Kushwaha if (!addr) { 652c517771aSPrabhakar Kushwaha printf("addr allocation failed\n"); 653c517771aSPrabhakar Kushwaha goto err_alloc; 654c517771aSPrabhakar Kushwaha } 655c517771aSPrabhakar Kushwaha memset(addr, 0x00, LDPAA_ETH_RX_BUFFER_SIZE); 6565753b0f1SPrabhakar Kushwaha flush_dcache_range((u64)addr, 6575753b0f1SPrabhakar Kushwaha (u64)(addr + LDPAA_ETH_RX_BUFFER_SIZE)); 658c517771aSPrabhakar Kushwaha 659c517771aSPrabhakar Kushwaha buf_array[i] = (uint64_t)addr; 660c517771aSPrabhakar Kushwaha debug("Release: buffer addr =0x%p\n", addr); 661c517771aSPrabhakar Kushwaha } 662c517771aSPrabhakar Kushwaha 663c517771aSPrabhakar Kushwaha release_bufs: 664c517771aSPrabhakar Kushwaha /* In case the portal is busy, retry until successful. 665c517771aSPrabhakar Kushwaha * This function is guaranteed to succeed in a reasonable amount 666c517771aSPrabhakar Kushwaha * of time. 667c517771aSPrabhakar Kushwaha */ 668c517771aSPrabhakar Kushwaha 669c517771aSPrabhakar Kushwaha do { 670c517771aSPrabhakar Kushwaha mdelay(1); 671c517771aSPrabhakar Kushwaha qbman_release_desc_clear(&rd); 672c517771aSPrabhakar Kushwaha qbman_release_desc_set_bpid(&rd, bpid); 673c517771aSPrabhakar Kushwaha } while (qbman_swp_release(dflt_dpio->sw_portal, &rd, buf_array, i)); 674c517771aSPrabhakar Kushwaha 675c517771aSPrabhakar Kushwaha return i; 676c517771aSPrabhakar Kushwaha 677c517771aSPrabhakar Kushwaha err_alloc: 678c517771aSPrabhakar Kushwaha if (i) 679c517771aSPrabhakar Kushwaha goto release_bufs; 680c517771aSPrabhakar Kushwaha 681c517771aSPrabhakar Kushwaha return 0; 682c517771aSPrabhakar Kushwaha } 683c517771aSPrabhakar Kushwaha 684c517771aSPrabhakar Kushwaha static int ldpaa_dpbp_seed(uint16_t bpid) 685c517771aSPrabhakar Kushwaha { 686c517771aSPrabhakar Kushwaha int i; 687c517771aSPrabhakar Kushwaha int count; 688c517771aSPrabhakar Kushwaha 689c517771aSPrabhakar Kushwaha for (i = 0; i < LDPAA_ETH_NUM_BUFS; i += 7) { 690c517771aSPrabhakar Kushwaha count = ldpaa_bp_add_7(bpid); 691c517771aSPrabhakar Kushwaha if (count < 7) 692c517771aSPrabhakar Kushwaha printf("Buffer Seed= %d\n", count); 693c517771aSPrabhakar Kushwaha } 694c517771aSPrabhakar Kushwaha 695c517771aSPrabhakar Kushwaha return 0; 696c517771aSPrabhakar Kushwaha } 697c517771aSPrabhakar Kushwaha 698c517771aSPrabhakar Kushwaha static int ldpaa_dpbp_setup(void) 699c517771aSPrabhakar Kushwaha { 700c517771aSPrabhakar Kushwaha int err; 701c517771aSPrabhakar Kushwaha 70287457d11SPrabhakar Kushwaha err = dpbp_open(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpbp->dpbp_attr.id, 703c517771aSPrabhakar Kushwaha &dflt_dpbp->dpbp_handle); 704c517771aSPrabhakar Kushwaha if (err) { 705c517771aSPrabhakar Kushwaha printf("dpbp_open() failed\n"); 706c517771aSPrabhakar Kushwaha goto err_open; 707c517771aSPrabhakar Kushwaha } 708c517771aSPrabhakar Kushwaha 70987457d11SPrabhakar Kushwaha err = dpbp_enable(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpbp->dpbp_handle); 710c517771aSPrabhakar Kushwaha if (err) { 711c517771aSPrabhakar Kushwaha printf("dpbp_enable() failed\n"); 712c517771aSPrabhakar Kushwaha goto err_enable; 713c517771aSPrabhakar Kushwaha } 714c517771aSPrabhakar Kushwaha 71587457d11SPrabhakar Kushwaha err = dpbp_get_attributes(dflt_mc_io, MC_CMD_NO_FLAGS, 71687457d11SPrabhakar Kushwaha dflt_dpbp->dpbp_handle, 717c517771aSPrabhakar Kushwaha &dflt_dpbp->dpbp_attr); 718c517771aSPrabhakar Kushwaha if (err) { 719c517771aSPrabhakar Kushwaha printf("dpbp_get_attributes() failed\n"); 720c517771aSPrabhakar Kushwaha goto err_get_attr; 721c517771aSPrabhakar Kushwaha } 722c517771aSPrabhakar Kushwaha 723c517771aSPrabhakar Kushwaha err = ldpaa_dpbp_seed(dflt_dpbp->dpbp_attr.bpid); 7242557c5a9SYogesh Gaur 725c517771aSPrabhakar Kushwaha if (err) { 726c517771aSPrabhakar Kushwaha printf("Buffer seeding failed for DPBP %d (bpid=%d)\n", 727c517771aSPrabhakar Kushwaha dflt_dpbp->dpbp_attr.id, dflt_dpbp->dpbp_attr.bpid); 728c517771aSPrabhakar Kushwaha goto err_seed; 729c517771aSPrabhakar Kushwaha } 730c517771aSPrabhakar Kushwaha 731c517771aSPrabhakar Kushwaha return 0; 732c517771aSPrabhakar Kushwaha 733c517771aSPrabhakar Kushwaha err_seed: 734c517771aSPrabhakar Kushwaha err_get_attr: 73587457d11SPrabhakar Kushwaha dpbp_disable(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpbp->dpbp_handle); 736c517771aSPrabhakar Kushwaha err_enable: 73787457d11SPrabhakar Kushwaha dpbp_close(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpbp->dpbp_handle); 738c517771aSPrabhakar Kushwaha err_open: 739c517771aSPrabhakar Kushwaha return err; 740c517771aSPrabhakar Kushwaha } 741c517771aSPrabhakar Kushwaha 742c517771aSPrabhakar Kushwaha static void ldpaa_dpbp_free(void) 743c517771aSPrabhakar Kushwaha { 744c517771aSPrabhakar Kushwaha ldpaa_dpbp_drain(); 74587457d11SPrabhakar Kushwaha dpbp_disable(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpbp->dpbp_handle); 74687457d11SPrabhakar Kushwaha dpbp_reset(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpbp->dpbp_handle); 74787457d11SPrabhakar Kushwaha dpbp_close(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpbp->dpbp_handle); 748c517771aSPrabhakar Kushwaha } 749c517771aSPrabhakar Kushwaha 7509a696f56SPrabhakar Kushwaha static int ldpaa_dpmac_version_check(struct fsl_mc_io *mc_io, 7519a696f56SPrabhakar Kushwaha struct ldpaa_eth_priv *priv) 7529a696f56SPrabhakar Kushwaha { 7539a696f56SPrabhakar Kushwaha int error; 7542557c5a9SYogesh Gaur uint16_t major_ver, minor_ver; 7559a696f56SPrabhakar Kushwaha 7562557c5a9SYogesh Gaur error = dpmac_get_api_version(dflt_mc_io, 0, 7572557c5a9SYogesh Gaur &major_ver, 7582557c5a9SYogesh Gaur &minor_ver); 7592557c5a9SYogesh Gaur if ((major_ver < DPMAC_VER_MAJOR) || 7602557c5a9SYogesh Gaur (major_ver == DPMAC_VER_MAJOR && minor_ver < DPMAC_VER_MINOR)) { 7619a696f56SPrabhakar Kushwaha printf("DPMAC version mismatch found %u.%u,", 7622557c5a9SYogesh Gaur major_ver, minor_ver); 7639a696f56SPrabhakar Kushwaha printf("supported version is %u.%u\n", 7649a696f56SPrabhakar Kushwaha DPMAC_VER_MAJOR, DPMAC_VER_MINOR); 7652557c5a9SYogesh Gaur return error; 7669a696f56SPrabhakar Kushwaha } 7679a696f56SPrabhakar Kushwaha 7689a696f56SPrabhakar Kushwaha return error; 7699a696f56SPrabhakar Kushwaha } 7709a696f56SPrabhakar Kushwaha 771c919ab9eSPrabhakar Kushwaha static int ldpaa_dpmac_setup(struct ldpaa_eth_priv *priv) 772c919ab9eSPrabhakar Kushwaha { 773c919ab9eSPrabhakar Kushwaha int err = 0; 774c919ab9eSPrabhakar Kushwaha struct dpmac_cfg dpmac_cfg; 775c919ab9eSPrabhakar Kushwaha 776c919ab9eSPrabhakar Kushwaha dpmac_cfg.mac_id = priv->dpmac_id; 7772557c5a9SYogesh Gaur 7782557c5a9SYogesh Gaur err = dpmac_create(dflt_mc_io, 7792557c5a9SYogesh Gaur dflt_dprc_handle, 7802557c5a9SYogesh Gaur MC_CMD_NO_FLAGS, &dpmac_cfg, 7812557c5a9SYogesh Gaur &priv->dpmac_id); 782c919ab9eSPrabhakar Kushwaha if (err) 783c919ab9eSPrabhakar Kushwaha printf("dpmac_create() failed\n"); 7849a696f56SPrabhakar Kushwaha 7859a696f56SPrabhakar Kushwaha err = ldpaa_dpmac_version_check(dflt_mc_io, priv); 7862557c5a9SYogesh Gaur if (err < 0) { 7879a696f56SPrabhakar Kushwaha printf("ldpaa_dpmac_version_check() failed: %d\n", err); 7882557c5a9SYogesh Gaur goto err_version_check; 7892557c5a9SYogesh Gaur } 7902557c5a9SYogesh Gaur 7912557c5a9SYogesh Gaur err = dpmac_open(dflt_mc_io, 7922557c5a9SYogesh Gaur MC_CMD_NO_FLAGS, 7932557c5a9SYogesh Gaur priv->dpmac_id, 7942557c5a9SYogesh Gaur &priv->dpmac_handle); 7952557c5a9SYogesh Gaur if (err < 0) { 7962557c5a9SYogesh Gaur printf("dpmac_open() failed: %d\n", err); 7972557c5a9SYogesh Gaur goto err_open; 7982557c5a9SYogesh Gaur } 7992557c5a9SYogesh Gaur 8002557c5a9SYogesh Gaur return err; 8012557c5a9SYogesh Gaur 8022557c5a9SYogesh Gaur err_open: 8032557c5a9SYogesh Gaur err_version_check: 8042557c5a9SYogesh Gaur dpmac_destroy(dflt_mc_io, 8052557c5a9SYogesh Gaur dflt_dprc_handle, 8062557c5a9SYogesh Gaur MC_CMD_NO_FLAGS, priv->dpmac_id); 8079a696f56SPrabhakar Kushwaha 808c919ab9eSPrabhakar Kushwaha return err; 809c919ab9eSPrabhakar Kushwaha } 810c919ab9eSPrabhakar Kushwaha 811c919ab9eSPrabhakar Kushwaha static int ldpaa_dpmac_bind(struct ldpaa_eth_priv *priv) 812c919ab9eSPrabhakar Kushwaha { 813c919ab9eSPrabhakar Kushwaha int err = 0; 814c919ab9eSPrabhakar Kushwaha struct dprc_connection_cfg dprc_connection_cfg = { 815c919ab9eSPrabhakar Kushwaha /* If both rates are zero the connection */ 816c919ab9eSPrabhakar Kushwaha /* will be configured in "best effort" mode. */ 817c919ab9eSPrabhakar Kushwaha .committed_rate = 0, 818c919ab9eSPrabhakar Kushwaha .max_rate = 0 819c919ab9eSPrabhakar Kushwaha }; 820c919ab9eSPrabhakar Kushwaha 8215038d3e5SPrabhakar Kushwaha #ifdef DEBUG 8225038d3e5SPrabhakar Kushwaha struct dprc_endpoint dbg_endpoint; 8235038d3e5SPrabhakar Kushwaha int state = 0; 8245038d3e5SPrabhakar Kushwaha #endif 8255038d3e5SPrabhakar Kushwaha 826c919ab9eSPrabhakar Kushwaha memset(&dpmac_endpoint, 0, sizeof(struct dprc_endpoint)); 827192bc694SBen Whitten strcpy(dpmac_endpoint.type, "dpmac"); 828c919ab9eSPrabhakar Kushwaha dpmac_endpoint.id = priv->dpmac_id; 829c919ab9eSPrabhakar Kushwaha 830c919ab9eSPrabhakar Kushwaha memset(&dpni_endpoint, 0, sizeof(struct dprc_endpoint)); 831192bc694SBen Whitten strcpy(dpni_endpoint.type, "dpni"); 832c919ab9eSPrabhakar Kushwaha dpni_endpoint.id = dflt_dpni->dpni_id; 833c919ab9eSPrabhakar Kushwaha 834c919ab9eSPrabhakar Kushwaha err = dprc_connect(dflt_mc_io, MC_CMD_NO_FLAGS, 835c919ab9eSPrabhakar Kushwaha dflt_dprc_handle, 836c919ab9eSPrabhakar Kushwaha &dpmac_endpoint, 837c919ab9eSPrabhakar Kushwaha &dpni_endpoint, 838c919ab9eSPrabhakar Kushwaha &dprc_connection_cfg); 8395038d3e5SPrabhakar Kushwaha if (err) 8405038d3e5SPrabhakar Kushwaha printf("dprc_connect() failed\n"); 8415038d3e5SPrabhakar Kushwaha 8425038d3e5SPrabhakar Kushwaha #ifdef DEBUG 8435038d3e5SPrabhakar Kushwaha err = dprc_get_connection(dflt_mc_io, MC_CMD_NO_FLAGS, 8445038d3e5SPrabhakar Kushwaha dflt_dprc_handle, &dpni_endpoint, 8455038d3e5SPrabhakar Kushwaha &dbg_endpoint, &state); 8465038d3e5SPrabhakar Kushwaha printf("%s, DPMAC Type= %s\n", __func__, dbg_endpoint.type); 8475038d3e5SPrabhakar Kushwaha printf("%s, DPMAC ID= %d\n", __func__, dbg_endpoint.id); 8485038d3e5SPrabhakar Kushwaha printf("%s, DPMAC State= %d\n", __func__, state); 8495038d3e5SPrabhakar Kushwaha 8505038d3e5SPrabhakar Kushwaha memset(&dbg_endpoint, 0, sizeof(struct dprc_endpoint)); 8515038d3e5SPrabhakar Kushwaha err = dprc_get_connection(dflt_mc_io, MC_CMD_NO_FLAGS, 8525038d3e5SPrabhakar Kushwaha dflt_dprc_handle, &dpmac_endpoint, 8535038d3e5SPrabhakar Kushwaha &dbg_endpoint, &state); 8545038d3e5SPrabhakar Kushwaha printf("%s, DPNI Type= %s\n", __func__, dbg_endpoint.type); 8555038d3e5SPrabhakar Kushwaha printf("%s, DPNI ID= %d\n", __func__, dbg_endpoint.id); 8565038d3e5SPrabhakar Kushwaha printf("%s, DPNI State= %d\n", __func__, state); 8575038d3e5SPrabhakar Kushwaha #endif 858c919ab9eSPrabhakar Kushwaha return err; 859c919ab9eSPrabhakar Kushwaha } 860c919ab9eSPrabhakar Kushwaha 861c517771aSPrabhakar Kushwaha static int ldpaa_dpni_setup(struct ldpaa_eth_priv *priv) 862c517771aSPrabhakar Kushwaha { 863c517771aSPrabhakar Kushwaha int err; 864c517771aSPrabhakar Kushwaha 865c517771aSPrabhakar Kushwaha /* and get a handle for the DPNI this interface is associate with */ 866c919ab9eSPrabhakar Kushwaha err = dpni_open(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpni->dpni_id, 867c919ab9eSPrabhakar Kushwaha &dflt_dpni->dpni_handle); 868c517771aSPrabhakar Kushwaha if (err) { 869c517771aSPrabhakar Kushwaha printf("dpni_open() failed\n"); 870c517771aSPrabhakar Kushwaha goto err_open; 871c517771aSPrabhakar Kushwaha } 87287457d11SPrabhakar Kushwaha err = dpni_get_attributes(dflt_mc_io, MC_CMD_NO_FLAGS, 873c919ab9eSPrabhakar Kushwaha dflt_dpni->dpni_handle, 874c919ab9eSPrabhakar Kushwaha &dflt_dpni->dpni_attrs); 875c517771aSPrabhakar Kushwaha if (err) { 876c517771aSPrabhakar Kushwaha printf("dpni_get_attributes() failed (err=%d)\n", err); 877c517771aSPrabhakar Kushwaha goto err_get_attr; 878c517771aSPrabhakar Kushwaha } 879c517771aSPrabhakar Kushwaha 880c517771aSPrabhakar Kushwaha /* Configure our buffers' layout */ 881c919ab9eSPrabhakar Kushwaha dflt_dpni->buf_layout.options = DPNI_BUF_LAYOUT_OPT_PARSER_RESULT | 882c517771aSPrabhakar Kushwaha DPNI_BUF_LAYOUT_OPT_FRAME_STATUS | 88314480454SPrabhakar Kushwaha DPNI_BUF_LAYOUT_OPT_PRIVATE_DATA_SIZE | 88414480454SPrabhakar Kushwaha DPNI_BUF_LAYOUT_OPT_DATA_ALIGN; 885c919ab9eSPrabhakar Kushwaha dflt_dpni->buf_layout.pass_parser_result = true; 886c919ab9eSPrabhakar Kushwaha dflt_dpni->buf_layout.pass_frame_status = true; 887c919ab9eSPrabhakar Kushwaha dflt_dpni->buf_layout.private_data_size = LDPAA_ETH_SWA_SIZE; 88814480454SPrabhakar Kushwaha /* HW erratum mandates data alignment in multiples of 256 */ 88914480454SPrabhakar Kushwaha dflt_dpni->buf_layout.data_align = LDPAA_ETH_BUF_ALIGN; 8902557c5a9SYogesh Gaur 891c517771aSPrabhakar Kushwaha /* ...rx, ... */ 8922557c5a9SYogesh Gaur err = dpni_set_buffer_layout(dflt_mc_io, MC_CMD_NO_FLAGS, 893c919ab9eSPrabhakar Kushwaha dflt_dpni->dpni_handle, 8942557c5a9SYogesh Gaur &dflt_dpni->buf_layout, DPNI_QUEUE_RX); 895c517771aSPrabhakar Kushwaha if (err) { 8962557c5a9SYogesh Gaur printf("dpni_set_buffer_layout() failed"); 897c517771aSPrabhakar Kushwaha goto err_buf_layout; 898c517771aSPrabhakar Kushwaha } 899c517771aSPrabhakar Kushwaha 900c517771aSPrabhakar Kushwaha /* ... tx, ... */ 90114480454SPrabhakar Kushwaha /* remove Rx-only options */ 90214480454SPrabhakar Kushwaha dflt_dpni->buf_layout.options &= ~(DPNI_BUF_LAYOUT_OPT_DATA_ALIGN | 90314480454SPrabhakar Kushwaha DPNI_BUF_LAYOUT_OPT_PARSER_RESULT); 9042557c5a9SYogesh Gaur err = dpni_set_buffer_layout(dflt_mc_io, MC_CMD_NO_FLAGS, 905c919ab9eSPrabhakar Kushwaha dflt_dpni->dpni_handle, 9062557c5a9SYogesh Gaur &dflt_dpni->buf_layout, DPNI_QUEUE_TX); 907c517771aSPrabhakar Kushwaha if (err) { 9082557c5a9SYogesh Gaur printf("dpni_set_buffer_layout() failed"); 909c517771aSPrabhakar Kushwaha goto err_buf_layout; 910c517771aSPrabhakar Kushwaha } 911c517771aSPrabhakar Kushwaha 912c517771aSPrabhakar Kushwaha /* ... tx-confirm. */ 913c919ab9eSPrabhakar Kushwaha dflt_dpni->buf_layout.options &= ~DPNI_BUF_LAYOUT_OPT_PRIVATE_DATA_SIZE; 9142557c5a9SYogesh Gaur err = dpni_set_buffer_layout(dflt_mc_io, MC_CMD_NO_FLAGS, 915c919ab9eSPrabhakar Kushwaha dflt_dpni->dpni_handle, 9162557c5a9SYogesh Gaur &dflt_dpni->buf_layout, 9172557c5a9SYogesh Gaur DPNI_QUEUE_TX_CONFIRM); 918c517771aSPrabhakar Kushwaha if (err) { 9192557c5a9SYogesh Gaur printf("dpni_set_buffer_layout() failed"); 920c517771aSPrabhakar Kushwaha goto err_buf_layout; 921c517771aSPrabhakar Kushwaha } 922c517771aSPrabhakar Kushwaha 923c517771aSPrabhakar Kushwaha /* Now that we've set our tx buffer layout, retrieve the minimum 924c517771aSPrabhakar Kushwaha * required tx data offset. 925c517771aSPrabhakar Kushwaha */ 92687457d11SPrabhakar Kushwaha err = dpni_get_tx_data_offset(dflt_mc_io, MC_CMD_NO_FLAGS, 927c919ab9eSPrabhakar Kushwaha dflt_dpni->dpni_handle, 928c919ab9eSPrabhakar Kushwaha &priv->tx_data_offset); 929c517771aSPrabhakar Kushwaha if (err) { 930c517771aSPrabhakar Kushwaha printf("dpni_get_tx_data_offset() failed\n"); 931c517771aSPrabhakar Kushwaha goto err_data_offset; 932c517771aSPrabhakar Kushwaha } 933c517771aSPrabhakar Kushwaha 934c517771aSPrabhakar Kushwaha /* Warn in case TX data offset is not multiple of 64 bytes. */ 935c517771aSPrabhakar Kushwaha WARN_ON(priv->tx_data_offset % 64); 936c517771aSPrabhakar Kushwaha 937c517771aSPrabhakar Kushwaha /* Accomodate SWA space. */ 938c517771aSPrabhakar Kushwaha priv->tx_data_offset += LDPAA_ETH_SWA_SIZE; 939c517771aSPrabhakar Kushwaha debug("priv->tx_data_offset=%d\n", priv->tx_data_offset); 940c517771aSPrabhakar Kushwaha 941c517771aSPrabhakar Kushwaha return 0; 942c517771aSPrabhakar Kushwaha 943c517771aSPrabhakar Kushwaha err_data_offset: 944c517771aSPrabhakar Kushwaha err_buf_layout: 945c517771aSPrabhakar Kushwaha err_get_attr: 946c919ab9eSPrabhakar Kushwaha dpni_close(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpni->dpni_handle); 947c517771aSPrabhakar Kushwaha err_open: 948c517771aSPrabhakar Kushwaha return err; 949c517771aSPrabhakar Kushwaha } 950c517771aSPrabhakar Kushwaha 951c517771aSPrabhakar Kushwaha static int ldpaa_dpni_bind(struct ldpaa_eth_priv *priv) 952c517771aSPrabhakar Kushwaha { 953c517771aSPrabhakar Kushwaha struct dpni_pools_cfg pools_params; 9542557c5a9SYogesh Gaur struct dpni_queue tx_queue; 955c517771aSPrabhakar Kushwaha int err = 0; 956c517771aSPrabhakar Kushwaha 95731a48cf4SPrabhakar Kushwaha memset(&pools_params, 0, sizeof(pools_params)); 958c517771aSPrabhakar Kushwaha pools_params.num_dpbp = 1; 959c517771aSPrabhakar Kushwaha pools_params.pools[0].dpbp_id = (uint16_t)dflt_dpbp->dpbp_attr.id; 960c517771aSPrabhakar Kushwaha pools_params.pools[0].buffer_size = LDPAA_ETH_RX_BUFFER_SIZE; 961c919ab9eSPrabhakar Kushwaha err = dpni_set_pools(dflt_mc_io, MC_CMD_NO_FLAGS, 962c919ab9eSPrabhakar Kushwaha dflt_dpni->dpni_handle, &pools_params); 963c517771aSPrabhakar Kushwaha if (err) { 964c517771aSPrabhakar Kushwaha printf("dpni_set_pools() failed\n"); 965c517771aSPrabhakar Kushwaha return err; 966c517771aSPrabhakar Kushwaha } 967c517771aSPrabhakar Kushwaha 9682557c5a9SYogesh Gaur memset(&tx_queue, 0, sizeof(struct dpni_queue)); 969c517771aSPrabhakar Kushwaha 9702557c5a9SYogesh Gaur err = dpni_set_queue(dflt_mc_io, MC_CMD_NO_FLAGS, 9712557c5a9SYogesh Gaur dflt_dpni->dpni_handle, 9722557c5a9SYogesh Gaur DPNI_QUEUE_TX, 0, 0, &tx_queue); 9732557c5a9SYogesh Gaur 974c517771aSPrabhakar Kushwaha if (err) { 9752557c5a9SYogesh Gaur printf("dpni_set_queue() failed\n"); 976c517771aSPrabhakar Kushwaha return err; 977c517771aSPrabhakar Kushwaha } 978c517771aSPrabhakar Kushwaha 9792557c5a9SYogesh Gaur err = dpni_set_tx_confirmation_mode(dflt_mc_io, MC_CMD_NO_FLAGS, 9806073548aSPrabhakar Kushwaha dflt_dpni->dpni_handle, 9812557c5a9SYogesh Gaur DPNI_CONF_DISABLE); 9826073548aSPrabhakar Kushwaha if (err) { 9832557c5a9SYogesh Gaur printf("dpni_set_tx_confirmation_mode() failed\n"); 9846073548aSPrabhakar Kushwaha return err; 9856073548aSPrabhakar Kushwaha } 9866073548aSPrabhakar Kushwaha 987c517771aSPrabhakar Kushwaha return 0; 988c517771aSPrabhakar Kushwaha } 989c517771aSPrabhakar Kushwaha 990c919ab9eSPrabhakar Kushwaha static int ldpaa_eth_netdev_init(struct eth_device *net_dev, 991c919ab9eSPrabhakar Kushwaha phy_interface_t enet_if) 992c517771aSPrabhakar Kushwaha { 993c517771aSPrabhakar Kushwaha int err; 994c517771aSPrabhakar Kushwaha struct ldpaa_eth_priv *priv = (struct ldpaa_eth_priv *)net_dev->priv; 995c517771aSPrabhakar Kushwaha 996c022ec03SPankaj Bansal snprintf(net_dev->name, ETH_NAME_LEN, "DPMAC%d@%s", priv->dpmac_id, 997c919ab9eSPrabhakar Kushwaha phy_interface_strings[enet_if]); 998c517771aSPrabhakar Kushwaha 999c517771aSPrabhakar Kushwaha net_dev->iobase = 0; 1000c517771aSPrabhakar Kushwaha net_dev->init = ldpaa_eth_open; 1001c517771aSPrabhakar Kushwaha net_dev->halt = ldpaa_eth_stop; 1002c517771aSPrabhakar Kushwaha net_dev->send = ldpaa_eth_tx; 1003c517771aSPrabhakar Kushwaha net_dev->recv = ldpaa_eth_pull_dequeue_rx; 1004c517771aSPrabhakar Kushwaha 10056c2b520aSPrabhakar Kushwaha #ifdef CONFIG_PHYLIB 10066c2b520aSPrabhakar Kushwaha err = init_phy(net_dev); 10076c2b520aSPrabhakar Kushwaha if (err < 0) 10086c2b520aSPrabhakar Kushwaha return err; 10096c2b520aSPrabhakar Kushwaha #endif 1010c517771aSPrabhakar Kushwaha 1011c517771aSPrabhakar Kushwaha err = eth_register(net_dev); 1012c517771aSPrabhakar Kushwaha if (err < 0) { 1013c517771aSPrabhakar Kushwaha printf("eth_register() = %d\n", err); 1014c517771aSPrabhakar Kushwaha return err; 1015c517771aSPrabhakar Kushwaha } 1016c517771aSPrabhakar Kushwaha 1017c517771aSPrabhakar Kushwaha return 0; 1018c517771aSPrabhakar Kushwaha } 1019c517771aSPrabhakar Kushwaha 1020c919ab9eSPrabhakar Kushwaha int ldpaa_eth_init(int dpmac_id, phy_interface_t enet_if) 1021c517771aSPrabhakar Kushwaha { 1022c517771aSPrabhakar Kushwaha struct eth_device *net_dev = NULL; 1023c517771aSPrabhakar Kushwaha struct ldpaa_eth_priv *priv = NULL; 1024c517771aSPrabhakar Kushwaha int err = 0; 1025c517771aSPrabhakar Kushwaha 1026c517771aSPrabhakar Kushwaha /* Net device */ 1027c517771aSPrabhakar Kushwaha net_dev = (struct eth_device *)malloc(sizeof(struct eth_device)); 1028c517771aSPrabhakar Kushwaha if (!net_dev) { 1029c517771aSPrabhakar Kushwaha printf("eth_device malloc() failed\n"); 1030c517771aSPrabhakar Kushwaha return -ENOMEM; 1031c517771aSPrabhakar Kushwaha } 1032c517771aSPrabhakar Kushwaha memset(net_dev, 0, sizeof(struct eth_device)); 1033c517771aSPrabhakar Kushwaha 1034c517771aSPrabhakar Kushwaha /* alloc the ldpaa ethernet private struct */ 1035c517771aSPrabhakar Kushwaha priv = (struct ldpaa_eth_priv *)malloc(sizeof(struct ldpaa_eth_priv)); 1036c517771aSPrabhakar Kushwaha if (!priv) { 1037c517771aSPrabhakar Kushwaha printf("ldpaa_eth_priv malloc() failed\n"); 1038c517771aSPrabhakar Kushwaha return -ENOMEM; 1039c517771aSPrabhakar Kushwaha } 1040c517771aSPrabhakar Kushwaha memset(priv, 0, sizeof(struct ldpaa_eth_priv)); 1041c517771aSPrabhakar Kushwaha 1042c517771aSPrabhakar Kushwaha net_dev->priv = (void *)priv; 1043c517771aSPrabhakar Kushwaha priv->net_dev = (struct eth_device *)net_dev; 1044c919ab9eSPrabhakar Kushwaha priv->dpmac_id = dpmac_id; 1045c919ab9eSPrabhakar Kushwaha debug("%s dpmac_id=%d\n", __func__, dpmac_id); 1046c517771aSPrabhakar Kushwaha 1047c919ab9eSPrabhakar Kushwaha err = ldpaa_eth_netdev_init(net_dev, enet_if); 1048c517771aSPrabhakar Kushwaha if (err) 1049c517771aSPrabhakar Kushwaha goto err_netdev_init; 1050c517771aSPrabhakar Kushwaha 1051c517771aSPrabhakar Kushwaha debug("ldpaa ethernet: Probed interface %s\n", net_dev->name); 1052c517771aSPrabhakar Kushwaha return 0; 1053c517771aSPrabhakar Kushwaha 1054c517771aSPrabhakar Kushwaha err_netdev_init: 1055c517771aSPrabhakar Kushwaha free(priv); 1056c517771aSPrabhakar Kushwaha net_dev->priv = NULL; 1057c517771aSPrabhakar Kushwaha free(net_dev); 1058c517771aSPrabhakar Kushwaha 1059c517771aSPrabhakar Kushwaha return err; 1060c517771aSPrabhakar Kushwaha } 1061