All of lore.kernel.org
 help / color / mirror / Atom feed
From: Ben Warren <bwarren@qstreams.com>
To: u-boot@lists.denx.de
Subject: [U-Boot-Users] [PATCH 2/2 (resubmit)] NET: Add Ethernet 1000BASE-X support for PPC4xx
Date: Wed, 31 Oct 2007 13:45:37 -0400	[thread overview]
Message-ID: <4728BF41.8040208@qstreams.com> (raw)
In-Reply-To: <4728ABA6.3090101@arlinx.com>

Larry,

I think this can be simplified a bit. More later on...

Larry Johnson wrote:
> This patch adds a new switch: "CONFIG_PHY_DYNAMIC_ANEG".  When this symbol
> is defined, the PHY will advertise it's capabilities for autonegotiation
> based on the capabilities shown in the PHY's status registers, including
> 1000BASE-X.  When "CONFIG_PHY_DYNAMIC_ANEG" is not defined, the PHY will
> advertise hard-coded capabilities, as before.
>
> Signed-off-by: Larry Johnson <lrj@acm.org>
> ---
>
>  common/miiphyutil.c |  155 +++++++++++++++++++++++++++++++++------------------
>  include/miiphy.h    |   21 +++++++
>  2 files changed, 121 insertions(+), 55 deletions(-)
>
> diff --git a/common/miiphyutil.c b/common/miiphyutil.c
> index 58ebc5e..b2f62d0 100644
> --- a/common/miiphyutil.c
> +++ b/common/miiphyutil.c
> @@ -344,101 +344,146 @@ int miiphy_reset (char *devname, unsigned char addr)
>
>  /*****************************************************************************
>   *
> - * Determine the ethernet speed (10/100).
> + * Determine the ethernet speed (10/100/1000).  Return 10 on error.
>   */
>  int miiphy_speed (char *devname, unsigned char addr)
>  {
> -	unsigned short reg;
> +	u16 bmcr;
>
>  #if defined(CONFIG_PHY_GIGE)
> -	if (miiphy_read (devname, addr, PHY_1000BTSR, &reg)) {
> -		printf ("PHY 1000BT Status read failed\n");
> -	} else {
> -		if (reg != 0xFFFF) {
> -			if ((reg & (PHY_1000BTSR_1000FD | PHY_1000BTSR_1000HD))
> -			    != 0) {
> -				return (_1000BASET);
> -			}
> +	u16 btsr;
> +
> +#if defined(CONFIG_PHY_DYNAMIC_ANEG)
>   
I don't think you need this CONFIG. It doesn't really do anything.
> +	u16 bmsr, exsr;
> +
> +	/* Check for 1000BASE-X. */
> +	if (miiphy_read (devname, addr, PHY_BMSR, &bmsr)) {
> +		printf ("PHY status");
> +		goto miiphy_read_failed;
> +	}
> +	if (bmsr & PHY_BMSR_EXT_STAT) {
> +
> +		if (miiphy_read (devname, addr, PHY_EXSR, &exsr)) {
> +			printf ("PHY extended status");
> +			goto miiphy_read_failed;
> +		}
> +		if (exsr & (PHY_EXSR_1000XF | PHY_EXSR_1000XH)) {
> +			/* 1000BASE-X */
> +			return _1000BASET;
>   
Per IEEE 802.3-2005, All PHYs with capabilities > 100Mbps must have 
PHY_MBSR_EXT_STAT set, and EXSR contains capability info for 1000BX and 
1000BT, so you can check for all four here. Please correct me if I'm wrong.
>  		}
>  	}
> +#endif /* defined(CONFIG_PHY_DYNAMIC_ANEG) */
> +
> +	/* Check for 1000BASE-T. */
> +	if (miiphy_read (devname, addr, PHY_1000BTSR, &btsr)) {
> +		printf ("PHY 1000BT status");
> +		goto miiphy_read_failed;
> +	}
> +	if (btsr != 0xFFFF &&
> +	    (btsr & (PHY_1000BTSR_1000FD | PHY_1000BTSR_1000HD))) {
> +		return _1000BASET;
> +	}
>   
And then you don't need to check 1000BTSR
>  #endif /* CONFIG_PHY_GIGE */
>
>  	/* Check Basic Management Control Register first. */
> -	if (miiphy_read (devname, addr, PHY_BMCR, &reg)) {
> -		puts ("PHY speed read failed, assuming 10bT\n");
> -		return (_10BASET);
> +	if (miiphy_read (devname, addr, PHY_BMCR, &bmcr)) {
> +		printf ("PHY speed");
> +		goto miiphy_read_failed;
>  	}
>  	/* Check if auto-negotiation is on. */
> -	if ((reg & PHY_BMCR_AUTON) != 0) {
> +	if (bmcr & PHY_BMCR_AUTON) {
>  		/* Get auto-negotiation results. */
> -		if (miiphy_read (devname, addr, PHY_ANLPAR, &reg)) {
> -			puts ("PHY AN speed read failed, assuming 10bT\n");
> -			return (_10BASET);
> -		}
> -		if ((reg & PHY_ANLPAR_100) != 0) {
> -			return (_100BASET);
> -		} else {
> -			return (_10BASET);
> +		u16 anlpar;
>   
Please move the anlpar declaration to the top of the function
> +
> +		if (miiphy_read (devname, addr, PHY_ANLPAR, &anlpar)) {
> +			printf ("PHY AN speed");
> +			goto miiphy_read_failed;
>  		}
> +		return (anlpar & PHY_ANLPAR_100) ? _100BASET : _10BASET;
>  	}
>  	/* Get speed from basic control settings. */
> -	else if (reg & PHY_BMCR_100MB) {
> -		return (_100BASET);
> -	} else {
> -		return (_10BASET);
> -	}
> +	return (bmcr & PHY_BMCR_100MB) ? _100BASET : _10BASET;
>
> +      miiphy_read_failed:
> +	printf (" read failed, assuming 10BASE-T\n");
> +	return _10BASET;
>  }
>
>  /*****************************************************************************
>   *
> - * Determine full/half duplex.
> + * Determine full/half duplex.  Return half on error.
>   */
>  int miiphy_duplex (char *devname, unsigned char addr)
>  {
> -	unsigned short reg;
> +	u16 bmcr;
>
>  #if defined(CONFIG_PHY_GIGE)
> -	if (miiphy_read (devname, addr, PHY_1000BTSR, &reg)) {
> -		printf ("PHY 1000BT Status read failed\n");
> -	} else {
> -		if ((reg != 0xFFFF) &&
> -		    (reg & (PHY_1000BTSR_1000FD | PHY_1000BTSR_1000HD))) {
> -			if ((reg & PHY_1000BTSR_1000FD) != 0) {
> -				return (FULL);
> -			} else {
> -				return (HALF);
> +	u16 btsr;
> +
> +#if defined(CONFIG_PHY_DYNAMIC_ANEG)
>   
Same as above. Don't need it, I don't think.
> +	u16 bmsr, exsr;
> +
> +	/* Check for 1000BASE-X. */
> +	if (miiphy_read (devname, addr, PHY_BMSR, &bmsr)) {
> +		printf ("PHY status");
> +		goto miiphy_read_failed;
> +	}
> +	if (bmsr & PHY_BMSR_EXT_STAT) {
> +
> +		if (miiphy_read (devname, addr, PHY_EXSR, &exsr)) {
> +			printf ("PHY extended status");
> +			goto miiphy_read_failed;
> +		}
> +		if (exsr & (PHY_EXSR_1000XF | PHY_EXSR_1000XH)) {
> +			/* 1000BASE-X */
> +			u16 anlpar;
> +
> +			if (miiphy_read (devname, addr, PHY_ANLPAR, &anlpar)) {
> +				printf ("1000BASE-X PHY AN duplex");
> +				goto miiphy_read_failed;
>  			}
> +			return (anlpar & PHY_X_ANLPAR_FD) ? FULL : HALF;
> +		}
> +	}
> +#endif /* defined(CONFIG_PHY_DYNAMIC_ANEG) */
> +
> +	/* Check for 1000BASE-T. */
> +	if (miiphy_read (devname, addr, PHY_1000BTSR, &btsr)) {
> +		printf ("PHY 1000BT status");
> +		goto miiphy_read_failed;
> +	}
> +	if (btsr != 0xFFFF) {
> +		if (btsr & PHY_1000BTSR_1000FD) {
> +			return FULL;
> +		} else if (btsr & PHY_1000BTSR_1000HD) {
> +			return HALF;
>  		}
>   
Same as above. All GigE capabilities are listed in EXSR
>  	}
>  #endif /* CONFIG_PHY_GIGE */
>
>  	/* Check Basic Management Control Register first. */
> -	if (miiphy_read (devname, addr, PHY_BMCR, &reg)) {
> -		puts ("PHY duplex read failed, assuming half duplex\n");
> -		return (HALF);
> +	if (miiphy_read (devname, addr, PHY_BMCR, &bmcr)) {
> +		puts ("PHY duplex");
> +		goto miiphy_read_failed;
>  	}
>  	/* Check if auto-negotiation is on. */
> -	if ((reg & PHY_BMCR_AUTON) != 0) {
> +	if (bmcr & PHY_BMCR_AUTON) {
>  		/* Get auto-negotiation results. */
> -		if (miiphy_read (devname, addr, PHY_ANLPAR, &reg)) {
> -			puts ("PHY AN duplex read failed, assuming half duplex\n");
> -			return (HALF);
> -		}
> +		u16 anlpar;
>   
See comment above
> -		if ((reg & (PHY_ANLPAR_10FD | PHY_ANLPAR_TXFD)) != 0) {
> -			return (FULL);
> -		} else {
> -			return (HALF);
> +		if (miiphy_read (devname, addr, PHY_ANLPAR, &anlpar)) {
> +			puts ("PHY AN duplex");
> +			goto miiphy_read_failed;
>  		}
> +		return (anlpar & (PHY_ANLPAR_10FD | PHY_ANLPAR_TXFD)) ?
> +		    FULL : HALF;
>  	}
>  	/* Get speed from basic control settings. */
> -	else if (reg & PHY_BMCR_DPLX) {
> -		return (FULL);
> -	} else {
> -		return (HALF);
> -	}
> +	return (bmcr & PHY_BMCR_DPLX) ? FULL : HALF;
>
> +      miiphy_read_failed:
> +	printf (" read failed, assuming half duplex\n");
> +	return HALF;
>  }
>
>  #ifdef CFG_FAULT_ECHO_LINK_DOWN
> diff --git a/include/miiphy.h b/include/miiphy.h
> index 42f2ad0..83234b9 100644
> --- a/include/miiphy.h
> +++ b/include/miiphy.h
> @@ -85,6 +85,7 @@ int bb_miiphy_write (char *devname, unsigned char addr,
>  #define PHY_ANLPNP		0x08
>  #define PHY_1000BTCR		0x09
>  #define PHY_1000BTSR		0x0A
> +#define PHY_EXSR		0x0F
>  #define PHY_PHYSTS		0x10
>  #define PHY_MIPSCR		0x11
>  #define PHY_MIPGSR		0x12
> @@ -118,6 +119,7 @@ int bb_miiphy_write (char *devname, unsigned char addr,
>  #define PHY_BMSR_100TXH		0x2000
>  #define PHY_BMSR_10TF		0x1000
>  #define PHY_BMSR_10TH		0x0800
> +#define PHY_BMSR_EXT_STAT	0x0100
>  #define PHY_BMSR_PRE_SUP	0x0040
>  #define PHY_BMSR_AUTN_COMP	0x0020
>  #define PHY_BMSR_RF		0x0010
> @@ -130,17 +132,30 @@ int bb_miiphy_write (char *devname, unsigned char addr,
>  #define PHY_ANLPAR_NP		0x8000
>  #define PHY_ANLPAR_ACK		0x4000
>  #define PHY_ANLPAR_RF		0x2000
> +#define PHY_ANLPAR_ASYMP	0x0800
> +#define PHY_ANLPAR_PAUSE	0x0400
>  #define PHY_ANLPAR_T4		0x0200
>  #define PHY_ANLPAR_TXFD		0x0100
>  #define PHY_ANLPAR_TX		0x0080
>  #define PHY_ANLPAR_10FD		0x0040
>  #define PHY_ANLPAR_10		0x0020
>  #define PHY_ANLPAR_100		0x0380	/* we can run at 100 */
> +/* phy ANLPAR 1000BASE-X */
> +#define PHY_X_ANLPAR_NP		0x8000
> +#define PHY_X_ANLPAR_ACK	0x4000
> +#define PHY_X_ANLPAR_RF_MASK	0x3000
> +#define PHY_X_ANLPAR_PAUSE_MASK	0x0180
> +#define PHY_X_ANLPAR_HD		0x0040
> +#define PHY_X_ANLPAR_FD		0x0020
>
>  #define PHY_ANLPAR_PSB_MASK	0x001f
>  #define PHY_ANLPAR_PSB_802_3	0x0001
>  #define PHY_ANLPAR_PSB_802_9	0x0002
>
> +/* phy 1000BTCR */
> +#define PHY_1000BTCR_1000FD	0x0200
> +#define PHY_1000BTCR_1000HD	0x0100
> +
>  /* phy 1000BTSR */
>  #define PHY_1000BTSR_MSCF	0x8000
>  #define PHY_1000BTSR_MSCR	0x4000
> @@ -149,4 +164,10 @@ int bb_miiphy_write (char *devname, unsigned char addr,
>  #define PHY_1000BTSR_1000FD	0x0800
>  #define PHY_1000BTSR_1000HD	0x0400
>
> +/* phy EXSR */
> +#define PHY_EXSR_1000XF		0x8000
> +#define PHY_EXSR_1000XH		0x4000
> +#define PHY_EXSR_1000TF		0x2000
> +#define PHY_EXSR_1000TH		0x1000
> +
>  #endif
>
> -------------------------------------------------------------------------
> This SF.net email is sponsored by: Splunk Inc.
> Still grepping through log files to find problems?  Stop.
> Now Search log events and configuration files using AJAX and a browser.
> Download your FREE copy of Splunk now >> http://get.splunk.com/
> _______________________________________________
> U-Boot-Users mailing list
> U-Boot-Users at lists.sourceforge.net
> https://lists.sourceforge.net/lists/listinfo/u-boot-users
>
>   
Nice work.

regards,
Ben

  reply	other threads:[~2007-10-31 17:45 UTC|newest]

Thread overview: 11+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2007-10-31 16:21 [U-Boot-Users] [PATCH 2/2 (resubmit)] NET: Add Ethernet 1000BASE-X support for PPC4xx Larry Johnson
2007-10-31 17:45 ` Ben Warren [this message]
2007-10-31 20:31   ` Larry Johnson
     [not found]     ` <4729E1A0.3010200@qstreams.com>
2007-11-14 16:59       ` Larry Johnson
2007-11-14 20:04         ` Stefan Roese
2007-11-14 21:37           ` Larry Johnson
2007-11-15  6:05             ` Stefan Roese
2007-11-19 20:00               ` [U-Boot-Users] " Larry Johnson
2007-11-19 20:19                 ` Larry Johnson
2007-11-14 20:21         ` [U-Boot-Users] [PATCH 2/2 (resubmit)] " Ben Warren
  -- strict thread matches above, loose matches on Subject: below --
2007-11-01 13:46 Larry Johnson

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=4728BF41.8040208@qstreams.com \
    --to=bwarren@qstreams.com \
    --cc=u-boot@lists.denx.de \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.