]> git.karo-electronics.de Git - karo-tx-uboot.git/blobdiff - net/eth.c
net: Remove duplicate bootfile syncing functionality
[karo-tx-uboot.git] / net / eth.c
index 13b7723bb47e545bdf480ccd65c2654f1e74ba35..a40abb5f949dd36d721342afe4eca4f0d3246296 100644 (file)
--- a/net/eth.c
+++ b/net/eth.c
@@ -32,7 +32,7 @@ void eth_parse_enetaddr(const char *addr, uchar *enetaddr)
 int eth_getenv_enetaddr(char *name, uchar *enetaddr)
 {
        eth_parse_enetaddr(getenv(name), enetaddr);
-       return is_valid_ether_addr(enetaddr);
+       return is_valid_ethaddr(enetaddr);
 }
 
 int eth_setenv_enetaddr(char *name, const uchar *enetaddr)
@@ -60,25 +60,55 @@ static inline int eth_setenv_enetaddr_by_index(const char *base_name, int index,
        return eth_setenv_enetaddr(enetvar, enetaddr);
 }
 
-static void eth_env_init(void)
-{
-       const char *s;
-
-       s = getenv("bootfile");
-       if (s != NULL)
-               copy_filename(BootFile, s, sizeof(BootFile));
-}
-
 static int eth_mac_skip(int index)
 {
        char enetvar[15];
        char *skip_state;
+
        sprintf(enetvar, index ? "eth%dmacskip" : "ethmacskip", index);
-       return ((skip_state = getenv(enetvar)) != NULL);
+       skip_state = getenv(enetvar);
+       return skip_state != NULL;
 }
 
 static void eth_current_changed(void);
 
+/*
+ * CPU and board-specific Ethernet initializations.  Aliased function
+ * signals caller to move on
+ */
+static int __def_eth_init(bd_t *bis)
+{
+       return -1;
+}
+int cpu_eth_init(bd_t *bis) __attribute__((weak, alias("__def_eth_init")));
+int board_eth_init(bd_t *bis) __attribute__((weak, alias("__def_eth_init")));
+
+static void eth_common_init(void)
+{
+       bootstage_mark(BOOTSTAGE_ID_NET_ETH_START);
+#if defined(CONFIG_MII) || defined(CONFIG_CMD_MII) || defined(CONFIG_PHYLIB)
+       miiphy_init();
+#endif
+
+#ifdef CONFIG_PHYLIB
+       phy_init();
+#endif
+
+       /*
+        * If board-specific initialization exists, call it.
+        * If not, call a CPU-specific one
+        */
+       if (board_eth_init != __def_eth_init) {
+               if (board_eth_init(gd->bd) < 0)
+                       printf("Board Net Initialization Failed\n");
+       } else if (cpu_eth_init != __def_eth_init) {
+               if (cpu_eth_init(gd->bd) < 0)
+                       printf("CPU Net Initialization Failed\n");
+       } else {
+               printf("Net Initialization Skipped\n");
+       }
+}
+
 #ifdef CONFIG_DM_ETH
 /**
  * struct eth_device_priv - private structure for each Ethernet device
@@ -239,6 +269,31 @@ int eth_get_dev_index(void)
        return -1;
 }
 
+static int eth_write_hwaddr(struct udevice *dev)
+{
+       struct eth_pdata *pdata = dev->platdata;
+       int ret = 0;
+
+       if (!dev || !device_active(dev))
+               return -EINVAL;
+
+       /* seq is valid since the device is active */
+       if (eth_get_ops(dev)->write_hwaddr && !eth_mac_skip(dev->seq)) {
+               if (!is_valid_ethaddr(pdata->enetaddr)) {
+                       printf("\nError: %s address %pM illegal value\n",
+                              dev->name, pdata->enetaddr);
+                       return -EINVAL;
+               }
+
+               ret = eth_get_ops(dev)->write_hwaddr(dev);
+               if (ret)
+                       printf("\nWarning: %s failed to set MAC address\n",
+                              dev->name);
+       }
+
+       return ret;
+}
+
 int eth_init(void)
 {
        struct udevice *current;
@@ -258,13 +313,22 @@ int eth_init(void)
                if (device_active(current)) {
                        uchar env_enetaddr[6];
                        struct eth_pdata *pdata = current->platdata;
+                       int enetaddr_changed = 0;
 
                        /* Sync environment with network device */
                        if (eth_getenv_enetaddr_by_index("eth", current->seq,
-                                                        env_enetaddr))
+                                                        env_enetaddr)) {
+                               enetaddr_changed = memcmp(pdata->enetaddr,
+                                       env_enetaddr, 6);
                                memcpy(pdata->enetaddr, env_enetaddr, 6);
-                       else
+                       } else {
+                               memset(env_enetaddr, 0, 6);
+                               enetaddr_changed = memcmp(pdata->enetaddr,
+                                       env_enetaddr, 6);
                                memset(pdata->enetaddr, 0, 6);
+                       }
+                       if (enetaddr_changed)
+                               eth_write_hwaddr(current);
 
                        ret = eth_get_ops(current)->start(current);
                        if (ret >= 0) {
@@ -274,8 +338,9 @@ int eth_init(void)
                                priv->state = ETH_STATE_ACTIVE;
                                return 0;
                        }
