在C程序中包含头文件时,链接器/编译器如何找到相应的代码?

时间:2016-03-01 21:40:49

标签: c linker pic32

我理解在创建.c和.h文件并将它们添加到我的项目时链接和编译是如何工作的。

但是当我将stdio.h这样的标题添加到我的项目中时会发生什么?我知道链接器在一些标准目录中搜索.h文件,然后粘贴它,但是头文件只包含函数原型而没有代码。编译器或链接器在哪里找到这些函数的代码,以及如何将它添加到我的源文件中?

我问的原因是因为我正在为微控制器编写一个引导加载程序,我想仔细查看实际发送给编译器的所有C代码。我正在为PIC32使用非优化的免费版XC32编译器,所以我不相信它只包括我实际使用的内容。

2 个答案:

答案 0 :(得分:4)

链接器根本不关心头文件。链接器甚至不知道这些存在,因为它只看到已编译的目标文件,这就是为什么您明确需要使用-l...选项指定要链接的库。链接器隐式链接标准C库(-lc),这是标准C函数的查找方式。在许多平台上,这不适用于sinpow等数学函数,这就是为什么当您想要使用这些函数时需要与-lm链接的原因。

回答指定链接到-l...的库的问题:编译器有一组标准目录。它也可能在工作目录中查找。您可以使用-L...编译器选项向库搜索路径添加更多目录。这告诉链接器也在指定的目录中查找库。

答案 1 :(得分:4)

您需要区分标题和库。

标题声明可供程序使用的设施。当您包含诸如<stdio.h>之类的标题时(注意:这是不是 - 重复而不是! - 库),您可以向编译器提供必要的信息使用标准I / O库中的工具。通常,C头文件不定义实现工具的实际代码。 C ++只有#header;&#39;库(Boost的某些部分是&#39;仅标题库的主要示例)。

图书馆提供设施的实施。 <stdio.h>标头声明了一个函数fopen();在某个地方有一个定义该功能的库。

某些标头(实际上,通常是很多标头)具有特权,它们声明的工具包含在C编译器链接程序的标准库中。您不必做任何特殊的事情来将功能链接到您的程序中。其他头文件来自C编译器不了解先验的库,对于那些,您必须告诉它在哪里找到库(例如,使用-L /opt/sometool/lib作为编译器选项)和库名称(例如, -lsometool,可能与/opt/sometool/lib/libsometool.so/opt/sometool/lib/libsometool.a相关联。请注意,SomeTool的标头可能位于/opt/sometool/include,您需要添加选项-I/opt/sometool/include才能找到sometool.h标题。

链接器不引用标头;编译器本身没有引用库。编译器控制程序确实处理混合(它通常作为单独的程序运行编译过程的多个阶段 - 编译器与链接器分开)。标题不包含有关库安装位置的信息。