0087-sunxi-Add-temporary-RISC-V-version-of-board-code.patch 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725
  1. From e3152c690732fb141500379f32fbe2203fa47059 Mon Sep 17 00:00:00 2001
  2. From: Samuel Holland <[email protected]>
  3. Date: Sat, 6 Aug 2022 00:48:38 -0500
  4. Subject: [PATCH 87/90] sunxi: Add temporary RISC-V version of board code
  5. Signed-off-by: Samuel Holland <[email protected]>
  6. ---
  7. board/sunxi/Makefile | 3 +-
  8. board/sunxi/board-riscv.c | 687 +++++++++++++++++++++++++++++++++
  9. include/configs/sunxi-common.h | 1 -
  10. 3 files changed, 689 insertions(+), 2 deletions(-)
  11. create mode 100644 board/sunxi/board-riscv.c
  12. --- a/board/sunxi/Makefile
  13. +++ b/board/sunxi/Makefile
  14. @@ -6,7 +6,8 @@
  15. #
  16. # (C) Copyright 2000-2003
  17. # Wolfgang Denk, DENX Software Engineering, [email protected].
  18. -obj-y += board.o
  19. +obj-$(CONFIG_ARM) += board.o
  20. +obj-$(CONFIG_RISCV) += board-riscv.o
  21. obj-$(CONFIG_SUN7I_GMAC) += gmac.o
  22. obj-$(CONFIG_MACH_SUN4I) += dram_sun4i_auto.o
  23. obj-$(CONFIG_MACH_SUN5I) += dram_sun5i_auto.o
  24. --- /dev/null
  25. +++ b/board/sunxi/board-riscv.c
  26. @@ -0,0 +1,687 @@
  27. +// SPDX-License-Identifier: GPL-2.0+
  28. +/*
  29. + * (C) Copyright 2012-2013 Henrik Nordstrom <[email protected]>
  30. + * (C) Copyright 2013 Luke Kenneth Casson Leighton <[email protected]>
  31. + *
  32. + * (C) Copyright 2007-2011
  33. + * Allwinner Technology Co., Ltd. <www.allwinnertech.com>
  34. + * Tom Cubie <[email protected]>
  35. + *
  36. + * Some board init for the Allwinner A10-evb board.
  37. + */
  38. +
  39. +#include <dm.h>
  40. +#include <cpu.h>
  41. +#include <env.h>
  42. +#include <env_internal.h>
  43. +#include <fdt_support.h>
  44. +#include <generic-phy.h>
  45. +#include <image.h>
  46. +#include <init.h>
  47. +#include <net.h>
  48. +#include <phy-sun4i-usb.h>
  49. +#include <ram.h>
  50. +#include <remoteproc.h>
  51. +#include <spl.h>
  52. +#include <status_led.h>
  53. +#include <sunxi_image.h>
  54. +#include <u-boot/crc.h>
  55. +#include <asm/csr.h>
  56. +#include <asm/global_data.h>
  57. +#include <asm/io.h>
  58. +
  59. +#ifdef CONFIG_RISCV
  60. +int board_init(void)
  61. +{
  62. + /* https://lore.kernel.org/u-boot/[email protected]/ */
  63. + return cpu_probe_all();
  64. +}
  65. +
  66. +int sunxi_get_sid(unsigned int *sid)
  67. +{
  68. + return -ENODEV;
  69. +}
  70. +
  71. +#define SPL_ADDR CONFIG_SUNXI_SRAM_ADDRESS
  72. +
  73. +/* The low 8-bits of the 'boot_media' field in the SPL header */
  74. +#define SUNXI_BOOTED_FROM_MMC0 0
  75. +#define SUNXI_BOOTED_FROM_NAND 1
  76. +#define SUNXI_BOOTED_FROM_MMC2 2
  77. +#define SUNXI_BOOTED_FROM_SPI 3
  78. +#define SUNXI_BOOTED_FROM_MMC0_HIGH 0x10
  79. +#define SUNXI_BOOTED_FROM_MMC2_HIGH 0x12
  80. +
  81. +#define SUNXI_INVALID_BOOT_SOURCE -1
  82. +
  83. +static int sunxi_egon_valid(struct boot_file_head *egon_head)
  84. +{
  85. + return !memcmp(egon_head->magic, BOOT0_MAGIC, 8); /* eGON.BT0 */
  86. +}
  87. +
  88. +static int sunxi_toc0_valid(struct toc0_main_info *toc0_info)
  89. +{
  90. + return !memcmp(toc0_info->name, TOC0_MAIN_INFO_NAME, 8); /* TOC0.GLH */
  91. +}
  92. +
  93. +static int sunxi_get_boot_source(void)
  94. +{
  95. + struct boot_file_head *egon_head = (void *)SPL_ADDR;
  96. + struct toc0_main_info *toc0_info = (void *)SPL_ADDR;
  97. +
  98. + /*
  99. + * On the ARMv5 SoCs, the SPL header in SRAM is overwritten by the
  100. + * exception vectors in U-Boot proper, so we won't find any
  101. + * information there. Also the FEL stash is only valid in the SPL,
  102. + * so we can't use that either. So if this is called from U-Boot
  103. + * proper, just return MMC0 as a placeholder, for now.
  104. + */
  105. + if (IS_ENABLED(CONFIG_MACH_SUNIV) &&
  106. + !IS_ENABLED(CONFIG_SPL_BUILD))
  107. + return SUNXI_BOOTED_FROM_MMC0;
  108. +
  109. + if (sunxi_egon_valid(egon_head))
  110. + return readb(&egon_head->boot_media);
  111. + if (sunxi_toc0_valid(toc0_info))
  112. + return readb(&toc0_info->platform[0]);
  113. +
  114. + /* Not a valid image, so we must have been booted via FEL. */
  115. + return SUNXI_INVALID_BOOT_SOURCE;
  116. +}
  117. +
  118. +/* The sunxi internal brom will try to loader external bootloader
  119. + * from mmc0, nand flash, mmc2.
  120. + */
  121. +uint32_t sunxi_get_boot_device(void)
  122. +{
  123. + int boot_source = sunxi_get_boot_source();
  124. +
  125. + /*
  126. + * When booting from the SD card or NAND memory, the "eGON.BT0"
  127. + * signature is expected to be found in memory at the address 0x0004
  128. + * (see the "mksunxiboot" tool, which generates this header).
  129. + *
  130. + * When booting in the FEL mode over USB, this signature is patched in
  131. + * memory and replaced with something else by the 'fel' tool. This other
  132. + * signature is selected in such a way, that it can't be present in a
  133. + * valid bootable SD card image (because the BROM would refuse to
  134. + * execute the SPL in this case).
  135. + *
  136. + * This checks for the signature and if it is not found returns to
  137. + * the FEL code in the BROM to wait and receive the main u-boot
  138. + * binary over USB. If it is found, it determines where SPL was
  139. + * read from.
  140. + */
  141. + switch (boot_source) {
  142. + case SUNXI_INVALID_BOOT_SOURCE:
  143. + return BOOT_DEVICE_BOARD;
  144. + case SUNXI_BOOTED_FROM_MMC0:
  145. + case SUNXI_BOOTED_FROM_MMC0_HIGH:
  146. + return BOOT_DEVICE_MMC1;
  147. + case SUNXI_BOOTED_FROM_NAND:
  148. + return BOOT_DEVICE_NAND;
  149. + case SUNXI_BOOTED_FROM_MMC2:
  150. + case SUNXI_BOOTED_FROM_MMC2_HIGH:
  151. + return BOOT_DEVICE_MMC2;
  152. + case SUNXI_BOOTED_FROM_SPI:
  153. + return BOOT_DEVICE_SPI;
  154. + }
  155. +
  156. + panic("Unknown boot source %d\n", boot_source);
  157. + return -1; /* Never reached */
  158. +}
  159. +
  160. +uint32_t sunxi_get_spl_size(void)
  161. +{
  162. + struct boot_file_head *egon_head = (void *)SPL_ADDR;
  163. + struct toc0_main_info *toc0_info = (void *)SPL_ADDR;
  164. +
  165. + if (sunxi_egon_valid(egon_head))
  166. + return readl(&egon_head->length);
  167. + if (sunxi_toc0_valid(toc0_info))
  168. + return readl(&toc0_info->length);
  169. +
  170. + /* Not a valid image, so use the default U-Boot offset. */
  171. + return 0;
  172. +}
  173. +
  174. +/*
  175. + * The eGON SPL image can be located at 8KB or at 128KB into an SD card or
  176. + * an eMMC device. The boot source has bit 4 set in the latter case.
  177. + * By adding 120KB to the normal offset when booting from a "high" location
  178. + * we can support both cases.
  179. + * Also U-Boot proper is located at least 32KB after the SPL, but will
  180. + * immediately follow the SPL if that is bigger than that.
  181. + */
  182. +unsigned long spl_mmc_get_uboot_raw_sector(struct mmc *mmc,
  183. + unsigned long raw_sect)
  184. +{
  185. + unsigned long spl_size = sunxi_get_spl_size();
  186. + unsigned long sector;
  187. +
  188. + sector = max(raw_sect, spl_size / 512);
  189. +
  190. + switch (sunxi_get_boot_source()) {
  191. + case SUNXI_BOOTED_FROM_MMC0_HIGH:
  192. + case SUNXI_BOOTED_FROM_MMC2_HIGH:
  193. + sector += (128 - 8) * 2;
  194. + break;
  195. + }
  196. +
  197. + printf("SPL size = %lu, sector = %lu\n", spl_size, sector);
  198. +
  199. + return sector;
  200. +}
  201. +
  202. +u32 spl_boot_device(void)
  203. +{
  204. + return sunxi_get_boot_device();
  205. +}
  206. +
  207. +#define CSR_MXSTATUS 0x7c0
  208. +#define CSR_MHCR 0x7c1
  209. +#define CSR_MCOR 0x7c2
  210. +#define CSR_MHINT 0x7c5
  211. +
  212. +int spl_board_init_f(void)
  213. +{
  214. + int ret;
  215. + struct udevice *dev;
  216. +
  217. + /* DDR init */
  218. + ret = uclass_get_device(UCLASS_RAM, 0, &dev);
  219. + if (ret) {
  220. + debug("DRAM init failed: %d\n", ret);
  221. + return ret;
  222. + }
  223. +
  224. + /* Initialize extension CSRs. */
  225. + printf("mxstatus=0x%08lx mhcr=0x%08lx mcor=0x%08lx mhint=0x%08lx\n",
  226. + csr_read(CSR_MXSTATUS),
  227. + csr_read(CSR_MHCR),
  228. + csr_read(CSR_MCOR),
  229. + csr_read(CSR_MHINT));
  230. +
  231. + csr_set(CSR_MXSTATUS, 0x638000);
  232. + csr_write(CSR_MCOR, 0x70013);
  233. + csr_write(CSR_MHCR, 0x11ff);
  234. + csr_write(CSR_MHINT, 0x16e30c);
  235. +
  236. + return 0;
  237. +}
  238. +
  239. +#ifdef CONFIG_SPL_BUILD
  240. +void spl_perform_fixups(struct spl_image_info *spl_image)
  241. +{
  242. + struct ram_info info;
  243. + struct udevice *dev;
  244. + int ret;
  245. +
  246. + ret = uclass_get_device(UCLASS_RAM, 0, &dev);
  247. + if (ret)
  248. + panic("No RAM device");
  249. +
  250. + ret = ram_get_info(dev, &info);
  251. + if (ret)
  252. + panic("No RAM info");
  253. +
  254. + ret = fdt_fixup_memory(spl_image->fdt_addr, info.base, info.size);
  255. + if (ret)
  256. + panic("Failed to update DTB");
  257. +}
  258. +#endif
  259. +#endif
  260. +
  261. +DECLARE_GLOBAL_DATA_PTR;
  262. +
  263. +/*
  264. + * Try to use the environment from the boot source first.
  265. + * For MMC, this means a FAT partition on the boot device (SD or eMMC).
  266. + * If the raw MMC environment is also enabled, this is tried next.
  267. + * When booting from NAND we try UBI first, then NAND directly.
  268. + * SPI flash falls back to FAT (on SD card).
  269. + */
  270. +enum env_location env_get_location(enum env_operation op, int prio)
  271. +{
  272. + if (prio > 1)
  273. + return ENVL_UNKNOWN;
  274. +
  275. + /* NOWHERE is exclusive, no other option can be defined. */
  276. + if (IS_ENABLED(CONFIG_ENV_IS_NOWHERE))
  277. + return ENVL_NOWHERE;
  278. +
  279. + switch (sunxi_get_boot_device()) {
  280. + case BOOT_DEVICE_MMC1:
  281. + case BOOT_DEVICE_MMC2:
  282. + if (prio == 0 && IS_ENABLED(CONFIG_ENV_IS_IN_FAT))
  283. + return ENVL_FAT;
  284. + if (IS_ENABLED(CONFIG_ENV_IS_IN_MMC))
  285. + return ENVL_MMC;
  286. + break;
  287. + case BOOT_DEVICE_NAND:
  288. + if (prio == 0 && IS_ENABLED(CONFIG_ENV_IS_IN_UBI))
  289. + return ENVL_UBI;
  290. + if (IS_ENABLED(CONFIG_ENV_IS_IN_NAND))
  291. + return ENVL_NAND;
  292. + break;
  293. + case BOOT_DEVICE_SPI:
  294. + if (prio == 0 && IS_ENABLED(CONFIG_ENV_IS_IN_SPI_FLASH))
  295. + return ENVL_SPI_FLASH;
  296. + if (IS_ENABLED(CONFIG_ENV_IS_IN_FAT))
  297. + return ENVL_FAT;
  298. + break;
  299. + case BOOT_DEVICE_BOARD:
  300. + break;
  301. + default:
  302. + break;
  303. + }
  304. +
  305. + /*
  306. + * If we come here for the first time, we *must* return a valid
  307. + * environment location other than ENVL_UNKNOWN, or the setup sequence
  308. + * in board_f() will silently hang. This is arguably a bug in
  309. + * env_init(), but for now pick one environment for which we know for
  310. + * sure to have a driver for. For all defconfigs this is either FAT
  311. + * or UBI, or NOWHERE, which is already handled above.
  312. + */
  313. + if (prio == 0) {
  314. + if (IS_ENABLED(CONFIG_ENV_IS_IN_FAT))
  315. + return ENVL_FAT;
  316. + if (IS_ENABLED(CONFIG_ENV_IS_IN_UBI))
  317. + return ENVL_UBI;
  318. + }
  319. +
  320. + return ENVL_UNKNOWN;
  321. +}
  322. +
  323. +/*
  324. + * On older SoCs the SPL is actually at address zero, so using NULL as
  325. + * an error value does not work.
  326. + */
  327. +#define INVALID_SPL_HEADER ((void *)~0UL)
  328. +
  329. +static struct boot_file_head * get_spl_header(uint8_t req_version)
  330. +{
  331. + struct boot_file_head *spl = (void *)(ulong)SPL_ADDR;
  332. + uint8_t spl_header_version = spl->spl_signature[3];
  333. +
  334. + /* Is there really the SPL header (still) there? */
  335. + if (memcmp(spl->spl_signature, SPL_SIGNATURE, 3) != 0)
  336. + return INVALID_SPL_HEADER;
  337. +
  338. + if (spl_header_version < req_version) {
  339. + printf("sunxi SPL version mismatch: expected %u, got %u\n",
  340. + req_version, spl_header_version);
  341. + return INVALID_SPL_HEADER;
  342. + }
  343. +
  344. + return spl;
  345. +}
  346. +
  347. +static const char *get_spl_dt_name(void)
  348. +{
  349. + struct boot_file_head *spl = get_spl_header(SPL_DT_HEADER_VERSION);
  350. +
  351. + /* Check if there is a DT name stored in the SPL header. */
  352. + if (spl != INVALID_SPL_HEADER && spl->dt_name_offset)
  353. + return (char *)spl + spl->dt_name_offset;
  354. +
  355. + return NULL;
  356. +}
  357. +
  358. +#if CONFIG_MMC_SUNXI_SLOT_EXTRA != -1
  359. +int mmc_get_env_dev(void)
  360. +{
  361. + switch (sunxi_get_boot_device()) {
  362. + case BOOT_DEVICE_MMC1:
  363. + return 0;
  364. + case BOOT_DEVICE_MMC2:
  365. + return 1;
  366. + default:
  367. + return CONFIG_SYS_MMC_ENV_DEV;
  368. + }
  369. +}
  370. +#endif
  371. +
  372. +#ifdef CONFIG_SPL_BUILD
  373. +void sunxi_board_init(void)
  374. +{
  375. +#ifdef CONFIG_LED_STATUS
  376. + if (IS_ENABLED(CONFIG_SPL_DRIVERS_MISC))
  377. + status_led_init();
  378. +#endif
  379. +}
  380. +#endif
  381. +
  382. +#ifdef CONFIG_USB_GADGET
  383. +int g_dnl_board_usb_cable_connected(void)
  384. +{
  385. + struct udevice *dev;
  386. + struct phy phy;
  387. + int ret;
  388. +
  389. + ret = uclass_get_device(UCLASS_USB_GADGET_GENERIC, 0, &dev);
  390. + if (ret) {
  391. + pr_err("%s: Cannot find USB device\n", __func__);
  392. + return ret;
  393. + }
  394. +
  395. + ret = generic_phy_get_by_name(dev, "usb", &phy);
  396. + if (ret) {
  397. + pr_err("failed to get %s USB PHY\n", dev->name);
  398. + return ret;
  399. + }
  400. +
  401. + ret = generic_phy_init(&phy);
  402. + if (ret) {
  403. + pr_debug("failed to init %s USB PHY\n", dev->name);
  404. + return ret;
  405. + }
  406. +
  407. + return sun4i_usb_phy_vbus_detect(&phy);
  408. +}
  409. +#endif
  410. +
  411. +#ifdef CONFIG_SERIAL_TAG
  412. +void get_board_serial(struct tag_serialnr *serialnr)
  413. +{
  414. + char *serial_string;
  415. + unsigned long long serial;
  416. +
  417. + serial_string = env_get("serial#");
  418. +
  419. + if (serial_string) {
  420. + serial = simple_strtoull(serial_string, NULL, 16);
  421. +
  422. + serialnr->high = (unsigned int) (serial >> 32);
  423. + serialnr->low = (unsigned int) (serial & 0xffffffff);
  424. + } else {
  425. + serialnr->high = 0;
  426. + serialnr->low = 0;
  427. + }
  428. +}
  429. +#endif
  430. +
  431. +/*
  432. + * Check the SPL header for the "sunxi" variant. If found: parse values
  433. + * that might have been passed by the loader ("fel" utility), and update
  434. + * the environment accordingly.
  435. + */
  436. +static void parse_spl_header(const uint32_t spl_addr)
  437. +{
  438. + struct boot_file_head *spl = get_spl_header(SPL_ENV_HEADER_VERSION);
  439. +
  440. + if (spl == INVALID_SPL_HEADER)
  441. + return;
  442. +
  443. + if (!spl->fel_script_address)
  444. + return;
  445. +
  446. + if (spl->fel_uEnv_length != 0) {
  447. + /*
  448. + * data is expected in uEnv.txt compatible format, so "env
  449. + * import -t" the string(s) at fel_script_address right away.
  450. + */
  451. + himport_r(&env_htab, (char *)(uintptr_t)spl->fel_script_address,
  452. + spl->fel_uEnv_length, '\n', H_NOCLEAR, 0, 0, NULL);
  453. + return;
  454. + }
  455. + /* otherwise assume .scr format (mkimage-type script) */
  456. + env_set_hex("fel_scriptaddr", spl->fel_script_address);
  457. +}
  458. +
  459. +static bool get_unique_sid(unsigned int *sid)
  460. +{
  461. + if (sunxi_get_sid(sid) != 0)
  462. + return false;
  463. +
  464. + if (!sid[0])
  465. + return false;
  466. +
  467. + /*
  468. + * The single words 1 - 3 of the SID have quite a few bits
  469. + * which are the same on many models, so we take a crc32
  470. + * of all 3 words, to get a more unique value.
  471. + *
  472. + * Note we only do this on newer SoCs as we cannot change
  473. + * the algorithm on older SoCs since those have been using
  474. + * fixed mac-addresses based on only using word 3 for a
  475. + * long time and changing a fixed mac-address with an
  476. + * u-boot update is not good.
  477. + */
  478. +#if !defined(CONFIG_MACH_SUN4I) && !defined(CONFIG_MACH_SUN5I) && \
  479. + !defined(CONFIG_MACH_SUN6I) && !defined(CONFIG_MACH_SUN7I) && \
  480. + !defined(CONFIG_MACH_SUN8I_A23) && !defined(CONFIG_MACH_SUN8I_A33)
  481. + sid[3] = crc32(0, (unsigned char *)&sid[1], 12);
  482. +#endif
  483. +
  484. + /* Ensure the NIC specific bytes of the mac are not all 0 */
  485. + if ((sid[3] & 0xffffff) == 0)
  486. + sid[3] |= 0x800000;
  487. +
  488. + return true;
  489. +}
  490. +
  491. +/*
  492. + * Note this function gets called multiple times.
  493. + * It must not make any changes to env variables which already exist.
  494. + */
  495. +static void setup_environment(const void *fdt)
  496. +{
  497. + char serial_string[17] = { 0 };
  498. + unsigned int sid[4];
  499. + uint8_t mac_addr[6];
  500. + char ethaddr[16];
  501. + int i;
  502. +
  503. + if (!get_unique_sid(sid))
  504. + return;
  505. +
  506. + for (i = 0; i < 4; i++) {
  507. + sprintf(ethaddr, "ethernet%d", i);
  508. + if (!fdt_get_alias(fdt, ethaddr))
  509. + continue;
  510. +
  511. + if (i == 0)
  512. + strcpy(ethaddr, "ethaddr");
  513. + else
  514. + sprintf(ethaddr, "eth%daddr", i);
  515. +
  516. + if (env_get(ethaddr))
  517. + continue;
  518. +
  519. + /* Non OUI / registered MAC address */
  520. + mac_addr[0] = (i << 4) | 0x02;
  521. + mac_addr[1] = (sid[0] >> 0) & 0xff;
  522. + mac_addr[2] = (sid[3] >> 24) & 0xff;
  523. + mac_addr[3] = (sid[3] >> 16) & 0xff;
  524. + mac_addr[4] = (sid[3] >> 8) & 0xff;
  525. + mac_addr[5] = (sid[3] >> 0) & 0xff;
  526. +
  527. + eth_env_set_enetaddr(ethaddr, mac_addr);
  528. + }
  529. +
  530. + if (!env_get("serial#")) {
  531. + snprintf(serial_string, sizeof(serial_string),
  532. + "%08x%08x", sid[0], sid[3]);
  533. +
  534. + env_set("serial#", serial_string);
  535. + }
  536. +}
  537. +
  538. +int misc_init_r(void)
  539. +{
  540. + const char *spl_dt_name;
  541. + uint boot;
  542. +
  543. + env_set("fel_booted", NULL);
  544. + env_set("fel_scriptaddr", NULL);
  545. + env_set("mmc_bootdev", NULL);
  546. +
  547. + boot = sunxi_get_boot_device();
  548. + /* determine if we are running in FEL mode */
  549. + if (boot == BOOT_DEVICE_BOARD) {
  550. + env_set("fel_booted", "1");
  551. + parse_spl_header(SPL_ADDR);
  552. + /* or if we booted from MMC, and which one */
  553. + } else if (boot == BOOT_DEVICE_MMC1) {
  554. + env_set("mmc_bootdev", "0");
  555. + } else if (boot == BOOT_DEVICE_MMC2) {
  556. + env_set("mmc_bootdev", "1");
  557. + }
  558. +
  559. + /* Set fdtfile to match the FIT configuration chosen in SPL. */
  560. + spl_dt_name = get_spl_dt_name();
  561. + if (spl_dt_name) {
  562. + char *prefix = IS_ENABLED(CONFIG_ARM64) ? "allwinner/" : "";
  563. + char str[64];
  564. +
  565. + snprintf(str, sizeof(str), "%s%s.dtb", prefix, spl_dt_name);
  566. + env_set("fdtfile", str);
  567. + }
  568. +
  569. + setup_environment(gd->fdt_blob);
  570. +
  571. + return 0;
  572. +}
  573. +
  574. +int board_late_init(void)
  575. +{
  576. +#ifdef CONFIG_USB_ETHER
  577. + usb_ether_init();
  578. +#endif
  579. +
  580. +#ifdef SUNXI_SCP_BASE
  581. + if (!rproc_load(0, SUNXI_SCP_BASE, SUNXI_SCP_MAX_SIZE)) {
  582. + puts("Starting SCP...\n");
  583. + rproc_start(0);
  584. + }
  585. +#endif
  586. +
  587. + return 0;
  588. +}
  589. +
  590. +static void bluetooth_dt_fixup(void *blob)
  591. +{
  592. + /* Some devices ship with a Bluetooth controller default address.
  593. + * Set a valid address through the device tree.
  594. + */
  595. + uchar tmp[ETH_ALEN], bdaddr[ETH_ALEN];
  596. + unsigned int sid[4];
  597. + int i;
  598. +
  599. + if (!CONFIG_BLUETOOTH_DT_DEVICE_FIXUP[0])
  600. + return;
  601. +
  602. + if (eth_env_get_enetaddr("bdaddr", tmp)) {
  603. + /* Convert between the binary formats of the corresponding stacks */
  604. + for (i = 0; i < ETH_ALEN; ++i)
  605. + bdaddr[i] = tmp[ETH_ALEN - i - 1];
  606. + } else {
  607. + if (!get_unique_sid(sid))
  608. + return;
  609. +
  610. + bdaddr[0] = ((sid[3] >> 0) & 0xff) ^ 1;
  611. + bdaddr[1] = (sid[3] >> 8) & 0xff;
  612. + bdaddr[2] = (sid[3] >> 16) & 0xff;
  613. + bdaddr[3] = (sid[3] >> 24) & 0xff;
  614. + bdaddr[4] = (sid[0] >> 0) & 0xff;
  615. + bdaddr[5] = 0x02;
  616. + }
  617. +
  618. + do_fixup_by_compat(blob, CONFIG_BLUETOOTH_DT_DEVICE_FIXUP,
  619. + "local-bd-address", bdaddr, ETH_ALEN, 1);
  620. +}
  621. +
  622. +int ft_board_setup(void *blob, struct bd_info *bd)
  623. +{
  624. + int __maybe_unused r;
  625. +
  626. + /*
  627. + * Call setup_environment and fdt_fixup_ethernet again
  628. + * in case the boot fdt has ethernet aliases the u-boot
  629. + * copy does not have.
  630. + */
  631. + setup_environment(blob);
  632. + fdt_fixup_ethernet(blob);
  633. +
  634. + bluetooth_dt_fixup(blob);
  635. +
  636. +#ifdef CONFIG_VIDEO_DT_SIMPLEFB
  637. + r = sunxi_simplefb_setup(blob);
  638. + if (r)
  639. + return r;
  640. +#endif
  641. + return 0;
  642. +}
  643. +
  644. +#ifdef CONFIG_SPL_LOAD_FIT
  645. +
  646. +static void set_spl_dt_name(const char *name)
  647. +{
  648. + struct boot_file_head *spl = get_spl_header(SPL_ENV_HEADER_VERSION);
  649. +
  650. + if (spl == INVALID_SPL_HEADER)
  651. + return;
  652. +
  653. + /* Promote the header version for U-Boot proper, if needed. */
  654. + if (spl->spl_signature[3] < SPL_DT_HEADER_VERSION)
  655. + spl->spl_signature[3] = SPL_DT_HEADER_VERSION;
  656. +
  657. + strcpy((char *)&spl->string_pool, name);
  658. + spl->dt_name_offset = offsetof(struct boot_file_head, string_pool);
  659. +}
  660. +
  661. +int board_fit_config_name_match(const char *name)
  662. +{
  663. + const char *best_dt_name = get_spl_dt_name();
  664. + int ret;
  665. +
  666. +#ifdef CONFIG_DEFAULT_DEVICE_TREE
  667. + if (best_dt_name == NULL)
  668. + best_dt_name = CONFIG_DEFAULT_DEVICE_TREE;
  669. +#endif
  670. +
  671. + if (best_dt_name == NULL) {
  672. + /* No DT name was provided, so accept the first config. */
  673. + return 0;
  674. + }
  675. +#ifdef CONFIG_PINE64_DT_SELECTION
  676. + if (strstr(best_dt_name, "-pine64-plus")) {
  677. + /* Differentiate the Pine A64 boards by their DRAM size. */
  678. + if ((gd->ram_size == 512 * 1024 * 1024))
  679. + best_dt_name = "sun50i-a64-pine64";
  680. + }
  681. +#endif
  682. +#ifdef CONFIG_PINEPHONE_DT_SELECTION
  683. + if (strstr(best_dt_name, "-pinephone")) {
  684. + /* Differentiate the PinePhone revisions by GPIO inputs. */
  685. + prcm_apb0_enable(PRCM_APB0_GATE_PIO);
  686. + sunxi_gpio_set_pull(SUNXI_GPL(6), SUNXI_GPIO_PULL_UP);
  687. + sunxi_gpio_set_cfgpin(SUNXI_GPL(6), SUNXI_GPIO_INPUT);
  688. + udelay(100);
  689. +
  690. + /* PL6 is pulled low by the modem on v1.2. */
  691. + if (gpio_get_value(SUNXI_GPL(6)) == 0)
  692. + best_dt_name = "sun50i-a64-pinephone-1.2";
  693. + else
  694. + best_dt_name = "sun50i-a64-pinephone-1.1";
  695. +
  696. + sunxi_gpio_set_cfgpin(SUNXI_GPL(6), SUNXI_GPIO_DISABLE);
  697. + sunxi_gpio_set_pull(SUNXI_GPL(6), SUNXI_GPIO_PULL_DISABLE);
  698. + prcm_apb0_disable(PRCM_APB0_GATE_PIO);
  699. + }
  700. +#endif
  701. +
  702. + ret = strcmp(name, best_dt_name);
  703. +
  704. + /*
  705. + * If one of the FIT configurations matches the most accurate DT name,
  706. + * update the SPL header to provide that DT name to U-Boot proper.
  707. + */
  708. + if (ret == 0)
  709. + set_spl_dt_name(best_dt_name);
  710. +
  711. + return ret;
  712. +}
  713. +#endif
  714. --- a/include/configs/sunxi-common.h
  715. +++ b/include/configs/sunxi-common.h
  716. @@ -12,7 +12,6 @@
  717. #ifndef _SUNXI_COMMON_CONFIG_H
  718. #define _SUNXI_COMMON_CONFIG_H
  719. -#include <asm/arch/cpu.h>
  720. #include <linux/stringify.h>
  721. /* Serial & console */