<div dir="ltr"><div class="gmail_extra"><div class="gmail_quote">On Mon, Jul 14, 2014 at 4:57 PM, Nikola Smiljanic <span dir="ltr"><<a href="mailto:popizdeh@gmail.com" target="_blank">popizdeh@gmail.com</a>></span> wrote:<br>
<blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex"><div dir="ltr"><div class="gmail_extra"><div class="gmail_quote">
<div class="">On Tue, Jul 15, 2014 at 9:27 AM, Reid Kleckner <span dir="ltr"><<a href="mailto:rnk@google.com" target="_blank">rnk@google.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">
<div dir="ltr"><div class="gmail_extra"><div class="gmail_quote"><div>I think their documentation is trying to warn the user that it won't work if you use it in a class template. </div></div></div></div></blockquote>
<div><br></div></div><div>I find you interpretation a bit of a stretch :) To me it means exactly what it says even though they don't implement it that way. Note that Aarons example with dependent base does work so this seems to break only if the base class is a template parameter.</div>
<div><br></div><div>template <typename T></div><div>struct Base {</div><div> void foo();</div><div>};</div><div><br></div><div>template <typename T></div><div>struct Derived : Base<T> {</div><div> void bar() {</div>
<div> __super::foo();</div><div> }</div><div>}; </div></div></div></div></blockquote><div><br></div><div>Yes, but this is because they will do lookup into base classes that are implicit specializations of known templates. For example, I could introduce a specialization of Base<int> that defines foo as something else, and they would do the wrong thing.</div>
<div><br></div><div>The reason that they would specifically bless __super in member functions instead of class bodies is because they never appear to parse member function bodies without first performing token substitution. They do appear to parse class bodies, so they can't handle __super when there are bases that they need to look into. Clang, on the other hand, always parses both class bodies and method bodies before instantiation.</div>
<div> </div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex"><div dir="ltr"><div class="gmail_extra"><div class="gmail_quote">
<div>I was also trying to figure out what you meant by "<span style="font-family:arial,sans-serif;font-size:13px">instantiate a template with a non-type template parameter using __super" and came up with this insanity:</span></div>
<div><span style="font-family:arial,sans-serif;font-size:13px"><br></span></div><div><div><font face="arial, sans-serif">struct Base {</font></div><div><font face="arial, sans-serif"> enum Enumerator {</font></div>
<div><font face="arial, sans-serif"> One, Two</font></div><div><font face="arial, sans-serif"> };</font></div><div><font face="arial, sans-serif"><br></font></div><div><font face="arial, sans-serif"> template <Enumerator e></font></div>
<div><font face="arial, sans-serif"> struct Inner {};</font></div><div><span style="font-family:arial,sans-serif">};</span><br></div><div><font face="arial, sans-serif"><br></font></div><div><font face="arial, sans-serif">struct Derived : Base</font></div>
<div><font face="arial, sans-serif">{</font></div><div><font face="arial, sans-serif"> Inner<__super::One> x;</font></div><div><font face="arial, sans-serif"> __super::Inner<Two> y;</font></div>
<div><font face="arial, sans-serif">};</font></div></div><div><br></div><div>First member declaration is ok but not the second one. It does work if you replace __super with Base. I can't say I understand their rules and that's why I suggested implementing __super only inside member functions as their documentation suggests.</div>
</div></div></div></blockquote><div><br></div><div>Huh. I actually had something like the 'x' declaration in mind. I thought it would tickle the relevant part of our mangler when we are mangling nested-name-specifiers. If you make that mangler case unreachable, does the 'x' decl hit it?</div>
<div><br></div><div>Maybe try something with real decls, like:</div><div><div>struct A { int h(); };</div><div>template <int (A::*MP)()> struct X { static void f() {} };</div><div>struct B : A { static void g(); };</div>
<div>void B::g() {</div><div> X<&__super::h>::f();</div><div>}</div></div><div><br></div><div>We should try to mangle __super while comping the name of X<&__super::h>::f().</div><div><br></div><div>I'm not sure what to do with the 'y' decl case. We could try to do something, but if it's too hard, I'm OK with giving up and forbidding __super outside of member functions.</div>
<div> </div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex"><div dir="ltr"><div class="gmail_extra"><div class="gmail_quote">
<div class=""><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex"><div dir="ltr"><div class="gmail_extra"><div class="gmail_quote">
<div><div>I think we need to do some overload resolution. MSVC resolves __super to B in this case:<br></div></div><div><div>struct A { void foo(int); };</div><div>struct B { void foo(short); };</div><div>struct C : A, B {</div>
<div> void foo(short x) {</div><div> __super::foo(x);</div><div> }</div><div>};</div></div><div><br></div><div>And they error out if you s/short/int/.</div></div></div></div>
</blockquote></div></div><br></div><div class="gmail_extra">No surprises here, besides that I don't know how to exactly do this. Hopefully Richard will point me in the right direction. I had a look at OverloadCandidateSet and Sema::addOverloadCandidate but I couldn't figure out where to get argument expressions from.</div>
</div></blockquote><div><br></div><div>I should look at the code again, but I was hoping this would fall right out of the way you split the lookup. :)</div></div><br></div></div>