放置在一个静态库时没有发现_sbrk功能 [英] _sbrk function not found when placed in a static library
问题描述
我创建的STM32F407微控制器,它具有了ARM Cortex M4内核裸机应用。因此,我提供的功能的实现如 _sbrk
自己。现在我发现,当我试图创建一个包含 _sbrk
静态库,并与我的的main.c
链接入一个应用程序,链接器说。
\"c:/progra~2/gnutoo~1/4947e~1.920/bin/../lib/gcc/arm-none-eabi/4.9.3/../../../../arm-none-eabi/lib/armv7e-m/softfp\\libg_nano.a(lib_a-sbrkr.o):在功能_sbrk_r:sbrkr.c :( text._sbrk_r + 0xC的):未定义的参考`_sbrk'
。
块引用>如果我采取相同的功能出来的静态库,并把它变成
的main.c
,一切编译/链接/运行就好了。我几乎可以肯定,这已经是与在该连接器中的所有图书馆阅读的顺序,当我自己的静态库阅读,没有定义
_sbrk
目前还不需要,因此被扔出去,却发现它无论如何需要的时候后,标准库中的一个链接,但我不指定任何标准库自己,因此不能改变的顺序链接这些库。我也试图声明_sbrk
功能__属性__((__ used__))
,以为链接不会扔掉的功能,但很可惜,这并没有解决我的问题。所以我的问题是,我怎样才能把
_sbrk
成静态库,而不会在未解决的参考?更新:连接最后的应用程序的命令是:
C:\\ PROGRA〜2 \\ GNUTOO〜1 \\ 4947E〜1.920 \\ BIN \\ AR10B2〜1.EXE -g -mcpu =的Cortex-M4 -mfpu = fpv4-SP-D16 -mfloat-ABI = softfp -mthumb - 高效多功能截面-fno-RTTI -fno-例外-std = C ++ 11 -fno使用-CXA-atexit对-fno线程安全,静-g -mcpu =的Cortex-M4 -mfpu = fpv4-SP-D16 -mfloat -abi = softfp -mthumb轮候册, - GC-部分-nostartfiles轮候册,-TC:/用户/理查德·彼得斯/文件/项目/嵌入式/ HTTP_SERVER / ldscripts / mem.ld轮候册,-T C:/用户/理查德·彼得斯/文件/项目/嵌入式/ HTTP_SERVER / ldscripts / sections.ldCMakeFiles \\ http_server.http_server.dir的\\ src \\ main.cpp.objCMakeFiles \\ http_server.http_server.dir的\\ src \\ vectors_stm32f4xx.c.objCMakeFiles \\ http_server.http_server.dir \\ http_server.http_server_linker_script_dummy.c.obj-oC:\\用户\\理查德· Peters\\Documents\\Projects\\Embedded-install\\targets\\http_server.http_server\\Generic-stm32f4xx\\bin\\http_server.http_server.elf\" C:\\用户\\理查德· Peters\\Documents\\Projects\\Embedded-install\\targets\\cmsis_stm.cmsis_stm\\Generic-stm32f4xx\\lib\\libcmsis_stm.cmsis_stm.a\"
块引用>其中,
AR10B2〜.EXE
解析为臂无 - EABI-G ++。exe文件
。添加下面让事情链接:
-lc -lgC:\\用户\\理查德· Peters\\Documents\\Projects\\Embedded-install\\targets\\cmsis_stm.cmsis_stm\\Generic-stm32f4xx\\lib\\libcmsis_stm.cmsis_stm.a\"
块引用>个
libcmsis_stm.cmsis_stm.a
函数库是使用下面的命令:
C:\\ PROGRA〜2 \\ GNUTOO〜1 \\ 4947E〜1.920 \\ BIN \\ ARM-NO〜2.EXE CQC:\\用户\\理查德· Peters\\Documents\\Projects\\Embedded-install\\targets\\cmsis_stm.cmsis_stm\\Generic-stm32f4xx\\lib\\libcmsis_stm.cmsis_stm.a\" CMakeFiles / cmsis_stm.cmsis_stm.dir / src目录/ CMSIS / system_stm32f4xx.c.obj
块引用>其中,
ARM-NO〜2.EXE
解析为臂无 - EABI-ar.exe
所以,还有一个问题:我想放置中断向量表,它是一个变量,进入静态库,但链接抛出变了,因为没有源文件需要该变量。也可把该变量,直到连接器处理输出部分的连接文件的机制?
解决方案在
LD
针对库链接,只会挑选那些需要的功能在那段时间的(因为已在被链接翻译单元的引用功能的前的)。链接器会忘记所有其他功能(和库将不被考虑后)。因此,链接顺序很重要。通常你会在你的应用程序对象文件链接(引用
的malloc
),那么标准库(提供的malloc
和反过来引用_sbrk
),然后你的(应用)库,它提供_sbrk
。因此,链接看起来应该像
臂无 - EABI - 海合会... -o out.elf startup.o main.o中-lc -lm -lapp </ P>
块引用>与
libapp </ code>所提供的
_sbrk
功能。因此,对象的顺序要被链接很重要。
更新
作为一个评论说:如果添加使用调试符号
-g
编译过程中,那么你必须打击的libg以及链接(-lg
)。
臂无 - EABI - 海合会... -o out.elf startup.o main.o中-lc -g -lm -lapp </ P>
块引用>I'm creating a bare-metal application for the stm32f407 microcontroller, which has an ARM Cortex M4 core. As such, I'm delivering the implementation of functions like
_sbrk
myself. I now find that when I try to create a static library containing_sbrk
, and link it with mymain.c
into an application, the linker says"c:/progra~2/gnutoo~1/4947e~1.920/bin/../lib/gcc/arm-none-eabi/4.9.3/../../../../arm-none-eabi/lib/armv7e-m/softfp\libg_nano.a(lib_a-sbrkr.o): In function _sbrk_r: sbrkr.c:(.text._sbrk_r+0xc): undefined reference to `_sbrk'".
If I take that same function out of the static library, and put it into
main.c
, everything compiles/links/runs just fine.I am almost certain that this has something to do with the order in which the linker reads in all libraries, and that when my own static library is read, no definition of
_sbrk
is required yet, and is therefore thrown out, only to find that it was needed anyway when later one of the standard libraries is linked in. However, I do not specify any standard libraries myself, and can therefore not change the order of linking those libraries. I also tried to declare the_sbrk
function as__attribute __ ((__ used__ ))
, thinking that the linker would not throw away that function, but alas, this has not solved my problem.So my question is, how can I put
_sbrk
into a static library, without running into unresolved references?Update: The command to link the final application is:
C:\PROGRA~2\GNUTOO~1\4947E~1.920\bin\AR10B2~1.EXE -g -mcpu=cortex-m4 -mfpu=fpv4-sp-d16 -mfloat-abi=softfp -mthumb -ffunction-sections -fno-rtti -fno-exceptions -std=c++11 -fno-use-cxa-atexit -fno-threadsafe-statics -g -mcpu=cortex-m4 -mfpu=fpv4-sp-d16 -mfloat-abi=softfp -mthumb -Wl,--gc-sections -nostartfiles -Wl,-T"C:/Users/Richard Peters/Documents/Projects/Embedded/http_server/ldscripts/mem.ld" -Wl,-T"C:/Users/Richard Peters/Documents/Projects/Embedded/http_server/ldscripts/sections.ld" "CMakeFiles\http_server.http_server.dir\src\main.cpp.obj" "CMakeFiles\http_server.http_server.dir\src\vectors_stm32f4xx.c.obj" "CMakeFiles\http_server.http_server.dir\http_server.http_server_linker_script_dummy.c.obj" -o "c:\Users\Richard Peters\Documents\Projects\Embedded-install\targets\http_server.http_server\Generic-stm32f4xx\bin\http_server.http_server.elf" "c:\Users\Richard Peters\Documents\Projects\Embedded-install\targets\cmsis_stm.cmsis_stm\Generic-stm32f4xx\lib\libcmsis_stm.cmsis_stm.a"
Where
AR10B2~.EXE
resolves toarm-none-eabi-g++.exe
.Adding the following makes the thing link:
-lc -lg "c:\Users\Richard Peters\Documents\Projects\Embedded-install\targets\cmsis_stm.cmsis_stm\Generic-stm32f4xx\lib\libcmsis_stm.cmsis_stm.a"
Th
libcmsis_stm.cmsis_stm.a
library is built with the following command:C:\PROGRA~2\GNUTOO~1\4947E~1.920\bin\ARM-NO~2.EXE cq "c:\Users\Richard Peters\Documents\Projects\Embedded-install\targets\cmsis_stm.cmsis_stm\Generic-stm32f4xx\lib\libcmsis_stm.cmsis_stm.a" CMakeFiles/cmsis_stm.cmsis_stm.dir/src/cmsis/system_stm32f4xx.c.obj
Where
ARM-NO~2.EXE
resolves toarm-none-eabi-ar.exe
So one question remains: I would like to place the interrupt vector table, which is a variable, into the static library, but the linker throws that variable away because no source file needs that variable. Is there a mechanism to keep that variable until the linker processes the output sections in the linker file?
解决方案When
ld
links against a library, it will only pick those functions which are required at that time (because of references to functions from translation units which have been linked in before). The linker will forget all other functions (and the library won't be considered later).Therefore the linking order does matter. Normally you would link in your application object file (which references
malloc
), then the standard library (which providesmalloc
and in turn references_sbrk
), and then your (application) library which provides_sbrk
.So linking should look like
arm-none-eabi-gcc ... -o out.elf startup.o main.o -lc -lm -lapp
with the
_sbrk
function being provided bylibapp
.So the order of the objects to be linked does matter.
Update
As stated in one of the comments: If you add debug symbols using
-g
during compilation, then you have to link against libg as well (-lg
).arm-none-eabi-gcc ... -o out.elf startup.o main.o -lc -g -lm -lapp
这篇关于放置在一个静态库时没有发现_sbrk功能的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!