Skep 'n Ubuntu-beeld vir ARM "van nuuts af"

Wanneer ontwikkeling net begin, is dit dikwels nie duidelik watter pakkette na die teiken rootfs sal gaan nie.

Met ander woorde, dit is te vroeg om LFS, buildroot of yocto (of iets anders) te gryp, maar jy moet reeds begin. Vir die rykes (ek het 4GB eMMC op proefmonsters) is daar 'n uitweg om 'n verspreiding aan ontwikkelaars te versprei wat hulle in staat sal stel om vinnig iets te lewer wat tans ontbreek, en dan kan ons altyd lyste van pakkette versamel en 'n lys skep vir die teikenwortels.

Hierdie artikel is nie nuut nie en is 'n eenvoudige kopieer-plak-instruksie.

Die doel van die artikel is om Ubuntu-rootfs vir ARM-borde te bou (in my geval, gebaseer op Colibri imx7d).

Bou 'n beeld

Ons stel die teiken rootfs bymekaar vir replikasie.

Ubuntu-basis uitpak

Ons kies self die vrystelling op grond van behoefte en ons eie voorkeure. Hier het ek 20 gegee.

$ mkdir ubuntu20
$ cd ubuntu20
$ mkdir rootfs
$ wget http://cdimage.ubuntu.com/ubuntu-base/releases/20.04/release/ubuntu-base-20.04-base-armhf.tar.gz
$ tar xf ubuntu-base-20.04-base-armhf.tar.gz -C rootfs

Gaan BINFMT-ondersteuning in die kern na

As u 'n algemene verspreiding het, is daar ondersteuning vir BINFMT_MISC en alles is gekonfigureer, indien nie, dan is ek seker dat u weet hoe om BINFMT-ondersteuning in die kern te aktiveer.

Maak seker dat BINFMT_MISC in die kern geaktiveer is:

$ zcat /proc/config.gz | grep BINFMT
CONFIG_BINFMT_ELF=y
CONFIG_COMPAT_BINFMT_ELF=y
CONFIG_BINFMT_SCRIPT=y
CONFIG_BINFMT_MISC=y

Nou moet jy die instellings nagaan:

$ ls /proc/sys/fs/binfmt_misc
qemu-arm  register  status
$ cat /proc/sys/fs/binfmt_misc/qemu-arm
enabled
interpreter /usr/bin/qemu-arm
flags: OC
offset 0
magic 7f454c4601010100000000000000000002002800
mask ffffffffffffff00fffffffffffffffffeffffff

U kan handmatig registreer deur bv. hier is hierdie instruksies.

Stel qemu statiese arm op

Nou het ons 'n staties saamgestelde qemu-instansie nodig.

!!! AANDAG!!!
As jy van plan is om 'n houer te gebruik om iets te bou, kyk na:
https://sourceware.org/bugzilla/show_bug.cgi?id=23960
https://bugs.launchpad.net/qemu/+bug/1805913
Dan vir x86_64 gasheer en arm gas moet jy die i386 weergawe van qemu gebruik:
http://ftp.ru.debian.org/debian/pool/main/q/qemu/qemu-user-static_5.0-13_i386.deb

$ wget http://ftp.debian.org/debian/pool/main/q/qemu/qemu-user-static_5.0-13_amd64.deb
$ alient -t qemu-user-static_5.0-13_amd64.deb
# путь в rootfs и имя исполняемого файла должно совпадать с /proc/sys/fs/binfmt_misc/qemu-arm
$ mkdir qemu
$ tar xf qemu-user-static-5.0.tgz -C qemu
$ file qemu/usr/bin/qemu-arm-static
qemu/usr/bin/qemu-arm-static: ELF 64-bit LSB executable, x86-64, version 1 (GNU/Linux), statically linked, BuildID[sha1]=be45f9a321cccc5c139cc1991a4042907f9673b6, for GNU/Linux 3.2.0, stripped
$ cp qemu/usr/bin/qemu-arm-static rootfs/usr/bin/qemu-arm
$ file rootfs/usr/bin/qemu-arm
rootfs/usr/bin/qemu-arm: ELF 64-bit LSB executable, x86-64, version 1 (GNU/Linux), statically linked, BuildID[sha1]=be45f9a321cccc5c139cc1991a4042907f9673b6, for GNU/Linux 3.2.0, stripped

