I have been trying to cross compile util-linux for arm but I keep ending up with dynamically linked executable files and I don't know why is this. My objective is static. I have been cross-compiling before different tools using similar steps and it has always worked so I don't know what I am doing wrong this time. I am using Ubuntu 16.04. Here are the commands I am running:

export CC=arm-linux-gnueabi-gcc
export ac_cs_linux_vers=4
export CFLAGS=-static
export CPPFLAGS=-static
export LDFLAGS=-static

./configure --host=arm-linux LDFLAGS=-static --disable-shared --without-tinfo --without-ncurses --disable-ipv6 --disable-pylibmount --enable-static-programs=fdisk,sfdisk,whereis --prefix=/opt/util-linux/arm --bindir=/opt/util-linux/arm/bin --sbindir=/opt/util-linux/arm/sbin

As you can see, I specified static at every place I could think of even repeating stuff "just to make sure it understands me" and after I run the configure script, here is the output:

util-linux  2.28.2

prefix:            /opt/util-linux/arm
exec prefix:       ${prefix}

localstatedir:     ${prefix}/var
bindir:            /opt/util-linux/arm/bin
sbindir:           /opt/util-linux/arm/sbin
libdir:            ${exec_prefix}/lib
includedir:        ${prefix}/include
usrbin_execdir:    ${exec_prefix}/bin
usrsbin_execdir:   ${exec_prefix}/sbin
usrlib_execdir:    ${exec_prefix}/lib

compiler:          arm-linux-gnueabi-gcc
cflags:            -static
suid cflags:       
ldflags:           -static
suid ldflags:      

Python:            /usr/bin/python
Python version:    2.7
Python libs:       ${exec_prefix}/lib/python2.7/site-packages

Bash completions:  /usr/share/bash-completion/completions
Systemd support:   no
Btrfs support:     yes


Then I do:

make fdisk


make whereis

and once the compilation is done, I do:

file fdisk

fdisk being the file that just got created and:

fdisk: ELF 32-bit LSB executable, ARM, EABI5 version 1 (SYSV), dynamically linked, interpreter /lib/ld-linux.so.3, for GNU/Linux 3.2.0, BuildID[sha1]=369363ef8f8173a3a1c2edc178eb77255a2dc415, not stripped

As you can see it says, "dynamically linked". I have been searching all over the Internet but I failed to find an answer. I also do:

./configure --host=arm-linux LDFLAGS=-static --disable-shared --without-tinfo --without-ncurses --disable-ipv6 --disable-pylibmount --prefix=/opt/util-linux/arm --bindir=/opt/util-linux/arm/bin --sbindir=/opt/util-linux/arm/sbin

Which is exactly the same configure command as the one before that except for the missing "--enable-static-programs" parameter which "should" by default compile everything as static except that it does not.

Am I doing something wrong or is this a Makefile error?


I just figured out why the original commands posted in my question weren't producing static files! I had to run make LDFLAGS="--static". After I did this, everything linked statically!

To repeat, I ran:

export CC=arm-linux-gnueabi-gcc
export ac_cs_linux_vers=4
export CFLAGS=-static
export SUID_CFLAGS=-static
export SUID_LDFLAGS=-static
export CPPFLAGS=-static
export LDFLAGS=-static


./configure --host=arm-linux-gnueabi --disable-shared --without-tinfo --without-ncurses --disable-ipv6 --disable-pylibmount --prefix=/opt/util-linux/arm --bindir=/opt/util-linux/arm/bin --sbindir=/opt/util-linux/arm/sbin

and then

make LDFLAGS="--static"

and everything linked statically! No more need for object files collection as demonstrated in my previous answer but yeah that too can be used as an alternative.

Also for your info, here is my version info as some of you will probably care:

$ arm-linux-gnueabi-gcc --version
arm-linux-gnueabi-gcc (Ubuntu/Linaro 5.4.0-6ubuntu1~16.04.1) 5.4.0 20160609
Copyright (C) 2015 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.  There is NO

