代码之家  ›  专栏  ›  技术社区  ›  Matt Ball

创建C/C++解析器/分析器的好工具[关闭]

  •  53
  • Matt Ball  · 技术社区  · 16 年前

    有哪些好的工具可以快速开始解析和分析C/C++代码?

    特别是,我正在寻找处理C/C++预处理器和语言的开源工具。这些工具最好使用lex/yacc(或flex/bison)作为语法,不要太复杂。他们应该处理最新的ANSI C/C++定义。

    以下是我迄今为止发现的,但还没有详细研究过(想法?):

    • CScope -老式的C分析器。不过,似乎没有进行完整的解析。被描述为查找C函数的荣耀的“grep”。
    • GCC -每个人最喜欢的开源编译器。很复杂,但似乎能解决所有问题。有一个相关的项目用于创建GCC扩展,名为 GEM ,但自GCC 4.1(2006)以来一直没有更新。
    • PUMA -PUre MAniulator。(摘自页面:“本项目的目的是 为C/C++源代码的分析和操作提供类库。为了这个 PUMA提供用于扫描、解析以及操作C/C的类++ 来源。)。这看起来很有希望,但自2001年以来就没有更新过。显然,PUMA已被纳入 AspectC++ ,但即使是这个项目自2006年以来也没有更新过。
    • 各种C/C++原始语法。你可以得到 c-c++-grammars-1.2.tar.gz ,但自1997年以来,它一直没有得到维护。在谷歌上搜索一下,就可以找到其他基本的lex/yacc语法作为起点。
    • 还有其他人吗?

    我希望以此为起点,将C/C++源代码翻译成一种新的玩具语言。

    谢谢! -马特

    (添加2/9):只是一个澄清:除了C/C++代码本身,我还想从预处理器中提取语义信息。我不想让“#define foo 42”消失在整数“42”中,而是继续附着在“foo”这个名字上。不幸的是,这排除了几个首先运行预处理器并且只提供C/C++解析树的解决方案)

    14 回复  |  直到 16 年前
        1
  •  34
  •   Adam Rosenfield    16 年前

    解析C++非常困难,因为语法是不可判定的。引用 Yossi Kreinin :

    极其复杂的语法

    “突出”应该从字面上解释,因为 所有流行语言 context-free (或“几乎”无上下文)语法,而C++有 undecidable 语法。如果你喜欢编译器和解析器,你可能知道这意味着什么。如果你不喜欢这种事情,有一个 simple example 显示了解析C++的问题: AA BB(CC); 对象定义还是函数声明?事实证明,答案在很大程度上取决于代码 之前 声明-“上下文”。这表明(在直观的层面上)C++语法对上下文非常敏感。

        2
  •  21
  •   epatel    10 年前

    你可以看看 clang 它使用llvm进行解析。

    现在完全支持C++ link

        3
  •  17
  •   Sean McCauliff    16 年前

    这个 ANTLR 解析器生成器具有 grammar 用于C/C++以及预处理器。我从未使用过它,所以我不能说它对C++的解析有多完整。ANTLR本身在解析更简单的语言方面对我来说是一个有用的工具。

        4
  •  16
  •   Łukasz Lew    16 年前

    根据您的问题 GCCXML 这可能是你的答案。 基本上,它使用GCC解析源代码,然后为您提供易于理解的XML解析树。 使用GCCXML,您将一劳永逸。

        5
  •  14
  •   Eli Bendersky    13 年前

    pycparser 是用Python编写的C(C99)的完整解析器。它有一个完全可配置的AST后端,因此它被用作您可能需要的任何语言处理的基础。

    不支持C++。当然,这是 比C更难。


    更新(2012) :毫无疑问,此时的答案是 Clang -它是模块化的,支持完整的C++(具有许多C++11特性),并且具有相对友好的代码库。它还有一个C API,用于绑定到高级语言(即。 for Python ).

        6
  •  8
  •   albert    6 年前

    看看如何 doxygen 工作正常,完整的源代码可用,并且基于flex。

    一个误导性的候选人是 GOLD 这是一个免费的基于Windows的解析器工具包,专门用于创建翻译器。他们的名单 支持的语言 指的是可以实现解析器的语言,而不是支持的解析语法列表。

    它们只有C和C#的语法,没有C++。

        7
  •  7
  •   none    16 年前

    Parsing C++ is a very complex challenge .

    有Boost/Spirit框架,几年前他们也有 play with the idea of implementing a C++ parser ,但它是 far from complete .

    完全正确地解析ISO C++绝非易事,事实上有许多相关的工作。但这是一项固有的复杂工作,如果不重写一个理解所有C语言的完整编译器前端,就不容易完成++ 预处理器。Spirit团队提供了一种名为“wave”的预处理器实现。

    也就是说,你可能想看看 pork/oink (基于elsa),这是一个专门用于源代码转换的C++解析器工具包,它正被Mozilla项目用于进行大规模的静态源代码分析和自动代码重写,最有趣的是它不仅支持大多数C++,还支持预处理器本身!

    另一方面,确实有一个专有的解决方案可用:EDG前端,它可以用于几乎所有与C++相关的工作。

    就我个人而言,我想看看Mozilla使用的基于elsa的pork/oink套件,除此之外,FSF现在已经批准了 gcc plugins 使用运行时库许可证,因此我认为,一旦人们可以使用二进制插件轻松地利用基于gcc的C++解析器来实现这些目的,事情就会迅速发生变化。

    所以,简而言之:如果你有钱:EDG,如果你需要一些免费/开源的东西 现在 :else/oink相当有前途,如果你有时间,你可能想在你的项目中使用gcc。

    C代码的另一种选择是 cscout .

        8
  •  6
  •   Charlie Martin    16 年前

    众所周知,C++的语法有点多毛。有 a good thread at Lambda about it, 但要点是C++语法可能需要任意多的前瞻性。

    对于我想象中你可能正在做的事情,我会考虑黑客攻击Gnu CC,或者 Splint Gnu CC确实非常彻底地分离了语言生成部分,所以你最好构建一个新的g++后端。

        9
  •  4
  •   Brett Rossier    15 年前

    实际上,PUMA和AspectJ仍然在积极维护和更新。我正在考虑使用AspectJ,并对自己缺乏更新感到疑惑。我给作者发了一封电子邮件,他说AspectJ和PUMA仍在开发中。您可以通过SVN获取源代码 https://svn.aspectc.org/repos/ 或者,您可以在以下网址获得常规二进制构建 http://akut.aspectc.org 与当今许多优秀的c++项目一样,作者没有时间跟上网页维护的步伐。如果你有全职工作和生活,这是有道理的。

        10
  •  4
  •   Ira Baxter    5 年前

    像这样更容易理解的东西怎么样 tiny-C Small C

        11
  •  3
  •   user52875    16 年前

    Elsa 它击败了我所知道的C++解析的其他一切,即使它不是100%兼容的。我是粉丝。有一个模块可以打印出C++,所以这可能是你的玩具项目的一个很好的起点。

        12
  •  2
  •   Scott Evernden    16 年前

    查看我们的 C++ Front End 对于一个功能齐全的C++解析器:构建AST、符号表、命名 以及类型分辨率。您甚至可以解析并保留预处理器 指令。C++前端构建在我们的 DMS Software Reengineering Toolkit ,这允许您使用该信息进行任意操作 使用源代码到源代码转换更改源代码。

    DMS是实现这种翻译器的理想引擎。

    话虽如此,我认为你想象的任务没有多大意义;我不 看到试图取代C++的巨大价值,你会发现构建 一个完整的翻译需要大量的工作,尤其是如果你 目标是一种“玩具”语言。而且,这可能没什么意义 如果C++的唯一目的是生成 C++的同构版本,更容易解析(等等,我们假设 一个强大的C++!).

    2012年5月编辑:DMS的C++前端现在处理GCC3/GCC4/C++11,微软VisualC 2005/2010。稳健。

    2015年2月编辑:现在处理GCC和MS方言的C++14。

    2015年8月编辑:现在解析并捕获统一树中的代码和预处理器指令。

    2020年5月编辑:在过去的几年里一直在做C++17。C++20正在开发中。

        13
  •  1
  •   Gerhard    16 年前

    不久前,我试图编写一个工具,为c文件自动生成单元测试。

    为了预压缩,我把文件放在GCC中。输出很难看,但您可以很容易地从预处理文件中跟踪原始代码的位置。但为了满足你的需求,你可能需要别的东西。

    使用 Metre 作为C解析器的基础。它是开源的,使用lex和yacc。这使得它很容易在短时间内启动和运行,而无需完全理解lex&yacc。

    自从lex&yacc解决方案无法帮助我跨函数跟踪功能,并在一次过程中解析整个函数的结构。它在短时间内变得无法维护,并被放弃了。

        14
  •  1
  •   t0mm13b    15 年前

    使用像GNU这样的工具怎么样 CFlow ,可以分析代码并生成调用图图表,以下是 opengroup (man page)不得不谈论cflow。cflow的GNU版本附带了源代码,也开源了。..

    希望这能有所帮助, 顺致敬意, 汤姆。

    推荐文章