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

List:       cfe-dev
Subject:    Re: [cfe-dev] API for auto type deduction in libclang
From:       Richard Smith <metafoo () gmail ! com>
Date:       2014-01-28 21:00:44
Message-ID: -3104018005426075068 () gmail297201516
[Download RAW message or body]

[Attachment #2 (multipart/alternative)]


On Tue Jan 28 2014 at 3:43:30 AM, Kevin Funk <krf@gmx.de> wrote:

> Am Sonntag, 26. Januar 2014, 13:00:24 schrieb Jacob Carlborg:
> > On 2014-01-25 22:03, Kevin Funk wrote:
> > > That doesn't work for me.
> > >
> > > For testing we have a small wrapper binary that basically creates a
> > > CXTranslationUnit and then traverses through the AST via
> > > clang_visitChildren().
> > >
> > > During the call to 'visit' it does the following (amongst other
> things):
> > > - auto location = clang_getCursorLocation(cursor)
> > > - auto type = clang_getCursorType(cursor)
> > > - auto typeString = clang_getTypeSpelling(type)
> > > - now: auto canonicalTypeString =
> > >
> > >      clang_getTypeSpelling(clang_getCanonicalType(type))
> > >
> > > It outputs all the values of those variabes to stdout, and when I pass
> > > "auto i = 5;" to it I get:
> > >
> > > """
> > > decl: "auto (canonical type: auto) i " of kind VarDecl (9) in
> > > stdin.cpp@1:6
> > >
> > >    "int (canonical type: int) " of kind IntegerLiteral (106) in
> > >    stdin.cpp@1:10
> > >
> > > """
> > >
> > > So the 'canonical type' of VarDecl still resolves to 'auto', instead of
> > > 'int'. Sorry, if we're doing something completely wrong, but I don't
> seem
> > > to get this working as you suggest.
> >
> > Ok, I see, you're using clang_getTypeSpelling. I created my tool before
> > clang_getTypeSpelling was available. For aggregates, typedefs and a
> > couple of other types I'm using the following code[1]:
> >
> > auto cursor = clang_getTypeDeclaration(type);
> > auto str = clang_getCursorSpelling(cursor);
> >
> > For basic types like "int", "char" and so on, the above will return an
> > empty string. For those types I use a big switch statement on the type
> > kind and just returns a string representation [2].
> >
> > [1]
> > https://github.com/jacob-carlborg/dstep/blob/master/
> dstep/translator/Type.d#
> > L43
> >
> > [2]
> > https://github.com/jacob-carlborg/dstep/blob/master/
> dstep/translator/Type.d#
> > L248
>
> Unfortunately, your source code doesn't help me, nor can I get it to work
> using any combination of getTypeDeclaration, getCursorSpelling, and the
> ones I
> referred to earlier...
>
> I wonder if there's some bug in Clang's type printers I'm experiencing
> here.
>
> Let's do some testing:
> Test file: test.cpp, containing 'auto i = 5;'
>
> $ clang -cc1 -std=c++11 -ast-dump test.cpp
> (...)
> `-VarDecl 0x1c2e5b0 <test.cpp:1:1, col:10> i 'int':'int'
>   `-IntegerLiteral 0x1c2e608 <col:10> 'int' 5
>
> => What I'd expect! ('auto' => 'int')
>
> Next try: My clang-standalone-parser (basically emulating 'clang -cc1
> -dump')
> but using libclang only [1]:
>
> $ ./clang-standalone-parser -std=c++11 test.cpp
> test.cpp:1:6 (5, 0-10) kind: VarDecl type: auto display name: i (...)
>   test.cpp:1:10 (9, 9-10) kind: IntegerLiteral type: int
>
> => Not what I'd expect, 'auto' is not deduced
>
> And the odd part here is: Breaking on the symbol
> 'clang::AutoType::getDeducedType()' for both clang and
> clang-standalone-parser
> shows that *both* versions actually call that function when trying to find
> a
> string representation for the type 'auto'. But with
> clang-standalone-parser,
> 'clang::AutoType::getDeducedType()' always returns an null QualType.
>
> Can someone make any sense out of this? Bug in Clang/LLVM? Note that the
> backtrace towards the call of getDeducedType is slightly different for the
> two
> versions (see attached file). Maybe this is the reason?
>

I would expect that clang's dumper is using VarDecl->getType() and your
standalone tool is using VarDecl->getTypeSourceInfo(). The former produces
the type of the variable (which is 'int'); the latter produces the
type-as-written (which is 'auto').

FWIW, we've been considering changing this for variables, but even if we
did, the problem would persist for functions with 'auto' return types.


> Any help greatly appreciated!
>
> Greets
>
> [1] http://quickgit.kde.org/?p=kdev-clang.git&a=blob&h=
> dbad9e8942cc5e20fd005677fc32a5a0b54977ae&hb=1fa9eca7a9a58404c3ef687fcfa638
> 00d459cff5&f=tests%2Fclang-standalone-parser.c
>
> Compiling is simple:
> $ clang clang-standalone-parser.c -I/path/to/llvm/include
> -L/path/to/llvm/lib
> -lclang -Wl,-rpath,'/path/to/llvm/lib' -o clang-standalone-parser
>
> --
> Kevin Funk_______________________________________________
> cfe-dev mailing list
> cfe-dev@cs.uiuc.edu
> http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev
>

[Attachment #5 (text/html)]

<div>On Tue Jan 28 2014 at 3:43:30 AM, Kevin Funk &lt;<a \
href="mailto:krf@gmx.de">krf@gmx.de</a>&gt; wrote:</div><blockquote \
class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc \
solid;padding-left:1ex">Am Sonntag, 26. Januar 2014, 13:00:24 schrieb Jacob \
Carlborg:<br>

&gt; On 2014-01-25 22:03, Kevin Funk wrote:<br>
&gt; &gt; That doesn&#39;t work for me.<br>
&gt; &gt;<br>
&gt; &gt; For testing we have a small wrapper binary that basically creates \
a<br> &gt; &gt; CXTranslationUnit and then traverses through the AST \
via<br> &gt; &gt; clang_visitChildren().<br>
&gt; &gt;<br>
&gt; &gt; During the call to &#39;visit&#39; it does the following (amongst \
other things):<br> &gt; &gt; - auto location = \
clang_getCursorLocation(<u></u>cursor)<br> &gt; &gt; - auto type = \
clang_getCursorType(cursor)<br> &gt; &gt; - auto typeString = \
clang_getTypeSpelling(type)<br> &gt; &gt; - now: auto canonicalTypeString \
=<br> &gt; &gt;<br>
&gt; &gt;      clang_getTypeSpelling(clang_<u></u>getCanonicalType(type))<br>
 &gt; &gt;<br>
&gt; &gt; It outputs all the values of those variabes to stdout, and when I \
pass<br> &gt; &gt; &quot;auto i = 5;&quot; to it I get:<br>
&gt; &gt;<br>
&gt; &gt; &quot;&quot;&quot;<br>
&gt; &gt; decl: &quot;auto (canonical type: auto) i &quot; of kind VarDecl \
(9) in<br> &gt; &gt; stdin.cpp@1:6<br>
&gt; &gt;<br>
&gt; &gt;    &quot;int (canonical type: int) &quot; of kind IntegerLiteral \
(106) in<br> &gt; &gt;    stdin.cpp@1:10<br>
&gt; &gt;<br>
&gt; &gt; &quot;&quot;&quot;<br>
&gt; &gt;<br>
&gt; &gt; So the &#39;canonical type&#39; of VarDecl still resolves to \
&#39;auto&#39;, instead of<br> &gt; &gt; &#39;int&#39;. Sorry, if we&#39;re \
doing something completely wrong, but I don&#39;t seem<br> &gt; &gt; to get \
this working as you suggest.<br> &gt;<br>
&gt; Ok, I see, you&#39;re using clang_getTypeSpelling. I created my tool \
before<br> &gt; clang_getTypeSpelling was available. For aggregates, \
typedefs and a<br> &gt; couple of other types I&#39;m using the following \
code[1]:<br> &gt;<br>
&gt; auto cursor = clang_getTypeDeclaration(type)<u></u>;<br>
&gt; auto str = clang_getCursorSpelling(<u></u>cursor);<br>
&gt;<br>
&gt; For basic types like &quot;int&quot;, &quot;char&quot; and so on, the \
above will return an<br> &gt; empty string. For those types I use a big \
switch statement on the type<br> &gt; kind and just returns a string \
representation [2].<br> &gt;<br>
&gt; [1]<br>
&gt; <a href="https://github.com/jacob-carlborg/dstep/blob/master/dstep/translator/Type.d#" \
target="_blank">https://github.com/jacob-<u></u>carlborg/dstep/blob/master/<u></u>dstep/translator/Type.d#</a><br>
 &gt; L43<br>
&gt;<br>
&gt; [2]<br>
&gt; <a href="https://github.com/jacob-carlborg/dstep/blob/master/dstep/translator/Type.d#" \
target="_blank">https://github.com/jacob-<u></u>carlborg/dstep/blob/master/<u></u>dstep/translator/Type.d#</a><br>
 &gt; L248<br>
<br>
Unfortunately, your source code doesn&#39;t help me, nor can I get it to \
work<br> using any combination of getTypeDeclaration, getCursorSpelling, \
and the ones I<br> referred to earlier...<br>
<br>
I wonder if there&#39;s some bug in Clang&#39;s type printers I&#39;m \
experiencing here.<br> <br>
Let&#39;s do some testing:<br>
Test file: test.cpp, containing &#39;auto i = 5;&#39;<br>
<br>
$ clang -cc1 -std=c++11 -ast-dump test.cpp<br>
(...)<br>
`-VarDecl 0x1c2e5b0 &lt;test.cpp:1:1, col:10&gt; i \
&#39;int&#39;:&#39;int&#39;<br>  `-IntegerLiteral 0x1c2e608 &lt;col:10&gt; \
&#39;int&#39; 5<br> <br>
=&gt; What I&#39;d expect! (&#39;auto&#39; =&gt; &#39;int&#39;)<br>
<br>
Next try: My clang-standalone-parser (basically emulating &#39;clang -cc1 \
-dump&#39;)<br> but using libclang only [1]:<br>
<br>
$ ./clang-standalone-parser -std=c++11 test.cpp<br>
test.cpp:1:6 (5, 0-10) kind: VarDecl type: auto display name: i (...)<br>
  test.cpp:1:10 (9, 9-10) kind: IntegerLiteral type: int<br>
<br>
=&gt; Not what I&#39;d expect, &#39;auto&#39; is not deduced<br>
<br>
And the odd part here is: Breaking on the symbol<br>
&#39;clang::AutoType::<u></u>getDeducedType()&#39; for both clang and \
clang-standalone-parser<br> shows that *both* versions actually call that \
function when trying to find a<br> string representation for the type \
&#39;auto&#39;. But with clang-standalone-parser,<br> \
&#39;clang::AutoType::<u></u>getDeducedType()&#39; always returns an null \
QualType.<br> <br>
Can someone make any sense out of this? Bug in Clang/LLVM? Note that \
the<br> backtrace towards the call of getDeducedType is slightly different \
for the two<br> versions (see attached file). Maybe this is the \
reason?<br></blockquote><div><br></div><div>I would expect that clang&#39;s \
dumper is using VarDecl-&gt;getType() and your standalone tool is using \
VarDecl-&gt;getTypeSourceInfo(). The former produces the type of the \
variable (which is &#39;int&#39;); the latter produces the type-as-written \
(which is &#39;auto&#39;).</div> <div><br></div><div>FWIW, we&#39;ve been \
considering changing this for variables, but even if we did, the problem \
would persist for functions with &#39;auto&#39; return types.</div><div> \
</div><blockquote class="gmail_quote" style="margin:0 0 0 \
.8ex;border-left:1px #ccc solid;padding-left:1ex">

Any help greatly appreciated!<br>
<br>
Greets<br>
<br>
[1] <a href="http://quickgit.kde.org/?p=kdev-clang.git&amp;a=blob&amp;h=dbad \
9e8942cc5e20fd005677fc32a5a0b54977ae&amp;hb=1fa9eca7a9a58404c3ef687fcfa63800d459cff5&amp;f=tests%2Fclang-standalone-parser.c" \
target="_blank">http://quickgit.kde.org/?p=<u></u>kdev-clang.git&amp;a=blob& \
amp;h=<u></u>dbad9e8942cc5e20fd005677fc32a5<u></u>a0b54977ae&amp;hb=<u></u>1 \
fa9eca7a9a58404c3ef687fcfa638<u></u>00d459cff5&amp;f=tests%2Fclang-<u></u>standalone-parser.c</a><br>


<br>
Compiling is simple:<br>
$ clang clang-standalone-parser.c -I/path/to/llvm/include \
                -L/path/to/llvm/lib<br>
-lclang -Wl,-rpath,&#39;/path/to/llvm/lib&#39; -o \
clang-standalone-parser<br> <br>
--<br>
Kevin Funk__________________________<u></u>_____________________<br>
cfe-dev mailing list<br>
<a href="mailto:cfe-dev@cs.uiuc.edu" \
target="_blank">cfe-dev@cs.uiuc.edu</a><br> <a \
href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev" \
target="_blank">http://lists.cs.uiuc.edu/<u></u>mailman/listinfo/cfe-dev</a><br>
 </blockquote>



_______________________________________________
cfe-dev mailing list
cfe-dev@cs.uiuc.edu
http://lists.cs.uiuc.edu/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