交叉编译时如何使用外部库?
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了交叉编译时如何使用外部库?相关的知识,希望对你有一定的参考价值。
我在x86 ubuntu机器上为raspberry pi ARM目标编写了一些代码。我正在使用gcc-linaro-armhf工具链。我能够在pi上交叉编译并运行一些独立的程序。现在,我想将我的代码链接到外部库,如ncurses。我怎样才能做到这一点。
我应该只将我的程序与主机上的现有ncurses lib链接,然后在ARM上运行吗? (我认为这不会起作用)我是否需要为arm获取lib的源代码或预构建版本,将其放入我的lib路径然后编译?
在这种情况下,最佳做法是什么?
我也想知道它如何用于c stdlib。在我的程序中,我使用了stdio函数,它在交叉编译后工作,没有做任何特殊的事情。我刚刚在makefile中为我的arm gcc提供了路径。所以,我想知道,它是如何得到正确的标准头文件和库?
关于你的一般问题:
为什么C库有效:
C库是交叉工具链的一部分。这就是找到标题并且程序正确链接和运行的原因。对于其他一些非常基本的系统库(如libm和libstdc ++)也是如此(并非在每种情况下都依赖于工具链配置)。
通常,在处理交叉开发时,您需要一些方法来交叉编译所需的库。在这种情况下使用二进制文件是非常罕见的。也就是说,特别是对于ARM硬件,因为有许多不同的配置,并且通常所有内容都以不同的方式被剥离。这就是为什么二进制文件在不同设备和Linux配置之间不是很多二进制兼容的原因。
如果您在Raspberry Pi上运行Ubuntu,那么您可能会在Internet上甚至在某些Ubuntu apt存储库中找到合适的ncurses库。然而,典型的方法是使用您拥有的特定工具链交叉编译库。
在需要交叉编译大量复杂库的情况下,有一些解决方案可以让生活变得像buildroot或ptxdist一样简单。这些程序为嵌入式设备构建完整的Linux内核和根文件系统。
但是,在您的情况下,只要您只想要ncurses,您就可以自己编译源代码。您只需下载源代码,在使用configure
选项指定工具链的同时运行--host
。 --prefix
选项将选择安装目录。在运行make
和make install
之后,考虑到一切正常,您将获得一组头文件和ARM编译库供您的应用程序链接。
关于交叉编译,您肯定会在互联网上找到大量信息,也许ncurses也在其发布的文档中有一些指示。
查询How the C library works in cross-tools
在配置期间编译和构建跨工具链时,它们将提供sysroot。
像--with-sysroot=${CLFS_CROSS_TOOLS}
--with-sysroot
--with-sysroot=dir
Tells GCC to consider dir as the root of a tree that contains (a subset of) the root filesystem of the target operating system. Target system headers, libraries and run-time object files will be searched for in there. More specifically, this acts as if --sysroot=dir was added to the default options of the built compiler. The specified directory is not copied into the install tree, unlike the options --with-headers and --with-libs that this option obsoletes. The default value, in case --with-sysroot is not given an argument, is ${gcc_tooldir}/sys-root. If the specified directory is a subdirectory of ${exec_prefix}, then it will be found relative to the GCC binaries if the installation tree is moved.
所以不是看/lib /usr/include
而是在编译时看起来/ Toolchain /(libc)和(包含文件)
你可以检查一下
arm-linux-gnueabihf-gcc -print-sysroot
这个节目在哪里寻找libc。
也
arm-linux-gnueabihf-gcc -print-search-dirs
给你清晰的图片
显然,你需要为你所针对的ARM编译一个ncurses
- 主机上的那个将完全没有任何好处[除非你的主机有一个ARM处理器 - 但你说的是x86,所以显然不是这样)。
可能有一些预构建的库可用,但我怀疑找到一个(工作和匹配你的特定条件)比从源自己构建库更多的工作 - 它应该不那么难,我希望ncurses
不需要花费很多分钟才能建成。
至于你的第一个问题,如果你打算在你的交叉编译工具链中使用ncurses库,那么你将准备好它的arm-built二进制文件。
你的第二个问题是它如何与std lib一起使用,它真的不是工具链用于编译/链接你的程序的系统libc / libm。也许你会从编译器的--print-file-name =选项中看到它:
arm-none-linux-gnuabi-gcc --print-file-name=libm.a
...(my working folder)/arm-2011.03(arm-toolchain folder)/bin/../arm-none-linux-gnuabi/libc/usr/lib/libm.a
arm-none-linux-gnuabi-gcc --print-file-name=libpthread.so
...(my working folder)/arm-2011.03(arm-toolchain folder)/bin/../arm-none-linux-gnuabi/libc/usr/lib/libpthread.so
我认为你的Raspberry工具链可能是一样的。你可以尝试一下。
Vinay的答案非常可靠。只是在为raspberry pi编译ncurses库时进行修正,设置rootfs的选项是--sysroot=<dir>
而不是--with-sysroot
。这就是我在使用以下编译器时发现的内容:
arm-linux-gnueabihf-gcc --version arm-linux-gnueabihf-gcc (crosstool-NG linaro-1.13.1+bzr2650 - Linaro GCC 2014.03) 4.8.3 20140303 (prerelease) Copyright (C) 2013 Free Software Foundation, Inc. This is free software; see the source for copying conditions. There is NO warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
以上是关于交叉编译时如何使用外部库?的主要内容,如果未能解决你的问题,请参考以下文章