Host [PC/Laptop]: Any x86/x86_64 AMD/Intel machine
Target [Raspberry Pi 4&5]: Raspberry Pi 5 or Raspberry Pi 4
Host: Any Linux machine (Ubuntu 22.04.1 LTS Tested)
Target: Raspberry Pi 4&5 Linux 64-bit OS (Raspberry Pi OS Bookworm Lite/Desktop tested)
This is based on https://www.interelectronix.com/qt-cross-compile-setup-scripts-raspberry-pi-4.html scripts. The main differences are downloading 64-bit cross-compiler instead of 32-bit and mkspecs for 64-bit Pi4 taken from Qt 6.6.1 source code is copied to the unpacked Qt 5.15.8 source code into the folder ~/rpi-qt/qt-everywhere-src-5.15.8/qtbase/mkspecs/devices/linux-rasp-pi4-aarch64. In the background the cross compile toolchains for Raspberry Pi from abhiTronix are used.
Storage and Time Requirements: The build directory takes around ~10GB space and about 2-5 hours to complete (based on dependencies & Host Machine Specifications). Networking: Your Target Machine (Raspberry Pi) and Host Machine (where you cross-compiling) both MUST have Internet Access, and MUST be on SAME Network to follow these instructions.
If you just brought a new Raspberry Pi or wanted to start from scratch just follow along. Otherwise, if you already has your Raspberry Pi setup, running, and Network Ready, then just skip to step 2.
This section assume you have at least 10GB SDcard or USB stick for installing Raspberry Pi Bookworm 64-bit OS and a Laptop/PC for uploading it.
Install rpi-imager
sudo apt install rpi-imager
rpi-imager
Select 64-bit Raspberry Pi OS Bookworm Lite/Desktop. Adjust settings form the gear button. For target storage select USB stick or sd card. I used USB since its much faster than sdcard.
If u dont want to use rpi-imager then:
Download the latest version of Raspberry Pi 64-bit OS from here on your laptop/pc. You will be needing an image writer to write the downloaded OS into the USB/SD card (micro SD card in our case). You can use Balena Etcher. Insert the SUB/SD card into the laptop/pc and run the image writer. Once open, browse and select the downloaded Raspbian image file. Select the correct device, that is the drive representing the USB/SD card.
If the drive (or device) selected is different from the SD card then the other selected drive will become corrupted. SO BE CAREFUL!
- Once the write is complete, eject the SD card and insert it into the Raspberry Pi and turn it on. It should start booting up. - Please remember that after booting the Pi, there might be situations when the user credentials like the "username" and password will be asked. Raspberry Pi comes with a default username
pi
and passwordraspberry
and so use it whenever it is being asked.
Now the you have your Raspberry Pi up and Running, its time to connect it your network with one of following ways:
If you have Monitor: Connect it to your raspberry pi along with a keyboard and mouse to navigate, and follow this guide https://www.raspberrypi.org/documentation/configuration/wireless/desktop.md
If you don't have Monitor: Follow this guide https://www.raspberrypi.org/documentation/configuration/wireless/wireless-cli.md
If you have Monitor: On the Raspberry Pi terminal, type: sudo raspi-config and menu should pop up on your terminal. To enable SSH, go to: Interfacing Options -> SSH -> Yes, and Click OK to enable it. Choose Finish finally and exit.
If you don't have Monitor: After setting up the network, if you don't have monitor or you operating it remotely. Then, enable SSH by just taking out your SD card, and hook it your computer, and simply create an empty file called ssh in the /boot/parition path inside SD card. Now insert back SD card into the Raspberry Pi.
From another Laptop/PC using SSH: To connect to your Pi from a different computer, copy and paste the following command into the terminal window but replace 192.160.1.47 with the IP address of the Raspberry Pi.
ssh pi@192.168.1.47
It will ask for password, and if not changed, it is default (raspberry), and so use it whenever it is being asked.
It is possible to configure your Raspberry Pi to allow access from another computer without needing to provide a password each time you connect. For more details, see here.
Connect to your Pi with ssh and download the zip file:
ssh pi@192.168.1.47
wget https://github.com/henrihallik/qt-cross-compile-pi5_aarch64/archive/refs/heads/main.zip
unzip main.zip
cd qt-cross-compile-pi5_aarch64
You can also download the zip file via browser from here https://github.com/henrihallik/qt-cross-compile-pi5_aarch64/archive/refs/heads/main.zip.
Make the script qt-cross-compile-script-pi4.sh executable and execute it:
sudo chmod +x qt-cross-compile-script-pi4.sh
sudo ./qt-cross-compile-script-pi4.sh
After a while all needed packages are installed, the needed directories are created and the symlinks are correctly set.
Make sure your Raspberry Pi and this Host machine (where you cross-compiling) MUST be on the SAME Network.
For testing, we used a PC with Ubuntu 22.04.1 LTS version.
wget https://github.com/henrihallik/qt-cross-compile-pi5_aarch64/archive/refs/heads/main.zip
unzip main.zip
cd qt-cross-compile-pi5_aarch64
You can also download the zip file via browser from here. https://github.com/henrihallik/qt-cross-compile-pi5_aarch64/archive/refs/heads/main.zip
chmod +x qt-cross-compile-script-host.sh
You need to change the ip address (raspberry_ip) of your raspberry pi in the script and if you changed the user (raspberry_user) and password (raspberry_pwd) of the raspberry.
nano qt-cross-compile-script-host.sh
sudo ./qt-cross-compile-script-host.sh
The script performs the following actions:
install all needed packages
create needed directories (~/rpi-qt)
download and extract Qt sources
patch Qt sources
download and extract cross compiler
rsync files from raspberry pi
download symlinker and set symlinks
configure Qt build
make and make install Qt build
rsync Qt binaries to raspberry
ERROR: Feature 'kms' was enabled, but the pre-condition 'libs.drm' failed. The ./configure command in the host script tried to find drm.h from /usr/include but such file did not exist in that folder so one must look where the libdrm headers are actually located. In my case i had to add to the ./configure command in the host script:
-I$HOME/rpi-qt/sysroot/usr/include/libdrm
Also if the libdrm.so file is not located in the ~/rpi-qt/sysroot/usr/lib/aarch64-linux-gnu then might need to specify that also with -L tag in the configure script
Enter the following command to update the device letting the linker to find the new QT binary files:
echo /usr/local/qt5.15/lib | sudo tee /etc/ld.so.conf.d/qt5.15.conf
sudo ldconfig
Read the blog Configuring Qt-Creator on Ubuntu 20 Lts for cross-compilation for including the compiled binaries (folder ~/rpi-qt/qt5.15) in Qt Creator.
Current workaround is to install qt5 with apt-get and then copy 2 files from its installation folder to the qt5.15 folder that was cross-compiled in your pc:
pi@pi5:/usr/lib/aarch64-linux-gnu/qt5/plugins/egldeviceintegrations $ sudo cp libqeglfs-kms-integration.so /usr/local/qt5.15/plugins/egldeviceintegrations/libqeglfs-kms-integration.so
pi@pi5:/usr/lib/aarch64-linux-gnu/qt5/plugins/egldeviceintegrations $ sudo cp libqeglfs-x11-integration.so /usr/local/qt5.15/plugins/egldeviceintegrations/libqeglfs-x11-integration.so
Then there should be 4 files in /usr/local/qt5.15/plugins/egldeviceintegrations/ folder:
libqeglfs-emu-integration.so libqeglfs-kms-egldevice-integration.so libqeglfs-kms-integration.so libqeglfs-x11-integration.so
drmModeGetResources failed (Operation not supported)
no screens available, assuming 24-bit color
https://stackoverflow.com/questions/64312387/rpi4-qt5-qml-drmmodegetresources-failed-error
eglfs using default card for card0, and this is not work. Need to force using card1 for eglfs.
Create a file to home folder eglfs.json
nano ~/eglfs.json
insert into it
{ "device": "/dev/dri/card1" }
save file
now before starting your app add a variable before your app name in terminal
QT_QPA_EGLFS_KMS_CONFIG=/home/YOURUSERNAME/eglfs.json /path/to/YOURAPP
or
put the variable at the beginning of your apps main method
int main(int argc, char *argv[]){
qputenv("QT_QPA_EGLFS_KMS_CONFIG", QByteArray("/home/pi/eglfs.json"));
...
}
I will later look into automatic these fixes in the scripts. Probably will need to add -x11 and maybe something else to the ./configure parameters
It seems that libcamera wants to use wait( GLIBCXX_3.4.30 method from but the cross-compiler im using has older libstc++ version thats GLIBCXX_3.4.11
- Delete all the files that start with libstdc++ from the folder ~/rpi-qt/tools/cross-pi-gcc-10.3.0-64/aarch64-linux-gnu/lib64
- Copy contents of the qt-cross-compile-pi5_aarch64/lib64 to ~/rpi-qt/tools/cross-pi-gcc-10.3.0-64/aarch64-linux-gnu/lib64
a more detailed solution here https://forum.arducam.com/t/error-undefined-reference-to-libcamera-generateconfiguration-when-cross-compiling/5698/8?u=henri
OR
find the same files(libstdc++.so.6.0.30, libstdc++fs.a, libstdc++fs.a, libstdc++.so.6.0.30-gdb.py) from your Raspberry Pi filesystem and use those instead. also need to make two symlinks manually in this case
pi@pi5:~ $ find / -type f -name 'libstdc++' 2>/dev/null
/usr/lib/aarch64-linux-gnu/libstdc++.so.6.0.30
/usr/lib/gcc/aarch64-linux-gnu/12/libstdc++.a
/usr/lib/gcc/aarch64-linux-gnu/12/libstdc++fs.a
/usr/share/doc/gcc-12-base/C++/changelog.libstdc++.gz
/usr/share/doc/gcc-12-base/C++/README.libstdc++-baseline.arm64
/usr/share/doc/gcc-12-base/C++/libstdc++_symbols.txt.arm64
/usr/share/gdb/auto-load/usr/lib/aarch64-linux-gnu/libstdc++.so.6.0.30-gdb.py
finally create the symlinks:
cd ~/rpi-qt/tools/cross-pi-gcc-10.3.0-64/aarch64-linux-gnu/lib64
ln -s libstdc++.so.6.0.30 libstdc++.so
ln -s libstdc++.so.6.0.30 libstdc++.so.6
Will automate this also later