1 /* 2 * (C) Copyright 2000-2004 3 * Wolfgang Denk, DENX Software Engineering, wd@denx.de. 4 * 5 * (C) Copyright 2012 6 * Ilya Yanok <ilya.yanok@gmail.com> 7 * 8 * SPDX-License-Identifier: GPL-2.0+ 9 */ 10 #include <common.h> 11 #include <errno.h> 12 #include <spl.h> 13 #include <net.h> 14 #include <linux/libfdt.h> 15 16 DECLARE_GLOBAL_DATA_PTR; 17 18 #if defined(CONFIG_SPL_ETH_SUPPORT) || defined(CONFIG_SPL_USB_ETHER) 19 static ulong spl_net_load_read(struct spl_load_info *load, ulong sector, 20 ulong count, void *buf) 21 { 22 debug("%s: sector %lx, count %lx, buf %lx\n", 23 __func__, sector, count, (ulong)buf); 24 memcpy(buf, (void *)(load_addr + sector), count); 25 return count; 26 } 27 28 static int spl_net_load_image(struct spl_image_info *spl_image, 29 struct spl_boot_device *bootdev) 30 { 31 struct image_header *header = (struct image_header *)load_addr; 32 int rv; 33 34 env_init(); 35 env_relocate(); 36 env_set("autoload", "yes"); 37 rv = eth_initialize(); 38 if (rv == 0) { 39 printf("No Ethernet devices found\n"); 40 return -ENODEV; 41 } 42 if (bootdev->boot_device_name) 43 env_set("ethact", bootdev->boot_device_name); 44 rv = net_loop(BOOTP); 45 if (rv < 0) { 46 printf("Problem booting with BOOTP\n"); 47 return rv; 48 } 49 50 if (IS_ENABLED(CONFIG_SPL_LOAD_FIT) && 51 image_get_magic(header) == FDT_MAGIC) { 52 struct spl_load_info load; 53 54 debug("Found FIT\n"); 55 load.bl_len = 1; 56 load.read = spl_net_load_read; 57 rv = spl_load_simple_fit(spl_image, &load, 0, header); 58 } else { 59 debug("Legacy image\n"); 60 61 rv = spl_parse_image_header(spl_image, header); 62 if (rv) 63 return rv; 64 65 memcpy((void *)spl_image->load_addr, header, spl_image->size); 66 } 67 68 return rv; 69 } 70 #endif 71 72 #ifdef CONFIG_SPL_ETH_SUPPORT 73 int spl_net_load_image_cpgmac(struct spl_image_info *spl_image, 74 struct spl_boot_device *bootdev) 75 { 76 #ifdef CONFIG_SPL_ETH_DEVICE 77 bootdev->boot_device_name = CONFIG_SPL_ETH_DEVICE; 78 #endif 79 80 return spl_net_load_image(spl_image, bootdev); 81 } 82 SPL_LOAD_IMAGE_METHOD("eth device", 0, BOOT_DEVICE_CPGMAC, 83 spl_net_load_image_cpgmac); 84 #endif 85 86 #ifdef CONFIG_SPL_USB_ETHER 87 int spl_net_load_image_usb(struct spl_image_info *spl_image, 88 struct spl_boot_device *bootdev) 89 { 90 bootdev->boot_device_name = "usb_ether"; 91 92 return spl_net_load_image(spl_image, bootdev); 93 } 94 SPL_LOAD_IMAGE_METHOD("USB eth", 0, BOOT_DEVICE_USBETH, spl_net_load_image_usb); 95 #endif 96