<html><head></head><body style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space; "><br><div><div>On Jan 27, 2010, at 6:48 AM, Sebastian Redl wrote:</div><br class="Apple-interchange-newline"><blockquote type="cite"><div>Hi,<br><br>I'm trying to clean up variable definition code. I've given VarDecl a<br>new method, isThisDeclarationADefinition(), and have implemented it thus:<br><br>VarDecl::DefinitionKind VarDecl::isThisDeclarationADefinition() const {<br>  // C++ [basic.def]p2:<br>  //   A declaration is a definition unless [...] it contains the 'extern'<br>  //   specifier or a linkage-specification and neither an initializer<br>[...],<br>  //   it declares a static data member in a class declaration [...].<br>  // C++ [temp.expl.spec]p15:<br>  //   An explicit specialization of a static data member of a template is a<br>  //   definition if the declaration includes an initializer; otherwise,<br>it is<br>  //   a declaration.<br>  // FIXME: Exact C rules?<br>  if (isStaticDataMember()) {<br>    if (isOutOfLine() && (hasInit() ||<br>          getTemplateSpecializationKind() != TSK_ExplicitSpecialization))<br>      return Definition;<br>    else<br>      return DeclarationOnly;<br>  }<br>  if (hasInit())<br>    return Definition;<br>  // AST for 'extern "C" int foo;' is annotated with 'extern'.<br>  if (hasExternalStorage())<br>    return DeclarationOnly;<br><br>  // Now, in C++, everything left is a definition, but in C, if this<br>variable<br>  // is global, it is a tentative definition.<br>  // FIXME: It's not a tentative definition if there's a known definite<br>  // definition.<br>  if (!getASTContext().getLang().CPlusPlus && isFileVarDecl())<br>    return TentativeDefinition;<br><br>  return Definition;<br>}<br><br>Are these semantics correct for C? </div></blockquote><div><br></div><div>They look correct to me, although (as you say below) you should double-check the tentative-definition semantics against isTentativeDefinition.</div><br><blockquote type="cite"><div>Can I have a standard quote? </div></blockquote><div><br></div><div>C99 6.9.2 sayeth:</div><div><br></div><div><div style="margin-top: 0px; margin-right: 0px; margin-bottom: 0px; margin-left: 0px; font: normal normal normal 12px/normal Times; ">1<span class="Apple-tab-span" style="white-space:pre">    </span>If the declaration of an identifier for an object has file scope and an initializer, the declaration is an external definition for the identifier.</div><div style="margin-top: 0px; margin-right: 0px; margin-bottom: 0px; margin-left: 0px; font: normal normal normal 12px/normal Times; ">2<span class="Apple-tab-span" style="white-space:pre">       </span>A declaration of an identifier for an object that has file scope without an initializer, and without a storage-class specifier or with the storage-class specifier <span style="font: 12.0px Courier"><b>static</b></span>, constitutes a <i>tentative definition</i>.</div></div><br><blockquote type="cite"><div>Are<br>global variables marked with __thread ever tentative definitions?<br></div></blockquote><div><br></div>I think they can be... they would just get a definition of 0 in each thread.</div><div><br><blockquote type="cite"><div>The current isTentativeDefinition() will return false if there is a<br>definite definition elsewhere in the file; I will fix this in my<br>implementation. Any other problems?<br></div></blockquote></div><div><br></div>I don't see any other issues. Thanks for working on this!<div><br><div><span class="Apple-tab-span" style="white-space:pre">  </span>- Doug</div></div></body></html>