]> granicus.if.org Git - clang/commitdiff
Add AST/Sema support for __builtin_types_compatible_p (a GNU extension).
authorSteve Naroff <snaroff@apple.com>
Wed, 1 Aug 2007 22:05:33 +0000 (22:05 +0000)
committerSteve Naroff <snaroff@apple.com>
Wed, 1 Aug 2007 22:05:33 +0000 (22:05 +0000)
Todo...still need to call the action from the parser...

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@40693 91177308-0d34-0410-b5e6-96231b3b80d8

AST/StmtPrinter.cpp
Parse/ParseExpr.cpp
Sema/Sema.h
Sema/SemaExpr.cpp
include/clang/AST/Expr.h
include/clang/AST/StmtNodes.def
include/clang/Parse/Action.h

index 18f605be922fe80311ab1eb59eb884888931de06..9ca17836d1bdb1d3ff92c4971d820f6ac3248f3f 100644 (file)
@@ -481,6 +481,12 @@ void StmtPrinter::VisitStmtExpr(StmtExpr *E) {
   OS << ")";
 }
 
+void StmtPrinter::VisitTypesCompatibleExpr(TypesCompatibleExpr *Node) {
+  OS << "__builtin_types_compatible_p(";
+  OS << Node->getArgType1().getAsString() << ",";
+  OS << Node->getArgType2().getAsString() << ")";
+}
+
 
 // C++
 
index de0a2a2d6774c5e5a216a36182c1cc436fa634da..15aca621792907b1f6fe99c00cca1f476805c001 100644 (file)
@@ -819,12 +819,12 @@ Parser::ExprResult Parser::ParseBuiltinPrimaryExpression() {
     Res = ParseAssignmentExpression();
     break;
   case tok::kw___builtin_types_compatible_p:
-    ParseTypeName();
+    TypeTy *Type1 = ParseTypeName();
     
     if (ExpectAndConsume(tok::comma, diag::err_expected_comma, "",tok::r_paren))
       return ExprResult(true);
     
-    ParseTypeName();
+    TypeTy *Type2 = ParseTypeName();
     break;
   }      
   
index ea724ab44b2e05c406032c99cfd6735acfe4c489..86378a4f06c74d0d0ec2ccc44a318833f27e0231 100644 (file)
@@ -280,6 +280,11 @@ public:
   
   virtual ExprResult ParseStmtExpr(SourceLocation LPLoc, StmtTy *SubStmt,
                                    SourceLocation RPLoc); // "({..})"
