Nowadays almost all PC and servers are 64bit. Once in a while one may need to develop and run 32bit apps. In this post we will go through several methods for both x86_64 and ARM64 machines.
I can think of 4 ways of doing this:
- Run a virtual machine, which in turn runs a 32bit OS. Not covered in this post.
- Set up 32bit chroot environment. (Recommended)
- Set up 32bit architecture with Debian multi-arch support (Recommended)
- Use gcc multi-lib feature to build 32bit binaries.
Here we go through some detailed steps for those approaches on X86_64/Ubuntu 20.04. Instructions should apply to other Debian-based distributions and different versions as well.
GCC Multi-Lib Approach
Although this is the simplest approach, I don’t recommend it because the GCC support varies for different CPU architectures and the command line options also varies, making it hard to generalize and port existing software. I believe mult-arch is the future direction.
- Install GCC multi-lib package
sudo apt install gcc-multilib
- Compile with -m32 option
gcc -m32 hello.c -o hello file hello ./hello
- Add 32bit as secondary architecture
sudo dpkg --add-architecture i386
- Install dev tools and 32bit specific dev tools and libraries
sudo apt update sudo apt install -y build-essential sudo apt install -y crossbuild-essential-i386 sudo apt install -y libc6:i386 sudo apt install -y libstdc++6:i386
- Develop with i686-linux-gnu- cross-compile prefix
i686-linux-gnu-gcc hello.c -o hello file hello ./hello
- Note for Ubuntu 18.04, crossbuild-essential-i386 meta-package does not exist. One needs to install below packages explicityly
sudo apt install -y dpkg-cross g++-i686-linux-gnu gcc-i686-linux-gnu
For more detailed descriptions, please refer to http://logan.tw/posts/2018/02/24/manage-chroot-environments-with-schroot/
- Install packages
sudo apt-get install schroot debootstrap
- Install 32bit environment (e.g., Ubuntu 20.04) (note the last URL arg can be ommited)
sudo debootstrap --arch=i386 focal /var/chroot/focal32 http://archive.ubuntu.com/ubuntu
- Edit /etc/schroot/schroot.conf file
[focal32] description=Ubuntu 20.04 Focal Fossil 32bit directory=/var/chroot/focal32 root-users=ubuntu,jsun users=ubuntu,jsun type=directory personality=linux32
- Create and enter 32bit chroot session
schroot -c focal32 ; enter as normal user schroot -c focal32 -u root ; enter as root user
- From inside the session, one can install build-essential meta-package and develop 32bit apps as if inside a 32bit machine.
- (Optional) One can even run 32bit graphic apps from inside the chroot environment.
ARM64 is often called aarch64, where ARM64 rooted from Linux community and aarch64 is official name from ARM. We will use those 2 terms inter-changeably.
GCC for aarch64 does not support multi-lib. So this option is not available.
It is similar to i386 case, except that architecture is “armhf” and cross-compile prefix is “arm-linux-gunueabihf-“.
sudo dpkg --add-architecture armhf sudo apt update sudo apt install -y build-essential sudo apt install -y crossbuild-essential-armhf sudo apt install -y libc6:armhf sudo apt install -y libstdc++6:armhf arm-linux-gnueabihf-gcc hello.c -o hello file hello ./hello
For chroot approach, it is similar to i386 case, with 2 exceptions:
- The architecture name is “armhf” instead of “i386”
- The repo URL is “http://ports.ubuntu.com/ubuntu-ports”, instead of “http://archive.ubuntu.com/ubuntu”
Note we can also set up the root filesystem from debian repos. Below is an example to set up debian sid for armhf 32bit architecture:
Below is an example to set up debian SID for armhf architecture:
- Install packages and bootstrap root filesystem
sudo apt-get install schroot debootstrap sudo debootstrap --arch=armhf sid /var/chroot/sid-armhf http://ftp.debian.org/debian/
- Modify and add to /etc/schroot/schroot.conf file
[sid32] description=Debian Sid 32bit directory=/var/chroot/sid-armhf root-users=ubuntu users=ubuntu type=directory personality=linux32
- Create and enter sid32 session, “schroot -c sid32”
- Multilib works for MIPS64.
- sudo apt install gcc-multilib g++-multilib
- compile with -mabi=32 flags, i.e., “gcc -mabi=32 hello.c”
- Multi-Arch does not work for MIPS64, at least for enabling 32bit dev
- I have not tried chroot approach on MIPS64 yet. Let me know if you have had any success.
- In Ubuntu chroot environment, the initial apt repo source is limited to main. You may find many packages are missing. To fix this, edit /etc/apt/source.list
deb http://archive.ubuntu.com/ubuntu xenial main universe multiverse