2013-10-29 44 views
7

广义属性我想在下面的例子来解析的类的成员函数广义属性:检查与libclang

class Foo 
{ 
public: 
    void foo [[interesting]](); 
    void bar(); 
}; 

使用libclang C API,我想foobar区分(和知道foo在源中具有interesting属性)。这可能吗?我很难找到解释在API中使用的概念的示例或文档(我找到了一个参考,但是当这些概念没有解释时,这很难使用)。如果存在

回答

1

虽然我无法找到AST中的广义属性(看起来在构建AST时或之前它们被删除,而不是在它之后),但我确实找到了解决方法。

有以下形式的annotate铛属性:

__attribute__((annotate("something"))) 

随着宏,我能得到一个合理的语法和注释这是在AST可见:

#define INTERESTING __attribute__((annotate("interesting"))) 

class Foo 
{ 
public: 
    INTERESTING void foo(); 
    void bar(); 
}; 

属性将是方法节点的子节点,其display_name是注释字符串。可能的AST转储:

<CursorKind.TRANSLATION_UNIT> 
    "test.h" 
{ 
    __builtin_va_list <CursorKind.TYPEDEF_DECL> 
    "__builtin_va_list" 
    type_info <CursorKind.CLASS_DECL> 
    "type_info" 
    Foo <CursorKind.CLASS_DECL> 
    "Foo" 
    { 
    <CursorKind.CXX_ACCESS_SPEC_DECL> 
     "" 
    foo <CursorKind.CXX_METHOD> 
     "foo()" 
    { 
     <CursorKind.ANNOTATE_ATTR> 
     "interesting" 
    } 
    bar <CursorKind.CXX_METHOD> 
     "bar()" 
    } 
} 

它也会产生与void foo INTERESTING();相同的输出。

2

像下面first_attr功能将取传递光标的第一属性的光标,或一个空指针,如果它不(未经测试的代码......需要注意的讲师)

CXChildVisitResult attr_visit(CXCursor cursor, CXCursor parent, CXClientData data) { 
    if (clang_isAttribute(cursor)) { 
     *data = cursor; 
     return CXChildVisit_Break; 
    } 
    return CXChildVisit_Continue; 
} 

CXCursor first_attr(const CXCursor& c) { 
    CXCursor attr; 
    unsigned visit_result = clang_visitChildren(c, attr_visit, &attr); 
    if (!visit_result) // attribute not found 
     attr = clang_getNullCursor(); 
    return attr; 
} 

作为认定其具体属性光标a代表的clang_getCursorKind(a)结果可以帮助,但暴露了唯一的属性是:

CXCursor_IBActionAttr 
CXCursor_IBOutletAttr 
CXCursor_IBOutletCollectionAttr 
CXCursor_CXXFinalAttr 
CXCursor_CXXOverrideAttr 
CXCursor_AnnotateAttr 
CXCursor_AsmLabelAttr 

一切将是一个CXCursor_UnexposedAttr的d我能想到的唯一方法就是查看clang_getCursorExtent(a)(即读取源代码;比照clang_tokenize)。在注释的情况下,所使用的特定注释可通过clang_getCursorDisplayName获得。

+0

我试图用python绑定来创建代码原型,但该属性在AST中根本不可见(甚至不是未暴露的属性)。当我添加它时,'noreturn'属性确实出现在我的AST转储中。 –