+                                   
+  // __builtin_types_compatible_p(type1, type2)
+  virtual ExprResult ParseTypesCompatibleExpr(SourceLocation LPLoc, 
+                                              TypeTy *arg1, TypeTy *arg2,
+                                              SourceLocation RPLoc);
   
   /// ParseCXXCasts - Parse {dynamic,static,reinterpret,const}_cast's.
   virtual ExprResult ParseCXXCasts(SourceLocation OpLoc, tok::TokenKind Kind,
index 1570f4a8e2f48dff7743e20aecbcdf72a2ec05dd..9ef2e679901dc1be543ef3e67439c848f786479d 100644 (file)
@@ -1565,3 +1565,15 @@ Sema::ExprResult Sema::ParseStmtExpr(SourceLocation LPLoc, StmtTy *substmt,
   
   return new StmtExpr(Compound, Ty, LPLoc, RPLoc);
 }
+
+Sema::ExprResult Sema::ParseTypesCompatibleExpr(SourceLocation LPLoc, 
+                                                TypeTy *arg1, TypeTy *arg2,
+                                                SourceLocation RPLoc) {
+  QualType argT1 = QualType::getFromOpaquePtr(arg1);
+  QualType argT2 = QualType::getFromOpaquePtr(arg2);
+  
+  assert((!argT1.isNull() && !argT2.isNull()) && "Missing type argument(s)");
+  
+  return new TypesCompatibleExpr(Context.IntTy, LPLoc, argT1, argT2, RPLoc);
+}
+
index 01917dc7a34c6fda25231ba45ae0294b1a7707bc..568d3e02b7c1225e56e8a6a00b178c18d8e564c6 100644 (file)
@@ -703,10 +703,9 @@ class StmtExpr : public Expr {
   CompoundStmt *SubStmt;
   SourceLocation LParenLoc, RParenLoc;
 public:
-    StmtExpr(CompoundStmt *substmt, QualType T,
-             SourceLocation lp, SourceLocation rp)
-    : Expr(StmtExprClass, T), SubStmt(substmt),  LParenLoc(lp), RParenLoc(rp) {
-    }
+  StmtExpr(CompoundStmt *substmt, QualType T,
+           SourceLocation lp, SourceLocation rp) :
+    Expr(StmtExprClass, T), SubStmt(substmt),  LParenLoc(lp), RParenLoc(rp) { }
   
   CompoundStmt *getSubStmt() { return SubStmt; }
   const CompoundStmt *getSubStmt() const { return SubStmt; }
@@ -722,6 +721,33 @@ public:
   static bool classof(const StmtExpr *) { return true; }
 };
 
+/// TypesCompatibleExpr - GNU builtin-in function __builtin_type_compatible_p.
+/// This AST node represents a function that returns 1 if two *types* (not
+/// expressions) are compatible. The result of this built-in function can be
+/// used in integer constant expressions.
+class TypesCompatibleExpr : public Expr {
+  QualType Type1;
+  QualType Type2;
+  SourceLocation LParenLoc, RParenLoc;
+public:
+  TypesCompatibleExpr(QualType ReturnType, SourceLocation LP, 
+                      QualType t1, QualType t2, SourceLocation RP) : 
+    Expr(TypesCompatibleExprClass, ReturnType), Type1(t1), Type2(t2),
+    LParenLoc(LP), RParenLoc(RP) {}
+
+  QualType getArgType1() { return Type1; }
+  QualType getArgType2() { return Type2; }
+    
+  virtual SourceRange getSourceRange() const {
+    return SourceRange(LParenLoc, RParenLoc);
+  }
+  virtual void visit(StmtVisitor &Visitor);
+  static bool classof(const Stmt *T) {
+    return T->getStmtClass() == TypesCompatibleExprClass; 
+  }
+  static bool classof(const TypesCompatibleExpr *) { return true; }
+};
+
 }  // end namespace clang
 
 #endif
index 4335b51469a5bcd5d0ad6d1ca179b126c74c17a3..375a52bc0dde4bdf8d731c33255d6b3f0c112fca 100644 (file)
@@ -67,11 +67,12 @@ STMT(49, OCUVectorComponent   , Expr)
 // GNU Extensions.
 STMT(50, AddrLabel            , Expr)
 STMT(51, StmtExpr             , Expr)
+STMT(52, TypesCompatibleExpr  , Expr)
 
 // C++ Expressions.
-STMT(52, CXXCastExpr          , Expr)
-STMT(53, CXXBoolLiteralExpr   , Expr)
-LAST_EXPR(53)
+STMT(53, CXXCastExpr          , Expr)
+STMT(54, CXXBoolLiteralExpr   , Expr)
+LAST_EXPR(54)
 
 #undef STMT
 #undef FIRST_STMT
index d9e3e12c4c69a4e45a43132635732283ad8b8f56..c019a0b22c14da856f8bb6da09188546b7e3b868 100644 (file)
@@ -375,6 +375,12 @@ public:
                                    SourceLocation RPLoc) { // "({..})"
     return 0;
   }
+  // __builtin_types_compatible_p(type1, type2)
+  virtual ExprResult ParseTypesCompatibleExpr(SourceLocation LPLoc, 
+                                              TypeTy *arg1, TypeTy *arg2,
+                                              SourceLocation RPLoc) {
+    return 0;
+  }
 
   //===------------------------- C++ Expressions --------------------------===//