如果这听起来有点愚蠢,我真的很抱歉。我刚刚读完 K&R,并做了一些练习。今年夏天,对于我的项目,我正在考虑重新实现一个 linux 实用程序以进一步扩展我对 C 的理解,因此我下载了 GNU tar 和 sed 的源代码,因为它们看起来都很有趣。但是,我无法理解它从哪里开始,主要实现在哪里,所有奇怪的宏来自哪里等等。
我有很多时间,所以这不是真正的问题。我是否应该先熟悉 GNU 工具链(即 make、binutils 等)才能理解这些程序?或者我应该从更小的东西开始(如果有的话)?
如果重要的话,我对 Java、C++ 和 Python 没有一点经验。
谢谢!
最佳答案
GNU 程序又大又复杂。 GNU Hello World的大小表明即使是最简单的 GNU 项目也需要围绕它进行大量代码和配置。
autotools 对于初学者来说很难理解,但是你不需要理解它们来阅读代码。即使您修改了代码,大多数时候您也可以简单地运行 make 来编译您的更改。
要阅读代码,您需要一个好的编辑器(VIM、Emacs)或 IDE (Eclipse) 和一些工具来浏览源代码。 tar 项目包含一个 src 目录,这是一个很好的起点。一个程序总是从 main 函数开始,也是如此
grep main *.c
或使用您的 IDE 搜索此功能。它在 tar.c 中。现在,跳过所有初始化的东西,直到
/* Main command execution. */
在那里,您会看到子命令的开关。如果你传递 -x 它会这样做,如果你传递 -c 它会那样做,等等。这是这些命令的分支结构。如果你想知道这些宏是什么,运行
grep EXTRACT_SUBCOMMAND *.h
在那里你可以看到它们在 common.h 中列出。
在 EXTRACT_SUBCOMMAND 下面你会看到一些有趣的东西:
read_and (extract_archive);
read_and() 的定义(再次使用 grep 获得):
read_and (void (*do_something) (void))
单个参数是一个类似于回调的函数指针,因此 read_and 应该会读取一些内容,然后调用函数 extract_archive
。再次,对其进行 grep,您将看到:
if (prepare_to_extract (current_stat_info.file_name, typeflag, &fun))
{
if (fun && (*fun) (current_stat_info.file_name, typeflag)
&& backup_option)
undo_last_backup ();
}
else
skip_member ();
请注意,真正的工作发生在调用 fun
时。 fun
也是一个函数指针,在 prepare_to_extract 中设置。 fun
可能指向 extract_file
,它执行实际的写入操作。
我希望我向您详细介绍了这一点,并向您展示了我如何浏览源代码。如果您有相关问题,请随时与我联系。
关于c - 如何理解 GNU 源代码?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3051091/