[cfe-commits] r110082 - in /cfe/trunk: include/clang/Basic/DiagnosticSemaKinds.td lib/Sema/JumpDiagnostics.cpp test/Sema/scope-check.c test/SemaCXX/scope-check.cpp

John McCall rjmccall at apple.com
Mon Aug 2 16:33:14 PDT 2010


Author: rjmccall
Date: Mon Aug  2 18:33:14 2010
New Revision: 110082

URL: http://llvm.org/viewvc/llvm-project?rev=110082&view=rev
Log:
Labels (and case statement) don't create independent scope parents for the
purposes of the jump checker.  Also extend Ted's iteration fix to labels.

Fixes PR7789.


Modified:
    cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td
    cfe/trunk/lib/Sema/JumpDiagnostics.cpp
    cfe/trunk/test/Sema/scope-check.c
    cfe/trunk/test/SemaCXX/scope-check.cpp

Modified: cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td?rev=110082&r1=110081&r2=110082&view=diff
==============================================================================
--- cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td (original)
+++ cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td Mon Aug  2 18:33:14 2010
@@ -1855,9 +1855,9 @@
 def err_redefinition_of_label : Error<"redefinition of label '%0'">;
 def err_undeclared_label_use : Error<"use of undeclared label '%0'">;
 
-def err_goto_into_protected_scope : Error<"illegal goto into protected scope">;
+def err_goto_into_protected_scope : Error<"goto into protected scope">;
 def err_switch_into_protected_scope : Error<
-  "illegal switch case into protected scope">;
+  "switch case is in protected scope">;
 def err_indirect_goto_without_addrlabel : Error<
   "indirect goto in function with no address-of-label expressions">;
 def warn_indirect_goto_in_protected_scope : Warning<

