CppAst.NET icon indicating copy to clipboard operation
CppAst.NET copied to clipboard

Can`t parse attributes defined by macro

Open NarutoUA opened this issue 4 years ago • 2 comments

I try to parse DirectX headers and parser doesn't handle uuid attribute if it is defined by macro:

MIDL_INTERFACE("9d06dffa-d1e5-4d07-83a8-1bb123f2f841")
ID3D11Device2 : public ID3D11Device1

As a workaround, replacing MIDL_INTERFACE by regex works and parser returns correct attributes

struct __declspec(uuid("9d06dffa-d1e5-4d07-83a8-1bb123f2f841")) __declspec(novtable)
ID3D11Device2 : public ID3D11Device1

Both ParseAttributes and ParseMacros are set to true

You can reproduce it if you replace input text in TestStructAttributes and enable macros parsing.

@"
#ifndef DECLSPEC_NOVTABLE
#if (_MSC_VER >= 1100) && defined(__cplusplus)
#define DECLSPEC_NOVTABLE __declspec(novtable)
#else
#define DECLSPEC_NOVTABLE
#endif
#endif

#ifndef DECLSPEC_UUID
#if (_MSC_VER >= 1100) && defined(__cplusplus)
#define DECLSPEC_UUID(x) __declspec(uuid(x))
#else
#define DECLSPEC_UUID(x)
#endif
#endif

#define MIDL_INTERFACE(x)   struct DECLSPEC_UUID(x) DECLSPEC_NOVTABLE

MIDL_INTERFACE(""9d06dffa-d1e5-4d07-83a8-1bb123f2f841"") Test{
    int a;
    int b;
};"

NarutoUA avatar Sep 02 '21 00:09 NarutoUA

Yes, unfortunately, I'm not sure if we have any workaround for this. The problem is that libclamg-C does not parse or give access to these attributes correctly, so we need to parse them ourselves... but then we parse from the original source, not the postprocessed sources, hence why attribute parsing doesn't work when using macros.

xoofx avatar Sep 26 '21 09:09 xoofx

This issue is causing us issues as well. I was wondering if during VisitMember(), when the CursorKind is CXCursorKind.CXCurser_MacroExpansion if we could expand the macro and create the elements that the macro expands into. That would expose the attributes or anything else in the macro at the point where it's supposed to be expanded. I've been looking at the code to see if doing something like this is possible. Another more specific option would be in ParseAttributes() where in addition to the check for a keyword, check if the token is a macro and if it is parse that macro. For our specific case we don't need a full macro parser, just a single expansion to get the macros content which will always be the [[attribute]] type.

ninloot avatar Apr 19 '22 22:04 ninloot