Adding support for {Class, ...}TemplateDeclSpecialization to libClang

classic Classic list List threaded Threaded
1 message Options
Reply | Threaded
Open this post in threaded view

Adding support for {Class, ...}TemplateDeclSpecialization to libClang

James Gregurich via cfe-dev
Hello all,

libclang does currently not allow retrieving information about implicit
nor explicit template instantiations. A visitor function passed to
clang_visitChildren() will be called for the template definition itself,
but not for any template instantiation.

This is a problem when one needs information that requires a knowledge
of the actual template parameters, for example the MemberRef access
"foo.x" in boop() has an empty spelling and no useful definition cursor set

template <class T> struct Foo { T x; };

template <class T> struct Bar { Foo<T> foo; void boop() { auto x =
foo.x; } };

int main() { Bar<int> b; b.boop(); }

The code seems to already have some code considering
ClassTemplateSpecializations, namely in libclang/CIndex.cpp, there's a
bool CursorVisitor::VisitClassTemplateSpecializationDecl() method.
However, it never gets called, which I've verified by placing a debug
std::cout in there.

I propose to add code to visit the explicit and implicit
specialisations, adding an appropriate CursorType and possibly a
function to query whether the Cursor is an implicit or an explicit
template specialisation. This would happen in analogy to clang++'s
-dump-ast option, putting the specialisations as children below the
ClassTemplateDecl as parent.

I've attached a (very dirty) patch as proof of concept: In
CursorVisitor::VisitClassTemplateDecl(), it iterates over all
specialisations and calls VisitClassTemplateSpecializationDecl() on them.

This is not beautiful yet, because it still won't expose any "Template
Specialisation" Cursor to the application, but at least all of its
children. Also, function and variable templates might require the same

Given that the actual Specialisation was visited (and the children only
when the visitor function returned CXChildVisit_Recurse), would such a
change be merged into upstream libclang? I would really need such a
feature, and it seems like a similar request has already been made [1].

What do I need to watch out for when implementing this, to not break any
software which uses libclang? (Ideally, it should just return
CXChildVisit_Continue on the newly added cursors, so it won't notice much)

And what's the purpose of the existing
VisitClassTemplateSpecializationDecl() method in its current state?

Kind regards,


[1] "[cfe-dev] Will libclang ever be able to step through classes
defined by template instantiations?", Wed Dec 6 08:35:49 PST 2017

cfe-dev mailing list
[hidden email]

proof_of_concept.patch (1K) Download Attachment
smime.p7s (7K) Download Attachment