我正在尝试执行PintOS命令pintos -f
(如果您不熟悉PintOS,请不要担心)。在内部,调用init.c
程序,其parse_options()
函数处理传递的命令行参数。以下是init.c的相关摘录
static char **
parse_options (char **argv)
{
for (; *argv != NULL && **argv == '-'; argv++)
{
char *save_ptr;
char *name = strtok_r (*argv, "=", &save_ptr); //fn to tokenise the string
char *value = strtok_r (NULL, "", &save_ptr);
if (!strcmp (name, "-h"))
usage ();
else if (!strcmp (name, "-q"))
power_off_when_done = true;
else if (!strcmp (name, "-r"))
reboot_when_done = true;
/*$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$*/
#ifdef FILESYS
else if (!strcmp (name, "-f"))
format_filesys = true;
#endif
/*$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$*/
else if (!strcmp (name, "-rs"))
random_init (atoi (value));
else if (!strcmp (name, "-mlfqs"))
thread_mlfqs = true;
#ifdef USERPROG
else if (!strcmp (name, "-ul"))
user_page_limit = atoi (value);
#endif
else
PANIC ("unknown option `%s' (use -h for help)", name);
}
return argv;
}
根据$$$$
部分中的代码,只有在定义了FILESYS时才会处理传递的-f
选项。
执行make
时,执行以下命令
gcc -m32 -c ../../threads/init.c -o threads/init.o -g -msoft-float -O -fno-stack- protector -nostdinc -I../.. -I../../lib -I../../lib/kernel -Wall -W -Wstrict-prototypes -Wmissing-prototypes -Wsystem-headers -DUSERPROG -DFILESYS -MMD -MF threads/init.d
这里,提供-DUSERPROG和-DFILESYS选项来定义FILESYS和USERPROG,以便可以执行代码的相关部分。但是,不知何故,FILESYS没有被定义,从pintos -f
命令的以下输出中可以看出
Kernel command line: -f
Kernel PANIC at ../../threads/init.c:261 in parse_options(): unknown option `-f' (use -h for help)
其他一些测试证实FILESYS未定义是问题所在。我检查了gcc语法,甚至编写了下面的Dummy程序,用gcc检查-DNAME选项。
DummyProg.c
#include "stdio.h"
int main()
{
#ifdef CHECK
printf("WORKING\n");
#endif
return 0;
}
使用gcc -DCHECK DummyProg.c
和./a.out
,屏幕上显示WORKING,符合语法等的有效性。我使用的gcc版本是 gcc(Ubuntu / Linaro 4.7.3-1ubuntu1 )4.7.3
请有人指出如何解决此问题。
答案 0 :(得分:1)
编译器可以帮助您理解这一点;诀窍是使用中留下的#define
语句捕获已处理的代码:
gcc -E -dD ...blah...
您必须从编译命令中删除-c
和-o <outfile>
选项,否则保持不变,除了添加两个新选项。
-E
告诉它仅执行预处理步骤,并将其输出到屏幕。
-dD
告诉它退出#define
和#undef
指令。
我的猜测是你的代码在某处有一个#undef FILESYS
指令,并且它覆盖了你的-DFILESYS
选项。
答案 1 :(得分:0)
要调试此类问题,请使用gcc
运行-E
。这将只通过预处理器cpp
运行代码。查看输出文件,看看在后处理步骤之后C编译器的输入是什么。
答案 2 :(得分:0)
您确定要构建整个可执行文件/库/...?
查看调用make
时触发的命令,只将一个文件编译成中间目标文件。没有链接到最终的二进制文件。
所以它猜你还在使用过时的版本。尝试前往顶级源目录并执行:
make clean && make