【问题标题】:How to understand glibc cross-reference?如何理解 glibc 交叉引用?
【发布时间】:2016-02-20 04:41:00
【问题描述】:

我正在尝试了解 hello world 程序是如何工作的:

#include <stdio.h>

int main(int argc, char **argv) {
    printf("Hello World!");
    return 0;
}

除了printf 部分外,大部分内容都很简单。我不知道它是如何工作的。为了理解它,我寻找了glibc cross reference并找到了this page

然后我搜索了printf,它返回了很多results

现在我的程序正在使用这些printfs 中的哪一个?如何确定?

另外,例如,当打开该页面中的first result 时,printf 函数中的函数将我引导至__printf_chk,其中__printf_chk 中的函数将我引导至__nldbl___vfprintf_chk,其中@ 中的函数987654337@ 将我引向__vfprintf_chk__vfprintf_chk 中的函数又将我引向__nldbl___vfprintf_chk,它创建了一个无限递归。怎么回事?

简而言之,我应该如何跟踪给定函数/源代码的来源?

【问题讨论】:

  • "现在我的程序正在使用这些 printfs 中的哪一个?如何确定它?"您应该弄清楚该库是如何构建的。这主要取决于如何调用编译器,这在 Makefiles 中定义。这可能同样难以理解。 glibc 不好玩吗? (剧透:glibc 不好玩。)
  • 另一个剧透:你最终会在 vfprintf in stdio-common/vfprintf.c 的定义中结束,但要了解它与 __printf 之类的函数之间的关系,你将不得不经历一大堆预处理器宏和 GCC 特定的属性声明。
  • @Rhymoid 是所有这些创建/保留可移植性的原因吗?
  • 我不能肯定,但这是我的猜测:有一个通用实现绝对可移植,然后针对特定平台的优化进行了一些调整(那些__nldbl 函数似乎与具有long double 的系统有关)。为了保持这个解决方案可维护,有一些宏和包装函数层。随着时间的推移,这一层不断增长,并变成了维护负担。 (遗憾的是,这种情况在软件工程中很常见。)
  • 与 glibc here 相比,知名的替代品包括 musl、uClibc 和 Dietlibc。

标签: c glibc libc


【解决方案1】:

我没有完整的答案,但我无法发表评论。看起来 __vfprintf_chk 调用了 vfprintf,它在 /stdio-common/vfprintf.c 中似乎别名为 _IO_vfprintf_internal。不知道最后一个函数的由来,但是这里看不到无限循环?

【讨论】:

  • In this page, __vfprintf_chk 呼叫__nldbl___vfprintf_chk
  • 我明白你的意思。看起来我不会有太大的帮助,我不知道你提到的递归是如何解决的,但 printf 似乎是定义here。找出哪个被使用需要深入了解哪个被构建系统编译/链接,除此之外别无他法。
【解决方案2】:

printf 的实现见stdio-common/printf.c

int
__printf (const char *format, ...)
{
   va_list arg;
   int done;

   va_start (arg, format);
   done = vfprintf (stdout, format, arg);
   va_end (arg);

   return done;
}

调用vfprintf

【讨论】:

  • 我怎么知道它调用 that printf 而不是其他人?
  • 这是让我感到困惑的主要部分。例如,当您在交叉引用页面中查找vfprintf 时,您会得到大约一打results,其中3 个被声明为函数定义。您的链接指向这些结果中的第二个函数定义,但我怎么知道第二个 vprintf 被调用而不是其他 2 个?
  • 没有简单的规则 - 您可能必须检查每个选项。由于可移植性和兼容性要求,glibc 非常密集。也就是说,清除某些选项的一种简单方法是查看文件路径和文件名。 __printf_chk 带您进入 sysdep 目录 - 您无需进入这些类型的目录即可进行核心实现。
猜你喜欢
  • 2011-05-20
  • 2014-07-03
  • 1970-01-01
  • 2017-02-11
  • 2019-05-26
  • 2021-07-08
  • 2014-12-19
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多