chroot

Eenvoudige skrif:

ch-mount.sh

#!/bin/bash

function mnt() {
    echo "MOUNTING"
    sudo mount -t proc /proc proc
    sudo mount --rbind /sys sys
    sudo mount --make-rslave sys
    sudo mount --rbind /dev dev
    sudo mount --make-rslave dev
    sudo mount -o bind /dev/pts dev/pts
    sudo chroot 
}

function umnt() {
    echo "UNMOUNTING"
    sudo umount proc
    sudo umount sys
    sudo umount dev/pts
    sudo umount dev

}

if [ "$1" == "-m" ] && [ -n "$2" ] ;
then
    mnt $1 $2
elif [ "$1" == "-u" ] && [ -n "$2" ];
then
    umnt $1 $2
else
    echo ""
    echo "Either 1'st, 2'nd or both parameters were missing"
    echo ""
    echo "1'st parameter can be one of these: -m(mount) OR -u(umount)"
    echo "2'nd parameter is the full path of rootfs directory(with trailing '/')"
    echo ""
    echo "For example: ch-mount -m /media/sdcard/"
    echo ""
    echo 1st parameter : 
    echo 2nd parameter : 
fi

Ons bewonder die resultaat:

$ ./ch-mount.sh -m rootfs/
# cat /etc/os-release
NAME="Ubuntu"
VERSION="20.04 LTS (Focal Fossa)"
ID=ubuntu
ID_LIKE=debian
PRETTY_NAME="Ubuntu 20.04 LTS"
VERSION_ID="20.04"
HOME_URL="https://www.ubuntu.com/"
SUPPORT_URL="https://help.ubuntu.com/"
BUG_REPORT_URL="https://bugs.launchpad.net/ubuntu/"
PRIVACY_POLICY_URL="https://www.ubuntu.com/legal/terms-and-policies/privacy-policy"
VERSION_CODENAME=focal
UBUNTU_CODENAME=focal
# uname -a
Linux NShubin 5.5.9-gentoo-x86_64 #1 SMP PREEMPT Mon Mar 16 14:34:52 MSK 2020 armv7l armv7l armv7l GNU/Linux

Net vir die pret, kom ons meet die grootte voor en na die installering van die minimum (vir my) stel pakkette:

# du -d 0 -h / 2>/dev/null
63M     /

Kom ons werk op:

# apt update
# apt upgrade --yes

Kom ons installeer die pakkette waarin ons belangstel:

# SYSTEMD_IGNORE_CHROOT=yes apt install --yes autoconf kmod socat ifupdown ethtool iputils-ping net-tools ssh g++ iproute2 dhcpcd5 incron ser2net udev systemd gcc minicom vim cmake make mtd-utils util-linux git strace gdb libiio-dev iiod

Kernkop-lêers en -modules is 'n aparte saak. Natuurlik sal ons nie die selflaaiprogram, kern, modules, toestelboom via Ubuntu installeer nie. Hulle sal van buite na ons toe kom of ons sal hulle self monteer of hulle sal deur die bordvervaardiger aan ons gegee word, dit is in elk geval buite die bestek van hierdie instruksie.

In 'n mate is weergawe-afwyking aanvaarbaar, maar dit is beter om dit uit die kernbou te neem.

# apt install --yes linux-headers-generic

Kom ons kyk wat gebeur het en dit het baie uitgedraai:

# apt clean
# du -d 0 -h / 2>/dev/null
770M    /

