The goal is to upgrade the Linux on Altera's DE0-Nano-SOC FPGA development board. To challenge us even further, the board confusingly also branded as the Atlas SoC board. The boards provided Linux version is from 2013, woefully outdated, and a stripped-down version. It comes with busybox instead of full commands, lacks all local development tools, and is requiring off-system cross-compiling.
root@socfpga:~# cat /etc/version 201309272205 root@socfpga:~# cat /etc/issue Poky 8.0 (Yocto Project 1.3 Reference Distro) 1.3 \l root@socfpga:~# uname -r 3.13.0-00298-g3c7cbb9-dirty
On the bright side, the minimal linux image coming with Altera's DE0-Nano-SOC FPGA development board uses only 189MB.
root@socfpga:~# df -h / Filesystem Size Used Available Use% Mounted on /dev/root 975.9M 188.7M 736.0M 20% /
With the hardware being somewhat comparable to popular Raspberry Pi or Beagleboard platforms, DE0-SoC boards are missing the platform support convenience that comes with a adopted Linux distribution for the specific Altera platform.
Original SD card partioning:
root@socfpga:~# fdisk -l /dev/mmcblk0 Disk /dev/mmcblk0: 64.0 GB, 64021856256 bytes 4 heads, 16 sectors/track, 1953792 cylinders, total 125042688 sectors Units = sectors of 1 * 512 = 512 bytes Sector size (logical/physical): 512 bytes / 512 bytes I/O size (minimum/optimal): 512 bytes / 512 bytes Disk identifier: 0xd68e23ba Device Boot Start End Blocks Id System /dev/mmcblk0p1 2121728 3799447 838860 b W95 FAT32 /dev/mmcblk0p2 14336 2111487 1048576 83 Linux /dev/mmcblk0p3 2048 4095 1024 a2 Unknown
Partition table entries are not in disk order
http://eewiki.net/display/linuxonarm/DE0-Nano-SoC+Kit, courtesy of Robert Nelson.
This approach requires approx 8-10 GB disk space.
First we need a ARM cross-compiler. Linaro provides one that is frequently used:
wget https://releases.linaro.org/components/toolchain/binaries/latest/arm-linux-gnueabihf/gcc-linaro-6.2.1-2016.11-x86_64_arm-linux-gnueabihf.tar.xz tar xf gcc-linaro-6.2.1-2016.11-x86_64_arm-linux-gnueabihf.tar.xz export CC=`pwd`/gcc-linaro-6.2.1-2016.11-x86_64_arm-linux-gnueabihf/bin/arm-linux-gnueabihf- fm@lts1604:/srv/app/bc/ubuntu$ ${CC}gcc --version arm-linux-gnueabihf-gcc (Linaro GCC 6.2-2016.11) 6.2.1 20161016 Copyright (C) 2016 Free Software Foundation, Inc. This is free software; see the source for copying conditions. There is NO warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
Next we need a Boot loader that can jump-start the OS.
git clone https://github.com/u-boot/u-boot fm@lts1604:/srv/app/bc/ubuntu$ cd u-boot/ fm@lts1604:/srv/app/bc/ubuntu/u-boot$ ls api board common configs doc dts fs Kbuild lib MAINTAINERS net README snapshot.commit tools arch cmd config.mk disk drivers examples include Kconfig Licenses Makefile post scripts test fm@lts1604:/srv/app/bc/ubuntu/u-boot$ git checkout v2017.01 -b tmp Switched to a new branch 'tmp'
Now we patch it for the DE0-Nano-SoC board:
wget -c https://rcn-ee.com/repos/git/u-boot-patches/v2017.01/0001-de0_nano-fixes.patch fm@lts1604:/srv/app/bc/ubuntu/u-boot$ patch -p1 < 0001-de0_nano-fixes.patch patching file include/configs/socfpga_de0_nano_soc.h
Finally we compile the Boot Loader:
fm@lts1604:/srv/app/bc/ubuntu/u-boot$ make ARCH=arm CROSS_COMPILE=${CC} distclean fm@lts1604:/srv/app/bc/ubuntu/u-boot$ fm@lts1604:/srv/app/bc/ubuntu/u-boot$ make ARCH=arm CROSS_COMPILE=${CC} socfpga_de0_nano_soc_defconfig HOSTCC scripts/basic/fixdep HOSTCC scripts/kconfig/conf.o SHIPPED scripts/kconfig/zconf.tab.c SHIPPED scripts/kconfig/zconf.lex.c SHIPPED scripts/kconfig/zconf.hash.c HOSTCC scripts/kconfig/zconf.tab.o HOSTLD scripts/kconfig/conf # # configuration written to .config # fm@lts1604:/srv/app/bc/ubuntu/u-boot$ fm@lts1604:/srv/app/bc/ubuntu/u-boot$ make ARCH=arm CROSS_COMPILE=${CC} u-boot-with-spl.sfp scripts/kconfig/conf --silentoldconfig Kconfig CHK include/config.h UPD include/config.h CFG u-boot.cfg GEN include/autoconf.mk GEN include/autoconf.mk.dep CFG spl/u-boot.cfg GEN spl/include/autoconf.mk CHK include/config/uboot.release UPD include/config/uboot.release ... LD spl/u-boot-spl OBJCOPY spl/u-boot-spl-nodtb.bin FDTGREP spl/u-boot-spl.dtb CAT spl/u-boot-spl-dtb.bin COPY spl/u-boot-spl.bin MKIMAGE spl/u-boot-spl.sfp OBJCOPY u-boot-nodtb.bin CAT u-boot-dtb.bin COPY u-boot.bin MKIMAGE u-boot.img SOCBOOT u-boot-with-spl.sfp
Now we build a Kernel:
fm@lts1604:/srv/app/bc/ubuntu$ git clone https://github.com/RobertCNelson/socfpga-kernel-dev Cloning into 'socfpga-kernel-dev'... remote: Counting objects: 283, done. remote: Total 283 (delta 0), reused 0 (delta 0), pack-reused 283 Receiving objects: 100% (283/283), 804.01 KiB | 348.00 KiB/s, done. Resolving deltas: 100% (187/187), done. Checking connectivity... done. fm@lts1604:/srv/app/bc/ubuntu$ cd socfpga-kernel-dev/ fm@lts1604:/srv/app/bc/ubuntu/socfpga-kernel-dev$ git checkout origin/v4.6.x -b tmp Branch tmp set up to track remote branch v4.6.x from origin. Switched to a new branch 'tmp' fm@lts1604:/srv/app/bc/ubuntu/socfpga-kernel-dev$ vi version.sh fm@lts1604:/srv/app/bc/ubuntu/socfpga-kernel-dev$ ./build_kernel.sh
Finally we get a pre-arranged minimal filesystem:
wget -c https://rcn-ee.com/rootfs/eewiki/minfs/ubuntu-16.04.1-minimal-armhf-2017-01-14.tar.xz
Write it all to SD card.
Clear out old partition table:
dd if=/dev/zero of=/dev/sdc bs=1M count=64
Write new partition table:
/dev/sdc1 1M Boot Loader /dev/sdc2 remaining space Linux
sfdisk /dev/sdc <<-__EOF__ 1M,1M,0xA2, ,,,- __EOF__
Write boot loader to /dev/sdc1:
dd if=u-boot/u-boot-with-spl.sfp of=/dev/sdc1
Format Linux partition:
mkfs.ext4 -L rootfs /dev/sdc2
Write file system to Linux partition:
tar xfvp ./*-*-*-armhf-*/armhf-rootfs-*.tar -C /media/fm/rootfs
Set uname_r in boot/uEnv.txt:
root@lts1604:/srv/app/bc/ubuntu# export kernel_version=4.6.5-socfpga-r1 root@lts1604:/srv/app/bc/ubuntu# sh -c "echo 'uname_r=${kernel_version}' > /media/fm/rootfs/boot/uEnv.txt" root@lts1604:/srv/app/bc/ubuntu# cat /media/fm/rootfs/boot/uEnv.txt uname_r=4.6.5-socfpga-r1
Copy kernel image:
root@lts1604:/srv/app/bc/ubuntu# cp -v ./socfpga-kernel-dev/deploy/${kernel_version}.zImage /media/fm/rootfs/boot/vmlinuz-${kernel_version} './socfpga-kernel-dev/deploy/4.6.5-socfpga-r1.zImage' -> '/media/fm/rootfs/boot/vmlinuz-4.6.5-socfpga-r1'
Copy device tree binaries:
root@lts1604:/srv/app/bc/ubuntu# mkdir -p /media/fm/rootfs/boot/dtbs/${kernel_version}/root@lts1604:/srv/app/bc/ubuntu# tar xfv ./socfpga-kernel-dev/deploy/${kernel_version}-dtbs.tar.gz -C /media/fm/rootfs/boot/dtbs/${kernel_version}/ ./socfpga_arria10_socdk_nand.dtb ./socfpga_arria10_socdk_qspi.dtb ./socfpga_arria10_socdk_sdmmc.dtb ./socfpga_arria10_swvp.dtb ./socfpga_arria5_socdk.dtb ./socfpga_cyclone5_de0_sockit.dtb ./socfpga_cyclone5_mcvevk.dtb ./socfpga_cyclone5_socdk.dtb ./socfpga_cyclone5_sockit.dtb ./socfpga_cyclone5_socrates.dtb ./socfpga_cyclone5_trcom.dtb ./socfpga_vt.dtb
Copy Kernel modules:
tar xfv ./socfpga-kernel-dev/deploy/${kernel_version}-modules.tar.gz -C /media/rootfs/
Create Filesystem table:
sh -c "echo '/dev/mmcblk0p2 / auto errors=remount-ro 0 1' >> /media/rootfs/etc/fstab"
Specify device IP in /etc/network/interfaces:
# /etc/network/interfaces -- configuration file for ifup(8), ifdown(8) # The loopback interface auto lo iface lo inet loopback # Wireless interfaces iface wlan0 inet dhcp wireless_mode managed wireless_essid any wpa-driver wext wpa-conf /etc/wpa_supplicant.conf iface atml0 inet dhcp # Wired or wireless interfaces auto eth0 iface eth0 inet static address 192.168.99.3 netmask 255.255.255.0 dns-nameservers 192.168.179.1 iface eth1 inet dhcp # Ethernet/RNDIS gadget (g_ether) # ... or on host side, usbnet and random hwaddr iface usb0 inet static address 192.168.7.2 netmask 255.255.255.0 network 192.168.7.0 gateway 192.168.7.1 # Bluetooth networking iface bnep0 inet dhcp
Sync and umount the sdcard. Its now ready to boot. After boot, the login will prompt for username ubuntu with password temppwd. The remaining work includes setting up DNS, routing, adding Ubuntu repositories to /etc/apt/sources.list. And finally, we are able to run apt-get update / apt-get upgrade / apt-get install.
root@arm:/home/fm# df -h / Filesystem Size Used Avail Use% Mounted on /dev/root 59G 1.4G 55G 3% /