-               } else
+               } else {
                        ret = eth_errno;
+               }
 
                debug("FAIL\n");
 
@@ -344,7 +409,9 @@ int eth_rx(void)
                ret = eth_get_ops(current)->recv(current, &packet);
                if (ret > 0)
                        net_process_received_packet(packet, ret);
-               else
+               if (ret >= 0 && eth_get_ops(current)->free_pkt)
+                       eth_get_ops(current)->free_pkt(current, packet, ret);
+               if (ret <= 0)
                        break;
        }
        if (ret == -EAGAIN)
@@ -356,38 +423,12 @@ int eth_rx(void)
        return ret;
 }
 
-static int eth_write_hwaddr(struct udevice *dev)
-{
-       struct eth_pdata *pdata = dev->platdata;
-       int ret = 0;
-
-       if (!dev || !device_active(dev))
-               return -EINVAL;
-
-       /* seq is valid since the device is active */
-       if (eth_get_ops(dev)->write_hwaddr && !eth_mac_skip(dev->seq)) {
-               if (!is_valid_ether_addr(pdata->enetaddr)) {
-                       printf("\nError: %s address %pM illegal value\n",
-                              dev->name, pdata->enetaddr);
-                       return -EINVAL;
-               }
-
-               ret = eth_get_ops(dev)->write_hwaddr(dev);
-               if (ret)
-                       printf("\nWarning: %s failed to set MAC address\n",
-                              dev->name);
-       }
-
-       return ret;
-}
-
 int eth_initialize(void)
 {
        int num_devices = 0;
        struct udevice *dev;
 
-       bootstage_mark(BOOTSTAGE_ID_NET_ETH_START);
-       eth_env_init();
+       eth_common_init();
 
        /*
         * Devices need to write the hwaddr even if not started so that Linux
@@ -467,8 +508,8 @@ static int eth_post_probe(struct udevice *dev)
                eth_get_ops(dev)->read_rom_hwaddr(dev);
 
        eth_getenv_enetaddr_by_index("eth", dev->seq, env_enetaddr);
-       if (!is_zero_ether_addr(env_enetaddr)) {
-               if (!is_zero_ether_addr(pdata->enetaddr) &&
+       if (!is_zero_ethaddr(env_enetaddr)) {
+               if (!is_zero_ethaddr(pdata->enetaddr) &&
                    memcmp(pdata->enetaddr, env_enetaddr, 6)) {
                        printf("\nWarning: %s MAC addresses don't match:\n",
                               dev->name);
@@ -480,14 +521,20 @@ static int eth_post_probe(struct udevice *dev)
 
                /* Override the ROM MAC address */
                memcpy(pdata->enetaddr, env_enetaddr, 6);
-       } else if (is_valid_ether_addr(pdata->enetaddr)) {
+       } else if (is_valid_ethaddr(pdata->enetaddr)) {
                eth_setenv_enetaddr_by_index("eth", dev->seq, pdata->enetaddr);
                printf("\nWarning: %s using MAC address from ROM\n",
                       dev->name);
-       } else if (is_zero_ether_addr(pdata->enetaddr)) {
+       } else if (is_zero_ethaddr(pdata->enetaddr)) {
+#ifdef CONFIG_NET_RANDOM_ETHADDR
+               net_random_ethaddr(pdata->enetaddr);
+               printf("\nWarning: %s (eth%d) using random MAC address - %pM\n",
+                      dev->name, dev->seq, pdata->enetaddr);
+#else
                printf("\nError: %s address not set.\n",
                       dev->name);
                return -EINVAL;
+#endif
        }
 
        return 0;
