]> granicus.if.org Git - clang/commitdiff
DebugInfo: PR19298: function local const variables duplicated in the root scope
authorDavid Blaikie <dblaikie@gmail.com>
Fri, 4 Apr 2014 20:56:17 +0000 (20:56 +0000)
committerDavid Blaikie <dblaikie@gmail.com>
Fri, 4 Apr 2014 20:56:17 +0000 (20:56 +0000)
See the comment for CodeGenFunction::tryEmitAsConstant that describes
how in some contexts (lambdas) we must not emit references to the
variable, but instead use the constant directly - because of this we end
up emitting a constant for the variable, as well as emitting the
variable itself.

Should we just skip putting the variable on the stack at all and omit
the debug info for the constant? It's not clear to me - what if the
address of the local is taken?

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@205651 91177308-0d34-0410-b5e6-96231b3b80d8

lib/CodeGen/CGDebugInfo.cpp
test/CodeGenCXX/debug-info.cpp

index 0e94b51817ef3c52134305d9909ef030de06bcc5..41f1ddb697c141e5806140ad5786d4e9604c20b8 100644 (file)
@@ -3227,6 +3227,9 @@ void CGDebugInfo::EmitGlobalVariable(const ValueDecl *VD,
   // Do not use DIGlobalVariable for enums.
   if (Ty.getTag() == llvm::dwarf::DW_TAG_enumeration_type)
     return;
+  // Do not emit separate definitions for function local const/statics.
+  if (isa<FunctionDecl>(VD->getDeclContext()))
+    return;
   llvm::DIGlobalVariable GV = DBuilder.createStaticVariable(
       Unit, Name, Name, Unit, getLineNumber(VD->getLocation()), Ty, true, Init,
       getOrCreateStaticDataMemberDeclarationOrNull(cast<VarDecl>(VD)));
index 2e7226d8696cd0a15089f45927fe7a87f4b9fcbc..7c89dfc04ce1bcdf3fcf3ae8bf32dfcff82faa8d 100644 (file)
@@ -51,11 +51,6 @@ namespace VirtualBase {
   }
 }
 
-void foo() {
-  const wchar_t c = L'x';
-  wchar_t d = c;
-}
-
 namespace b5249287 {
 template <typename T> class A {
   struct B;
@@ -88,6 +83,13 @@ foo func(foo f) {
 // CHECK: [[FUNC:![0-9]*]] = {{.*}} metadata !"_ZN7pr147634funcENS_3fooE", i32 {{[0-9]*}}, metadata [[FUNC_TYPE:![0-9]*]], {{.*}} ; [ DW_TAG_subprogram ] {{.*}} [def] [func]
 }
 
+void foo() {
+  const wchar_t c = L'x';
+  wchar_t d = c;
+}
+
+// CHECK-NOT: ; [ DW_TAG_variable ] [c]
+
 namespace pr9608 { // also pr9600
 struct incomplete;
 incomplete (*x)[3];
@@ -96,9 +98,11 @@ incomplete (*x)[3];
 // CHECK: [[INCARRAY]] = {{.*}}metadata !"_ZTSN6pr960810incompleteE", metadata {{![0-9]*}}, i32 0, null, null, null} ; [ DW_TAG_array_type ] [line 0, size 0, align 0, offset 0] [from _ZTSN6pr960810incompleteE]
 }
 
-// For some reason the argument for PR14763 ended up all the way down here
+// For some reason function arguments ended up down here
 // CHECK: = metadata !{i32 {{[0-9]*}}, metadata [[FUNC]], {{.*}}, metadata !"[[FOO]]", i32 8192, i32 0} ; [ DW_TAG_arg_variable ] [f]
 
+// CHECK: ; [ DW_TAG_auto_variable ] [c]
+
 namespace pr16214 {
 struct a {
   int i;