[cfe-commits] r120093 - in /cfe/trunk: include/clang/Analysis/AnalysisContext.h include/clang/Checker/PathSensitive/AnalysisManager.h include/clang/Checker/PathSensitive/GRExprEngine.h lib/Analysis/AnalysisContext.cpp lib/Checker/AggExprVisitor.cpp lib/Checker/Environment.cpp lib/Checker/GRCXXExprEngine.cpp lib/Checker/GRCoreEngine.cpp lib/Checker/GRExprEngine.cpp

Zhongxing Xu xuzhongxing at gmail.com
Wed Nov 24 05:08:52 PST 2010


Author: zhongxingxu
Date: Wed Nov 24 07:08:51 2010
New Revision: 120093

URL: http://llvm.org/viewvc/llvm-project?rev=120093&view=rev
Log:
Let StackFrameContext represent if the call expr is evaluated as lvalue.
This is required for supporting const reference to temporary objects.

Modified:
    cfe/trunk/include/clang/Analysis/AnalysisContext.h
    cfe/trunk/include/clang/Checker/PathSensitive/AnalysisManager.h
    cfe/trunk/include/clang/Checker/PathSensitive/GRExprEngine.h
    cfe/trunk/lib/Analysis/AnalysisContext.cpp
    cfe/trunk/lib/Checker/AggExprVisitor.cpp
    cfe/trunk/lib/Checker/Environment.cpp
    cfe/trunk/lib/Checker/GRCXXExprEngine.cpp
    cfe/trunk/lib/Checker/GRCoreEngine.cpp
    cfe/trunk/lib/Checker/GRExprEngine.cpp

Modified: cfe/trunk/include/clang/Analysis/AnalysisContext.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Analysis/AnalysisContext.h?rev=120093&r1=120092&r2=120093&view=diff
==============================================================================
--- cfe/trunk/include/clang/Analysis/AnalysisContext.h (original)
+++ cfe/trunk/include/clang/Analysis/AnalysisContext.h Wed Nov 24 07:08:51 2010
@@ -198,8 +198,9 @@
 };
 
 class StackFrameContext : public LocationContext {
-  // The callsite where this stack frame is established.
-  const Stmt *CallSite;
+  // The callsite where this stack frame is established. The int bit indicates
+  // whether the call expr should return an l-value when it has reference type.
+  llvm::PointerIntPair<const Stmt *, 1> CallSite;
 
   // The parent block of the callsite.
   const CFGBlock *Block;
@@ -209,14 +210,17 @@
 
   friend class LocationContextManager;
   StackFrameContext(AnalysisContext *ctx, const LocationContext *parent,
-                    const Stmt *s, const CFGBlock *blk, unsigned idx)
-    : LocationContext(StackFrame, ctx, parent), CallSite(s), Block(blk),
-      Index(idx) {}
+                    const Stmt *s, bool asLValue, const CFGBlock *blk, 
+                    unsigned idx)
+    : LocationContext(StackFrame, ctx, parent), CallSite(s, asLValue), 
+      Block(blk), Index(idx) {}
 
 public:
   ~StackFrameContext() {}
 
-  const Stmt *getCallSite() const { return CallSite; }
+  const Stmt *getCallSite() const { return CallSite.getPointer(); }
+
+  bool evalAsLValue() const { return CallSite.getInt(); }
 
   const CFGBlock *getCallSiteBlock() const { return Block; }
 
@@ -226,8 +230,9 @@
 
   static void Profile(llvm::FoldingSetNodeID &ID, AnalysisContext *ctx,
                       const LocationContext *parent, const Stmt *s,
-                      const CFGBlock *blk, unsigned idx) {
+                      bool asLValue, const CFGBlock *blk, unsigned idx) {
     ProfileCommon(ID, StackFrame, ctx, parent, s);
+    ID.AddBoolean(asLValue);
     ID.AddPointer(blk);
     ID.AddInteger(idx);
   }
