uboot/net/eth_common.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0+
   2/*
   3 * (C) Copyright 2001-2015
   4 * Wolfgang Denk, DENX Software Engineering, wd@denx.de.
   5 * Joe Hershberger, National Instruments
   6 */
   7
   8#include <common.h>
   9#include <bootstage.h>
  10#include <dm.h>
  11#include <env.h>
  12#include <miiphy.h>
  13#include <net.h>
  14#include "eth_internal.h"
  15
  16int eth_env_get_enetaddr_by_index(const char *base_name, int index,
  17                                 uchar *enetaddr)
  18{
  19        char enetvar[32];
  20        sprintf(enetvar, index ? "%s%daddr" : "%saddr", base_name, index);
  21        return eth_env_get_enetaddr(enetvar, enetaddr);
  22}
  23
  24int eth_env_set_enetaddr_by_index(const char *base_name, int index,
  25                                 uchar *enetaddr)
  26{
  27        char enetvar[32];
  28        sprintf(enetvar, index ? "%s%daddr" : "%saddr", base_name, index);
  29        return eth_env_set_enetaddr(enetvar, enetaddr);
  30}
  31
  32void eth_common_init(void)
  33{
  34        bootstage_mark(BOOTSTAGE_ID_NET_ETH_START);
  35#if CONFIG_IS_ENABLED(ETH)
  36#if defined(CONFIG_MII) || defined(CONFIG_CMD_MII) || defined(CONFIG_PHYLIB)
  37        miiphy_init();
  38#endif
  39
  40#ifdef CONFIG_PHYLIB
  41        phy_init();
  42#endif
  43#endif
  44}
  45
  46int eth_mac_skip(int index)
  47{
  48        char enetvar[15];
  49        char *skip_state;
  50
  51        sprintf(enetvar, index ? "eth%dmacskip" : "ethmacskip", index);
  52        skip_state = env_get(enetvar);
  53        return skip_state != NULL;
  54}
  55
  56void eth_current_changed(void)
  57{
  58        char *act = env_get("ethact");
  59        char *ethrotate;
  60
  61        /*
  62         * The call to eth_get_dev() below has a side effect of rotating
  63         * ethernet device if uc_priv->current == NULL. This is not what
  64         * we want when 'ethrotate' variable is 'no'.
  65         */
  66        ethrotate = env_get("ethrotate");
  67        if ((ethrotate != NULL) && (strcmp(ethrotate, "no") == 0))
  68                return;
  69
  70        /* update current ethernet name */
  71        if (eth_get_dev()) {
  72                if (act == NULL || strcmp(act, eth_get_name()) != 0)
  73                        env_set("ethact", eth_get_name());
  74        }
  75        /*
  76         * remove the variable completely if there is no active
  77         * interface
  78         */
  79        else if (act != NULL)
  80                env_set("ethact", NULL);
  81}
  82
  83void eth_try_another(int first_restart)
  84{
  85        static void *first_failed;
  86        char *ethrotate;
  87
  88        /*
  89         * Do not rotate between network interfaces when
  90         * 'ethrotate' variable is set to 'no'.
  91         */
  92        ethrotate = env_get("ethrotate");
  93        if ((ethrotate != NULL) && (strcmp(ethrotate, "no") == 0))
  94                return;
  95
  96        if (!eth_get_dev())
  97                return;
  98
  99        if (first_restart)
 100                first_failed = eth_get_dev();
 101
 102        eth_set_current_to_next();
 103
 104        eth_current_changed();
 105
 106        if (first_failed == eth_get_dev())
 107                net_restart_wrap = 1;
 108}
 109
 110void eth_set_current(void)
 111{
 112        static char *act;
 113        static int  env_changed_id;
 114        int     env_id;
 115
 116        env_id = env_get_id();
 117        if ((act == NULL) || (env_changed_id != env_id)) {
 118                act = env_get("ethact");
 119                env_changed_id = env_id;
 120        }
 121
 122        if (act == NULL) {
 123                char *ethprime = env_get("ethprime");
 124                void *dev = NULL;
 125
 126                if (ethprime)
 127                        dev = eth_get_dev_by_name(ethprime);
 128                if (dev)
 129                        eth_set_dev(dev);
 130                else
 131                        eth_set_dev(NULL);
 132        } else {
 133                eth_set_dev(eth_get_dev_by_name(act));
 134        }
 135
 136        eth_current_changed();
 137}
 138
 139const char *eth_get_name(void)
 140{
 141        return eth_get_dev() ? eth_get_dev()->name : "unknown";
 142}
 143