如何影响函数的地址?

时间:2013-02-06 13:38:12

标签: c assembly

是否有影响,设置或定义函数(相对)地址的方法?也许链接器脚本有任何可能性来确保函数abc()始终驻留在OFFSET + 0x0034C0(仅作为示例)。 我想以某种方式“控制”内存中函数的位置,使这些位置进行某种参数化。 目前我正在使用gcc在我的x86上寻找一种方法。但是,真正的应用程序应该在嵌入式设备上运行。

此致

3 个答案:

答案 0 :(得分:8)

你可以用linker script magic和gcc一起做,是的。看看如何定义section placement,然后在你的源代码中放置指令,将函数放在你选择的部分中。

完全不确定这是否可以在x86机器上运行,因为操作系统可能有......反对意见。这更适合直接嵌入式使用。

在完整操作系统上控制代码位置的是什么?

答案 1 :(得分:1)

这个典型的通用实现是一个向量表(我也听说过这个称为补丁表)。

首先,在你的C文件中,编写你的函数:

void my_first_function(int){ /* do something */ }
void my_second_function(int){ /* do something */ }

然后,在您的C文件中创建一个定义表格布局的结构:

struct MyVectorTable
{
  void (*first_function)(int);
  int (*second_function)(float, char);

  // all the rest
};

接下来,在您的C文件中创建一个静态表:

static struct MyVectorTable my_vector_table = {
  my_first_function,
  my_second_function,
};

最后将地址公开为void *

void* get_table_base_address(void) { return &my_vector_table; }

现在你应该能够将所有函数作为基址的偏移量。

如果所有函数都具有相同的调用签名,则可以通过使用函数指针数组而不是结构来简化此操作。但是,数组和结构都将保存指针,因此指针数学基本相同。

这也允许您使用链接器在特定地址找到补丁表。

答案 2 :(得分:1)

执行此操作的最佳方法IMO是将函数放入用户定义的部分,如上面提到的展开。您可以找到一个将函数myFunc置于下方4kByte边界的简单示例:

通过修改链接描述文件在内存中创建一个新部分:

/* .my_section will be the name of the section in the final executable */
.my_section : ALIGN (8)
{
    . = ALIGN (0x1000);

    KEEP(*(.mysection))    /* The section will be called ".mysection" in the
                              compiled translation unit (.obj) */

    . = ALIGN (8);
} >rom

现在,使用gcc的attribute功能将函数放入我们刚创建的部分:

void myFunc(void) __attribute__ ((section(".mysection"))); // The section name to use 
                                                           // here is ".mysection", 
                                                           // not ".my_section"

// Looks like you need to use __attribute__ along with function declaration, rather 
// than with the function definition, though I'm not sure why

void myFunc(void)
{
    // ...
}

如果您现在objdump,则会看到名称为.my_section的部分,其中myFunc代码位于地址0x2000,而不是{{1} }}

0x12e8

此代码适用于ARM-Cortex的Disassembly of section .my_section: 000012e8 <myFunc-0xd18>: ... 00002000 <myFunc>: 2000: b508 push {r3, lr} ... 套件。我对x86不太确定......