Moenie vergeet om 'n wagwoord in te stel nie.

Verpak die beeld

$ sudo tar -C rootfs --transform "s|^./||" --numeric-owner --owner=0 --group=0 -c ./ | tar --delete ./ | gzip > rootfs.tar.gz

Boonop kan ons etckeeper installeer met die autopush-instelling

Wel, kom ons sê ons het ons samestelling versprei, die werk het begin oor hoe om later verskillende weergawes van ons stelsel die beste saam te stel.

enswagter kan ons te hulp kom.

Veiligheid is 'n persoonlike saak:

  • jy kan sekere takke beskerm
  • genereer 'n unieke sleutel vir elke toestel
  • deaktiveer kragstoot
  • ens. ...
# ssh-keygen
# apt install etckeeper
# etckeeper init
# cd /etc
# git remote add origin ...

Kom ons stel autopush op

Ons kan natuurlik vooraf takke op die toestel skep (kom ons sê ons maak 'n skrif of 'n diens wat sal loop die eerste keer dat dit bekendgestel word).

# cat /etc/etckeeper/etckeeper.conf
PUSH_REMOTE="origin"

Of ons kan iets slimmer doen ...

Lui manier

Kom ons het 'n soort unieke identifiseerder, kom ons sê die reeksnommer van die verwerker (wel, of MAC - ernstige maatskappye koop die reeks):

kat / proc / cpuinfo

# cat /proc/cpuinfo
processor       : 0
model name      : ARMv7 Processor rev 5 (v7l)
BogoMIPS        : 60.36
Features        : half thumb fastmult vfp edsp neon vfpv3 tls vfpv4 idiva idivt vfpd32 lpae evtstrm 
CPU implementer : 0x41
CPU architecture: 7
CPU variant     : 0x0
CPU part        : 0xc07
CPU revision    : 5

processor       : 1
model name      : ARMv7 Processor rev 5 (v7l)
BogoMIPS        : 60.36
Features        : half thumb fastmult vfp edsp neon vfpv3 tls vfpv4 idiva idivt vfpd32 lpae evtstrm 
CPU implementer : 0x41
CPU architecture: 7
CPU variant     : 0x0
CPU part        : 0xc07
CPU revision    : 5

Hardware        : Freescale i.MX7 Dual (Device Tree)
Revision        : 0000
Serial          : 06372509

Dan kan ons dit gebruik vir die naam van die tak waarheen ons sal druk:

# cat /proc/cpuinfo | grep Serial | cut -d':' -f 2 | tr -d [:blank:]
06372509

Kom ons skep 'n eenvoudige skrif:

# cat /etc/etckeeper/commit.d/40myown-push
#!/bin/sh
set -e

if [ "$VCS" = git ] && [ -d .git ]; then
  branch=$(cat /proc/cpuinfo | grep Serial | cut -d':' -f 2 | tr -d [:blank:])
  cd /etc/
  git push origin master:${branch}
fi

En dit is al - na 'n rukkie kan ons na die veranderinge kyk en 'n lys pakkette vir die teikenfirmware skep.

Aanbevole materiaal

BINFMT_MISC
Kernel Ondersteuning vir diverse Binêre Formate (binfmt_misc)
Samestelling met qemu gebruiker chroot
Die bou van Ubuntu rootfs vir ARM
Hoe om 'n pasgemaakte Ubuntu regstreeks van nuuts af te skep
Crossdev qemu-statiese-gebruiker-chroot
ens bewaarder

getdents64 probleem

readdir() gee NULL (errno=EOVERFLOW) terug vir 32-bis gebruiker-statiese qemu op 64-bis gasheer
Ext4 64 bis hash breek 32 bit glibc 2.28+
compiler_id_detection misluk vir armhf wanneer QEMU-gebruikermodus-emulasie gebruik word
CMake werk nie behoorlik onder qemu-arm nie

Bron: will.com