This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

10/100 MII PHY on second EMAC channel

Hello,

I am working on a custom hardware design that has two Ethernet PHY devices connected to the EMAC.  Interface RGMII1 (pins K17, K16, etc) is connected to a AR8031 PHY using RGMII and this appears to be working OK as interface eth0.

There is a second 10/100 PHY (KSZ8041) connected to the GPMC_Ax pins in MII mode which is defined in the device tree as:

cpsw_default: cpsw_default {
	pinctrl-single,pins = <

		...

		/* Slave 2 - connected to Micrel KSZ8041NL PHY. */
		0x40 (PIN_OUTPUT_PULLDOWN | MUX_MODE1) /* gpmc_a0.gmii2_txen */
		0x44 (PIN_INPUT_PULLDOWN | MUX_MODE1) /* gpmc_a1.gmii2_rxdv */
		0x48 (PIN_OUTPUT_PULLDOWN | MUX_MODE1) /* gpmc_a2.gmii2_txd3 */
		0x4c (PIN_OUTPUT_PULLDOWN | MUX_MODE1) /* gpmc_a3.gmii2_txd2 */
		0x50 (PIN_OUTPUT_PULLDOWN | MUX_MODE1) /* gpmc_a4.gmii2_txd1 */
		0x54 (PIN_OUTPUT_PULLDOWN | MUX_MODE1) /* gpmc_a5.gmii2_txd0 */
		0x58 (PIN_INPUT_PULLDOWN | MUX_MODE1) /* gpmc_a6.gmii2_txclk */
		0x5c (PIN_INPUT_PULLDOWN | MUX_MODE1) /* gpmc_a7.gmii2_rxclk */
		0x60 (PIN_INPUT_PULLDOWN | MUX_MODE1) /* gpmc_a8.gmii2_rxd3 */
		0x64 (PIN_INPUT_PULLDOWN | MUX_MODE1) /* gpmc_a9.gmii2_rxd2 */
		0x68 (PIN_INPUT_PULLDOWN | MUX_MODE1) /* gpmc_a10.gmii2_rxd1 */
		0x6c (PIN_INPUT_PULLDOWN | MUX_MODE1) /* gpmc_a11.gmii2_rxd0 */
		0x70 (PIN_INPUT_PULLDOWN | MUX_MODE1) /* gpmc_wait0.gmii2_crs */
		0x74 (PIN_INPUT_PULLDOWN | MUX_MODE1) /* gpmc_wpn.gmii2.rxer */
		0x78 (PIN_INPUT_PULLDOWN | MUX_MODE1) /* gpmc_be1n_mux0.gmii2.col */

This interface appears to Linux as eth1 but I can't get any data to pass through the interface?

Have I missed something obvious?

Thanks,

Andy.

  • Hi Andy,

    Eth1 does not come up automatically. It has to be started by a command (http://processors.wiki.ti.com/index.php/Linux_Core_CPSW_User's_Guide#Bringing_Up_interfaces ).

    Another thing is that if you have configured the CPSW in Dual EMAC mode the two Ethernet ports must be connected to different subnet segments (http://processors.wiki.ti.com/index.php/Linux_Core_CPSW_User's_Guide#Constrains ).

  • Hi Biser,

    The CPSW is configured in dual EMAC mode as follows in the device tree:

    &mac {
    	status = "okay";
    	pinctrl-names = "default", "sleep";
    	pinctrl-0 = <&cpsw_default>;
    	pinctrl-1 = <&cpsw_sleep>;
    	dual_emac = <1>;
    };
    
    &davinci_mdio {
    	status = "okay";
    	pinctrl-names = "default", "sleep";
    	pinctrl-0 = <&davinci_mdio_default>;
    	pinctrl-1 = <&davinci_mdio_sleep>;
    };
    
    &cpsw_emac0 {
    	phy_id = <&davinci_mdio>, <4>;
    	phy-mode = "rgmii-txid";
    	dual_emac_res_vlan = <1>;
    };
    
    &cpsw_emac1 {
    	phy_id = <&davinci_mdio>, <1>;
    	phy-mode = "mii";
    	dual_emac_res_vlan = <2>;
    };

    The init script on my platform brings up eth0 using "udhcpc eth0" which gets an IP address in the 192.168.10.x range and eth1 is brought up using "ifconfig eth1 192.168.0.7 netmask 255.255.255.0" based on me having read the information in the document to which you referred.

    Regards,

    Andy.

  • Andy,

    Could you post what is printed on the console as you bring up eth1? There should be an indication that the PHY has established a link. Could you also post the results of what ethtool says lists for eth1? The command is "ethtool eth1".

  • Hello Schuyler,

    The various messages output by the kernel as the system boots up are:

    davinci_mdio 4a101000.mdio: phy[0]: device 4a101000.mdio:00, driver Micrel KSZ8041
    davinci_mdio 4a101000.mdio: phy[1]: device 4a101000.mdio:01, driver Micrel KSZ8041
    davinci_mdio 4a101000.mdio: phy[4]: device 4a101000.mdio:04, driver Atheros 8031 ethernet
    cpsw 4a100000.ethernet: Detected MACID = 90:59:af:91:24:5b
    cpsw 4a100000.ethernet: cpsw: Detected MACID = 90:59:af:91:24:5d
    
    net eth1: initializing cpsw version 1.12 (0)
    net eth1: phy found : id is : 0x221513
    IPv6: ADDRCONF(NETDEV_UP): eth1: link is not ready
    net eth0: initializing cpsw version 1.12 (0)
    net eth0: phy found : id is : 0x4dd074
    IPv6: ADDRCONF(NETDEV_UP): eth0: link is not ready

    As the init script runs and issues the calls to udhcpc for eth0 and ifconfig for eth1 then I get the following:

    libphy: 4a101000.mdio:04 - Link is Up - 100/Full
    IPv6: ADDRCONF(NETDEV_CHANGE): eth0: link becomes ready
    libphy: 4a101000.mdio:01 - Link is Up - 100/Full
    IPv6: ADDRCONF(NETDEV_CHANGE): eth1: link becomes ready
    

    The output from ethtool for eth1 gives:

    # ethtool eth1
    Settings for eth1:
            Supported ports: [ TP MII ]
            Supported link modes:   10baseT/Half 10baseT/Full 
                                    100baseT/Half 100baseT/Full 
            Supported pause frame use: Symmetric Receive-only
            Supports auto-negotiation: Yes
            Advertised link modes:  10baseT/Half 10baseT/Full 
                                    100baseT/Half 100baseT/Full 
            Advertised pause frame use: Symmetric Receive-only
            Advertised auto-negotiation: Yes
            Link partner advertised link modes:  10baseT/Half 10baseT/Full 
                                                 100baseT/Half 100baseT/Full 
            Link partner advertised pause frame use: Symmetric
            Link partner advertised auto-negotiation: Yes
            Speed: 100Mb/s
            Duplex: Full
            Port: MII
            PHYAD: 1
            Transceiver: external
            Auto-negotiation: on
            Supports Wake-on: d
            Wake-on: d
            Current message level: 0x00000000 (0)
                                   
            Link detected: yes
    

    The output from the PHY on eth1 is connected to a Micrel switch from which I can read the registers and it appears that the link between the PHY and the switch is establishing correctly which the above output seems to confirm.  

    When I try to run a "ping" test to an IP address on the same subnet as eth1 and capture the packets with tcpdump all I see are the "whois 192.168.0.1" arp packets but never any responses.

    Regards,

    Andy.

  • Hello Schuyler,

    One question has just occurred to me. The init script I use is a custom written file at /etc/init.d/rcS that performs the initialisation in a defined order to minimise boot time. When it gets to the Ethernet initialisation it is in effect running:

    udhcpc eth0 &
    ifconfig eth1 192.168.0.7 netmask 255.255.255.0 up

    As the call to the DHCP server for eth0 is spawned as a background task any delay in response from the DHCP server may mean that eth1 is configured and brought up before eth0. Given the limitations of dual EMAC mode highlighted by Biser could this cause problems and should we wait for eth0 to have established with an IP address from the DHCP server before trying to bring up eth1?

    Thanks,

    Andy.
  • Andy,

    From the console log it looks the interface is being initialized for ipv6 traffic. A different technique is used for ip addresses, no ARP or dhcp traffic like ipv4. If you want ipv4 the script you mention might be setting eth1 to ipv6.

  • Hello Schuyler,

    Although the final target will need ipv6 support I have rebuilt my kernel with ipv6 disabled in order to test things out.  Sadly I still can't get any traffic to pass through this interface.  With ipv6 disabled the kernel messages now show:

    udhcpc (v1.22.1) started
    net eth0: initializing cpsw version 1.12 (0)
    net eth0: phy found : id is : 0x4dd074
    Sending discover...
    libphy: 4a101000.mdio:04 - Link is Up - 100/Full
    Sending discover...
    Sending select for 192.168.10.219...
    Lease of 192.168.10.219 obtained, lease time 3600
    deleting routers
    SIOCDELRT: No such process
    adding dns 95.210.254.9
    adding dns 95.210.254.8
    
    net eth1: initializing cpsw version 1.12 (0)
    net eth1: phy found : id is : 0x221513
    libphy: 4a101000.mdio:01 - Link is Up - 100/Full
    

    The output from ifconfig shows:

    # ifconfig -a
    eth0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 1500  metric 1
            inet 192.168.10.219  netmask 255.255.255.0  broadcast 192.168.10.255
            ether 90:59:af:91:24:5b  txqueuelen 1000  (Ethernet)
            RX packets 102  bytes 11528 (11.2 KiB)
            RX errors 0  dropped 0  overruns 0  frame 0
            TX packets 2  bytes 684 (684.0 B)
            TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0
            device interrupt 56  
    
    eth1: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 1500  metric 1
            inet 192.168.0.7  netmask 255.255.255.0  broadcast 192.168.0.255
            ether 90:59:af:91:24:5d  txqueuelen 1000  (Ethernet)
            RX packets 0  bytes 0 (0.0 B)
            RX errors 0  dropped 0  overruns 0  frame 0
            TX packets 36  bytes 2160 (2.1 KiB)
            TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0
    
    lo: flags=73<UP,LOOPBACK,RUNNING>  mtu 65536  metric 1
            inet 127.0.0.1  netmask 255.0.0.0
            loop  txqueuelen 0  (Local Loopback)
            RX packets 33  bytes 5784 (5.6 KiB)
            RX errors 0  dropped 0  overruns 0  frame 0
            TX packets 33  bytes 5784 (5.6 KiB)
            TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0
    

    I am now beginning to wonder whether the PHY might actually be being configured correctly but that the Micrel KS8995M switch it is connected to isn't passing the packets across.  On that score, I am waiting to see if the hardware team can tell me how to route the output of the PHY directly to an RJ45 connector.

    Thanks,

    Andy.