Modified: cfe/trunk/lib/Sema/JumpDiagnostics.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/JumpDiagnostics.cpp?rev=110082&r1=110081&r2=110082&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/JumpDiagnostics.cpp (original)
+++ cfe/trunk/lib/Sema/JumpDiagnostics.cpp Mon Aug  2 18:33:14 2010
@@ -180,22 +180,6 @@
   
   // If we found a label, remember that it is in ParentScope scope.
   switch (S->getStmtClass()) {
-  case Stmt::LabelStmtClass:
-  case Stmt::DefaultStmtClass:
-    LabelAndGotoScopes[S] = ParentScope;
-    break;
-  case Stmt::CaseStmtClass: {
-    // Specially handle CaseStmts since they can nest each other in the
-    // AST and blow out the stack when we walk them.
-    CaseStmt *CS = cast<CaseStmt>(S);
-    do {
-      LabelAndGotoScopes[CS] = ParentScope;
-      S = CS; // 'CS' is the new current statement (if it isn't already).
-      CS = dyn_cast<CaseStmt>(CS->getSubStmt());
-    } while (CS);
-    break;
-  }
-
   case Stmt::AddrLabelExprClass:
     IndirectJumpTargets.push_back(cast<AddrLabelExpr>(S)->getLabel());
     break;
@@ -235,6 +219,24 @@
     Stmt *SubStmt = *CI;
     if (SubStmt == 0) continue;
 
+    // Cases, labels, and defaults aren't "scope parents".  It's also
+    // important to handle these iteratively instead of recursively in
+    // order to avoid blowing out the stack.
+    while (true) {
+      Stmt *Next;
+      if (isa<CaseStmt>(SubStmt))
+        Next = cast<CaseStmt>(SubStmt)->getSubStmt();
+      else if (isa<DefaultStmt>(SubStmt))
+        Next = cast<DefaultStmt>(SubStmt)->getSubStmt();
+      else if (isa<LabelStmt>(SubStmt))
+        Next = cast<LabelStmt>(SubStmt)->getSubStmt();
+      else
+        break;
+
+      LabelAndGotoScopes[SubStmt] = ParentScope;
+      SubStmt = Next;
+    }
+
     // If this is a declstmt with a VLA definition, it defines a scope from here
     // to the end of the containing context.
     if (DeclStmt *DS = dyn_cast<DeclStmt>(SubStmt)) {

Modified: cfe/trunk/test/Sema/scope-check.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Sema/scope-check.c?rev=110082&r1=110081&r2=110082&view=diff
==============================================================================
--- cfe/trunk/test/Sema/scope-check.c (original)
+++ cfe/trunk/test/Sema/scope-check.c Mon Aug  2 18:33:14 2010
@@ -1,7 +1,7 @@
 // RUN: %clang_cc1 -fsyntax-only -verify -fblocks -std=gnu99 %s -Wno-unreachable-code
 
 int test1(int x) {
-  goto L;    // expected-error{{illegal goto into protected scope}}
+  goto L;    // expected-error{{goto into protected scope}}
   int a[x];  // expected-note {{jump bypasses initialization of variable length array}}
   int b[x];  // expected-note {{jump bypasses initialization of variable length array}}
   L:
@@ -9,7 +9,7 @@
 }
 
 int test2(int x) {
-  goto L;            // expected-error{{illegal goto into protected scope}}
+  goto L;            // expected-error{{goto into protected scope}}
   typedef int a[x];  // expected-note {{jump bypasses initialization of VLA typedef}}
   L:
   return sizeof(a);
@@ -18,14 +18,14 @@
 void test3clean(int*);
 
 int test3() {
-  goto L;            // expected-error{{illegal goto into protected scope}}
+  goto L;            // expected-error{{goto into protected scope}}
 int a __attribute((cleanup(test3clean))); // expected-note {{jump bypasses initialization of variable with __attribute__((cleanup))}}
 L:
   return a;
 }
 
 int test4(int x) {
-  goto L;       // expected-error{{illegal goto into protected scope}}
+  goto L;       // expected-error{{goto into protected scope}}
 int a[x];       // expected-note {{jump bypasses initialization of variable length array}}
   test4(x);
 L:
@@ -50,7 +50,7 @@
   switch (x) {
   case 1: ;
     int a[x];       // expected-note {{jump bypasses initialization of variable length array}}
-  case 2:           // expected-error {{illegal switch case into protected scope}}
+  case 2:           // expected-error {{switch case is in protected scope}}
     a[1] = 2;
     break;
   }
@@ -58,17 +58,17 @@
 
 int test8(int x) {
   // For statement.
-  goto L2;     // expected-error {{illegal goto into protected scope}}
+  goto L2;     // expected-error {{goto into protected scope}}
   for (int arr[x];   // expected-note {{jump bypasses initialization of variable length array}}  
        ; ++x)
     L2:;
 
   // Statement expressions.
-  goto L3;   // expected-error {{illegal goto into protected scope}}
+  goto L3;   // expected-error {{goto into protected scope}}
   int Y = ({  int a[x];   // expected-note {{jump bypasses initialization of variable length array}}  
            L3: 4; });
   
-  goto L4; // expected-error {{illegal goto into protected scope}}
+  goto L4; // expected-error {{goto into protected scope}}
   {
     int A[x],  // expected-note {{jump bypasses initialization of variable length array}}
         B[x];  // expected-note {{jump bypasses initialization of variable length array}}
@@ -91,7 +91,7 @@
     int A[x], B = ({ if (x)
                        goto L7;
                      else 
-                       goto L8;  // expected-error {{illegal goto into protected scope}}
+                       goto L8;  // expected-error {{goto into protected scope}}
                      4; }),
         C[x];   // expected-note {{jump bypasses initialization of variable length array}}
   L8:; // bad
@@ -103,7 +103,7 @@
                goto L9;
              else
                // FIXME:
-               goto L10;  // fixme-error {{illegal goto into protected scope}}
+               goto L10;  // fixme-error {{goto into protected scope}}
            4; })];
   L10:; // bad
   }
@@ -123,7 +123,7 @@
   }
   
   // Statement expressions 2.
-  goto L1;     // expected-error {{illegal goto into protected scope}}
+  goto L1;     // expected-error {{goto into protected scope}}
   return x == ({
                  int a[x];   // expected-note {{jump bypasses initialization of variable length array}}  
                L1:
@@ -151,14 +151,14 @@
 }
 
 void test10(int n, void *P) {
-  goto L0;     // expected-error {{illegal goto into protected scope}}
+  goto L0;     // expected-error {{goto into protected scope}}
   typedef int A[n];  // expected-note {{jump bypasses initialization of VLA typedef}}
 L0:
   
-  goto L1;      // expected-error {{illegal goto into protected scope}}
+  goto L1;      // expected-error {{goto into protected scope}}
   A b, c[10];        // expected-note 2 {{jump bypasses initialization of variable length array}}
 L1:
-  goto L2;     // expected-error {{illegal goto into protected scope}}
+  goto L2;     // expected-error {{goto into protected scope}}
   A d[n];      // expected-note {{jump bypasses initialization of variable length array}}
 L2:
   return;
@@ -171,7 +171,7 @@
     case 2: 
     case 3:;
       int Arr[n]; // expected-note {{jump bypasses initialization of variable length array}}
-    case 4:       // expected-error {{illegal switch case into protected scope}}
+    case 4:       // expected-error {{switch case is in protected scope}}
       return;
     }
   };
@@ -185,7 +185,7 @@
   L1:
     goto L2;
   L2:
-    goto L3;    // expected-error {{illegal goto into protected scope}}
+    goto L3;    // expected-error {{goto into protected scope}}
     int Arr[n]; // expected-note {{jump bypasses initialization of variable length array}}
   L3:
     goto L4;

Modified: cfe/trunk/test/SemaCXX/scope-check.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaCXX/scope-check.cpp?rev=110082&r1=110081&r2=110082&view=diff
==============================================================================
--- cfe/trunk/test/SemaCXX/scope-check.cpp (original)
+++ cfe/trunk/test/SemaCXX/scope-check.cpp Mon Aug  2 18:33:14 2010
@@ -133,3 +133,21 @@
     return;
   }
 }
+
+// PR7789
+namespace test8 {
+  void test1(int c) {
+    switch (c) {
+    case 0:
+      int x = 56; // expected-note {{jump bypasses variable initialization}}
+    case 1:       // expected-error {{switch case is in protected scope}}
+      x = 10;
+    }
+  }
+
+  void test2() {
+    goto l2;     // expected-error {{goto into protected scope}}
+  l1: int x = 5; // expected-note {{jump bypasses variable initialization}}
+  l2: x++;
+  }
+}





More information about the cfe-commits mailing list