在C90中,我可以重新定义main
并给它另一个名称,并可能使用#define
添加额外的参数?
例如,将其放在标题文件中:
#include <stdio.h>
#include <stdlib.h>
#define main( void ) new_main( void )
int new_main( void );
编译时标头不会显示任何错误。但是,当我尝试使用主c文件编译时,我不断出现错误
In function '_start': Undefined reference to 'main'
不,您不能这样做,因为它会违反语言和OS标准。名称main
及其参数argc
,argv
和environ
构成了系统加载程序调用约定的一部分。
有点简化解释(没有ABI级别,只是API级别(。当您的程序被加载到内存中并即将开始时,加载程序需要知道要调用哪个功能作为入口点,以及如何将其环境传递给它。如果可以更改主和/或其参数列表的名称,则需要将新调用接口的详细信息传达给加载程序。而且没有方便的方法可以做(除了编写自己的可执行加载程序外(。
In function '_start': Undefined reference to 'main'
在这里,您可以看到Linux/POISX Elf Loader接口的实现细节。编译器将函数 _start
添加到幕后程序,这是一个实际的程序入口点。_start
的任务是对使用LIBC的大多数程序进行额外的初始化步骤。是_start
,后来呼叫您的main
。从理论上讲,您可以编写一个程序,该程序具有其自己的函数,称为_start
,没有main
,这很好。这并不是微不足道的,因为您必须确保不再将默认的_start
代码附加到您的程序上(没有双重定义(,但这是可行的。不,出于相同的原因,您不能选择除_start
以外的其他名称。
汇编单元中#define main new_main
的存在不会影响实现将在程序启动上调用功能的名称。该实现将调用一个称为main
的函数,无论您定义什么宏。
如果您要使用这样的#define
来防止main()
的主要声明以该名称产生函数,则需要在其他地方包含main()
的定义;然后可以调用原始版本。例如,如果原始定义不使用其参数,并且仅通过从main((返回而不是使用exit()
]来退出,则可以将#define main new_main
放置在main
的主要定义使用的标头文件中,并且然后在另一个文件中执行类似:
#include <stdio.h>
#include <conio.h> // For getch() function.
int main(void)
{
int result = main();
printf("nExit code was %d. Strike any key.n", result);
getch();
return result;
}
在大多数情况下,最好在普通的"主"函数中添加任何此类代码,但是在每个构建中代码生成工具或某些构建工具产生包含main
的文件的情况下,此方法可能很有用不能修改其他原因以包括此类代码。
不,你不能(正如格里格里所说(。
但是,您可以立即致电您的代理人
int
your_new_main(int argc, char* argv[], char* envp[]) {
... //your stuff goes here
}
//just place this in an include file, and only include in main...
int
main( int argc, char* argv[], char* envp[])
{
int result = your_new_main(argc, argv);
return result;
}
至于是否到处支持Envp?
- 是char *envp []作为main((便携式的第三个参数
假设您使用的是gcc
将-nostdlib
传递给程序,然后通过将其传递给gcc
,然后将其传递给链接器-Wl,-enew_main
来设置新条目。这样做不会让您访问C Runtime在调用主机之前所具有的任何不错的功能,您必须自己做。
您可以查看有关main
之前发生的事情的资源。
Main