[prev in list] [next in list] [prev in thread] [next in thread] 

List:       cfe-dev
Subject:    Re: [cfe-dev] Iterating over AST node objects
From:       David Rector via cfe-dev <cfe-dev () lists ! llvm ! org>
Date:       2020-10-31 0:30:03
Message-ID: 0053604C-4EEE-449B-912E-97AFF84901A3 () gmail ! com
[Download RAW message or body]

[Attachment #2 (multipart/alternative)]


Yes those lines represent nodes.  You do not necessarily need ASTContext to look at a \
node's descendants: you can just use the node's methods.  

Were these sugar (= syntax-only) type nodes, you could iterate over the child of each \
successive node via `desugar()`, and successively desugar while searching for a Type \
subclass T via `getAs<T>()`.  

But pointee types/array element types are of course not sugar: they are distinct \
semantic entities, so desugar/getAs won't will not pass through them.  Hence your \
problem.

Fortunately there seems to be a `getPointeeOrArrayElementType()` to help peel off the \
semantic layers you want to look through, analogous to `desugar()` — but \
unfortunately there is not a `getAs` analog for this case, so you have to write the \
search manually.  

Something like this should work (not tested):

```
PointerType *getInnermostPointerType(const Type *T) {
  const PointerType *res = nullptr;

  while (true) {
    const Type *pointeeOrElement = T->getPointeeOrArrayElementType();
    if (pointeeOrElement == T)
      // T is neither a pointer nor array type: we're done.
      break;

    // T is a pointer or array type.
    if (isa<PointerType>(T)) 
      res = cast<PointerType>(T);
   
    // iterate T, keep looking
    T = pointeeOrElement;
  }
  return res;
}
```

> On Oct 30, 2020, at 2:12 PM, Pratyush Das via cfe-dev <cfe-dev@lists.llvm.org> \
> wrote: 
> Hi,
> 
> If I dump() a clang::Type object, I can see this AST representation - 
> 
> ConstantArrayType 0x555562830ea0 'const char **const [0]' 0 
> `-QualType 0x555562830c81 'const char **const' const
> `-PointerType 0x555562830c80 'const char **'
> `-PointerType 0x5555627ed2a0 'const char *'
> `-QualType 0x5555627ec7d1 'const char' const
> `-BuiltinType 0x5555627ec7d0 'char'
> 
> Is there a way to use the ASTContext to iterate over each node? (Do each of those \
> lines represent a node?) 
> My motivation is to get the inner most PointerType object.
> 
> Regards,
> 
> -- 
> Pratyush Das
> _______________________________________________
> cfe-dev mailing list
> cfe-dev@lists.llvm.org
> https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-dev


[Attachment #5 (unknown)]

<html><head><meta http-equiv="Content-Type" content="text/html; \
charset=utf-8"></head><body style="word-wrap: break-word; -webkit-nbsp-mode: space; \
line-break: after-white-space;" class=""><div style="margin: 0px; font-stretch: \
normal; line-height: normal;" class="">Yes those lines represent nodes. &nbsp;You do \
not necessarily need ASTContext to look at a node's descendants: you can just use the \
node's methods. &nbsp;</div><div style="margin: 0px; font-stretch: normal; \
line-height: normal;" class=""><br class=""></div><div style="margin: 0px; \
font-stretch: normal; line-height: normal;" class="">Were these sugar (= syntax-only) \
type nodes, you could iterate over the child of each successive node via `desugar()`, \
and successively desugar while searching for a Type subclass T via \
`getAs&lt;T&gt;()`. &nbsp;</div><div style="margin: 0px; font-stretch: normal; \
line-height: normal;" class=""><br class=""></div><div style="margin: 0px; \
font-stretch: normal; line-height: normal;" class="">But pointee types/array element \
types are of course not sugar: they are distinct semantic entities,&nbsp;so \
desugar/getAs won't will not pass through them.&nbsp; Hence your problem.</div><div \
style="margin: 0px; font-stretch: normal; line-height: normal; min-height: 14px;" \
class=""><br class=""></div><div style="margin: 0px; font-stretch: normal; \
line-height: normal;" class="">Fortunately there seems to be a \
`getPointeeOrArrayElementType()` to help peel off the semantic layers you want to \
look through, analogous to `desugar()` — but unfortunately there is not a `getAs` \
analog for this case, so you have to write the search manually. &nbsp;</div><div \
style="margin: 0px; font-stretch: normal; line-height: normal; min-height: 14px;" \
class=""><br class=""></div><div style="margin: 0px; font-stretch: normal; \
line-height: normal;" class="">Something like this should work (not \
tested):</div><div style="margin: 0px; font-stretch: normal; line-height: normal; \
min-height: 14px;" class=""><br class=""></div><div style="margin: 0px; font-stretch: \
normal; line-height: normal;" class="">```</div><div style="margin: 0px; \
font-stretch: normal; line-height: normal; font-family: Menlo;" class="">PointerType \
*getInnermostPointerType(const Type *T) {</div><div style="margin: 0px; font-stretch: \
normal; line-height: normal; font-family: Menlo;" class="">&nbsp; const PointerType \
*res = nullptr;</div><div style="margin: 0px; font-stretch: normal; line-height: \
normal; font-family: Menlo; min-height: 14px;" class=""><br class=""></div><div \
style="margin: 0px; font-stretch: normal; line-height: normal; font-family: Menlo;" \
class="">&nbsp; while (true) {</div><div style="margin: 0px; font-stretch: normal; \
line-height: normal; font-family: Menlo;" class="">&nbsp; &nbsp; const Type \
*pointeeOrElement = T-&gt;getPointeeOrArrayElementType();</div><div style="margin: \
0px; font-stretch: normal; line-height: normal; font-family: Menlo;" class="">&nbsp; \
&nbsp; if (pointeeOrElement == T)</div><div style="margin: 0px; font-stretch: normal; \
line-height: normal; font-family: Menlo;" class="">&nbsp; &nbsp; &nbsp; // T is \
neither a pointer nor array type: we're done.</div><div style="margin: 0px; \
font-stretch: normal; line-height: normal; font-family: Menlo;" class="">&nbsp; \
&nbsp; &nbsp; break;</div><div style="margin: 0px; font-stretch: normal; line-height: \
normal; font-family: Menlo; min-height: 14px;" class=""><br class=""></div><div \
style="margin: 0px; font-stretch: normal; line-height: normal; font-family: Menlo;" \
class="">&nbsp; &nbsp; // T is a pointer or array type.</div><div style="margin: 0px; \
font-stretch: normal; line-height: normal; font-family: Menlo;" class="">&nbsp; \
&nbsp; if (isa&lt;PointerType&gt;(T))&nbsp;</div><div style="margin: 0px; \
font-stretch: normal; line-height: normal; font-family: Menlo;" class="">&nbsp; \
&nbsp; &nbsp; res = cast&lt;PointerType&gt;(T);</div><p style="margin: 0px; \
font-stretch: normal; line-height: normal; font-family: Menlo; min-height: 14px;" \
class="">&nbsp; &nbsp;<br class="webkit-block-placeholder"></p><div style="margin: \
0px; font-stretch: normal; line-height: normal; font-family: Menlo;" class="">&nbsp; \
&nbsp; // iterate T, keep looking</div><div style="margin: 0px; font-stretch: normal; \
line-height: normal; font-family: Menlo;" class="">&nbsp; &nbsp; T = \
pointeeOrElement;</div><div style="margin: 0px; font-stretch: normal; line-height: \
normal; font-family: Menlo;" class="">&nbsp; }</div><div style="margin: 0px; \
font-stretch: normal; line-height: normal; font-family: Menlo;" class="">&nbsp; \
return res;</div><div style="margin: 0px; font-stretch: normal; line-height: normal; \
font-family: Menlo;" class="">}</div><div style="margin: 0px; font-stretch: normal; \
line-height: normal;" class="">```</div><div><br class=""><blockquote type="cite" \
class=""><div class="">On Oct 30, 2020, at 2:12 PM, Pratyush Das via cfe-dev &lt;<a \
href="mailto:cfe-dev@lists.llvm.org" class="">cfe-dev@lists.llvm.org</a>&gt; \
wrote:</div><br class="Apple-interchange-newline"><div class=""><div dir="ltr" \
class="">Hi,<div class=""><br class=""></div><div class="">If I dump() a clang::Type \
object, I can see this AST representation -&nbsp;</div><div class=""><br \
class=""></div><div class=""><font face="monospace" class="">ConstantArrayType \
0x555562830ea0 'const char **const [0]' 0 <br class="">`-QualType 0x555562830c81 \
'const char **const' const<br class="">&nbsp; `-PointerType 0x555562830c80 'const \
char **'<br class="">&nbsp; &nbsp; `-PointerType 0x5555627ed2a0 'const char *'<br \
class="">&nbsp; &nbsp; &nbsp; `-QualType 0x5555627ec7d1 'const char' const<br \
class="">&nbsp; &nbsp; &nbsp; &nbsp; `-BuiltinType 0x5555627ec7d0 \
'char'</font></div><div class=""><br class=""></div><div class=""><div class="">Is \
there a way to use the ASTContext to iterate over each node? (Do each of those lines \
represent a node?)</div><div class=""><br class=""></div><div class="">My motivation \
is to get the inner most&nbsp;PointerType object.</div><div class=""><br \
class=""></div><div class="">Regards,</div><div class=""><div class=""><br \
class=""></div>-- <br class=""><div dir="ltr" class="gmail_signature" \
data-smartmail="gmail_signature"><div dir="ltr" class=""><div class=""><div dir="ltr" \
class=""><div class="">Pratyush Das<br \
class=""></div></div></div></div></div></div></div></div> \
_______________________________________________<br class="">cfe-dev mailing list<br \
class=""><a href="mailto:cfe-dev@lists.llvm.org" \
class="">cfe-dev@lists.llvm.org</a><br \
class="">https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-dev<br \
class=""></div></blockquote></div><br class=""></body></html>


[Attachment #6 (text/plain)]

_______________________________________________
cfe-dev mailing list
cfe-dev@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-dev


[prev in list] [next in list] [prev in thread] [next in thread] 

Configure | About | News | Add a list | Sponsored by KoreLogic