Skip to content

Conversation

@balazs-benics-sonarsource
Copy link
Contributor

This helps to gain contextual information about how we entered a CFG block.

The noexprcrash.c test probably changed due to the fact that now BlockEntrance ProgramPoint Profile also hashes the pointer of the previous CFG block. I didn't investigate.

CPP-6483

This helps to gain contextual information about how we entered
a CFG block.

The `noexprcrash.c` test probably changed due to the fact that now
BlockEntrance ProgramPoint Profile also hashes the pointer of the
previous CFG block. I didn't investigate.

CPP-6483
@llvmbot llvmbot added clang Clang issues not falling into any other category clang:analysis labels May 21, 2025
@balazs-benics-sonarsource
Copy link
Contributor Author

/cc @necto

@llvmbot
Copy link
Member

llvmbot commented May 21, 2025

@llvm/pr-subscribers-clang-analysis
@llvm/pr-subscribers-clang

@llvm/pr-subscribers-clang-static-analyzer-1

Author: Balázs Benics (balazs-benics-sonarsource)

Changes

This helps to gain contextual information about how we entered a CFG block.

The noexprcrash.c test probably changed due to the fact that now BlockEntrance ProgramPoint Profile also hashes the pointer of the previous CFG block. I didn't investigate.

CPP-6483


Full diff: https://github.com/llvm/llvm-project/pull/140861.diff

3 Files Affected:

  • (modified) clang/include/clang/Analysis/ProgramPoint.h (+12-6)
  • (modified) clang/lib/StaticAnalyzer/Core/CoreEngine.cpp (+1-1)
  • (modified) clang/test/Analysis/exploration_order/noexprcrash.c (+6-5)
diff --git a/clang/include/clang/Analysis/ProgramPoint.h b/clang/include/clang/Analysis/ProgramPoint.h
index c40aa3d8ffb72..096ad48a42984 100644
--- a/clang/include/clang/Analysis/ProgramPoint.h
+++ b/clang/include/clang/Analysis/ProgramPoint.h
@@ -224,10 +224,14 @@ class ProgramPoint {
 
 class BlockEntrance : public ProgramPoint {
 public:
-  BlockEntrance(const CFGBlock *B, const LocationContext *L,
-                const ProgramPointTag *tag = nullptr)
-    : ProgramPoint(B, BlockEntranceKind, L, tag) {
-    assert(B && "BlockEntrance requires non-null block");
+  BlockEntrance(const CFGBlock *PrevBlock, const CFGBlock *CurrBlock,
+                const LocationContext *L, const ProgramPointTag *Tag = nullptr)
+      : ProgramPoint(CurrBlock, PrevBlock, BlockEntranceKind, L, Tag) {
+    assert(CurrBlock && "BlockEntrance requires non-null block");
+  }
+
+  const CFGBlock *getPreviousBlock() const {
+    return reinterpret_cast<const CFGBlock *>(getData2());
   }
 
   const CFGBlock *getBlock() const {
@@ -760,13 +764,15 @@ template <> struct DenseMapInfo<clang::ProgramPoint> {
 static inline clang::ProgramPoint getEmptyKey() {
   uintptr_t x =
    reinterpret_cast<uintptr_t>(DenseMapInfo<void*>::getEmptyKey()) & ~0x7;
-  return clang::BlockEntrance(reinterpret_cast<clang::CFGBlock*>(x), nullptr);
+  return clang::BlockEntrance(nullptr, reinterpret_cast<clang::CFGBlock *>(x),
+                              nullptr);
 }
 
 static inline clang::ProgramPoint getTombstoneKey() {
   uintptr_t x =
    reinterpret_cast<uintptr_t>(DenseMapInfo<void*>::getTombstoneKey()) & ~0x7;
-  return clang::BlockEntrance(reinterpret_cast<clang::CFGBlock*>(x), nullptr);
+  return clang::BlockEntrance(nullptr, reinterpret_cast<clang::CFGBlock *>(x),
+                              nullptr);
 }
 
 static unsigned getHashValue(const clang::ProgramPoint &Loc) {
diff --git a/clang/lib/StaticAnalyzer/Core/CoreEngine.cpp b/clang/lib/StaticAnalyzer/Core/CoreEngine.cpp
index 8cc086a12ad70..bedb11f8b94a5 100644
--- a/clang/lib/StaticAnalyzer/Core/CoreEngine.cpp
+++ b/clang/lib/StaticAnalyzer/Core/CoreEngine.cpp
@@ -315,7 +315,7 @@ void CoreEngine::HandleBlockEdge(const BlockEdge &L, ExplodedNode *Pred) {
 
   // Call into the ExprEngine to process entering the CFGBlock.
   ExplodedNodeSet dstNodes;
-  BlockEntrance BE(Blk, Pred->getLocationContext());
+  BlockEntrance BE(L.getSrc(), L.getDst(), Pred->getLocationContext());
   NodeBuilderWithSinks nodeBuilder(Pred, dstNodes, BuilderCtx, BE);
   ExprEng.processCFGBlockEntrance(L, nodeBuilder, Pred);
 
diff --git a/clang/test/Analysis/exploration_order/noexprcrash.c b/clang/test/Analysis/exploration_order/noexprcrash.c
index 75c2f0e6798a3..427c669783374 100644
--- a/clang/test/Analysis/exploration_order/noexprcrash.c
+++ b/clang/test/Analysis/exploration_order/noexprcrash.c
@@ -1,17 +1,18 @@
-// RUN: %clang_analyze_cc1 -analyzer-checker=core,debug.ExprInspection -verify -analyzer-config exploration_strategy=unexplored_first %s
-// RUN: %clang_analyze_cc1 -analyzer-checker=core,debug.ExprInspection -verify -analyzer-config exploration_strategy=dfs %s
+// RUN: %clang_analyze_cc1 -analyzer-checker=core,debug.ExprInspection -verify=common,ufirst -analyzer-config exploration_strategy=unexplored_first %s
+// RUN: %clang_analyze_cc1 -analyzer-checker=core,debug.ExprInspection -verify=common,dfs -analyzer-config exploration_strategy=dfs %s
 
 extern void clang_analyzer_eval(int);
 
 typedef struct { char a; } b;
 int c(b* input) {
-    int x = (input->a ?: input) ? 1 : 0; // expected-warning{{pointer/integer type mismatch}}
+    int x = (input->a ?: input) ? 1 : 0; // common-warning{{pointer/integer type mismatch}}
     if (input->a) {
       // FIXME: The value should actually be "TRUE",
       // but is incorrect due to a bug.
-      clang_analyzer_eval(x); // expected-warning{{FALSE}}
+      // dfs-warning@+1 {{FALSE}} ufirst-warning@+1 {{TRUE}}
+      clang_analyzer_eval(x);
     } else {
-      clang_analyzer_eval(x); // expected-warning{{TRUE}}
+      clang_analyzer_eval(x); // common-warning{{TRUE}}
     }
     return x;
 }

Copy link
Contributor

@NagyDonat NagyDonat left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM, straightforward simple extension.

@balazs-benics-sonarsource balazs-benics-sonarsource merged commit 8818728 into llvm:main May 21, 2025
15 checks passed
@balazs-benics-sonarsource balazs-benics-sonarsource deleted the bb/upstream-improve-blockentrances branch May 21, 2025 11:33
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

clang:analysis clang:static analyzer clang Clang issues not falling into any other category

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants