]> git.dujemihanovic.xyz Git - u-boot.git/commitdiff
net: rtl8169: add minimal support for 8125B variant
authorEugen Hristev <eugen.hristev@collabora.com>
Tue, 25 Apr 2023 13:06:58 +0000 (16:06 +0300)
committerTom Rini <trini@konsulko.com>
Fri, 5 May 2023 21:59:20 +0000 (17:59 -0400)
Add minimal support for 8125B version.
Changes are based on the Linux driver.
Tested on Radxa Rock 5B Rk3588 board.

Connection to a laptop worked fine in 100 Mbps mode.
1000 Mbps mode is not working at the moment.

Signed-off-by: Eugen Hristev <eugen.hristev@collabora.com>
Reviewed-by: Ramon Fried <rfried.dev@gmail.com>
drivers/net/rtl8169.c

index c9c07a5a8ffe7f1a963b0e09b0ec7334913a56f9..2276a465e7878c4dbfd1ccf7ccd9c76103e08b2f 100644 (file)
@@ -118,9 +118,9 @@ enum RTL8169_registers {
        FLASH = 0x30,
        ERSR = 0x36,
        ChipCmd = 0x37,
-       TxPoll = 0x38,
-       IntrMask = 0x3C,
-       IntrStatus = 0x3E,
+       TxPoll_8169 = 0x38,
+       IntrMask_8169 = 0x3C,
+       IntrStatus_8169 = 0x3E,
        TxConfig = 0x40,
        RxConfig = 0x44,
        RxMissed = 0x4C,
@@ -148,6 +148,12 @@ enum RTL8169_registers {
        FuncForceEvent = 0xFC,
 };
 
+enum RTL8125_registers {
+       IntrMask_8125 = 0x38,
+       IntrStatus_8125 = 0x3C,
+       TxPoll_8125 = 0x90,
+};
+
 enum RTL8169_register_content {
        /*InterruptStatusBits */
        SYSErr = 0x8000,
@@ -263,6 +269,7 @@ static struct {
        {"RTL-8101e",           0x34, 0xff7e1880,},
        {"RTL-8100e",           0x32, 0xff7e1880,},
        {"RTL-8168h/8111h",     0x54, 0xff7e1880,},
+       {"RTL-8125B",           0x64, 0xff7e1880,},
 };
 
 enum _DescStatusBit {
@@ -347,6 +354,7 @@ static struct pci_device_id supported[] = {
        { PCI_DEVICE(PCI_VENDOR_ID_REALTEK, 0x8167) },
        { PCI_DEVICE(PCI_VENDOR_ID_REALTEK, 0x8168) },
        { PCI_DEVICE(PCI_VENDOR_ID_REALTEK, 0x8169) },
+       { PCI_DEVICE(PCI_VENDOR_ID_REALTEK, 0x8125) },
        {}
 };
 
@@ -517,6 +525,7 @@ static int rtl_recv_common(struct udevice *dev, unsigned long dev_iobase,
        /* return true if there's an ethernet packet ready to read */
        /* nic->packet should contain data on return */
        /* nic->packetlen should contain length of data */
+       struct pci_child_plat *pplat = dev_get_parent_plat(dev);
        int cur_rx;
        int length = 0;
 
@@ -558,6 +567,10 @@ static int rtl_recv_common(struct udevice *dev, unsigned long dev_iobase,
                return length;
 
        } else {
+               u32 IntrStatus = IntrStatus_8169;
+
+               if (pplat->device == 0x8125)
+                       IntrStatus = IntrStatus_8125;
                ushort sts = RTL_R8(IntrStatus);
                RTL_W8(IntrStatus, sts & ~(TxErr | RxErr | SYSErr));
                udelay(100);    /* wait */
@@ -582,6 +595,7 @@ static int rtl_send_common(struct udevice *dev, unsigned long dev_iobase,
 {
        /* send the packet to destination */
 
+       struct pci_child_plat *pplat = dev_get_parent_plat(dev);
        u32 to;
        u8 *ptxb;
        int entry = tpc->cur_tx % NUM_TX_DESC;
@@ -618,7 +632,10 @@ static int rtl_send_common(struct udevice *dev, unsigned long dev_iobase,
                                    ((len > ETH_ZLEN) ? len : ETH_ZLEN));
        }
        rtl_flush_tx_desc(&tpc->TxDescArray[entry]);
-       RTL_W8(TxPoll, 0x40);   /* set polling bit */
+       if (pplat->device == 0x8125)
+               RTL_W8(TxPoll_8125, 0x1);       /* set polling bit */
+       else
+               RTL_W8(TxPoll_8169, 0x40);      /* set polling bit */
 
        tpc->cur_tx++;
        to = currticks() + TX_TIMEOUT;
@@ -824,21 +841,26 @@ static int rtl8169_eth_start(struct udevice *dev)
        return 0;
 }
 
-static void rtl_halt_common(unsigned long dev_iobase)
+static void rtl_halt_common(struct udevice *dev)
 {
+       struct rtl8169_private *priv = dev_get_priv(dev);
+       struct pci_child_plat *pplat = dev_get_parent_plat(dev);
        int i;
 
 #ifdef DEBUG_RTL8169
        printf ("%s\n", __FUNCTION__);
 #endif
 
-       ioaddr = dev_iobase;
+       ioaddr = priv->iobase;
 
        /* Stop the chip's Tx and Rx DMA processes. */
        RTL_W8(ChipCmd, 0x00);
 
        /* Disable interrupts by clearing the interrupt mask. */
-       RTL_W16(IntrMask, 0x0000);
+       if (pplat->device == 0x8125)
+               RTL_W16(IntrMask_8125, 0x0000);
+       else
+               RTL_W16(IntrMask_8169, 0x0000);
 
        RTL_W32(RxMissed, 0);
 
@@ -849,9 +871,7 @@ static void rtl_halt_common(unsigned long dev_iobase)
 
 void rtl8169_eth_stop(struct udevice *dev)
 {
-       struct rtl8169_private *priv = dev_get_priv(dev);
-
-       rtl_halt_common(priv->iobase);
+       rtl_halt_common(dev);
 }
 
 static int rtl8169_write_hwaddr(struct udevice *dev)
@@ -1025,23 +1045,25 @@ static int rtl8169_eth_probe(struct udevice *dev)
        struct pci_child_plat *pplat = dev_get_parent_plat(dev);
        struct rtl8169_private *priv = dev_get_priv(dev);
        struct eth_pdata *plat = dev_get_plat(dev);
-       u32 iobase;
        int region;
        int ret;
 
-       debug("rtl8169: REALTEK RTL8169 @0x%x\n", iobase);
        switch (pplat->device) {
        case 0x8168:
+       case 0x8125:
                region = 2;
                break;
        default:
                region = 1;
                break;
        }
-       dm_pci_read_config32(dev, PCI_BASE_ADDRESS_0 + region * 4, &iobase);
-       iobase &= ~0xf;
-       priv->iobase = (int)dm_pci_mem_to_phys(dev, iobase);
 
+       priv->iobase = (ulong)dm_pci_map_bar(dev,
+                                            PCI_BASE_ADDRESS_0 + region * 4,
+                                            0, 0,
+                                            PCI_REGION_TYPE, PCI_REGION_MEM);
+
+       debug("rtl8169: REALTEK RTL8169 @0x%lx\n", priv->iobase);
        ret = rtl_init(priv->iobase, dev->name, plat->enetaddr);
        if (ret < 0) {
                printf(pr_fmt("failed to initialize card: %d\n"), ret);