如何在Python中获取C文件的变量名列表

1 投票
2 回答
2366 浏览
提问于 2025-04-17 15:06

我有一个C语言的文件,想用Python来创建一个所有定义的变量名的列表。

比如,从下面这个C语言文件:

int mynum = 12;

// Timers
VAR_IN_SECTION(task_timers, .mem_layout)
timers_t timers[DSP_NUM_TASK_TIMERS];

我希望能用一些Python的“魔法”来返回:

["mynum", "timers"]

这该怎么做呢?希望这个方法不局限于良好的C语言格式。用什么样的Python“魔法”可以实现呢?

注意:这个是用来解析一个只包含变量声明的文件。

2 个回答

1

这个在你给的示例输入文件上是有效的,但我敢肯定,在我说它能在C语言的语法上普遍适用之前,我需要进行很多更多的测试。

>>> s = """int mynum = 12;
... 
... // Timers
... VAR_IN_SECTION(task_timers, .mem_layout)
... timers_t timers[DSP_NUM_TASK_TIMERS];"""
>>>
>>> import re
>>> re.findall(r'\w+[ \t]+(\w+)',s)
['mynum', 'timers']

上面提到的答案不能识别指针:

int *p;

为了能识别指针,可能需要稍微调整一下正则表达式:

>>> re.findall(r'\w+[ \t]+(?:\*\s*)?(\w+)',s)
['mynum', 'timers', 'p']

在C语言中,你不能只查找各种类型(比如intfloatdoublechar等),因为这些类型可以被重新定义(typedef),而且你还有struct(和union?)这样的结构,它们的工作方式也类似……更不用说在任何时候,你都可以用#include "anyfile.c"来包含其他文件——作为程序员,这样做可能会很麻烦,但确实是可能的。我认为在c99标准中,你还可以在任何地方声明变量(例如,在宏中)。你想要识别这些吗?换句话说,要正确处理这个问题,你需要一个完整的C语言解析器来帮你完成这些复杂的工作。

2

你可以使用GCC-XML这个工具,把C语言源文件中的声明转换成XML格式。然后,你可以用Python的XML解析器(比如lxml.etree)来处理这些结果。

GCC-XML生成的XML结构比较简单,容易解析。它会给你提供变量声明(标签:<Variable>)和类型定义(有多个标签,比如<FundamentalType><Pointer><Struct>等等)。你需要做一些处理,递归地推导出实际的类型(例如,Pointer指向一个子类型,也就是它所指向的类型),但如果你愿意花点时间去研究,它会提供你所需的一切。

如果你只想要变量名,可以解析XML,找到Variable标签,然后提取它的name属性。

有趣的是,我正在一个项目中构建这样一个解析器。虽然我现在还不能分享,但我希望最终能开源发布。

示例:

typedef int* myintptr;

myintptr p;   

生成的XML大概是这样的:

<Variable id="_3" name="p" type="_64" context="_1" location="f0:5" file="f0" line="5"/>
<Typedef id="_64" name="myintptr" type="_63" context="_1" location="f0:3" file="f0" line="3"/>
<PointerType id="_63" type="_156" size="64" align="64"/>
<FundamentalType id="_156" name="int" size="32" align="32"/>

撰写回答