The objective of these instructions is to create a complete Arm64 OS (Userland and Kernel) using Debian Debootstrap and RPI-Update for use on the Raspberry Pi 3 and 4.
Prerequisites:
- An existing Debian/Raspbian system (any architecture will do)
- An empty SD card formatted as per a standard Raspbian installation mounted to /mnt/sd on the build system
- 1st Partition 0-256MB = FAT32 (Mount to /mnt/sd/boot)
- 2nd Partition 256MB+ = EXT4 (Mount to /mnt/sd)
The utility used by the Debian installer, and recognized as the official way to install a Debian base system, is debootstrap. We will also need QEMU if we are building an Arm64 system on another host architecture (x64 or ArmHF most likely)
So lets install them.
sudo apt install debootstrap qemu
Now lets tell debootstrap to set-up a base Debian Arm64 installation on our SD card. This may take a while and will download an entire basic Debian system.
sudo debootstrap --arch arm64 bullseye /mnt/sd http://ftp.uk.debian.org/debian
Before we can do anything with our new system we have to make it accessible from our hosts architecture, we do this using QEMU.
sudo cp /usr/bin/qemu-arm64-static /mnt/sd/usr/bin
Now we have a basic Debian system we can chroot into and start setting up.
sudo mount -t proc /proc /mnt/sd/proc/
sudo mount -t sysfs /sys /mnt/sd/sys/
sudo mount -o bind /dev /mnt/sd/dev/
sudo chroot /mnt/sd /bin/bash
Now we are chrooted into our new Debian system there are a few things we need to configure to make it useable. Lets deal with "apt" first so we can install new packages.
To set-up "apt" we need to tell it which sources to use, I'll use the UK Debian mirror in this example.
editor /etc/apt/sources.list
deb http://ftp.uk.debian.org/debian stable main contrib non-free
deb-src http://ftp.uk.debian.org/debian stable main contrib non-free
deb http://ftp.uk.debian.org/debian stable-updates main contrib non-free
deb-src http://ftp.uk.debian.org/debian stable-updates main contrib non-free
deb http://security.debian.org/ stable/updates main contrib non-free
deb-src http://security.debian.org/ stable/updates main contrib non-free
To minimise the number of packages that apt installs you can also disable the automatic installation of Recommended packages
editor /etc/apt/apt.conf.d/99_norecommends
APT::Install-Recommends "false";
APT::AutoRemove::RecommendsImportant "false";
APT::AutoRemove::SuggestsImportant "false";
Once that file is saved we can update the apt repositories and make sure everything is updated.
apt update
apt upgrade
Now we can set-up some other basic system settings.
Select your Timezone.
dpkg-reconfigure tzdata
Select your language and input settings.
apt install locales
dpkg-reconfigure locales
I will use echo commands in these instructions for simplicity, alternatively you can use "editor" to edit these files.
Setup your network interfaces. (Example using a basic wired connection using DHCP, customise to suit)
echo \
'auto lo
iface lo inet loopback
auto eth0
iface eth0 inet dhcp
allow-hotplug wlan0
iface wlan0 inet dhcp
wpa-conf /etc/wpa_supplicant/wpa_supplicant.conf' \
> /etc/network/interfaces
Setup your DNS nameservers (Example using Cloudflare servers)
echo \
'nameserver 1.1.1.1
nameserver 1.0.0.1' \
> /etc/resolv.conf
Setup your hostname (Example using Pi-Example)
echo 'Pi-Example' > /etc/hostname
Set-up your hosts file (including IPV4 and IPV6)
echo \
'127.0.0.1 localhost
127.0.1.1 Pi-Example
::1 ip6-localhost ip6-loopback
fe00::0 ip6-localnet
ff02::1 ip6-allnodes
ff02::2 ip6-allrouters
ff02::3 ip6-allhosts' \
> /etc/hosts
If you are going to be using a wireless network connection rather than wired you will need to setup wpasupplicant with your wifi connection details like this example.
apt install wpasupplicant
editor /etc/wpa_supplicant/wpa_supplicant.conf
ctrl_interface=DIR=/var/run/wpa_supplicant GROUP=netdev
update_config=1
country=GB
network={
ssid="Your network name/SSID"
psk="Your WPA/WPA2 security key"
key_mgmt=WPA-PSK
}
Set-up your basic drive mounts for / , /boot & /proc
editor /etc/fstab
This example assumes a standard Raspberry Pi SD card set-up.
# <file system> <dir> <type> <options> <dump> <pass>
proc /proc proc defaults 0 0
/dev/mmcblk0p1 /boot vfat defaults 0 2
/dev/mmcblk0p2 / ext4 defaults,noatime 0 1
passwd
These are additional packages you may expect to find on a basic (Commandline) Debian system on the Raspberry Pi
apt install aptitude ca-certificates crda fake-hwclock firmware-brcm80211 gnupg man-db manpages net-tools ntp usb-modeswitch ssh sudo wget xz-utils
Install additional packages if you want to use a GUI and RDP (lxqt as an example)
apt install xorg xorgxrdp xrdp lxqt lightdm
Install mesa drivers to enable 3D acceleration (Note: I'm unsure of which specific packages are required but this should cover all bases)
apt install libegl-mesa0 libgbm1 libgl1-mesa-dev libgl1-mesa-dri libglapi-mesa libglx-mesa0 libosmesa6 mesa-opencl-icd mesa-va-drivers mesa-vdpau-drivers mesa-vulkan-drivers mesa-utils
Standard Raspbian has the "pi" user so I'll use that as an example.
Create a user called "pi" that uses the "bash" shell, who has a home directory of "/home/pi" and is a member of the same groups as in a standard Raspbian install.
mkdir /home/pi
groupadd spi
groupadd i2c
groupadd gpio
useradd -s /bin/bash -d /home/pi -G sudo,video,adm,dialout,cdrom,audio,plugdev,games,users,input,netdev,spi,i2c,gpio pi
chown pi:pi /home/pi
Set the users password
passwd pi
In order for your BASH settings (~/.bashrc) to load on log-in you require a .profile file in your user and root home directories.
editor /home/pi/.profile
# if running bash
if [ -n "$BASH_VERSION" ]; then
# include .bashrc if it exists
if [ -f "$HOME/.bashrc" ]; then
. "$HOME/.bashrc"
fi
fi
# set PATH so it includes user's private bin if it exists
if [ -d "$HOME/bin" ] ; then
PATH="$HOME/bin:$PATH"
fi
# set PATH for RaspberryPi userland files in /opt/vc/bin if they exist
if [ -d "/opt/vc/bin" ] ; then
PATH="$PATH:/opt/vc/bin"
fi
cp /home/pi/.profile /root/
chown pi:pi /home/pi/.profile
cd /usr/local/bin
wget https://raw.githubusercontent.com/raspberrypi/rpi-update/master/rpi-update
chmod +x rpi-update
apt install curl binutils cmake git build-essential
WANT_32BIT=1 WANT_64BIT=1 WANT_PI4=1 rpi-update
Set-up config.txt and cmdline.txt
echo 'dwc_otg.lpm_enable=0 console=tty1 root=/dev/mmcblk0p2 rootfstype=ext4 elevator=deadline fsck.repair=yes rootwait net.ifnames=0' > /boot/cmdline.txt
echo $'ngpu_mem=16\narm_64bit=1\ndtoverlay=vc4-fkms-v3d' > /boot/config.txt
(Incomplete and Unsupported. For full working Userland firmware I would recommend to multi-arch armhf as you can just use the rpi-update installed files in that case)
Build and install from Source
cd /tmp
git clone https://github.com/raspberrypi/userland
cd userland
./buildme --aarch64
dpkg --add-architecture armhf
dpkg --add-architecture armel
apt update
apt install libc6:armhf libc6:armel
echo '/opt/vc/lib' > /etc/ld.so.conf.d/00-vmcs.conf
echo 'Defaults secure_path="/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/opt/vc/bin"' > /etc/sudoers.d/opt-path
editor /etc/udev/rules.d/99-com.rules
SUBSYSTEM=="vchiq",GROUP="video",MODE="0660"
SUBSYSTEM=="vcio",GROUP="video",MODE="0660"
SUBSYSTEM=="vc-mem",GROUP="video",MODE="0660"
SUBSYSTEM=="input", GROUP="input", MODE="0660"
SUBSYSTEM=="i2c-dev", GROUP="i2c", MODE="0660"
SUBSYSTEM=="spidev", GROUP="spi", MODE="0660"
SUBSYSTEM=="bcm2835-gpiomem", GROUP="gpio", MODE="0660"
SUBSYSTEM=="rpivid-*", GROUP="video", MODE="0660"
KERNEL=="vcsm-cma", GROUP="video", MODE="0660"
SUBSYSTEM=="gpio", GROUP="gpio", MODE="0660"
SUBSYSTEM=="gpio*", PROGRAM="/bin/sh -c '\
chown -R root:gpio /sys/class/gpio && chmod -R 770 /sys/class/gpio;\
chown -R root:gpio /sys/devices/virtual/gpio && chmod -R 770 /sys/devices/virtual/gpio;\
chown -R root:gpio /sys$devpath && chmod -R 770 /sys$devpath\
'"
SUBSYSTEM=="pwm*", PROGRAM="/bin/sh -c '\
chown -R root:gpio /sys/class/pwm && chmod -R 770 /sys/class/pwm;\
chown -R root:gpio /sys/devices/platform/soc/*.pwm/pwm/pwmchip* && chmod -R 770 /sys/devices/platform/soc/*.pwm/pwm/pwmchip*\
'"
KERNEL=="ttyAMA[01]", PROGRAM="/bin/sh -c '\
ALIASES=/proc/device-tree/aliases; \
if cmp -s $ALIASES/uart0 $ALIASES/serial0; then \
echo 0;\
elif cmp -s $ALIASES/uart0 $ALIASES/serial1; then \
echo 1; \
else \
exit 1; \
fi\
'", SYMLINK+="serial%c"
KERNEL=="ttyS0", PROGRAM="/bin/sh -c '\
ALIASES=/proc/device-tree/aliases; \
if cmp -s $ALIASES/uart1 $ALIASES/serial0; then \
echo 0; \
elif cmp -s $ALIASES/uart1 $ALIASES/serial1; then \
echo 1; \
else \
exit 1; \
fi \
'", SYMLINK+="serial%c"
If there is anything else you wish to configure such as SSH keys (Note SSH is enabled in this build but not configured), this can be done in the chroot environment you have been working.
Once complete you should be able to exit the chroot environment and unmount your new SD card.
exit
sudo umount /mnt/sd/*
sudo umount /mnt/sd
Your 64-bit Debian Bullseye is now ready for use, Just insert the card into your PI and power on.
what about the missing libraspberrypi stuff (/opt/vc)? do you download those from the official raspbian mirrors or maybe kali?