linux - open() 是从 libc 源代码的哪个位置获得链接的?

标签 linux gcc linker system-calls libc

我基本上需要为我的目的自定义一些 linux 系统调用接口(interface)(比如 sys_open)。我非常了解 GNU Linker ld --wrap=symbol 选项并使用该逻辑来更改 open() libc 包装器。虽然这达到了目的,但我真的很想知道在 libc 源代码中,实际实现发挥了作用。

以下两个地方是我的主要怀疑对象(注意 fcntrl.h 只有声明)

  • GLIBC_DIR/io/open.c
  • GLIBC_DIR/ports/sysdeps/unix/sysv/linux/generic/open.c

示例驱动程序:

#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>

int main(int argc, char *argv[])
{
    int fd;

    if ((fd = open("sample.c", O_RDONLY)) == -1) {
        fprintf(stderr, "file not found\n");
        exit(1);
    }

    return 0;
}

相关片段:

main:
  401dd1:       bf 44 90 48 00          mov    $0x489044,%edi
  401dd6:       b8 00 00 00 00          mov    $0x0,%eax
  401ddb:       e8 10 03 03 00          callq  4320f0 <__libc_open>

......
......

 __libc_open:
  4320f0:       83 3d 69 8e 28 00 00    cmpl   $0x0,0x288e69(%rip)        
  4320f7:       75 14                   jne    43210d <__open_nocancel+0x14>

__open_nocancel:
  4320f9:       b8 02 00 00 00          mov    $0x2,%eax
  4320fe:       0f 05                   syscall 

为简单起见,我准备了所有可执行的 libc 源代码静态。也非常小心,让 GCC 正确地选择了自定义的 libc.a。我尝试添加一个 puts 语句,但提到的两个源代码根本没有被调用。查看可执行文件的程序集 [如上所示],sys_open 调用(__open_nocancel 中的 0x2)已以某种方式放置在可执行文件中。

所以我的问题是:

  • open() 相关的代码逻辑神奇地来自 libc 中的什么地方?
  • 当 libc 源代码树中没有显式命名为 open 的函数时,链接器如何能够成功 Hook open() 函数?

最佳答案

From where exactly in libc, the open()-related code logic magically come?

来自sysdeps/unix/syscall-template.S

How is the linker able to successfully hook the open() function when there is no function explicitly named open in libc source tree?

如果您使用正确的 -DSYSCALL_SYMBOL=... 对上述源代码进行预处理,您会发现 中提到了 open来源。

关于linux - open() 是从 libc 源代码的哪个位置获得链接的?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31355686/

相关文章:

php - 如何使用 nginx 反向代理 ssh 到我的远程 docker 容器

linux - BASH:- 将字符串解析为单独的命令行参数

c - 使用编译标志 -o3 进行数组复制

c++ - 编译与静态链接

linux - Firebird DB-监控表

linux - 如何使用 MobaXTerm 便携版查找空目录

Gcc 和 ld 参数

c++ - 好友定义不适用于 gcc4.9

c - 使用一个编译器创建的静态 C 库是否与另一个兼容?

linux - 有效地在 ELF 文件中添加新部分