Skip to content

Commit 5b18c74

Browse files
committed
Lazily IR-declare global variables
Analogous to #4420.
1 parent 3883e04 commit 5b18c74

5 files changed

Lines changed: 22 additions & 7 deletions

File tree

gen/declarations.cpp

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -253,9 +253,12 @@ class CodegenVisitor : public Visitor {
253253
decl->toPrettyChars());
254254
LOG_SCOPE;
255255

256-
if (decl->ir->isDefined()) {
256+
if (decl->ir->isDefined())
257+
return;
258+
259+
// skip external declarations (IR-declared lazily)
260+
if (decl->storage_class & STCextern)
257261
return;
258-
}
259262

260263
if (decl->type->ty == TY::Terror) {
261264
error(decl->loc, "%s `%s` had semantic errors when compiling",

gen/llvmhelpers.cpp

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -957,6 +957,9 @@ DValue *DtoDeclarationExp(Dsymbol *declaration) {
957957
// static
958958
if (vd->isDataseg()) {
959959
Declaration_codegen(vd);
960+
if (vd->storage_class & STCextern) {
961+
DtoResolveVariable(vd); // make sure there's an IR declaration
962+
}
960963
} else {
961964
DtoVarDeclaration(vd);
962965
}

tests/codegen/avr.d

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,3 +11,5 @@ version (D_SoftFloat) {} else static assert(0);
1111
int definedGlobal = 123;
1212
// CHECK: @_D3avr14declaredGlobali = external global i32
1313
extern int declaredGlobal;
14+
15+
int dummyRef() { return declaredGlobal; } // make sure `declaredGlobal` is IR-declared

tests/codegen/wasi.d

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,8 +15,6 @@ version (CRuntime_WASI) {} else static assert(0);
1515

1616
// CHECK: @_D4wasi13definedGlobali = global i32 123
1717
int definedGlobal = 123;
18-
// CHECK: @_D4wasi14declaredGlobali = external global i32
19-
extern int declaredGlobal;
2018

2119

2220
// make sure the ModuleInfo ref is emitted into the __minfo section:
Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,18 @@
1-
// RUN: not %ldc -c %s 2>&1 | FileCheck %s
1+
// It should compile fine when not referencing the colliding external global:
2+
// RUN: %ldc -c %s -d-version=DontReference
3+
4+
// But fail if referenced:
5+
// RUN: not %ldc -c %s -verrors-context=false 2>&1 | FileCheck %s
26

37
extern(C) extern int myGlobal;
48

5-
// CHECK: global_var_collision.d(9): Error: Global variable type does not match previous declaration with same mangled name: `myGlobal`
6-
// CHECK: Previous IR type: i32, mutable, thread-local
9+
version (DontReference) {} else
10+
{
11+
int dummyRef() { return myGlobal; }
12+
}
13+
14+
// CHECK: global_var_collision.d([[@LINE+4]]): Error: Global variable type does not match previous declaration with same mangled name: `myGlobal`
15+
// CHECK-NEXT: Previous IR type: i32, mutable, thread-local
716
// CHECK-NEXT: New IR type: i64, const, non-thread-local
817
pragma(mangle, myGlobal.mangleof)
918
extern(C) __gshared const long myGlobal2 = 123;

0 commit comments

Comments
 (0)