Diese Seite enthält eine Zusammenfassung von „Erkenntnissen“ bei der erstmaligen Konfiguration eines Zynq-SoCs gewonnen wurden. Die Doku dazu ist zum Teil leider sehr verstreut.

Folgendes sollte durch die erstellte Konfiguration abgedeckt werden:

  • Es sollte ein Linux auf dem Zynq laufen
  • Mit schreibbarem/persistenten Userspace auf der SD-Karte
  • Bitfile soll aus dem Linux in die programmierbare Logik (PL) geladen werden können (nicht nur im FSBL!)

Der erste Versuch erfolgt auf einem Zybo-Board.

Status

  • Linux läuft mit openSUSE-Userspace \o/

Installationsanleitung

Dieser Abschnitt beschreibt, wie man Linux auf dem Zynq zum Laufen bekommt und damit ein Bitfile in die PL lädt.

Vorbereitung

Folgende Tools müssen installiert werden:

Folgende Git-Repositories werden benötigt:

  • linux-xlnx (getesteter Commit: 047a00be376f4aa99d4c0b2f8937fb7c8fbf5272)
  • u-boot-xlnx (getesteter Commit: 21812b5fd359d8756d619a15b49b6079ae3f9f36)

Weiteres:

  • Linux-Userspace: hier kann im Prinzip jede armv7-kompatible Distribution verwendet werden. Wir haben einen aktuellen Snapshot (vom 30. April 2018) von OpenSUSE Tumbleweed verwendet: rootfs-Download

Für Vivado kann folgendes Wrapper-Skript (vivado_2018.1) verwendet werden:

#!/bin/bash

cmd=$@

while [ ! -z "$1" ]
do
    shift
done

source /opt/Xilinx/Vivado/2018.1/settings64.sh

exec $cmd

Der Aufruf von Vivado erfolgt dann mit

vivado_2018.1 vivado

Bauen von U-Boot

git clone https://github.com/Xilinx/u-boot-xlnx.git
cd u-boot-xlnx

Hier wird ein Wrapper-Skript für make erstellt, das dafür sorgt, dass die richtige Umgebung für Cross-Kompilierung verwendet wird. Das folgende Skript sollte make_wrap_zynq.sh heißen:

#!/bin/sh                                                                                               

export ARCH=arm
export CROSS_COMPILE=arm-linux-gnueabihf-

make $@

Wir laden eine Standardkonfiguration...

./make_wrap_zynq.sh zynq_zybo_config

... und kompilieren diese (mit 4 parallelen Prozessen):

./make_wrap_zynq.sh -j4

Dies erstellt folgende relevante Ausgabedateien:

  • spl/boot.bin: der first-stage bootloader (FSBL) für den Zynq + u-boot-SPL
  • u-boot.img: das eigentliche u-boot-Binary

Bauen des Linux-Kernels

git clone https://github.com/Xilinx/linux-xlnx.git
cd linux-xlnx

Hier wird wieder ein Wrapper-Skript make_wrap_zynq.sh erstellt. Zu beachten ist, dass der Pfad zu den u-boot-Tools angegeben werden muss:

#!/bin/sh                                                                                               

export ARCH=arm
export CROSS_COMPILE=arm-linux-gnueabihf-

export PATH="/home/thomas/Software/u-boot-xlnx/tools/:$PATH"

make LOADADDR=0x8000 $@

Wir laden eine Standardkonfiguration...

./make_wrap_zynq.sh zynq_zybo_defconfig

... kompilieren diese (mit 4 parallelen Prozessen) ...

./make_wrap_zynq.sh -j4

... und installieren die Module in einen temporären Ordner:

./make_wrap_zynq.sh INSTALL_MOD_PATH=/tmp/zynq_modules modules_install

Vorbereiten der SD-Karte

Auf der SD-Karte wird eine DOS-Partitionstabelle mit 2 Partitionen erstellt:

  1. 256 MiB FAT32 (Typ W95 FAT32; 0x0B, boot-Flag gesetzt)
  2. Rest der Karte für Linux (Typ Linux, 0x83)

Partitionen formatieren (es wird angenommen, dass die SD-Karte als /dev/mmcblk0 im System auftaucht):

mkfs -t vfat -F 32 -n BOOT /dev/mmcblk0p1
mkfs -t ext4 -L root /dev/mmcblk0p2

Wir mounten die frisch erstellten Dateisysteme:

mkdir -p /mnt/boot
mkdir -p /mnt/root
mount /dev/mmcblk0p1 /mnt/boot
mount /dev/mmcblk0p2 /mnt/root

Füllen der boot-Partition

Auf der boot-Partition befinden sich der FSBL, u-boot (und seine Konfiguration) und der Linux-Kernel.

Bei den ersten Tests hat sich gezeigt, dass der u-boot-SPL versucht, den Linux-Kernel direkt zu laden, wenn dieser uImage heißt. Da das beim Testen fehlgeschlagen ist, wird das Image im Folgenden umbenannt. Evtl. kann man dem SPL diesen Schritt durch ändern der Standardkonfiguration abgewöhnen.

cp u-boot-xlnx/spl/boot.bin /mnt/boot
cp u-boot-xlnx/u-boot.img /mnt/boot
cp linux-xlnx/arch/arm/boot/uImage /mnt/boot/uImage_renamed
cp linux-xlnx/arch/arm/boot/dts/zynq-zybo.dtb devicetree.dtb

Zusätzlich muss die u-boot-Konfiguration /mnt/boot/uEnv.txt erstellt werden:

console=tty0                                                                                            
fdt_high=0x10000000
initrd_high=0x10000000
bootargs=console=ttyPS0,115200 root=/dev/mmcblk0p2 rootwait rw
bootcmd=fatload mmc 0 0x00008000 uImage_foo; fatload mmc 0 0x01000000 devicetree.dtb; bootm 0x00008000 - 0x01000000

Füllen der root-Partition

Auf der root-Partition muss zuerst das rootfs entpackt werden:

cd /mnt/root
tar xpvf ~/Downloads/openSUSE-Tumbleweed-ARM-JeOS.armv7-rootfs.armv7l-2018.04.30-Build2.6.tar.xz

Anschließend kopieren wir die Kernelmodule:

cp -r /tmp/zynq_modules/lib/modules/4.14.0-xilinx-00096-g047a00be376f /mnt/root/lib/modules/

Abschluss

Unmounten der SD-Karte nicht vergessen!

umount /mnt/boot /mnt/root

Das System sollte jetzt erfolgreich starten!

wird fortgesetzt...