@@ -295,8 +300,8 @@
 
   const StackFrameContext *getStackFrame(AnalysisContext *ctx,
                                          const LocationContext *parent,
-                                         const Stmt *s, const CFGBlock *blk,
-                                         unsigned idx);
+                                         const Stmt *s, bool asLValue,
+                                         const CFGBlock *blk, unsigned idx);
 
   const ScopeContext *getScope(AnalysisContext *ctx,
                                const LocationContext *parent,

Modified: cfe/trunk/include/clang/Checker/PathSensitive/AnalysisManager.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Checker/PathSensitive/AnalysisManager.h?rev=120093&r1=120092&r2=120093&view=diff
==============================================================================
--- cfe/trunk/include/clang/Checker/PathSensitive/AnalysisManager.h (original)
+++ cfe/trunk/include/clang/Checker/PathSensitive/AnalysisManager.h Wed Nov 24 07:08:51 2010
@@ -178,23 +178,24 @@
 
   const StackFrameContext *getStackFrame(AnalysisContext *Ctx,
                                          LocationContext const *Parent,
-                                         Stmt const *S, const CFGBlock *Blk,
-                                         unsigned Idx) {
-    return LocCtxMgr.getStackFrame(Ctx, Parent, S, Blk, Idx);
+                                         const Stmt *S, bool asLValue,
+                                         const CFGBlock *Blk, unsigned Idx) {
+    return LocCtxMgr.getStackFrame(Ctx, Parent, S, asLValue, Blk, Idx);
   }
 
   // Get the top level stack frame.
   const StackFrameContext *getStackFrame(Decl const *D, 
                                          idx::TranslationUnit *TU) {
-    return LocCtxMgr.getStackFrame(AnaCtxMgr.getContext(D, TU), 0, 0, 0, 0);
+    return LocCtxMgr.getStackFrame(AnaCtxMgr.getContext(D, TU), 0, 0, 0, 0, 0);
   }
 
   // Get a stack frame with parent.
-  StackFrameContext const *getStackFrame(Decl const *D, 
+  StackFrameContext const *getStackFrame(const Decl *D, 
                                          LocationContext const *Parent,
-                                         Stmt const *S, const CFGBlock *Blk,
-                                         unsigned Idx) {
-    return LocCtxMgr.getStackFrame(AnaCtxMgr.getContext(D), Parent, S, Blk,Idx);
+                                         const Stmt *S, bool asLValue,
+                                         const CFGBlock *Blk, unsigned Idx) {
+    return LocCtxMgr.getStackFrame(AnaCtxMgr.getContext(D), Parent, S, asLValue,
+                                   Blk,Idx);
   }
 };
 

Modified: cfe/trunk/include/clang/Checker/PathSensitive/GRExprEngine.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Checker/PathSensitive/GRExprEngine.h?rev=120093&r1=120092&r2=120093&view=diff
==============================================================================
--- cfe/trunk/include/clang/Checker/PathSensitive/GRExprEngine.h (original)
+++ cfe/trunk/include/clang/Checker/PathSensitive/GRExprEngine.h Wed Nov 24 07:08:51 2010
@@ -424,9 +424,16 @@
 
   void VisitCXXThisExpr(const CXXThisExpr *TE, ExplodedNode *Pred, 
                         ExplodedNodeSet & Dst);
-  
+
+  void VisitCXXTemporaryObjectExpr(const CXXTemporaryObjectExpr *expr,
+                                   ExplodedNode *Pred, ExplodedNodeSet &Dst, 
+                                   bool asLValue) {
+    VisitCXXConstructExpr(expr, 0, Pred, Dst, asLValue);
+  }
+
   void VisitCXXConstructExpr(const CXXConstructExpr *E, const MemRegion *Dest,
-                             ExplodedNode *Pred, ExplodedNodeSet &Dst);
+                             ExplodedNode *Pred, ExplodedNodeSet &Dst, 
+                             bool asLValue);
 
   void VisitCXXDestructor(const CXXDestructorDecl *DD,
                           const MemRegion *Dest, const Stmt *S,

Modified: cfe/trunk/lib/Analysis/AnalysisContext.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Analysis/AnalysisContext.cpp?rev=120093&r1=120092&r2=120093&view=diff
==============================================================================
--- cfe/trunk/lib/Analysis/AnalysisContext.cpp (original)
+++ cfe/trunk/lib/Analysis/AnalysisContext.cpp Wed Nov 24 07:08:51 2010
@@ -152,7 +152,8 @@
 }
 
 void StackFrameContext::Profile(llvm::FoldingSetNodeID &ID) {
-  Profile(ID, getAnalysisContext(), getParent(), CallSite, Block, Index);
+  Profile(ID, getAnalysisContext(), getParent(), CallSite.getPointer(),
+          CallSite.getInt(), Block, Index);
 }
 
 void ScopeContext::Profile(llvm::FoldingSetNodeID &ID) {
@@ -188,15 +189,15 @@
 const StackFrameContext*
 LocationContextManager::getStackFrame(AnalysisContext *ctx,
                                       const LocationContext *parent,
-                                      const Stmt *s, const CFGBlock *blk,
-                                      unsigned idx) {
+                                      const Stmt *s, bool asLValue,
+                                      const CFGBlock *blk, unsigned idx) {
   llvm::FoldingSetNodeID ID;
-  StackFrameContext::Profile(ID, ctx, parent, s, blk, idx);
+  StackFrameContext::Profile(ID, ctx, parent, s, asLValue, blk, idx);
   void *InsertPos;
   StackFrameContext *L =
    cast_or_null<StackFrameContext>(Contexts.FindNodeOrInsertPos(ID, InsertPos));
   if (!L) {
-    L = new StackFrameContext(ctx, parent, s, blk, idx);
+    L = new StackFrameContext(ctx, parent, s, asLValue, blk, idx);
     Contexts.InsertNode(L, InsertPos);
   }
   return L;

Modified: cfe/trunk/lib/Checker/AggExprVisitor.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Checker/AggExprVisitor.cpp?rev=120093&r1=120092&r2=120093&view=diff
==============================================================================
--- cfe/trunk/lib/Checker/AggExprVisitor.cpp (original)
+++ cfe/trunk/lib/Checker/AggExprVisitor.cpp Wed Nov 24 07:08:51 2010
@@ -53,7 +53,7 @@
 }
 
 void AggExprVisitor::VisitCXXConstructExpr(CXXConstructExpr *E) {
-  Eng.VisitCXXConstructExpr(E, Dest, Pred, DstSet);
+  Eng.VisitCXXConstructExpr(E, Dest, Pred, DstSet, false);
 }
 
 void GRExprEngine::VisitAggExpr(const Expr *E, const MemRegion *Dest, 

Modified: cfe/trunk/lib/Checker/Environment.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Checker/Environment.cpp?rev=120093&r1=120092&r2=120093&view=diff
==============================================================================
--- cfe/trunk/lib/Checker/Environment.cpp (original)
+++ cfe/trunk/lib/Checker/Environment.cpp Wed Nov 24 07:08:51 2010
@@ -65,11 +65,22 @@
         if (CT->isVoidType())
           return UnknownVal();
 
+        if (C->getCastKind() == CK_NoOp) {
+          E = C->getSubExpr();
+          continue;
+        }
         break;
       }
 
-        // Handle all other Stmt* using a lookup.
-
+      case Stmt::CXXExprWithTemporariesClass:
+        E = cast<CXXExprWithTemporaries>(E)->getSubExpr();
+        continue;
+
+      case Stmt::CXXBindTemporaryExprClass:
+        E = cast<CXXBindTemporaryExpr>(E)->getSubExpr();
+        continue;
+        
+      // Handle all other Stmt* using a lookup.
       default:
         break;
     };

