r182880 - [analyzer] Accept references to variables declared "extern void" (C only).

Jordan Rose jordan_rose at apple.com
Wed May 29 13:50:34 PDT 2013


Author: jrose
Date: Wed May 29 15:50:34 2013
New Revision: 182880

URL: http://llvm.org/viewvc/llvm-project?rev=182880&view=rev
Log:
[analyzer] Accept references to variables declared "extern void" (C only).

In C, 'void' is treated like any other incomplete type, and though it is
never completed, you can cast the address of a void-typed variable to do
something useful. (In C++ it's illegal to declare a variable with void type.)

Previously we asserted on this code; now we just treat it like any other
incomplete type.

And speaking of incomplete types, we don't know their extent. Actually
check that in TypedValueRegion::getExtent, though that's not being used
by any checkers that are on by default.

Modified:
    cfe/trunk/lib/StaticAnalyzer/Core/ExprEngine.cpp
    cfe/trunk/lib/StaticAnalyzer/Core/MemRegion.cpp
    cfe/trunk/test/Analysis/misc-ps.c
    cfe/trunk/test/Analysis/out-of-bounds.c

Modified: cfe/trunk/lib/StaticAnalyzer/Core/ExprEngine.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/StaticAnalyzer/Core/ExprEngine.cpp?rev=182880&r1=182879&r2=182880&view=diff
==============================================================================
--- cfe/trunk/lib/StaticAnalyzer/Core/ExprEngine.cpp (original)
+++ cfe/trunk/lib/StaticAnalyzer/Core/ExprEngine.cpp Wed May 29 15:50:34 2013
@@ -1613,7 +1613,9 @@ void ExprEngine::VisitCommonDeclRefExpr(
   const LocationContext *LCtx = Pred->getLocationContext();
 
   if (const VarDecl *VD = dyn_cast<VarDecl>(D)) {
-    assert(Ex->isGLValue());
+    // C permits "extern void v", and if you cast the address to a valid type,
+    // you can even do things with it. We simply pretend 
+    assert(Ex->isGLValue() || VD->getType()->isVoidType());
     SVal V = state->getLValue(VD, Pred->getLocationContext());
 
     // For references, the 'lvalue' is the pointer address stored in the

Modified: cfe/trunk/lib/StaticAnalyzer/Core/MemRegion.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/StaticAnalyzer/Core/MemRegion.cpp?rev=182880&r1=182879&r2=182880&view=diff
==============================================================================
--- cfe/trunk/lib/StaticAnalyzer/Core/MemRegion.cpp (original)
+++ cfe/trunk/lib/StaticAnalyzer/Core/MemRegion.cpp Wed May 29 15:50:34 2013
@@ -186,7 +186,7 @@ DefinedOrUnknownSVal TypedValueRegion::g
 
   if (isa<VariableArrayType>(T))
     return nonloc::SymbolVal(svalBuilder.getSymbolManager().getExtentSymbol(this));
-  if (isa<IncompleteArrayType>(T))
+  if (T->isIncompleteType())
     return UnknownVal();
 
   CharUnits size = Ctx.getTypeSizeInChars(T);

Modified: cfe/trunk/test/Analysis/misc-ps.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Analysis/misc-ps.c?rev=182880&r1=182879&r2=182880&view=diff
==============================================================================
--- cfe/trunk/test/Analysis/misc-ps.c (original)
+++ cfe/trunk/test/Analysis/misc-ps.c Wed May 29 15:50:34 2013
@@ -1,4 +1,6 @@
-// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -analyze -disable-free -analyzer-eagerly-assume -analyzer-checker=core -analyzer-checker=deadcode -verify %s
+// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -analyze -disable-free -analyzer-eagerly-assume -analyzer-checker=core,deadcode,debug.ExprInspection -verify %s
+
+void clang_analyzer_eval(int);
 
 int size_rdar9373039 = 1;
 int foo_rdar9373039(const char *);
@@ -175,3 +177,17 @@ void sinkAfterRegularNode(struct PR15684
   context->callback(uninitialized); // expected-warning {{uninitialized}}
 }
 
+
+// PR16131: C permits variables to be declared extern void.
+static void PR16131(int x) {
+  extern void v;
+
+  int *ip = (int *)&v;
+  char *cp = (char *)&v;
+  clang_analyzer_eval(ip == cp); // expected-warning{{TRUE}}
+  // expected-warning at -1 {{comparison of distinct pointer types}}
+
+  *ip = 42;
+  clang_analyzer_eval(*ip == 42); // expected-warning{{TRUE}}
+  clang_analyzer_eval(*(int *)&v == 42); // expected-warning{{TRUE}}
+}

Modified: cfe/trunk/test/Analysis/out-of-bounds.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Analysis/out-of-bounds.c?rev=182880&r1=182879&r2=182880&view=diff
==============================================================================
--- cfe/trunk/test/Analysis/out-of-bounds.c (original)
+++ cfe/trunk/test/Analysis/out-of-bounds.c Wed May 29 15:50:34 2013
@@ -154,3 +154,15 @@ void test_index_below_symboloc() {
   buf[-1] = 0; // no-warning;
 }
 
+void test_incomplete_struct() {
+  extern struct incomplete incomplete;
+  int *p = (int *)&incomplete;
+  p[1] = 42; // no-warning
+}
+
+void test_extern_void() {
+  extern void v;
+  int *p = (int *)&v;
+  p[1] = 42; // no-warning
+}
+





More information about the cfe-commits mailing list