$ arm-linux-androideabi-ld --version
GNU gold (GNU Binutils 1.11
Copyright (C) 2015 Free Software Foundation, Inc.
This program is free software; you may redistribute it under the terms of
the GNU General Public License version 3 or (at your option) a later version.
This program has absolutely no warranty.

The static binaries are built with a .static extension; after the build, I get

$ file fdisk.static
fdisk.static: ELF 32-bit LSB executable, ARM, EABI5 version 1 (GNU/Linux), statically linked, for GNU/Linux 3.2.0, BuildID[sha1]=b51ec4b17f772b881d2a1eaefd368cfb96d0db12, not stripped

I got this with only

./configure --host=arm-linux-gnueabihf --enable-static-programs=fdisk

(you shouldn't need any FLAGS variables; replace gnueabihf with gnueabi in your setup, I just used that because I already had a working armhf cross-compilation setup).

  • Thx for your response. I am not getting any files with .static extensions. I get all sorts of files but .static ones. Not sure what I am doing wrong and why it fails to generate static files. – rwx Oct 31 '16 at 10:27

Update -- See my other answer below

Ok, after hours (literally) and hours of analyzing the Makefile file created by the configure script of util-linux and another Makefile file created by another utility that does end up with statically linked files, I successfully retrieved the parameters passed to arm-linux-gnueabi-gcc that produce statically linked files. So I ended up with this:

arm-linux-gnueabi-gcc -ffloat-store -static -DHAVE_CONFIG_H -static  -D_U_="__attribute__((unused))" -o <name_of_your_file> <object files produced by the compiler separated by space>

So after compiling whereis:

make whereis

I then did a search for all the object files produced:

find . -name "*.o"

I ended up with:


So then I consolidated all those object files into one line and I ran another command:

arm-linux-gnueabi-gcc -ffloat-store -static -DHAVE_CONFIG_H -static  -D_U_="__attribute__((unused))" -o mywhereis ./misc-utils/whereis.o ./lib/libcommon_la-blkdev.o ./lib/libcommon_la-sysfs.o ./lib/libcommon_la-idcache.o ./lib/libcommon_la-procutils.o ./lib/libcommon_la-mbsalign.o ./lib/libcommon_la-linux_version.o ./lib/libcommon_la-env.o ./lib/libcommon_la-pager.o ./lib/libcommon_la-strutils.o ./lib/libcommon_la-mangle.o ./lib/libcommon_la-timeutils.o ./lib/libcommon_la-fileutils.o ./lib/libcommon_la-exec_shell.o ./lib/libcommon_la-match.o ./lib/libcommon_la-crc32.o ./lib/libcommon_la-md5.o ./lib/libcommon_la-randutils.o ./lib/libcommon_la-ttyutils.o ./lib/libcommon_la-cpuset.o ./lib/libcommon_la-color-names.o ./lib/libcommon_la-ismounted.o ./lib/libcommon_la-path.o ./lib/libcommon_la-canonicalize.o ./lib/libcommon_la-loopdev.o ./lib/libcommon_la-setproctitle.o ./lib/libcommon_la-strv.o

And voila! :) mywhereis got generated.

So I then did the honors by running the file command:

mywhereis: ELF 32-bit LSB executable, ARM, EABI5 version 1 (SYSV), statically linked, for GNU/Linux 3.2.0, BuildID[sha1]=a5b7c4ad147dc26ed211a7aa643f744a29e477f3, not stripped

What a relieve!! Ok the solution is not ideal but it does the job and in can be streamlined!

I spent about 8 hours in total working on this and experimenting and I realized there may not be "one fix for all" but this does indeed do the job! I tested the file on my Android phone and it works!!

Also, this solution appears to be a "one fix for all" as it just links the object files to create a statically linked file. I tested this with another utility from a completely different source package and that too worked.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.