[cfe-dev] Matching Type to template

Richard Trieu via cfe-dev cfe-dev at lists.llvm.org
Fri Mar 18 22:10:00 PDT 2016


On Wed, Mar 16, 2016 at 2:07 PM, Daniel Dilts via cfe-dev <
cfe-dev at lists.llvm.org> wrote:

> I have a type that I have gotten with this expression:
> callExpr->getArg(i)->IgnoreImplicit()->getType()
>
> I am matching it against a set of types that I want to process.  Currently
> I am doing a string compare with the result of getAsString() and the
> desired type.  This works for trivial types (int, float, etc.) but it
> doesn't scale to more complex types.
>
Using getAsString() isn't the best way to determine types are the same.
ASTContext has all the things you need to do this.  Instead of doing:

  QualType Ty = callExpr->getArg(i)->IgnoreImplicit()->getType();
  if (Ty.getAsString() == "int") {...}

Use the type comparison function and the saved types by:

  if (Context.hasSameType(Ty, Context.IntTy) {...}


> How would I test to see if the type is an instantiation of std::vector,
> and find the element type of the vector?
>
This requires a bit more work and you'll need to traverse the many classes
of Type.   The specific Type is TemplateSpecializationType.

  QualType Ty = callExpr->getArg(i)->IgnoreImplicit()->getType();
  const TemplateSpecializationType *TST =
Ty->getAs<TemplateSpecializationType>();
  if (!TST) return;

Make sure you are dealing with a template specialization.

  TemplatedDecl *TD = TST->getTemplateName().getAsTemplateDecl();
  if (!TD) return;

The TemplateDecl stores information about the template being specialized,
from it, you can check:

  if (!TD->getIdentifier()->isStr("vector")) return;
  if (!TD->isInStdNamespace()) return;

isStr() is a specialized function to check if the identifier matches a
string literal.
isInStdNamespace() checks the namespace, looking through inline namespaces.

  if (TST->getNumArgs < 1) return;

Checks that specialization of vector has at least on template argument.
Use "< 1" instead of "!= 1" because std::vector is usually defined with
additional template arguments beyond the first one, but are mostly
defaulted away so users don't see them.

  const TemplateArgument &TA = TST->getArg(0);

Get the first template argument.

  if (TA.getKind() != TemplateArgument::Type) return;

Make sure the template argument is a type.

  QualType ElementType = TA.getAsType();

Retrieve the type from the template argument, which for std::vector is the
element type.

>
> _______________________________________________
> cfe-dev mailing list
> cfe-dev at lists.llvm.org
> http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-dev
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/cfe-dev/attachments/20160318/6070264b/attachment.html>


More information about the cfe-dev mailing list