@@ -514,16 +561,6 @@ UCLASS_DRIVER(eth) = {
 #endif
 
 #ifndef CONFIG_DM_ETH
-/*
- * CPU and board-specific Ethernet initializations.  Aliased function
- * signals caller to move on
- */
-static int __def_eth_init(bd_t *bis)
-{
-       return -1;
-}
-int cpu_eth_init(bd_t *bis) __attribute__((weak, alias("__def_eth_init")));
-int board_eth_init(bd_t *bis) __attribute__((weak, alias("__def_eth_init")));
 
 #ifdef CONFIG_API
 static struct {
@@ -605,39 +642,46 @@ int eth_write_hwaddr(struct eth_device *dev, const char *base_name,
 
        eth_getenv_enetaddr_by_index(base_name, eth_number, env_enetaddr);
 
-       if (!is_zero_ether_addr(env_enetaddr)) {
-               if (!is_zero_ether_addr(dev->enetaddr) &&
+       if (!is_zero_ethaddr(env_enetaddr)) {
+               if (!is_zero_ethaddr(dev->enetaddr) &&
                    memcmp(dev->enetaddr, env_enetaddr, 6)) {
                        printf("\nWarning: %s MAC addresses don't match:\n",
-                               dev->name);
+                              dev->name);
                        printf("Address in SROM is         %pM\n",
-                               dev->enetaddr);
+                              dev->enetaddr);
                        printf("Address in environment is  %pM\n",
-                               env_enetaddr);
+                              env_enetaddr);
                }
 
                memcpy(dev->enetaddr, env_enetaddr, 6);
-       } else if (is_valid_ether_addr(dev->enetaddr)) {
+       } else if (is_valid_ethaddr(dev->enetaddr)) {
                eth_setenv_enetaddr_by_index(base_name, eth_number,
                                             dev->enetaddr);
                printf("\nWarning: %s using MAC address from net device\n",
-                       dev->name);
-       } else if (is_zero_ether_addr(dev->enetaddr)) {
+                      dev->name);
+       } else if (is_zero_ethaddr(dev->enetaddr)) {
+#ifdef CONFIG_NET_RANDOM_ETHADDR
+               net_random_ethaddr(dev->enetaddr);
+               printf("\nWarning: %s (eth%d) using random MAC address - %pM\n",
+                      dev->name, eth_number, dev->enetaddr);
+#else
                printf("\nError: %s address not set.\n",
                       dev->name);
                return -EINVAL;
+#endif
        }
 
        if (dev->write_hwaddr && !eth_mac_skip(eth_number)) {
-               if (!is_valid_ether_addr(dev->enetaddr)) {
+               if (!is_valid_ethaddr(dev->enetaddr)) {
                        printf("\nError: %s address %pM illegal value\n",
-                                dev->name, dev->enetaddr);
+                              dev->name, dev->enetaddr);
                        return -EINVAL;
                }
 
                ret = dev->write_hwaddr(dev);
                if (ret)
-                       printf("\nWarning: %s failed to set MAC address\n", dev->name);
+                       printf("\nWarning: %s failed to set MAC address\n",
+                              dev->name);
        }
 
        return ret;
@@ -651,7 +695,8 @@ int eth_register(struct eth_device *dev)
        assert(strlen(dev->name) < sizeof(dev->name));
 
        if (!eth_devices) {
-               eth_current = eth_devices = dev;
+               eth_devices = dev;
+               eth_current = dev;
                eth_current_changed();
        } else {
                for (d = eth_devices; d->next != eth_devices; d = d->next)
@@ -698,32 +743,10 @@ int eth_unregister(struct eth_device *dev)
 int eth_initialize(void)
 {
        int num_devices = 0;
+
        eth_devices = NULL;
        eth_current = NULL;
-
-       bootstage_mark(BOOTSTAGE_ID_NET_ETH_START);
-#if defined(CONFIG_MII) || defined(CONFIG_CMD_MII) || defined(CONFIG_PHYLIB)
-       miiphy_init();
-#endif
-
-#ifdef CONFIG_PHYLIB
-       phy_init();
-#endif
-
-       eth_env_init();
-
-       /*
-        * If board-specific initialization exists, call it.
-        * If not, call a CPU-specific one
-        */
-       if (board_eth_init != __def_eth_init) {
-               if (board_eth_init(gd->bd) < 0)
-                       printf("Board Net Initialization Failed\n");
-       } else if (cpu_eth_init != __def_eth_init) {
-               if (cpu_eth_init(gd->bd) < 0)
-                       printf("CPU Net Initialization Failed\n");
-       } else
-               printf("Net Initialization Skipped\n");
+       eth_common_init();
 
        if (!eth_devices) {
                puts("No ethernet found.\n");
@@ -766,14 +789,14 @@ int eth_initialize(void)
  * mcast_addr: multicast ipaddr from which multicast Mac is made
  * join: 1=join, 0=leave.
  */
-int eth_mcast_join(IPaddr_t mcast_ip, int join)
+int eth_mcast_join(struct in_addr mcast_ip, int join)
 {
        u8 mcast_mac[6];
        if (!eth_current || !eth_current->mcast)
                return -1;
-       mcast_mac[5] = htonl(mcast_ip) & 0xff;
-       mcast_mac[4] = (htonl(mcast_ip)>>8) & 0xff;
-       mcast_mac[3] = (htonl(mcast_ip)>>16) & 0x7f;
+       mcast_mac[5] = htonl(mcast_ip.s_addr) & 0xff;
+       mcast_mac[4] = (htonl(mcast_ip.s_addr)>>8) & 0xff;
+       mcast_mac[3] = (htonl(mcast_ip.s_addr)>>16) & 0x7f;
        mcast_mac[2] = 0x5e;
        mcast_mac[1] = 0x0;
        mcast_mac[0] = 0x1;
@@ -820,10 +843,21 @@ int eth_init(void)
        dev = eth_devices;
        do {
                uchar env_enetaddr[6];
+               int enetaddr_changed = 0;
 
                if (eth_getenv_enetaddr_by_index("eth", dev->index,
-                                                env_enetaddr))
+                                                env_enetaddr)) {
+                       enetaddr_changed = memcmp(dev->enetaddr,
+                               env_enetaddr, 6);
                        memcpy(dev->enetaddr, env_enetaddr, 6);
+               } else {
+                       memset(env_enetaddr, 0, 6);
+                       enetaddr_changed = memcmp(dev->enetaddr,
+                               env_enetaddr, 6);
+                       memset(dev->enetaddr, 0, 6);
+               }
+               if (enetaddr_changed)
+                       eth_write_hwaddr(dev, "eth", dev->index);
 
                dev = dev->next;
        } while (dev != eth_devices);
@@ -956,7 +990,7 @@ void eth_try_another(int first_restart)
        eth_current_changed();
 
        if (first_failed == eth_get_dev())
-               NetRestartWrap = 1;
+               net_restart_wrap = 1;
 }
 
 void eth_set_current(void)