Date: Wed, 2 May 2012 01:21:58 +0000 (UTC) From: Adrian Chadd <adrian@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r234906 - head/sys/mips/atheros Message-ID: <201205020121.q421LwFU056899@svn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: adrian Date: Wed May 2 01:21:57 2012 New Revision: 234906 URL: http://svn.freebsd.org/changeset/base/234906 Log: MII related infrastructure changes. * Add a new method to set the MII mode - GMII, RGMII, RMII, MII. + arge0 supports all four (two for non-Gige interfaces.) + arge1 only supports two (one for non-gige interfaces.) * Set the MII clock speed when changing the MAC PLL speed. + Needed for AR91xx and AR71xx; not needed for AR724x. Tested: * AR71xx only, I'll do AR913x testing tonight and fix whichever issues creep up. TODO: * Implement the missing AR7242 arge0 PLL configuration, but don't adjust the MII speed accordingly. * .. the AR7240/AR7241 don't require this, so make sure it's not set accidentally. Bugs (not fixed here): * Statically configured arge speeds are still broken - investigate why that is on the AP96 board. Autonegotiate is working fine, but there still seems to be an occasionally heavy packet loss issue. Obtained from: Linux/Atheros/OpenWRT Modified: head/sys/mips/atheros/ar71xx_chip.c head/sys/mips/atheros/ar71xx_chip.h head/sys/mips/atheros/ar71xx_cpudef.h head/sys/mips/atheros/ar724x_chip.c head/sys/mips/atheros/ar91xx_chip.c Modified: head/sys/mips/atheros/ar71xx_chip.c ============================================================================== --- head/sys/mips/atheros/ar71xx_chip.c Wed May 2 01:14:15 2012 (r234905) +++ head/sys/mips/atheros/ar71xx_chip.c Wed May 2 01:21:57 2012 (r234906) @@ -176,6 +176,50 @@ ar71xx_chip_set_mii_speed(uint32_t unit, ATH_WRITE_REG(reg, val); } +void +ar71xx_chip_set_mii_if(uint32_t unit, uint32_t mii_mode) +{ + uint32_t val, reg, mii_if; + + switch (unit) { + case 0: + reg = AR71XX_MII0_CTRL; + if (mii_mode == AR71XX_MII_MODE_GMII) + mii_if = MII0_CTRL_IF_GMII; + else if (mii_mode == AR71XX_MII_MODE_MII) + mii_if = MII0_CTRL_IF_MII; + else if (mii_mode == AR71XX_MII_MODE_RGMII) + mii_if = MII0_CTRL_IF_RGMII; + else if (mii_mode == AR71XX_MII_MODE_RMII) + mii_if = MII0_CTRL_IF_RMII; + else + printf("%s: invalid MII mode (%d) for unit %d\n", + __func__, mii_mode, unit); + return; + break; + case 1: + reg = AR71XX_MII1_CTRL; + if (mii_mode == AR71XX_MII_MODE_RGMII) + mii_if = MII1_CTRL_IF_RGMII; + if (mii_mode == AR71XX_MII_MODE_RMII) + mii_if = MII1_CTRL_IF_RMII; + else + printf("%s: invalid MII mode (%d) for unit %d\n", + __func__, mii_mode, unit); + return; + break; + default: + printf("%s: invalid MII unit set for arge unit: %d\n", + __func__, unit); + return; + } + + val = ATH_READ_REG(reg); + val &= ~(MII_CTRL_IF_MASK << MII_CTRL_IF_SHIFT); + val |= (mii_if & MII_CTRL_IF_MASK) << MII_CTRL_IF_SHIFT; + ATH_WRITE_REG(reg, val); +} + /* Speed is either 10, 100 or 1000 */ static void ar71xx_chip_set_pll_ge(int unit, int speed) @@ -197,6 +241,7 @@ ar71xx_chip_set_pll_ge(int unit, int spe __func__, unit, speed); return; } + switch (unit) { case 0: ar71xx_write_pll(AR71XX_PLL_SEC_CONFIG, @@ -213,6 +258,12 @@ ar71xx_chip_set_pll_ge(int unit, int spe __func__, unit); return; } + + /* + * AR71xx and AR913x require this; AR724x doesn't require + * an MII clock change at all. + */ + ar71xx_chip_set_mii_speed(unit, speed); } static void @@ -278,6 +329,7 @@ struct ar71xx_cpu_def ar71xx_chip_def = &ar71xx_chip_device_stopped, &ar71xx_chip_set_pll_ge, &ar71xx_chip_set_mii_speed, + &ar71xx_chip_set_mii_if, &ar71xx_chip_ddr_flush_ge, &ar71xx_chip_get_eth_pll, &ar71xx_chip_ddr_flush_ip2, Modified: head/sys/mips/atheros/ar71xx_chip.h ============================================================================== --- head/sys/mips/atheros/ar71xx_chip.h Wed May 2 01:14:15 2012 (r234905) +++ head/sys/mips/atheros/ar71xx_chip.h Wed May 2 01:21:57 2012 (r234906) @@ -31,5 +31,6 @@ extern struct ar71xx_cpu_def ar71xx_chip_def; extern void ar71xx_chip_set_mii_speed(uint32_t unit, uint32_t speed); +extern void ar71xx_chip_set_mii_if(uint32_t unit, uint32_t mii_if); #endif Modified: head/sys/mips/atheros/ar71xx_cpudef.h ============================================================================== --- head/sys/mips/atheros/ar71xx_cpudef.h Wed May 2 01:14:15 2012 (r234905) +++ head/sys/mips/atheros/ar71xx_cpudef.h Wed May 2 01:21:57 2012 (r234906) @@ -37,6 +37,7 @@ struct ar71xx_cpu_def { int (* ar71xx_chip_device_stopped) (uint32_t); void (* ar71xx_chip_set_pll_ge) (int, int); void (* ar71xx_chip_set_mii_speed) (uint32_t, uint32_t); + void (* ar71xx_chip_set_mii_if) (uint32_t, ar71xx_mii_mode); void (* ar71xx_chip_ddr_flush_ge) (int); uint32_t (* ar71xx_chip_get_eth_pll) (unsigned int, int); @@ -90,6 +91,11 @@ static inline void ar71xx_device_set_mii ar71xx_cpu_ops->ar71xx_chip_set_mii_speed(unit, speed); } +static inline void ar71xx_device_set_mii_if(int unit, ar71xx_mii_mode mii_cfg) +{ + ar71xx_cpu_ops->ar71xx_chip_set_mii_if(unit, mii_cfg); +} + static inline void ar71xx_device_flush_ddr_ge(int unit) { ar71xx_cpu_ops->ar71xx_chip_ddr_flush_ge(unit); Modified: head/sys/mips/atheros/ar724x_chip.c ============================================================================== --- head/sys/mips/atheros/ar724x_chip.c Wed May 2 01:14:15 2012 (r234905) +++ head/sys/mips/atheros/ar724x_chip.c Wed May 2 01:21:57 2012 (r234906) @@ -56,6 +56,7 @@ __FBSDID("$FreeBSD$"); #include <mips/atheros/ar71xx_cpudef.h> #include <mips/atheros/ar71xx_setup.h> +#include <mips/atheros/ar71xx_chip.h> #include <mips/atheros/ar724x_chip.h> #include <mips/sentry5/s5reg.h> @@ -130,6 +131,13 @@ ar724x_chip_set_mii_speed(uint32_t unit, return; } +/* + * XXX TODO: set the PLL for arge0 only on AR7242. + * The PLL/clock requirements are different. + * + * Otherwise, it's a NULL function for AR7240, AR7241 and + * AR7242 arge1. + */ static void ar724x_chip_set_pll_ge(int unit, int speed) { @@ -229,6 +237,7 @@ struct ar71xx_cpu_def ar724x_chip_def = &ar724x_chip_device_stopped, &ar724x_chip_set_pll_ge, &ar724x_chip_set_mii_speed, + &ar71xx_chip_set_mii_if, &ar724x_chip_ddr_flush_ge, &ar724x_chip_get_eth_pll, &ar724x_chip_ddr_flush_ip2, Modified: head/sys/mips/atheros/ar91xx_chip.c ============================================================================== --- head/sys/mips/atheros/ar91xx_chip.c Wed May 2 01:14:15 2012 (r234905) +++ head/sys/mips/atheros/ar91xx_chip.c Wed May 2 01:21:57 2012 (r234906) @@ -147,6 +147,7 @@ ar91xx_chip_set_pll_ge(int unit, int spe __func__, unit); return; } + ar71xx_chip_set_mii_speed(unit, speed); } static void @@ -211,6 +212,7 @@ struct ar71xx_cpu_def ar91xx_chip_def = &ar91xx_chip_device_stopped, &ar91xx_chip_set_pll_ge, &ar71xx_chip_set_mii_speed, + &ar71xx_chip_set_mii_if, &ar91xx_chip_ddr_flush_ge, &ar91xx_chip_get_eth_pll, &ar91xx_chip_ddr_flush_ip2,
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201205020121.q421LwFU056899>