Compiling Crypto++ for armhf for cross compiling

2019-07-14 20:08发布

问题:

I want to cross compile the library crypto++ for deployment on a beaglebone running Debian. My host PC runs Ubuntu 14.04 LTS in a 64-bit configuration.

I face the following problem when I invoke the make command from eclipse

arm-linux-gnueabihf-g++-4.8 -L/usr/include/cryptopp -o "GCMwithAES"  ./main.o   -lcryptopp
/usr/lib/../lib/libcryptopp.so: file not recognized: File format not recognized

My guess is that since the compiler is configured for armhf, it cannot recognize the library that was compiled for amd64.

I have successfully cross compiled and run standard (ie no external libraries) programs from my host PC to my target device.

Solutions that I have tried

  • Used libcrypto++ packages with the architecture specified as armhf as done in multiarch. The armhf libraries get installed ( as per apt) but I am unable to include and link my code with them.
  • Manually try to compile the library as per the instruction given on this wiki. However, I always run into errors whenever I try to compile the library.

How do I install the libcryptopp libraries of the armhf architecture on my x64 based PC so I can cross compile? or is there any other way to resolve this issue.

Edit

As suggested in the answer below I tried out the method suggested. I slightly modified the script setenv-embed.sh since I had gcc-4.8 instead of gcc-4.7. The results of running the script are

CPP: /usr/bin/arm-linux-gnueabihf-cpp 
CXX: /usr/bin/arm-linux-gnueabihf-g++
AR: /usr/bin/arm-linux-gnueabihf-ar
LD: /usr/bin/arm-linux-gnueabihf-ld
RANLIB: /usr/bin/arm-linux-gnueabihf-gcc-ranlib-4.8

ARM_EMBEDDED_TOOLCHAIN: /usr/bin
ARM_EMBEDDED_CXX_HEADERS: /usr/arm-linux-gnueabihf/include/c++/4.8.2
ARM_EMBEDDED_FLAGS: -march=armv7-a mfloat-abi=hard -mfpu=neon -I/usr/arm-linux-gnueabihf/include/c++/4.8.2 -I/usr/arm-linux-gnueabihf/include/c++/4.8.2/arm-linux-gnueabihf 
ARM_EMBEDDED_SYSROOT: /usr/arm-linux-gnueabihf

I build the library using the make command and run into the following error

/usr/lib/gcc-cross/arm-linux-gnueabihf/4.8/../../../../arm-linux-gnueabihf/bin/‌​ld: cannot find /usr/arm-linux-gnueabihf/lib/libc.so.6 inside /usr/arm-linux-gnueabihf
/usr/lib/gcc-cross/arm-linux-gnueabihf/4.8/../../../../arm-linux-gnueabihf/bin/‌​ld: cannot find /usr/arm-linux-gnueabihf/lib/libc_nonshared.a inside /usr/arm-linux-gnueabihf        
/usr/lib/gcc-cross/arm-linux-gnueabihf/4.8/../../../../arm-linux-gnueabihf/bin/‌​ld: cannot find /usr/arm-linux-gnueabihf/lib/ld-linux-armhf.so.3 inside /usr/arm-linux-gnueabihf

But when I open the location /usr/arm-linux-gnueabihf/lib I can find all the three error files mentioned above ie libc.so.6, libc_nonshared.a and ld-linux-armhf.so.3

As per the suggestions of @jww, I'm shifting this to a new question since I'm having trouble linking. My results here are left for completeness.

回答1:

How do I install the libcryptopp libraries of the armhf architecture on my x64 based PC so I can cross compile? or is there any other way to resolve this issue.

Checkout ARM Embedded (Command Line) on the Crypto++ wiki.

Note: that wiki page is a bit dated. You can now use GNUmakefile-cross. I have not updated the page to reflect recent changes like GNUmakefile-cross.

GNUmakefile-cross is a special purpose built for cross-compiling on Android, iOS, Windows Phone, ARM Embedded, and bare metal (I doubt anyone would do the later, but I tested it as a platform). You will still need to run the setenv-embedded.sh script.

To fetch the latest sources from GitHub:

git clone https://github.com/weidai11/cryptopp.git cryptopp-armhf

The GitHub sources are quite active at the moment. We are preparing for a Crypto++ 5.6.3 release. 5.6.3 will include GNUmakefile-cross.


The complete instructions will look something like (assuming you have the tools installed):

git clone https://github.com/weidai11/cryptopp.git cryptopp-armhf
cd cryptopp-armhf

# Note the leading dot!!!
. ./setenv-embedded.sh
# The command above must execute successfully
# It cannot display a message like "**CXX is not valid**"

# Build it
make -f GNUmakefile-cross static dynamic cryptest.exe

# Check it
$ find . -name cryptest.exe
./cryptest.exe
$ /usr/bin/arm-linux-gnueabi-readelf -h ./cryptest.exe | grep -i 'class\|machine' 
  Class:                             ELF32
  Machine: 

Because the GitHub sources are quite active at the moment, I've already added all the other files from Crypto++-Mobile.zip and Setenv-embedded.sh.zip to the official Crypto++ sources. You only need to get setenv-embedded.sh out of the Setenv-embedded.sh.zip.



回答2:

In addition to jww's answer, I wanted to add some further notes. (These notes are relevant for version 5.6.3 released 20-Nov-2015.)

It may be necessary to edit the config.h file to change some options. See Config.h on the Crypto++ wiki. In particular:

  • CRYPTOPP_NO_UNALIGNED_DATA_ACCESS may need to be defined so that the code operates properly on systems that can't do unaligned data read/writes (e.g. ARM).
  • CRYPTOPP_INIT_PRIORITY and CRYPTOPP_USER_PRIORITY may need to be defined. See Static Initialization Order Fiasco - Crypto++ Wiki for details.
  • CRYPTOPP_MAINTAIN_BACKWARDS_COMPATIBILITY_562 may need to be defined or undefined, depending on whether the project using it is using older API features or not.

After building the library, it is very much worth running the test program cryptest.exe v on the target system, to check if the library has been built okay for that system. For example, by doing this, I discovered that the library doesn't work properly on the ARM-based BeagleBone Black unless I define CRYPTOPP_NO_UNALIGNED_DATA_ACCESS in config.h (it freezes indefinitely on the test step Testing MessageDigest algorithm SHA-384.).