使用编译器选项覆盖宏

发布于 2024-10-02 06:34:29 字数 392 浏览 3 评论 0原文

我需要通过我的头文件覆盖某些宏定义。而且我不被允许更改源代码。我必须使用 gcc,但如果有人知道任何其他编译器上有类似的东西,那么它也会有所帮助。

这就是我真正需要的:

假设我有包含大量 .c 文件的代码库。这些 .c 文件包括 .h 文件。在每个文件包含所有 .h 文件后,我希望编译器的行为就像我有另一个我想在调用编译器时指定的 extra.h 文件一样。我在该 .h 文件中所做的是 #undef 一些宏,并按照我想要的方式重新定义宏。

注意:我知道 gcc 中的 --preinclude 选项,但是使用 --preinclude 会用原始源代码的 .h 覆盖我的 extra.h。我需要的是某种帖子包含选项。

I need to be override certain macro definition by my header file. And I am not allowed to change source code. And I have to use gcc, but if anyone is aware of something similar on any other compiler then also it will help.

Here is what I exactly need:

Lets say I have code base with lot of .c files. These .c files include .h files. After all the .h files have been included for each file I want the compiler to behave as if I have another extra.h file which I want to specify when invoking the compiler. What I do in that .h file is #undef some macro and re-define the macro the way I want them to be.

Note: I am aware of --preinclude option in gcc, but using --preinclude over-rides my extra.h by the .h of the original source code. What I need is some kind of post include option.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

許願樹丅啲祈禱 2024-10-09 06:34:29

除非您统一有一个始终包含在源文件最后的特定标头,否则这将很棘手。

