You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

寻求可区分-fPIC与非-fPIC编译目标文件的MWE

体现PIC与非PIC代码差异的最小示例

你的原示例无法体现差异,是因为函数仅包含本地算术运算,没有涉及全局变量、外部函数调用等需要寻址的操作——这类场景下PIC和非PIC生成的机器码完全一致。

要观察到差异,需要构造一个引用全局变量或调用外部函数的场景,以下是最小可行示例:

示例代码

// pic_demo.c
int global_var = 42;

int get_global() {
    return global_var;
}

编译命令

  • 编译非PIC目标文件:
    gcc -c pic_demo.c -o pic_demo.o
    
  • 编译PIC目标文件:
    gcc -c -fPIC pic_demo.c -o pic_demo_pic.o
    

查看差异

使用objdump -d命令反汇编两个目标文件,对比get_global函数的机器码:

非PIC版本反汇编片段

0000000000000000 <get_global>:
   0:   8b 05 00 00 00 00       mov    0x0(%rip),%eax        # 6 <get_global+0x6>
                        2: R_X86_64_PC32        global_var-0x4
   6:   c3                      retq

这里直接通过RIP相对寻址访问global_var,属于直接引用。

PIC版本反汇编片段

0000000000000000 <get_global>:
   0:   48 8b 05 00 00 00 00    mov    0x0(%rip),%rax        # 7 <get_global+0x7>
                        3: R_X86_64_REX_GOTPCRELX  global_var-0x4
   7:   8b 00                   mov    (%rax),%eax
   9:   c3                      retq

PIC版本会先通过RIP相对寻址找到GOT(全局偏移表)中global_var的条目,再间接读取变量值——这是为了保证代码加载到任意内存地址时,都能正确定位全局变量,符合位置无关的要求。

内容的提问来源于stack exchange,提问作者MaPo

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.18 15:56:04