[cfe-commits] r113356 - in /cfe/trunk: include/clang/AST/ include/clang/Basic/ include/clang/Parse/ include/clang/Sema/ include/clang/Serialization/ lib/AST/ lib/Parse/ lib/Sema/ lib/Serialization/ test/Parser/

Daniel Dunbar daniel at zuster.org
Wed Sep 8 12:02:14 PDT 2010


FYI:
--
/Volumes/Data/Users/ddunbar/llvm/tools/clang/tools/libclang/CXCursor.cpp:60:11:
warning:
      enumeration value 'CXXUuidofExprClass' not handled in switch
[-Wswitch-enum]
  switch (S->getStmtClass()) {
          ^
1 warning generated.
--

 - Daniel

On Wed, Sep 8, 2010 at 5:20 AM, Francois Pichet <pichet2000 at gmail.com> wrote:
> Author: fpichet
> Date: Wed Sep  8 07:20:18 2010
> New Revision: 113356
>
> URL: http://llvm.org/viewvc/llvm-project?rev=113356&view=rev
> Log:
> Microsoft's __uuidof operator implementation part 1.
>
> Modified:
>    cfe/trunk/include/clang/AST/ExprCXX.h
>    cfe/trunk/include/clang/AST/RecursiveASTVisitor.h
>    cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td
>    cfe/trunk/include/clang/Basic/StmtNodes.td
>    cfe/trunk/include/clang/Basic/TokenKinds.def
>    cfe/trunk/include/clang/Parse/Parser.h
>    cfe/trunk/include/clang/Sema/Sema.h
>    cfe/trunk/include/clang/Serialization/ASTBitCodes.h
>    cfe/trunk/lib/AST/ExprCXX.cpp
>    cfe/trunk/lib/AST/StmtPrinter.cpp
>    cfe/trunk/lib/AST/StmtProfile.cpp
>    cfe/trunk/lib/Parse/ParseExpr.cpp
>    cfe/trunk/lib/Parse/ParseExprCXX.cpp
>    cfe/trunk/lib/Sema/Sema.cpp
>    cfe/trunk/lib/Sema/SemaExprCXX.cpp
>    cfe/trunk/lib/Sema/TreeTransform.h
>    cfe/trunk/lib/Serialization/ASTReaderStmt.cpp
>    cfe/trunk/lib/Serialization/ASTWriterStmt.cpp
>    cfe/trunk/test/Parser/MicrosoftExtensions.c
>
> Modified: cfe/trunk/include/clang/AST/ExprCXX.h
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/ExprCXX.h?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/include/clang/AST/ExprCXX.h (original)
> +++ cfe/trunk/include/clang/AST/ExprCXX.h Wed Sep  8 07:20:18 2010
> @@ -396,6 +396,74 @@
>   virtual child_iterator child_end();
>  };
>
> +/// CXXUuidofExpr - A microsoft C++ @c __uuidof expression, which gets
> +/// the _GUID that corresponds to the supplied type or expression.
> +///
> +/// This represents code like @c __uuidof(COMTYPE) or @c __uuidof(*comPtr)
> +class CXXUuidofExpr : public Expr {
> +private:
> +  llvm::PointerUnion<Stmt *, TypeSourceInfo *> Operand;
> +  SourceRange Range;
> +
> +public:
> +  CXXUuidofExpr(QualType Ty, TypeSourceInfo *Operand, SourceRange R)
> +    : Expr(CXXUuidofExprClass, Ty,
> +        false, Operand->getType()->isDependentType()),
> +      Operand(Operand), Range(R) { }
> +
> +  CXXUuidofExpr(QualType Ty, Expr *Operand, SourceRange R)
> +    : Expr(CXXUuidofExprClass, Ty,
> +        false, Operand->isTypeDependent()),
> +      Operand(Operand), Range(R) { }
> +
> +  CXXUuidofExpr(EmptyShell Empty, bool isExpr)
> +    : Expr(CXXUuidofExprClass, Empty) {
> +    if (isExpr)
> +      Operand = (Expr*)0;
> +    else
> +      Operand = (TypeSourceInfo*)0;
> +  }
> +
> +  bool isTypeOperand() const { return Operand.is<TypeSourceInfo *>(); }
> +
> +  /// \brief Retrieves the type operand of this __uuidof() expression after
> +  /// various required adjustments (removing reference types, cv-qualifiers).
> +  QualType getTypeOperand() const;
> +
> +  /// \brief Retrieve source information for the type operand.
> +  TypeSourceInfo *getTypeOperandSourceInfo() const {
> +    assert(isTypeOperand() && "Cannot call getTypeOperand for __uuidof(expr)");
> +    return Operand.get<TypeSourceInfo *>();
> +  }
> +
> +  void setTypeOperandSourceInfo(TypeSourceInfo *TSI) {
> +    assert(isTypeOperand() && "Cannot call getTypeOperand for __uuidof(expr)");
> +    Operand = TSI;
> +  }
> +
> +  Expr *getExprOperand() const {
> +    assert(!isTypeOperand() && "Cannot call getExprOperand for __uuidof(type)");
> +    return static_cast<Expr*>(Operand.get<Stmt *>());
> +  }
> +
> +  void setExprOperand(Expr *E) {
> +    assert(!isTypeOperand() && "Cannot call getExprOperand for __uuidof(type)");
> +    Operand = E;
> +  }
> +
> +  virtual SourceRange getSourceRange() const { return Range; }
> +  void setSourceRange(SourceRange R) { Range = R; }
> +
> +  static bool classof(const Stmt *T) {
> +    return T->getStmtClass() == CXXUuidofExprClass;
> +  }
> +  static bool classof(const CXXUuidofExpr *) { return true; }
> +
> +  // Iterators
> +  virtual child_iterator child_begin();
> +  virtual child_iterator child_end();
> +};
> +
>  /// CXXThisExpr - Represents the "this" expression in C++, which is a
>  /// pointer to the object on which the current member function is
>  /// executing (C++ [expr.prim]p3). Example:
>
> Modified: cfe/trunk/include/clang/AST/RecursiveASTVisitor.h
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/RecursiveASTVisitor.h?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/include/clang/AST/RecursiveASTVisitor.h (original)
> +++ cfe/trunk/include/clang/AST/RecursiveASTVisitor.h Wed Sep  8 07:20:18 2010
> @@ -1769,6 +1769,13 @@
>       TRY_TO(TraverseTypeLoc(S->getTypeOperandSourceInfo()->getTypeLoc()));
>   })
>
> +DEF_TRAVERSE_STMT(CXXUuidofExpr, {
> +    // The child-iterator will pick up the arg if it's an expression,
> +    // but not if it's a type.
> +    if (S->isTypeOperand())
> +      TRY_TO(TraverseTypeLoc(S->getTypeOperandSourceInfo()->getTypeLoc()));
> +  })
> +
>  DEF_TRAVERSE_STMT(TypesCompatibleExpr, {
>     TRY_TO(TraverseTypeLoc(S->getArgTInfo1()->getTypeLoc()));
>     TRY_TO(TraverseTypeLoc(S->getArgTInfo2()->getTypeLoc()));
>
> Modified: cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td (original)
> +++ cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td Wed Sep  8 07:20:18 2010
> @@ -2392,6 +2392,8 @@
>  // Other C++ expressions
>  def err_need_header_before_typeid : Error<
>   "you need to include <typeinfo> before using the 'typeid' operator">;
> +def err_need_header_before_ms_uuidof : Error<
> +  "you need to include <guiddef.h> before using the '__uuidof' operator">;
>  def err_incomplete_typeid : Error<"'typeid' of incomplete type %0">;
>  def err_static_illegal_in_new : Error<
>   "the 'static' modifier for the array size is not legal in new expressions">;
>
> Modified: cfe/trunk/include/clang/Basic/StmtNodes.td
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/StmtNodes.td?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/include/clang/Basic/StmtNodes.td (original)
> +++ cfe/trunk/include/clang/Basic/StmtNodes.td Wed Sep  8 07:20:18 2010
> @@ -127,3 +127,7 @@
>  def ShuffleVectorExpr : DStmt<Expr>;
>  def BlockExpr : DStmt<Expr>;
>  def BlockDeclRefExpr : DStmt<Expr>;
> +
> +// Microsoft Extensions.
> +def CXXUuidofExpr : DStmt<Expr>;
> +
>
> Modified: cfe/trunk/include/clang/Basic/TokenKinds.def
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/TokenKinds.def?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/include/clang/Basic/TokenKinds.def (original)
> +++ cfe/trunk/include/clang/Basic/TokenKinds.def Wed Sep  8 07:20:18 2010
> @@ -369,11 +369,13 @@
>  // Microsoft extensions which should be disabled in strict conformance mode
>  KEYWORD(__ptr64                   , KEYMS)
>  KEYWORD(__w64                     , KEYMS)
> +KEYWORD(__uuidof                  , KEYMS)
>  ALIAS("_asm"         , asm        , KEYMS)
>  ALIAS("_cdecl"       , __cdecl    , KEYMS)
>  ALIAS("_fastcall"    , __fastcall , KEYMS)
>  ALIAS("_stdcall"     , __stdcall  , KEYMS)
>  ALIAS("_thiscall"    , __thiscall , KEYMS)
> +ALIAS("_uuidof"      ,__uuidof    , KEYMS)
>
>  // Borland Extensions which should be disabled in strict conformance mode.
>  ALIAS("_pascal"      , __pascal   , KEYBORLAND)
>
> Modified: cfe/trunk/include/clang/Parse/Parser.h
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Parse/Parser.h?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/include/clang/Parse/Parser.h (original)
> +++ cfe/trunk/include/clang/Parse/Parser.h Wed Sep  8 07:20:18 2010
> @@ -1029,6 +1029,10 @@
>   ExprResult ParseCXXTypeid();
>
>   //===--------------------------------------------------------------------===//
> +  //  C++ : Microsoft __uuidof Expression
> +  ExprResult ParseCXXUuidof();
> +
> +  //===--------------------------------------------------------------------===//
>   // C++ 5.2.4: C++ Pseudo-Destructor Expressions
>   ExprResult ParseCXXPseudoDestructor(ExprArg Base, SourceLocation OpLoc,
>                                             tok::TokenKind OpKind,
>
> Modified: cfe/trunk/include/clang/Sema/Sema.h
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Sema/Sema.h?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/include/clang/Sema/Sema.h (original)
> +++ cfe/trunk/include/clang/Sema/Sema.h Wed Sep  8 07:20:18 2010
> @@ -365,6 +365,9 @@
>   /// standard library.
>   LazyDeclPtr StdBadAlloc;
>
> +  /// \brief The MSVC "_GUID" struct, which is defined in MSVC header files.
> +  RecordDecl *MSVCGuidDecl;
> +
>   /// A flag to remember whether the implicit forms of operator new and delete
>   /// have been declared.
>   bool GlobalNewDeleteDeclared;
> @@ -2156,6 +2159,22 @@
>                             void *TyOrExpr,
>                             SourceLocation RParenLoc);
>
> +  ExprResult BuildCXXUuidof(QualType TypeInfoType,
> +                            SourceLocation TypeidLoc,
> +                            TypeSourceInfo *Operand,
> +                            SourceLocation RParenLoc);
> +  ExprResult BuildCXXUuidof(QualType TypeInfoType,
> +                            SourceLocation TypeidLoc,
> +                            Expr *Operand,
> +                            SourceLocation RParenLoc);
> +
> +  /// ActOnCXXUuidof - Parse __uuidof( something ).
> +  virtual ExprResult ActOnCXXUuidof(SourceLocation OpLoc,
> +                                    SourceLocation LParenLoc, bool isType,
> +                                    void *TyOrExpr,
> +                                    SourceLocation RParenLoc);
> +
> +
>   //// ActOnCXXThis -  Parse 'this' pointer.
>   ExprResult ActOnCXXThis(SourceLocation ThisLoc);
>
>
> Modified: cfe/trunk/include/clang/Serialization/ASTBitCodes.h
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Serialization/ASTBitCodes.h?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/include/clang/Serialization/ASTBitCodes.h (original)
> +++ cfe/trunk/include/clang/Serialization/ASTBitCodes.h Wed Sep  8 07:20:18 2010
> @@ -875,6 +875,8 @@
>       EXPR_CXX_NULL_PTR_LITERAL,  // CXXNullPtrLiteralExpr
>       EXPR_CXX_TYPEID_EXPR,       // CXXTypeidExpr (of expr).
>       EXPR_CXX_TYPEID_TYPE,       // CXXTypeidExpr (of type).
> +      EXPR_CXX_UUIDOF_EXPR,       // CXXUuidofExpr (of expr).
> +      EXPR_CXX_UUIDOF_TYPE,       // CXXUuidofExpr (of type).
>       EXPR_CXX_THIS,              // CXXThisExpr
>       EXPR_CXX_THROW,             // CXXThrowExpr
>       EXPR_CXX_DEFAULT_ARG,       // CXXDefaultArgExpr
>
> Modified: cfe/trunk/lib/AST/ExprCXX.cpp
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ExprCXX.cpp?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/lib/AST/ExprCXX.cpp (original)
> +++ cfe/trunk/lib/AST/ExprCXX.cpp Wed Sep  8 07:20:18 2010
> @@ -39,6 +39,22 @@
>                          : reinterpret_cast<Stmt **>(&Operand) + 1;
>  }
>
> +QualType CXXUuidofExpr::getTypeOperand() const {
> +  assert(isTypeOperand() && "Cannot call getTypeOperand for __uuidof(expr)");
> +  return Operand.get<TypeSourceInfo *>()->getType().getNonReferenceType()
> +                                                        .getUnqualifiedType();
> +}
> +
> +// CXXUuidofExpr - has child iterators if the operand is an expression
> +Stmt::child_iterator CXXUuidofExpr::child_begin() {
> +  return isTypeOperand() ? child_iterator()
> +                         : reinterpret_cast<Stmt **>(&Operand);
> +}
> +Stmt::child_iterator CXXUuidofExpr::child_end() {
> +  return isTypeOperand() ? child_iterator()
> +                         : reinterpret_cast<Stmt **>(&Operand) + 1;
> +}
> +
>  // CXXBoolLiteralExpr
>  Stmt::child_iterator CXXBoolLiteralExpr::child_begin() {
>   return child_iterator();
>
> Modified: cfe/trunk/lib/AST/StmtPrinter.cpp
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/StmtPrinter.cpp?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/lib/AST/StmtPrinter.cpp (original)
> +++ cfe/trunk/lib/AST/StmtPrinter.cpp Wed Sep  8 07:20:18 2010
> @@ -1002,6 +1002,16 @@
>   OS << ")";
>  }
>
> +void StmtPrinter::VisitCXXUuidofExpr(CXXUuidofExpr *Node) {
> +  OS << "__uuidof(";
> +  if (Node->isTypeOperand()) {
> +    OS << Node->getTypeOperand().getAsString(Policy);
> +  } else {
> +    PrintExpr(Node->getExprOperand());
> +  }
> +  OS << ")";
> +}
> +
>  void StmtPrinter::VisitCXXBoolLiteralExpr(CXXBoolLiteralExpr *Node) {
>   OS << (Node->getValue() ? "true" : "false");
>  }
>
> Modified: cfe/trunk/lib/AST/StmtProfile.cpp
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/StmtProfile.cpp?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/lib/AST/StmtProfile.cpp (original)
> +++ cfe/trunk/lib/AST/StmtProfile.cpp Wed Sep  8 07:20:18 2010
> @@ -687,6 +687,12 @@
>     VisitType(S->getTypeOperand());
>  }
>
> +void StmtProfiler::VisitCXXUuidofExpr(CXXUuidofExpr *S) {
> +  VisitExpr(S);
> +  if (S->isTypeOperand())
> +    VisitType(S->getTypeOperand());
> +}
> +
>  void StmtProfiler::VisitCXXThisExpr(CXXThisExpr *S) {
>   VisitExpr(S);
>  }
>
> Modified: cfe/trunk/lib/Parse/ParseExpr.cpp
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Parse/ParseExpr.cpp?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/lib/Parse/ParseExpr.cpp (original)
> +++ cfe/trunk/lib/Parse/ParseExpr.cpp Wed Sep  8 07:20:18 2010
> @@ -768,6 +768,9 @@
>   case tok::kw_typeid:
>     Res = ParseCXXTypeid();
>     break;
> +  case tok::kw___uuidof:
> +    Res = ParseCXXUuidof();
> +    break;
>   case tok::kw_this:
>     Res = ParseCXXThis();
>     break;
>
> Modified: cfe/trunk/lib/Parse/ParseExprCXX.cpp
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Parse/ParseExprCXX.cpp?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/lib/Parse/ParseExprCXX.cpp (original)
> +++ cfe/trunk/lib/Parse/ParseExprCXX.cpp Wed Sep  8 07:20:18 2010
> @@ -534,6 +534,54 @@
>   return move(Result);
>  }
>
> +/// ParseCXXUuidof - This handles the Microsoft C++ __uuidof expression.
> +///
> +///         '__uuidof' '(' expression ')'
> +///         '__uuidof' '(' type-id ')'
> +///
> +ExprResult Parser::ParseCXXUuidof() {
> +  assert(Tok.is(tok::kw___uuidof) && "Not '__uuidof'!");
> +
> +  SourceLocation OpLoc = ConsumeToken();
> +  SourceLocation LParenLoc = Tok.getLocation();
> +  SourceLocation RParenLoc;
> +
> +  // __uuidof expressions are always parenthesized.
> +  if (ExpectAndConsume(tok::l_paren, diag::err_expected_lparen_after,
> +      "__uuidof"))
> +    return ExprError();
> +
> +  ExprResult Result;
> +
> +  if (isTypeIdInParens()) {
> +    TypeResult Ty = ParseTypeName();
> +
> +    // Match the ')'.
> +    RParenLoc = MatchRHSPunctuation(tok::r_paren, LParenLoc);
> +
> +    if (Ty.isInvalid())
> +      return ExprError();
> +
> +    Result = Actions.ActOnCXXUuidof(OpLoc, LParenLoc, /*isType=*/true,
> +                                    Ty.get().getAsOpaquePtr(), RParenLoc);
> +  } else {
> +    EnterExpressionEvaluationContext Unevaluated(Actions, Sema::Unevaluated);
> +    Result = ParseExpression();
> +
> +    // Match the ')'.
> +    if (Result.isInvalid())
> +      SkipUntil(tok::r_paren);
> +    else {
> +      RParenLoc = MatchRHSPunctuation(tok::r_paren, LParenLoc);
> +
> +      Result = Actions.ActOnCXXUuidof(OpLoc, LParenLoc, /*isType=*/false,
> +                                      Result.release(), RParenLoc);
> +    }
> +  }
> +
> +  return move(Result);
> +}
> +
>  /// \brief Parse a C++ pseudo-destructor expression after the base,
>  /// . or -> operator, and nested-name-specifier have already been
>  /// parsed.
>
> Modified: cfe/trunk/lib/Sema/Sema.cpp
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/Sema.cpp?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/lib/Sema/Sema.cpp (original)
> +++ cfe/trunk/lib/Sema/Sema.cpp Wed Sep  8 07:20:18 2010
> @@ -138,7 +138,7 @@
>     CompleteTranslationUnit(CompleteTranslationUnit),
>     NumSFINAEErrors(0), SuppressAccessChecking(false),
>     NonInstantiationEntries(0), CurrentInstantiationScope(0), TyposCorrected(0),
> -    AnalysisWarnings(*this)
> +    AnalysisWarnings(*this), MSVCGuidDecl(0)
>  {
>   TUScope = 0;
>   if (getLangOptions().CPlusPlus)
>
> Modified: cfe/trunk/lib/Sema/SemaExprCXX.cpp
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaExprCXX.cpp?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/lib/Sema/SemaExprCXX.cpp (original)
> +++ cfe/trunk/lib/Sema/SemaExprCXX.cpp Wed Sep  8 07:20:18 2010
> @@ -370,6 +370,62 @@
>   return BuildCXXTypeId(TypeInfoType, OpLoc, (Expr*)TyOrExpr, RParenLoc);
>  }
>
> +/// \brief Build a Microsoft __uuidof expression with a type operand.
> +ExprResult Sema::BuildCXXUuidof(QualType TypeInfoType,
> +                                SourceLocation TypeidLoc,
> +                                TypeSourceInfo *Operand,
> +                                SourceLocation RParenLoc) {
> +  // FIXME: add __uuidof semantic analysis for type operand.
> +  return Owned(new (Context) CXXUuidofExpr(TypeInfoType.withConst(),
> +                                           Operand,
> +                                           SourceRange(TypeidLoc, RParenLoc)));
> +}
> +
> +/// \brief Build a Microsoft __uuidof expression with an expression operand.
> +ExprResult Sema::BuildCXXUuidof(QualType TypeInfoType,
> +                                SourceLocation TypeidLoc,
> +                                Expr *E,
> +                                SourceLocation RParenLoc) {
> +  // FIXME: add __uuidof semantic analysis for expr operand.
> +  return Owned(new (Context) CXXUuidofExpr(TypeInfoType.withConst(),
> +                                           E,
> +                                           SourceRange(TypeidLoc, RParenLoc)));
> +}
> +
> +/// ActOnCXXUuidof - Parse __uuidof( type-id ) or __uuidof (expression);
> +ExprResult
> +Sema::ActOnCXXUuidof(SourceLocation OpLoc, SourceLocation LParenLoc,
> +                     bool isType, void *TyOrExpr, SourceLocation RParenLoc) {
> +  // If MSVCGuidDecl has not been cached, do the lookup.
> +  if (!MSVCGuidDecl) {
> +    IdentifierInfo *GuidII = &PP.getIdentifierTable().get("_GUID");
> +    LookupResult R(*this, GuidII, SourceLocation(), LookupTagName);
> +    LookupQualifiedName(R, Context.getTranslationUnitDecl());
> +    MSVCGuidDecl = R.getAsSingle<RecordDecl>();
> +    if (!MSVCGuidDecl)
> +      return ExprError(Diag(OpLoc, diag::err_need_header_before_ms_uuidof));
> +  }
> +
> +  QualType GuidType = Context.getTypeDeclType(MSVCGuidDecl);
> +
> +  if (isType) {
> +    // The operand is a type; handle it as such.
> +    TypeSourceInfo *TInfo = 0;
> +    QualType T = GetTypeFromParser(ParsedType::getFromOpaquePtr(TyOrExpr),
> +                                   &TInfo);
> +    if (T.isNull())
> +      return ExprError();
> +
> +    if (!TInfo)
> +      TInfo = Context.getTrivialTypeSourceInfo(T, OpLoc);
> +
> +    return BuildCXXUuidof(GuidType, OpLoc, TInfo, RParenLoc);
> +  }
> +
> +  // The operand is an expression.
> +  return BuildCXXUuidof(GuidType, OpLoc, (Expr*)TyOrExpr, RParenLoc);
> +}
> +
>  /// ActOnCXXBoolLiteral - Parse {true,false} literals.
>  ExprResult
>  Sema::ActOnCXXBoolLiteral(SourceLocation OpLoc, tok::TokenKind Kind) {
>
> Modified: cfe/trunk/lib/Sema/TreeTransform.h
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/TreeTransform.h?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/lib/Sema/TreeTransform.h (original)
> +++ cfe/trunk/lib/Sema/TreeTransform.h Wed Sep  8 07:20:18 2010
> @@ -1513,6 +1513,7 @@
>                                     RParenLoc);
>   }
>
> +
>   /// \brief Build a new C++ typeid(expr) expression.
>   ///
>   /// By default, performs semantic analysis to build the new expression.
> @@ -1525,6 +1526,30 @@
>                                     RParenLoc);
>   }
>
> +  /// \brief Build a new C++ __uuidof(type) expression.
> +  ///
> +  /// By default, performs semantic analysis to build the new expression.
> +  /// Subclasses may override this routine to provide different behavior.
> +  ExprResult RebuildCXXUuidofExpr(QualType TypeInfoType,
> +                                        SourceLocation TypeidLoc,
> +                                        TypeSourceInfo *Operand,
> +                                        SourceLocation RParenLoc) {
> +    return getSema().BuildCXXUuidof(TypeInfoType, TypeidLoc, Operand,
> +                                    RParenLoc);
> +  }
> +
> +  /// \brief Build a new C++ __uuidof(expr) expression.
> +  ///
> +  /// By default, performs semantic analysis to build the new expression.
> +  /// Subclasses may override this routine to provide different behavior.
> +  ExprResult RebuildCXXUuidofExpr(QualType TypeInfoType,
> +                                        SourceLocation TypeidLoc,
> +                                        Expr *Operand,
> +                                        SourceLocation RParenLoc) {
> +    return getSema().BuildCXXUuidof(TypeInfoType, TypeidLoc, Operand,
> +                                    RParenLoc);
> +  }
> +
>   /// \brief Build a new C++ "this" expression.
>   ///
>   /// By default, builds a new "this" expression without performing any
> @@ -5145,6 +5170,44 @@
>
>  template<typename Derived>
>  ExprResult
> +TreeTransform<Derived>::TransformCXXUuidofExpr(CXXUuidofExpr *E) {
> +  if (E->isTypeOperand()) {
> +    TypeSourceInfo *TInfo
> +      = getDerived().TransformType(E->getTypeOperandSourceInfo());
> +    if (!TInfo)
> +      return ExprError();
> +
> +    if (!getDerived().AlwaysRebuild() &&
> +        TInfo == E->getTypeOperandSourceInfo())
> +      return SemaRef.Owned(E->Retain());
> +
> +    return getDerived().RebuildCXXTypeidExpr(E->getType(),
> +                                             E->getLocStart(),
> +                                             TInfo,
> +                                             E->getLocEnd());
> +  }
> +
> +  // We don't know whether the expression is potentially evaluated until
> +  // after we perform semantic analysis, so the expression is potentially
> +  // potentially evaluated.
> +  EnterExpressionEvaluationContext Unevaluated(SemaRef, Sema::Unevaluated);
> +
> +  ExprResult SubExpr = getDerived().TransformExpr(E->getExprOperand());
> +  if (SubExpr.isInvalid())
> +    return ExprError();
> +
> +  if (!getDerived().AlwaysRebuild() &&
> +      SubExpr.get() == E->getExprOperand())
> +    return SemaRef.Owned(E->Retain());
> +
> +  return getDerived().RebuildCXXUuidofExpr(E->getType(),
> +                                           E->getLocStart(),
> +                                           SubExpr.get(),
> +                                           E->getLocEnd());
> +}
> +
> +template<typename Derived>
> +ExprResult
>  TreeTransform<Derived>::TransformCXXBoolLiteralExpr(CXXBoolLiteralExpr *E) {
>   return SemaRef.Owned(E->Retain());
>  }
>
> Modified: cfe/trunk/lib/Serialization/ASTReaderStmt.cpp
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Serialization/ASTReaderStmt.cpp?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/lib/Serialization/ASTReaderStmt.cpp (original)
> +++ cfe/trunk/lib/Serialization/ASTReaderStmt.cpp Wed Sep  8 07:20:18 2010
> @@ -134,6 +134,7 @@
>     void VisitCXXBoolLiteralExpr(CXXBoolLiteralExpr *E);
>     void VisitCXXNullPtrLiteralExpr(CXXNullPtrLiteralExpr *E);
>     void VisitCXXTypeidExpr(CXXTypeidExpr *E);
> +    void VisitCXXUuidofExpr(CXXUuidofExpr *E);
>     void VisitCXXThisExpr(CXXThisExpr *E);
>     void VisitCXXThrowExpr(CXXThrowExpr *E);
>     void VisitCXXDefaultArgExpr(CXXDefaultArgExpr *E);
> @@ -1028,6 +1029,18 @@
>   // typeid(42+2)
>   E->setExprOperand(Reader.ReadSubExpr());
>  }
> +void ASTStmtReader::VisitCXXUuidofExpr(CXXUuidofExpr *E) {
> +  VisitExpr(E);
> +  E->setSourceRange(Reader.ReadSourceRange(Record, Idx));
> +  if (E->isTypeOperand()) { // __uuidof(ComType)
> +    E->setTypeOperandSourceInfo(
> +        Reader.GetTypeSourceInfo(DeclsCursor, Record, Idx));
> +    return;
> +  }
> +
> +  // __uuidof(expr)
> +  E->setExprOperand(Reader.ReadSubExpr());
> +}
>
>  void ASTStmtReader::VisitCXXThisExpr(CXXThisExpr *E) {
>   VisitExpr(E);
> @@ -1678,6 +1691,12 @@
>     case EXPR_CXX_TYPEID_TYPE:
>       S = new (Context) CXXTypeidExpr(Empty, false);
>       break;
> +    case EXPR_CXX_UUIDOF_EXPR:
> +      S = new (Context) CXXUuidofExpr(Empty, true);
> +      break;
> +    case EXPR_CXX_UUIDOF_TYPE:
> +      S = new (Context) CXXUuidofExpr(Empty, false);
> +      break;
>     case EXPR_CXX_THIS:
>       S = new (Context) CXXThisExpr(Empty);
>       break;
>
> Modified: cfe/trunk/lib/Serialization/ASTWriterStmt.cpp
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Serialization/ASTWriterStmt.cpp?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/lib/Serialization/ASTWriterStmt.cpp (original)
> +++ cfe/trunk/lib/Serialization/ASTWriterStmt.cpp Wed Sep  8 07:20:18 2010
> @@ -131,6 +131,7 @@
>     void VisitCXXBoolLiteralExpr(CXXBoolLiteralExpr *E);
>     void VisitCXXNullPtrLiteralExpr(CXXNullPtrLiteralExpr *E);
>     void VisitCXXTypeidExpr(CXXTypeidExpr *E);
> +    void VisitCXXUuidofExpr(CXXUuidofExpr *E);
>     void VisitCXXThisExpr(CXXThisExpr *E);
>     void VisitCXXThrowExpr(CXXThrowExpr *E);
>     void VisitCXXDefaultArgExpr(CXXDefaultArgExpr *E);
> @@ -1039,6 +1040,18 @@
>   }
>  }
>
> +void ASTStmtWriter::VisitCXXUuidofExpr(CXXUuidofExpr *E) {
> +  VisitExpr(E);
> +  Writer.AddSourceRange(E->getSourceRange(), Record);
> +  if (E->isTypeOperand()) {
> +    Writer.AddTypeSourceInfo(E->getTypeOperandSourceInfo(), Record);
> +    Code = serialization::EXPR_CXX_UUIDOF_TYPE;
> +  } else {
> +    Writer.AddStmt(E->getExprOperand());
> +    Code = serialization::EXPR_CXX_UUIDOF_EXPR;
> +  }
> +}
> +
>  void ASTStmtWriter::VisitCXXThisExpr(CXXThisExpr *E) {
>   VisitExpr(E);
>   Writer.AddSourceLocation(E->getLocation(), Record);
>
> Modified: cfe/trunk/test/Parser/MicrosoftExtensions.c
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Parser/MicrosoftExtensions.c?rev=113356&r1=113355&r2=113356&view=diff
> ==============================================================================
> --- cfe/trunk/test/Parser/MicrosoftExtensions.c (original)
> +++ cfe/trunk/test/Parser/MicrosoftExtensions.c Wed Sep  8 07:20:18 2010
> @@ -1,4 +1,4 @@
> -// RUN: %clang_cc1 -triple i386-mingw32 -fsyntax-only -verify -fms-extensions -Wno-missing-declarations -x objective-c++ %s
> +// RUN: %clang_cc1 -triple i386-mingw32 -fsyntax-only -verify -fms-extensions -Wno-unused-value -Wno-missing-declarations -x objective-c++ %s
>  __stdcall int func0();
>  int __stdcall func();
>  typedef int (__cdecl *tptr)();
> @@ -36,3 +36,40 @@
>  char x = FOO(a);
>
>  typedef enum E { e1 };
> +
> +
> +void uuidof_test1()
> +{
> +  __uuidof(0);  // expected-error {{you need to include <guiddef.h> before using the '__uuidof' operator}}
> +}
> +
> +typedef struct _GUID
> +{
> +    unsigned long  Data1;
> +    unsigned short Data2;
> +    unsigned short Data3;
> +    unsigned char  Data4[8];
> +} GUID;
> +struct __declspec(uuid("00000000-0000-0000-3231-000000000046")) A { };
> +struct __declspec(uuid("00000000-0000-0000-1234-000000000047")) B { };
> +class C {};
> +
> +void uuidof_test2()
> +{
> +  A* a = new A;
> +  B b;
> +  __uuidof(A);
> +  __uuidof(*a);
> +  __uuidof(B);
> +  __uuidof(&b);
> +  _uuidof(0);
> +
> +   // FIXME, this must not compile
> +  _uuidof(1);
> +   // FIXME, this must not compile
> +  _uuidof(C);
> +
> +   C c;
> +   // FIXME, this must not compile
> +  _uuidof(c);
> +}
>
>
> _______________________________________________
> cfe-commits mailing list
> cfe-commits at cs.uiuc.edu
> http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits
>




More information about the cfe-commits mailing list