我认为如果必须的话,我的处理方法是:

  • 创建一个新目录,将其命名为 headers
  • 放入与常规标头同名的合适的虚拟标头,其中末尾包含 #include "extra.h" (或者可能 #include< /code>,但我会尽力避免这种情况)。
  • 虚拟标头还将通过某种机制包含原始文件,甚至可能使用 #include "/usr/include/header.h" 但最好使用其他一些技术 - 例如 #include "include /标题。”
  • extra.h 标头始终会重新定义其所有宏 - 它不会具有正常的 #ifndef EXTRA_H_INCLUDED / #define EXTRA_H_INCLUDED / #endif 多个包含守卫,这样每次包含时都会重新定义相关的宏。
  • 因此,extra.h 无法定义任何类型。 (或者,更准确地说,如果确实如此,则必须通过多个包含防护来保护它们免受多重定义;关键点是每次包含文件时都必须定义宏 - 有点像 ;。)
  • 每个重新定义的宏都将受到 #undef REDEFINED_MACRO#define REDEFINED_MACRO ... 的显式保护。
  • 在取消定义宏之前测试宏是否已定义是没有意义的。
  • 构建过程将被修改为先在 headers 目录中查找,然后再查找其他地方。编译器选项将是 -I./headers 或类似的选项,具体取决于您定位 headers 目录的位置。
  • 根据您决定如何定位标头的正常版本,您可能需要另一个 -I 选项(例如 -I/usr 如果您使用过 >#include "include/header.h" 符号)再次定位标准头。

结果是编译器直接使用您的私有标头,但它们包括标准标头,然后是您的 extra.h 标头 - 从而无需修改 C 源代码或普通标头即可实现您想要的目标。

但整个尝试存在一些误导……你最好不要尝试这个。

Unless you uniformly have one specific header that is always included last in the source files, this is going to be tricky.

I think the way I'd approach it, if I had to, would be:

  • Create a new directory, call it headers.
  • Put in there suitable dummy headers with the same name as the regular headers, which would contain #include "extra.h" at the end (or possibly #include <extra.h>, but I would try to avoid that).
  • The dummy headers would also include the original files by some mechanism, possibly even using #include "/usr/include/header.h" but preferably some other technique - such as #include "include/header.".
  • The extra.h header would always redefine all its macros - it would not have the normal #ifndef EXTRA_H_INCLUDED / #define EXTRA_H_INCLUDED / #endif multiple inclusion guards, so that each time it is included, it would redefine the relevant macros.
  • Consequently, extra.h cannot define any types. (Or, more precisely, if it does, those must be protected against multiple definition by multiple include guards; the key point is that the macros must be defined each time the file is included - a bit like <assert.h>.)
  • Each redefined macro would be explicitly protected by #undef REDEFINED_MACRO and then #define REDEFINED_MACRO ....
  • There is no point in testing whether the macro is defined before undefining it.
  • The build process would be modified to look in the headers directory before looking anywhere else. The compiler option would be -I./headers or something similar, depending on exactly where you locate the headers directory.
  • Depending on how you have decided to locate the normal versions of the headers, you might need another -I option (such as -I/usr if you've used #include "include/header.h" notation) to locate the standard headers again.

The upshot is that your private headers get used directly by the compiler, but they include the standard headers and then your extra.h header - thus achieving what you wanted without modifying the C source or the normal headers.

But there is something misguided about the whole attempt...you would be better off not trying this.

孤城病女 2024-10-09 06:34:29

您可以使用
GCC 的 -include file 选项,因为此功能:

如果给出多个 -include 选项,则文件按照它们在命令行中出现的顺序包含。

因此我知道您必须从命令行包含所有 *.h 文件,只需将“extra.h”保留在 -include 选项列表中的最后一个标头,您就应该得到您想要的内容。

You can use
-include file option of GCC, because of this feature:

If multiple -include options are given, the files are included in the order they appear on the command line.

So as I understand you must include ALL *.h files from the command line,- just keep your "extra.h" the last header in -include option list and you should get what you want.

睡美人的小仙女 2024-10-09 06:34:29

要求是在 .c 文件中的所有其他 .h 文件之后插入 extra.h。因此,将其添加到每个 .h 文件的末尾会将其插入到 .c 文件中按顺序包含的两个 .h 文件之间,这不是本意。

您可以在 makefile 中使用 sed/awk 来:
- 首先创建重复的 .c 文件,在每个 .c 文件内的其他 #include 行之后插入 '#include "extra.h"' (在 .c 文件内重新解析 #ifdef 块将是乏味/棘手的)
- 然后实现编译那些重复的 .c 文件的目标
- 最后删除重复的.c文件

The requirement is to insert extra.h after all the other .h files in a .c file. So adding it at the end of each .h file will insert it between two .h files included in sequence inside a .c file, which is not the intention.

You can use sed/awk inside makefile(s) to:
- first create duplicate .c files inserting '#include "extra.h"' after other #include lines inside each of the .c files (it will be tedious/ticky to resole #ifdef blocks inside the .c files)
- then achieve your target compiling those duplicate .c files
- finally delete the duplicate .c files

黎歌 2024-10-09 06:34:29

根据您的要求,我可以想到两种方法来做到这一点,并且我希望这两种方法都应该相对简单。

第一种方法根本不触及源代码,但是它要求您 #undef'ing 的每个头文件都有一个头保护。您可以将需要“更改”内容的每个头文件复制并连接到一个整体文件中,即“extra.h”文件。然后在该文件的末尾,继续重新定义您需要的所有宏。然后在编译时包含该文件。标头防护将防止包含原始标头。显然,这种方法存在许多潜在问题,而且一般情况下肯定行不通。

第二种方法更干净、更可靠,但它需要您直接编辑代码,尽管是非侵入式的。对于需要重新定义内容的每个标头,使用“.orig”后缀或其他内容制作该标头的副本,然后直接编辑实际的标头文件。完成所有操作后,只需在客户获取代码之前将所有“.orig”文件复制回实际标头即可。我认为您的要求并没有那么严格,以至于您甚至暂时无法更改代码。

如果这些都不起作用,那么我怀疑除了直接破解 GCC 并自己添加“-postinclude”选项之外,您是否会从任何人那里找到有效的答案。

There are two ways I can think of doing this according to your requirements, and both should be relatively simple, I hope.

The first way does not touch the source code at all, however it requires that each header file you are #undef'ing things from has a header guard. You can copy and concatenate every header file that you need to "change" things in into one monolithic file, your "extra.h" file. Then at the end of that file, go ahead and redefine all the macros you need. Then include this file when you compile. The header guards will prevent the original headers from being included. Obviously, there are a number of potential problems with this approach, and it certainly wouldn't work in general.

The second way is a lot cleaner and more reliable, but it requires you to edit the code directly, albeit non-intrusively. For each header you need to redefine things in, make a copy of that header with an ".orig" suffix or something, then edit the actual header file directly. After you are all done doing whatever you are doing, then just copy all the ".orig" files back into the actual headers before your customers obtain the code. I assume your requirements aren't so draconian that you can't change the code even temporarily.

If none of that works, then I doubt you are going to find an effective answer from anybody short of hacking GCC directly and adding a "-postinclude" option yourself.

み零 2024-10-09 06:34:29

Makefile 可用于通过 -U 和 -D 编译器 (gcc) 选项重新定义宏。但为什么在评估原始版本后重新定义它们呢?我想不出有必要这样做。您能说出您希望通过此实现什么目标吗?

Makefile could be used to redefine the macros through the -U and -D compiler(gcc) options. But why redefine them after the originals are evaluated? I cannot think of a need for such a thing. Can you tell what are you hoping to achieve through this?

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文