<html><body style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space; "><br><div><div>On Aug 25, 2009, at 4:46 PM, Anders Carlsson wrote:</div><br class="Apple-interchange-newline"><blockquote type="cite"><div>Author: andersca<br>Date: Tue Aug 25 18:46:41 2009<br>New Revision: 80055<br><br>URL: <a href="http://llvm.org/viewvc/llvm-project?rev=80055&view=rev">http://llvm.org/viewvc/llvm-project?rev=80055&view=rev</a><br>Log:<br>Parsing of pseudo-destructors.<br></div></blockquote><div><br></div>Cool.</div><div><br><blockquote type="cite"><div>Modified:<br> cfe/trunk/include/clang/Parse/Action.h<br> cfe/trunk/lib/Parse/ParseExpr.cpp<br> cfe/trunk/lib/Sema/Sema.h<br> cfe/trunk/lib/Sema/SemaExpr.cpp<br> cfe/trunk/lib/Sema/SemaExprCXX.cpp<br><br>Modified: cfe/trunk/include/clang/Parse/Action.h<br>URL: <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Parse/Action.h?rev=80055&r1=80054&r2=80055&view=diff">http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Parse/Action.h?rev=80055&r1=80054&r2=80055&view=diff</a><br><br>==============================================================================<br>--- cfe/trunk/include/clang/Parse/Action.h (original)<br>+++ cfe/trunk/include/clang/Parse/Action.h Tue Aug 25 18:46:41 2009<br>@@ -1263,7 +1263,16 @@<br> return ExprEmpty();<br> }<br><br>-<br>+ virtual OwningExprResult<br>+ ActOnPseudoDtorReferenceExpr(Scope *S, ExprArg Base,<br>+ SourceLocation OpLoc,<br>+ tok::TokenKind OpKind,<br>+ SourceLocation ClassNameLoc,<br>+ IdentifierInfo *ClassName,<br>+ const CXXScopeSpec *SS = 0) {<br>+ return ExprEmpty();<br>+ }<br></div></blockquote><div><br></div>No documentation? :)</div><div><br><blockquote type="cite"><div> /// ActOnFinishFullExpr - Called whenever a full expression has been parsed.<br> /// (C++ [intro.execution]p12).<br> virtual OwningExprResult ActOnFinishFullExpr(ExprArg Expr) {<br><br>Modified: cfe/trunk/lib/Parse/ParseExpr.cpp<br>URL: <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Parse/ParseExpr.cpp?rev=80055&r1=80054&r2=80055&view=diff">http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Parse/ParseExpr.cpp?rev=80055&r1=80054&r2=80055&view=diff</a><br><br>==============================================================================<br>--- cfe/trunk/lib/Parse/ParseExpr.cpp (original)<br>+++ cfe/trunk/lib/Parse/ParseExpr.cpp Tue Aug 25 18:46:41 2009<br>@@ -933,18 +933,34 @@<br> ParseOptionalCXXScopeSpecifier(SS);<br> }<br><br>- if (Tok.isNot(tok::identifier)) {<br>+ if (<a href="http://Tok.is">Tok.is</a>(tok::identifier)) {<br>+ if (!LHS.isInvalid())<br>+ LHS = Actions.ActOnMemberReferenceExpr(CurScope, move(LHS), OpLoc,<br>+ OpKind, Tok.getLocation(),<br>+ *Tok.getIdentifierInfo(),<br>+ ObjCImpDecl, &SS);<br>+ } else if (getLang().CPlusPlus && <a href="http://Tok.is">Tok.is</a>(tok::tilde)) {<br>+ // We have a C++ pseudo-destructor.<br>+ <br>+ // Consume the tilde.<br>+ ConsumeToken();<br>+ <br>+ if (!Tok.is(tok::identifier)) {<br>+ Diag(Tok, diag::err_expected_ident);<br>+ return ExprError();<br>+ }<br>+ <br>+ if (!LHS.isInvalid())<br>+ LHS = Actions.ActOnPseudoDtorReferenceExpr(CurScope, move(LHS), <br>+ OpLoc, OpKind,<br>+ Tok.getLocation(), <br>+ Tok.getIdentifierInfo(),<br>+ &SS);<br></div></blockquote><div><br></div><div>There's an oddity in the grammar here that might cause confusion. In particular, something like this:</div><div><br></div><div> t.~T()</div><div><br></div><div>syntactically looks like both a</div><div><br></div><div> postfix-expression . pseudo-destructor-name</div><div><br></div><div>and a </div><div><br></div><div> postfix-expression . template[opt] id-expression</div><div><br></div><div>so both go through the same path in the parser. Whether it is actually a pseudo-destructor or whether it is a call to the destructor is something that semantic analysis determines, which makes the action name ActOnPseudoDtorReferenceExpr a bit misleading. Perhaps we should call it ActOnDestructorReferenceExpr?</div><div><br></div><blockquote type="cite"><div>+Sema::OwningExprResult<br>+Sema::ActOnPseudoDtorReferenceExpr(Scope *S, ExprArg Base,<br>+ SourceLocation OpLoc,<br>+ tok::TokenKind OpKind,<br>+ SourceLocation ClassNameLoc,<br>+ IdentifierInfo *ClassName,<br>+ const CXXScopeSpec *SS) {<br>+ if (SS && SS->isInvalid())<br>+ return ExprError();<br>+ <br>+ // Since this might be a postfix expression, get rid of ParenListExprs.<br>+ Base = MaybeConvertParenListExprToParenExpr(S, move(Base));<br>+ <br>+ Expr *BaseExpr = Base.takeAs<Expr>();<br>+ assert(BaseExpr && "no record expression");<br>+ <br>+ // Perform default conversions.<br>+ DefaultFunctionArrayConversion(BaseExpr);<br></div></blockquote><br></div><div>Should check here to determine whether the type of Base is a scalar type or pointer to a scalar type (depending on . vs ->), and of course turn this into an actual member reference (e.g., via a call to ActOnMemberReferenceExpr) when the type is a class type.</div><div><br></div><div><span class="Apple-tab-span" style="white-space:pre"> </span>- Doug</div></body></html>