<html><head></head><body style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space; "><div><div>On Sep 17, 2010, at 6:22 PM, Jim Goodnow II wrote:</div><br class="Apple-interchange-newline"><blockquote type="cite"><div>At 08:04 AM 9/17/2010, Douglas Gregor wrote:<br><br><blockquote type="cite">On Sep 17, 2010, at 2:30 AM, Jim Goodnow II wrote:<br></blockquote><blockquote type="cite"><br></blockquote><blockquote type="cite"><blockquote type="cite">Hi,<br></blockquote></blockquote><blockquote type="cite"><blockquote type="cite"><br></blockquote></blockquote><blockquote type="cite"><blockquote type="cite">One of the things that I'm seeing in several places is where<br></blockquote></blockquote><blockquote type="cite"><blockquote type="cite">VarDecl::getInit() is returning an Expr that is CXXConstructExpr when<br></blockquote></blockquote><blockquote type="cite"><blockquote type="cite">a class variable is declared. However, the logic that follows the<br></blockquote></blockquote><blockquote type="cite"><blockquote type="cite">getInit() call usually assumes that if a non-NULL value is returned,<br></blockquote></blockquote><blockquote type="cite"><blockquote type="cite">there is a value being assigned. In the case of a constructor, that's<br></blockquote></blockquote><blockquote type="cite"><blockquote type="cite">sort of true but not completely unless it is a copy constructor.<br></blockquote></blockquote><blockquote type="cite"><br></blockquote><blockquote type="cite">It need not always be a copy constructor. Any constructor could <br></blockquote><blockquote type="cite">occur there. A CXXConstructExpr occurs anywhere that we're <br></blockquote><blockquote type="cite">performing initialization by constructor.<br></blockquote><br>Yes, I am aware of that. The problem is distinguishing between:<br><br>foo f;<br>foo f1 = f;<br><br>Both declarations will return a CXXConstructExpr from getInit(), but <br>the code I am finding is assuming that there is an assignment <br>happening which is not the case in the first declaration.<br><br><br><blockquote type="cite"><blockquote type="cite">So,<br></blockquote></blockquote><blockquote type="cite"><blockquote type="cite">a question of philosophy:<br></blockquote></blockquote><blockquote type="cite"><blockquote type="cite"><br></blockquote></blockquote><blockquote type="cite"><blockquote type="cite">Should getInit() return NULL when the constructor is not a copy<br></blockquote></blockquote><blockquote type="cite"><blockquote type="cite">constructor to support the logic in most cases? This might break or<br></blockquote></blockquote><blockquote type="cite"><blockquote type="cite">require a rework of things that do handle getInit() correctly like<br></blockquote></blockquote><blockquote type="cite"><blockquote type="cite">CodeGen and require a different call to get a non-copy <br></blockquote></blockquote><blockquote type="cite">constructor initializer.<br></blockquote><blockquote type="cite"><blockquote type="cite"><br></blockquote></blockquote><blockquote type="cite"><blockquote type="cite">Or should the calls to getInit() be qualified by an additional call<br></blockquote></blockquote><blockquote type="cite"><blockquote type="cite">to an 'isCopyConstructor()' function where appropriate?<br></blockquote></blockquote><blockquote type="cite"><br></blockquote><blockquote type="cite"><br></blockquote><blockquote type="cite">Why do you consider copy constructors to be special? They are <br></blockquote><blockquote type="cite">elidable in some cases (and CXXConstructExpr tells us when the <br></blockquote><blockquote type="cite">construction can be elided), but they aren't the only kinds of <br></blockquote><blockquote type="cite">constructors that are elidable (C++0x allows move constructors to be <br></blockquote><blockquote type="cite">elided, too). Static analysis need not treat them as special, unless <br></blockquote><blockquote type="cite">for some reason that improves results.<br></blockquote><blockquote type="cite"><br></blockquote><blockquote type="cite"> - Doug<br></blockquote><br>Again, I'm looking at code in the static analyzer and other places <br>that is assuming an assignment is taking place because getInit() is <br>not returning a NULL. My question is how to distinguish between the <br>two examples I gave before?</div></blockquote><div><br></div><div>See VarDecl's hasCXXDirectInitializer():</div><div><br></div><div><div style="margin-top: 0px; margin-right: 0px; margin-bottom: 0px; margin-left: 0px; font: normal normal normal 11px/normal Monaco; color: rgb(71, 144, 117); "><font class="Apple-style-span" color="#000000" face="Helvetica"><span class="Apple-style-span" style="font-size: medium;"><font class="Apple-style-span" face="Monaco" size="3"><span class="Apple-style-span" style="font-size: 11px;"> /// hasCXXDirectInitializer - If true, the initializer was a direct<br> /// initializer, e.g: "int x(1);". The Init expression will be the expression<br> /// inside the parens or a "ClassType(a,b,c)" class constructor expression for<br> /// class types. Clients can distinguish between "int x(1);" and "int x=1;"<br> /// by checking hasCXXDirectInitializer.<br><br></span></font></span></font></div></div>-Argiris</div><div><br><blockquote type="cite"><div>One way is to check the result for a <br>constructor and then look at the constructor and see if it is a copy <br>constructor or not. So,<br><br>if (Expr *Init = D->getInit()) {<br><br>becomes<br><br>Expr *Init = D->getInit();<br>if (Init && (!isa<CXXConstructExpr>(Init) ||<br> dyn_cast<CXXConstructExpr>(Init)->getConstructor()->isCopyConstructor())) <br>{<br><br> - jim<br><br>_______________________________________________<br>cfe-dev mailing list<br><a href="mailto:cfe-dev@cs.uiuc.edu">cfe-dev@cs.uiuc.edu</a><br>http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev<br></div></blockquote></div><br></body></html>