diff options
| -rw-r--r-- | net/eth-uclass.c | 40 | 
1 files changed, 32 insertions, 8 deletions
| diff --git a/net/eth-uclass.c b/net/eth-uclass.c index 4e3933fd05f..e34d7af0229 100644 --- a/net/eth-uclass.c +++ b/net/eth-uclass.c @@ -47,6 +47,8 @@ struct eth_uclass_priv {  /* eth_errno - This stores the most recent failure code from DM functions */  static int eth_errno; +/* Are we currently in eth_init() or eth_halt()? */ +static bool in_init_halt;  /* board-specific Ethernet Interface initializations. */  __weak int board_interface_eth_init(struct udevice *dev, @@ -284,11 +286,19 @@ U_BOOT_ENV_CALLBACK(ethaddr, on_ethaddr);  int eth_init(void)  { -	char *ethact = env_get("ethact"); -	char *ethrotate = env_get("ethrotate");  	struct udevice *current = NULL;  	struct udevice *old_current;  	int ret = -ENODEV; +	char *ethrotate; +	char *ethact; + +	if (in_init_halt) +		return -EBUSY; + +	in_init_halt = true; + +	ethact = env_get("ethact"); +	ethrotate = env_get("ethrotate");  	/*  	 * When 'ethrotate' variable is set to 'no' and 'ethact' variable @@ -297,8 +307,10 @@ int eth_init(void)  	if ((ethrotate != NULL) && (strcmp(ethrotate, "no") == 0)) {  		if (ethact) {  			current = eth_get_dev_by_name(ethact); -			if (!current) -				return -EINVAL; +			if (!current) { +				ret = -EINVAL; +				goto end; +			}  		}  	} @@ -306,7 +318,8 @@ int eth_init(void)  		current = eth_get_dev();  		if (!current) {  			log_err("No ethernet found.\n"); -			return -ENODEV; +			ret = -ENODEV; +			goto end;  		}  	} @@ -323,7 +336,8 @@ int eth_init(void)  					priv->state = ETH_STATE_ACTIVE;  					priv->running = true; -					return 0; +					ret = 0; +					goto end;  				}  			} else {  				ret = eth_errno; @@ -343,6 +357,8 @@ int eth_init(void)  		current = eth_get_dev();  	} while (old_current != current); +end: +	in_init_halt = false;  	return ret;  } @@ -351,17 +367,25 @@ void eth_halt(void)  	struct udevice *current;  	struct eth_device_priv *priv; +	if (in_init_halt) +		return; + +	in_init_halt = true; +  	current = eth_get_dev();  	if (!current) -		return; +		goto end;  	priv = dev_get_uclass_priv(current);  	if (!priv || !priv->running) -		return; +		goto end;  	eth_get_ops(current)->stop(current);  	priv->state = ETH_STATE_PASSIVE;  	priv->running = false; + +end: +	in_init_halt = false;  }  int eth_is_active(struct udevice *dev) | 
