xazax.hun created this revision.
Herald added subscribers: baloghadamsoftware, whisperity.

This patch attempts to fix PR34451.

The `getBestDynamicClassType` call can only handle `RecordDecls` and pointers 
to `RecordDecls`. The code removed all the implicit casts, this includes the 
array to pointer decay. After removing the decay, the checker passed an array 
type to `getBestDynamicClassType` which triggered the assertion.


Repository:
  rL LLVM

https://reviews.llvm.org/D37978

Files:
  lib/StaticAnalyzer/Checkers/VirtualCallChecker.cpp
  test/Analysis/virtualcall.cpp


Index: test/Analysis/virtualcall.cpp
===================================================================
--- test/Analysis/virtualcall.cpp
+++ test/Analysis/virtualcall.cpp
@@ -271,3 +271,24 @@
 #if !PUREONLY
        //expected-note-re@-2 2{{{{^}}Calling '~E'}}
 #endif
+
+namespace PR34451 {
+struct a {
+  void b() {
+    a c[1];
+    c->b();
+  }
+};
+
+class e {
+ public:
+  void b() const;
+};
+
+class c {
+  void m_fn2() const;
+  e d[];
+};
+
+void c::m_fn2() const { d->b(); }
+}
Index: lib/StaticAnalyzer/Checkers/VirtualCallChecker.cpp
===================================================================
--- lib/StaticAnalyzer/Checkers/VirtualCallChecker.cpp
+++ lib/StaticAnalyzer/Checkers/VirtualCallChecker.cpp
@@ -146,7 +146,7 @@
     if (CME->getQualifier())
       CallIsNonVirtual = true;
 
-    if (const Expr *Base = CME->getBase()->IgnoreImpCasts()) {
+    if (const Expr *Base = CME->getBase()) {
       // The most derived class is marked final.
       if (Base->getBestDynamicClassType()->hasAttr<FinalAttr>())
         CallIsNonVirtual = true;


Index: test/Analysis/virtualcall.cpp
===================================================================
--- test/Analysis/virtualcall.cpp
+++ test/Analysis/virtualcall.cpp
@@ -271,3 +271,24 @@
 #if !PUREONLY
 	//expected-note-re@-2 2{{{{^}}Calling '~E'}}
 #endif
+
+namespace PR34451 {
+struct a {
+  void b() {
+    a c[1];
+    c->b();
+  }
+};
+
+class e {
+ public:
+  void b() const;
+};
+
+class c {
+  void m_fn2() const;
+  e d[];
+};
+
+void c::m_fn2() const { d->b(); }
+}
Index: lib/StaticAnalyzer/Checkers/VirtualCallChecker.cpp
===================================================================
--- lib/StaticAnalyzer/Checkers/VirtualCallChecker.cpp
+++ lib/StaticAnalyzer/Checkers/VirtualCallChecker.cpp
@@ -146,7 +146,7 @@
     if (CME->getQualifier())
       CallIsNonVirtual = true;
 
-    if (const Expr *Base = CME->getBase()->IgnoreImpCasts()) {
+    if (const Expr *Base = CME->getBase()) {
       // The most derived class is marked final.
       if (Base->getBestDynamicClassType()->hasAttr<FinalAttr>())
         CallIsNonVirtual = true;
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to