Modified: cfe/trunk/lib/Checker/GRCXXExprEngine.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Checker/GRCXXExprEngine.cpp?rev=120093&r1=120092&r2=120093&view=diff
==============================================================================
--- cfe/trunk/lib/Checker/GRCXXExprEngine.cpp (original)
+++ cfe/trunk/lib/Checker/GRCXXExprEngine.cpp Wed Nov 24 07:08:51 2010
@@ -100,7 +100,7 @@
 void GRExprEngine::VisitCXXConstructExpr(const CXXConstructExpr *E, 
                                          const MemRegion *Dest,
                                          ExplodedNode *Pred,
-                                         ExplodedNodeSet &Dst) {
+                                         ExplodedNodeSet &Dst, bool asLValue) {
   if (!Dest)
     Dest = ValMgr.getRegionManager().getCXXObjectRegion(E,
                                                     Pred->getLocationContext());
@@ -125,7 +125,7 @@
   // The callee stack frame context used to create the 'this' parameter region.
   const StackFrameContext *SFC = AMgr.getStackFrame(CD, 
                                                     Pred->getLocationContext(),
-                                   E, Builder->getBlock(), Builder->getIndex());
+                        E, asLValue, Builder->getBlock(), Builder->getIndex());
 
   const CXXThisRegion *ThisR =getCXXThisRegion(E->getConstructor()->getParent(),
                                                SFC);
@@ -153,7 +153,7 @@
   // Create the context for 'this' region.
   const StackFrameContext *SFC = AMgr.getStackFrame(DD,
                                                     Pred->getLocationContext(),
-                                                    S, Builder->getBlock(),
+                                                 S, false, Builder->getBlock(),
                                                     Builder->getIndex());
 
   const CXXThisRegion *ThisR = getCXXThisRegion(DD->getParent(), SFC);
@@ -239,7 +239,7 @@
 
   const StackFrameContext *SFC = AMgr.getStackFrame(MD, 
                                                     Pred->getLocationContext(),
-                                                    MCE, 
+                                                    MCE, false,
                                                     Builder->getBlock(), 
                                                     Builder->getIndex());
   const CXXThisRegion *ThisR = getCXXThisRegion(MD->getParent(), SFC);

Modified: cfe/trunk/lib/Checker/GRCoreEngine.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Checker/GRCoreEngine.cpp?rev=120093&r1=120092&r2=120093&view=diff
==============================================================================
--- cfe/trunk/lib/Checker/GRCoreEngine.cpp (original)
+++ cfe/trunk/lib/Checker/GRCoreEngine.cpp Wed Nov 24 07:08:51 2010
@@ -758,7 +758,7 @@
     const StackFrameContext *OldLocCtx = CalleeCtx;
     const StackFrameContext *NewLocCtx = AMgr.getStackFrame(NewAnaCtx, 
                                                OldLocCtx->getParent(),
-                                               OldLocCtx->getCallSite(),
+                                               OldLocCtx->getCallSite(), false,
                                                OldLocCtx->getCallSiteBlock(), 
                                                OldLocCtx->getIndex());
 

Modified: cfe/trunk/lib/Checker/GRExprEngine.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Checker/GRExprEngine.cpp?rev=120093&r1=120092&r2=120093&view=diff
==============================================================================
--- cfe/trunk/lib/Checker/GRExprEngine.cpp (original)
+++ cfe/trunk/lib/Checker/GRExprEngine.cpp Wed Nov 24 07:08:51 2010
@@ -918,7 +918,7 @@
       const CXXConstructExpr *C = cast<CXXConstructExpr>(S);
       // For block-level CXXConstructExpr, we don't have a destination region.
       // Let VisitCXXConstructExpr() create one.
-      VisitCXXConstructExpr(C, 0, Pred, Dst);
+      VisitCXXConstructExpr(C, 0, Pred, Dst, false);
       break;
     }
 
@@ -1117,7 +1117,6 @@
 
   switch (Ex->getStmtClass()) {
     // C++ stuff we don't support yet.
-    case Stmt::CXXExprWithTemporariesClass:
     case Stmt::CXXMemberCallExprClass:
     case Stmt::CXXScalarValueInitExprClass: {
       SaveAndRestore<bool> OldSink(Builder->BuildSinks);
@@ -1147,6 +1146,24 @@
       break;
     }
 
+    case Stmt::CXXExprWithTemporariesClass: {
+      const CXXExprWithTemporaries *expr = cast<CXXExprWithTemporaries>(Ex);
+      VisitLValue(expr->getSubExpr(), Pred, Dst);
+      break;
+    }
+
+    case Stmt::CXXBindTemporaryExprClass: {
+      const CXXBindTemporaryExpr *expr = cast<CXXBindTemporaryExpr>(Ex);
+      VisitLValue(expr->getSubExpr(), Pred, Dst);
+      break;
+    }
+
+    case Stmt::CXXTemporaryObjectExprClass: {
+      const CXXTemporaryObjectExpr *expr = cast<CXXTemporaryObjectExpr>(Ex);
+      VisitCXXTemporaryObjectExpr(expr, Pred, Dst, true);
+      break;
+    }
+
     case Stmt::CompoundLiteralExprClass:
       VisitCompoundLiteralExpr(cast<CompoundLiteralExpr>(Ex), Pred, Dst, true);
       return;
@@ -1643,11 +1660,13 @@
   if (const CXXConstructExpr *CCE = dyn_cast<CXXConstructExpr>(CE)) {
     const CXXThisRegion *ThisR =
       getCXXThisRegion(CCE->getConstructor()->getParent(), calleeCtx);
-    // We might not have 'this' region in the binding if we didn't inline
-    // the ctor call.
+
     SVal ThisV = state->getSVal(ThisR);
-    loc::MemRegionVal *V = dyn_cast<loc::MemRegionVal>(&ThisV);
-    if (V) {
+
+    if (calleeCtx->evalAsLValue()) {
+      state = state->BindExpr(CCE, ThisV);
+    } else {
+      loc::MemRegionVal *V = cast<loc::MemRegionVal>(&ThisV);
       SVal ObjVal = state->getSVal(V->getRegion());
       assert(isa<nonloc::LazyCompoundVal>(ObjVal));
       state = state->BindExpr(CCE, ObjVal);
@@ -2073,7 +2092,7 @@
     const StackFrameContext *stackFrame = 
       AMgr.getStackFrame(AMgr.getAnalysisContext(FD), 
                          Pred->getLocationContext(),
-                         CE, Builder->getBlock(), Builder->getIndex());
+                         CE, false, Builder->getBlock(), Builder->getIndex());
     // Now we have the definition of the callee, create a CallEnter node.
     CallEnter Loc(CE, stackFrame, Pred->getLocationContext());
 
@@ -2089,7 +2108,7 @@
       return false;
     const StackFrameContext *stackFrame = 
       AMgr.getStackFrame(C, Pred->getLocationContext(),
-                         CE, Builder->getBlock(), Builder->getIndex());
+                         CE, false, Builder->getBlock(), Builder->getIndex());
     CallEnter Loc(CE, stackFrame, Pred->getLocationContext());
     ExplodedNode *N = Builder->generateNode(Loc, state, Pred);
     Dst.Add(N);





More information about the cfe-commits mailing list