【问题标题】:Place segments of external static library to specific locations将外部静态库的段放置到特定位置
【发布时间】:2023-03-12 13:11:01
【问题描述】:

我的应用程序调用了一些放置在外部静态库中的函数。我将外部静态库链接到我的应用程序,一切正常(在这种情况下,我使用的是 GCC)。

尽管如此,库的文本、.data 和 .bss 部分的位置(地址)是由链接器选择的。我可以通过修改链接器脚本来选择/更改它们的位置,但这很乏味,因为我必须指定库的所有函数、变量等。我的意思是这样的:

. = 0x1000; /* new location */
KEEP(*(.text.library_function1));
KEEP(*(.text.library_function2));
[...]

另一种解决方案是通过为每个函数/变量放置一个节属性来构建外部库,然后通过重新定位整个节来修改链接器。比如:

/* C source file */
unsigned char __attribute__((section (".myLibrarySection"))) variable1[10];
unsigned char __attribute__((section (".myLibrarySection"))) variable2[10];

/* Linker script */
. = 0x1000;
KEEP(*(.myLibrarySection))

但是,我希望能够重新定位外部静态库的整个 .text、.data 和 .bss 段,而无需使用这些技巧。

我想要这样的东西(在链接器脚本中):

. = 0x1000;
KEEP(*(.text.library_file_name))

是否可以使用 GCC 工具链?

是否可以使用其他工具链(IAR、Keil 等)?

【问题讨论】:

    标签: c gcc linker keil iar


    【解决方案1】:

    您可以在 ld 中使用archive:filename 语法。

    首先将外部库中的所有.o 文件放入静态库.a 文件中(如果它们还没有的话)。这是静态库二进制文件的正常分发方式。

    然后在链接描述文件中,指定:

    .text.special : {
        . = 0x1000;
        *libspecial.a:*(.text .text.*)
    }
    
    .text {
        *(.text .text.*)
    }
    

    通配符将选择来自libspecial.a 的所有文件并将它们放在第一部分。后面的通配符将选择剩下的任何东西。如果需要将.text.special 部分放在普通部分之后,可以类似的方式使用EXCLUDE_FILE 指令。

    【讨论】:

      【解决方案2】:

      您可以对您的库进行后处理以重命名部分吗?

      # Untested!
      TMP=`mktemp -d`
      trap "rm -rf $TMP" EXIT
      cd $TMP
      ar x path/to/your/lib.a
      for o in *.o; do
        for s in text data bss; do
          objcopy --rename-section .$s=.mynew$s $o
        done
      done
      ar rcs path/to/your/lib.a *.o
      

      【讨论】:

        猜你喜欢
        • 2011-10-16
        • 1970-01-01
        • 1970-01-01
        • 2018-10-04
        • 2016-10-27
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2015-09-26
        相关资源
        最近更新 更多