With the DRAM init code and the SPL's ability to load the ATF binary as well, we can now officially get rid of the boot0 boot method, which involed a closed-source proprietary blob to be used. Rework the Pine64 README file to document how to build the firmware.
Signed-off-by: Andre Przywara <andre.przyw...@arm.com> --- board/sunxi/README.pine64 | 177 ++++++++++++++++++++++++++++++---------------- 1 file changed, 115 insertions(+), 62 deletions(-) diff --git a/board/sunxi/README.pine64 b/board/sunxi/README.pine64 index 5553415..41fb58e 100644 --- a/board/sunxi/README.pine64 +++ b/board/sunxi/README.pine64 @@ -8,75 +8,130 @@ This chip has ARM Cortex A-53 cores and thus can run both in AArch32 in AArch32 mode and executes 32-bit code from the Boot ROM (BROM). This has some implications on U-Boot. -Quick start -============ -- Get hold of a boot0.img file (see below for more details). -- Get the boot0img tool source from the tools directory in [1] and compile - that on your host. -- Build U-Boot: +Quick Start / Overview +====================== +- Build the ARM Trusted Firmware binary (see "ARM Trusted firmware (ATF)" below) +- Build U-Boot (see "SPL/U-Boot" below) +- Transfer to an uSD card (see "microSD card" below) +- Boot and enjoy! + +Building the firmware +===================== + +The Allwinner A64 firmware consists of three parts: U-Boot's SPL, an +ARM Trusted Firmware (ATF) build and the U-Boot proper. +The SPL will load both ATF and U-Boot proper along with the right device +tree blob (.dtb) and will pass execution to ATF (in EL3), which in turn will +drop into the U-Boot proper (in EL2). +As the ATF binary will become part of the U-Boot image file, you will need +to build it first. + + ARM Trusted firmware (ATF) +---------------------------- +Checkout the "allwinner" branch from the github repository [1] and build it: +$ export CROSS_COMPILE=aarch64-linux-gnu- +$ make PLAT=sun50iw1p1 DEBUG=1 bl31 + The resulting binary is build/sun50iw1p1/debug/bl31.bin. Copy this to the + root of the U-Boot source tree (or create a symbolic link). + + SPL/U-Boot +------------ +Both U-Boot proper and the SPL are using the 64-bit mode. As the boot ROM +enters the SPL still in AArch32 secure SVC mode, there is some shim code to +enter AArch64 very early. The rest of the SPL runs in AArch64 EL3. +U-boot proper runs in EL2 and can load any AArch64 code, EFI applications or +arm64 Linux kernel images (often named "Image") using the booti command. + +$ make clean $ export CROSS_COMPILE=aarch64-linux-gnu- $ make pine64_plus_defconfig $ make -- You also need a compiled ARM Trusted Firmware (ATF) binary. Checkout the - "allwinner" branch from the github repository [2] and build it: -$ export CROSS_COMPILE=aarch64-linux-gnu- -$ make PLAT=sun50iw1p1 DEBUG=1 bl31 - The resulting binary is build/sun50iw1p1/debug/bl31.bin. -Now put an empty (or disposable) micro SD card in your card reader and learn -its device file name, replacing /dev/sd<x> below with the result (that could -be /dev/mmcblk<x> as well): +This will build the SPL in spl/sunxi-spl.bin and a FIT image called u-boot.itb, +which contains the rest of the firmware. + -$ ./boot0img --device /dev/sd<x> -e -u u-boot.bin -B boot0.img \ - -d trampoline64:0x44000 -s bl31.bin -a 0x44008 -p 100 -(either copying the respective files to the working directory or specifying -the paths directly) +Boot process +============ +The on-die BROM code will try several methods to load and execute the firmware. +On the Pine64 this will result in the following boot order: +1) Reading 32KB from sector 16 (@8K) of the microSD card to SRAM A1. If the +BROM finds the magic "eGON" header in the first bytes, it will execute that +code. If not, it will: +2) Initialize the SPI0 controller and try to access a NOR flash connected to +it (using the CS0 pin). If a flash chip is found, the BROM will load the +first 32KB (from offset 0) into SRAM A1. Now it checks for the magic eGON +header and will execute the code upon finding it. If not, it will: +3) Initialize the USB OTG controller and will wait for a host to connect to +it, speaking the Allwinner proprietary (but deciphered) "FEL" USB protocol. + +To boot the Pine64 board, you can use U-Boot and any of the described methods. -This will create a new partition table (with a 100 MB FAT boot partition), -copies boot0.img, ATF and U-Boot to the proper locations on the SD card and -will fill in the magic Allwinner header to be recognized by boot0. -Prefix the above call with "sudo" if you don't have write access to the -uSD card. You can also use "-o output.img" instead of "--device /dev/sd<x>" -to create an image file and "dd" that to the uSD card. -Omitting the "-p" option will skip the partition table. +FEL boot (USB OTG) +------------------ +FEL is the name of the Allwinner defined USB boot protocol built in the +mask ROM of most Allwinner SoCs. It allows to bootstrap a board solely +by using the USB-OTG interface and a host port on another computer. +As the FEL mode is controlled by the boot ROM, it expects to be running in +AArch32. For now the AArch64 SPL cannot properly return into FEL mode, so the +feature is disabled in the configuration at the moment. -Now put this uSD card in the board and power it on. You should be greeted by -the U-Boot prompt. +microSD card +------------ +Transfer the SPL and the U-Boot FIT image directly to an uSD card: +# dd if=spl/sunxi-spl.bin of=/dev/sdx bs=8k seek=1 +# dd if=u-boot.itb of=/dev/sdx bs=8k seek=5 +# sync +(replace /dev/sdx with you SD card device file name, which could be +/dev/mmcblk[x] as well). +Alternative you can concatenate the SPL and the U-Boot FIT image into a single +file and transfer that instead: +$ cat spl/sunxi-spl.bin u-boot.itb > u-boot-sunxi-with-spl.bin +# dd if=u-boot-sunxi-with-spl.bin of=/dev/sdx bs=8k seek=1 -Main U-Boot -============ -The main U-Boot proper is a real 64-bit ARMv8 port and runs entirely in the -64-bit AArch64 mode. It can load any AArch64 code, EFI applications or arm64 -Linux kernel images (often named "Image") using the booti command. -Launching 32-bit code and kernels is technically possible, though not without -drawbacks (or hacks to avoid them) and currently not implemented. +You can partition the microSD card, but leave the first MB unallocated (most +partitioning tools will do this anyway). -SPL support -============ -The main task of the SPL support is to bring up the DRAM controller and make -DRAM actually accessible. At the moment there is no documentation or source -code available which would do this. -There are currently two ways to overcome this situation: using a tainted 32-bit -SPL (involving some hacks and resulting in a non-redistributable binary, thus -not described here) or using the Allwinner boot0 blob. - -boot0 method -------------- +NOR flash +--------- +The Pine64 board can be booted via an SPI NOR flash chip connected to SPI0/CS0 +on the PI-2 headers. The SoPine module and the Pinebook notebook come with +a SPI flash soldered already. +Create the SPL and FIT image like described above for the SD card. +Now connect either an "A to A" USB cable to the upper USB port on the Pine64 +or get an adaptor and use a regular A-microB cable connected to it. +Remove a microSD card from the slot and power on the board. +On your host computer download and build the sunxi-tools package[2], then +use "sunxi-fel" to access the board: +$ ./sunxi-fel ver -v -p +This should give you an output starting with: AWUSBFEX soc=00001689(A64) ... +Now use the sunxi-fel tool to write to the NOR flash: +$ ./sunxi-fel spiflash-write 0 spl/sunxi-spl.bin +$ ./sunxi-fel spiflash-write 32768 u-boot.itb +Now boot the board without an SD card inserted and you should see the +U-Boot prompt on the serial console. + +(Legacy) boot0 method +--------------------- boot0 is Allwiner's secondary program loader and it can be used as some kind -of SPL replacement to get U-Boot up and running. -The binary is a 32 KByte blob and contained on every Pine64 image distributed -so far. It can be easily extracted from a micro SD card or an image file: +of SPL replacement to get U-Boot up and running from an microSD card. +For some time using boot0 was the only option to get the Pine64 booted. +With working DRAM init code in U-Boot's SPL this is no longer necessary, +but this method is described here for the sake of completeness. + +The boot0 binary is a 32 KByte blob and contained in the official Pine64 images +distributed by Pine64 or Allwinner. It can be easily extracted from a micro +SD card or an image file: # dd if=/dev/sd<x> of=boot0.bin bs=8k skip=1 count=4 where /dev/sd<x> is the device name of the uSD card or the name of the image file. Apparently Allwinner allows re-distribution of this proprietary code as-is. -For the time being this boot0 blob is the only redistributable way of making -U-Boot work on the Pine64. Beside loading the various parts of the (original) -firmware it also switches the core into AArch64 mode. +This boot0 blob takes care of DRAM initialisation and loads the remaining +firmware parts, then switches the core into AArch64 mode. The original boot0 code looks for U-Boot at a certain place on an uSD card (at 19096 KB), also it expects a header with magic bytes and a checksum. -There is a tool called boot0img[1] which takes a boot0.bin image and a compiled +There is a tool called boot0img[3] which takes a boot0.bin image and a compiled U-Boot binary (plus other binaries) and will populate that header accordingly. To make space for the magic header, the pine64_plus_defconfig will make sure there is sufficient space at the beginning of the U-Boot binary. @@ -85,14 +140,12 @@ places on the uSD card and works around unused, but mandatory parts by using trampoline code. See the output of "boot0img -h" for more information. boot0img can also patch boot0 to avoid loading U-Boot from 19MB, instead fetching it from just behind the boot0 binary (-B option). +$ ./boot0img -o firmware.img -B boot0.img -u u-boot-dtb.bin -e -s bl31.bin \ +-a 0x44008 -d trampoline64:0x44000 +Then write this image to a microSD card, replacing /dev/sdx with the right +device file (see above): +$ dd if=firmware.img of=/dev/sdx bs=8k seek=1 -FEL boot -========= -FEL is the name of the Allwinner defined USB boot protocol built-in the -mask ROM of most Allwinner SoCs. It allows to bootstrap a board solely -by using the USB-OTG interface and a host port on another computer. -Since FEL boot does not work with boot0, it requires the libdram hack, which -is not described here. - -[1] https://github.com/apritzel/pine64/ -[2] https://github.com/apritzel/arm-trusted-firmware.git +[1] https://github.com/apritzel/arm-trusted-firmware.git +[2] git://github.com/linux-sunxi/sunxi-tools.git +[3] https://github.com/apritzel/pine64/ -- 2.8.2 _______________________________________________ U-Boot mailing list U-Boot@lists.denx.de https://lists.denx.de/listinfo/u-boot