Author: Amr Hesham
Date: 2025-03-31T19:41:29+02:00
New Revision: 143c37123b93a3dbd0fafd0296516ac1ab2afc36

URL: 
https://github.com/llvm/llvm-project/commit/143c37123b93a3dbd0fafd0296516ac1ab2afc36
DIFF: 
https://github.com/llvm/llvm-project/commit/143c37123b93a3dbd0fafd0296516ac1ab2afc36.diff

LOG: [CIR] Upstream zero init for global variables (#133100)

This change adds zero initialization for global variables

Added: 
    

Modified: 
    clang/include/clang/CIR/Dialect/Builder/CIRBaseBuilder.h
    clang/lib/CIR/CodeGen/CIRGenModule.cpp
    clang/test/CIR/CodeGen/array.cpp
    clang/test/CIR/Lowering/array.cpp
    clang/test/CIR/Lowering/global-var-simple.cpp
    clang/test/CIR/Lowering/hello.c
    clang/test/CIR/global-var-simple.cpp

Removed: 
    


################################################################################
diff  --git a/clang/include/clang/CIR/Dialect/Builder/CIRBaseBuilder.h 
b/clang/include/clang/CIR/Dialect/Builder/CIRBaseBuilder.h
index ac7658276ec37..8b17cb7446afa 100644
--- a/clang/include/clang/CIR/Dialect/Builder/CIRBaseBuilder.h
+++ b/clang/include/clang/CIR/Dialect/Builder/CIRBaseBuilder.h
@@ -67,6 +67,30 @@ class CIRBaseBuilderTy : public mlir::OpBuilder {
     return create<cir::ConstantOp>(loc, attr.getType(), attr);
   }
 
+  mlir::TypedAttr getConstNullPtrAttr(mlir::Type t) {
+    assert(mlir::isa<cir::PointerType>(t) && "expected cir.ptr");
+    return getConstPtrAttr(t, 0);
+  }
+
+  mlir::TypedAttr getZeroAttr(mlir::Type t) {
+    return cir::ZeroAttr::get(getContext(), t);
+  }
+
+  mlir::TypedAttr getZeroInitAttr(mlir::Type ty) {
+    if (mlir::isa<cir::IntType>(ty))
+      return cir::IntAttr::get(ty, 0);
+    if (cir::isAnyFloatingPointType(ty))
+      return cir::FPAttr::getZero(ty);
+    if (auto arrTy = mlir::dyn_cast<cir::ArrayType>(ty))
+      return getZeroAttr(arrTy);
+    if (auto ptrTy = mlir::dyn_cast<cir::PointerType>(ty))
+      return getConstNullPtrAttr(ptrTy);
+    if (mlir::isa<cir::BoolType>(ty)) {
+      return getCIRBoolAttr(false);
+    }
+    llvm_unreachable("Zero initializer for given type is NYI");
+  }
+
   cir::ConstantOp getBool(bool state, mlir::Location loc) {
     return create<cir::ConstantOp>(loc, getBoolTy(), getCIRBoolAttr(state));
   }

diff  --git a/clang/lib/CIR/CodeGen/CIRGenModule.cpp 
b/clang/lib/CIR/CodeGen/CIRGenModule.cpp
index 9776a4e09f9e0..2a37d6c7d1888 100644
--- a/clang/lib/CIR/CodeGen/CIRGenModule.cpp
+++ b/clang/lib/CIR/CodeGen/CIRGenModule.cpp
@@ -140,17 +140,20 @@ void CIRGenModule::emitGlobalVarDefinition(const 
clang::VarDecl *vd,
     // certain constant expressions is implemented for now.
     const VarDecl *initDecl;
     const Expr *initExpr = vd->getAnyInitializer(initDecl);
+    mlir::Attribute initializer;
     if (initExpr) {
-      mlir::Attribute initializer;
       if (APValue *value = initDecl->evaluateValue()) {
         ConstantEmitter emitter(*this);
         initializer = emitter.tryEmitPrivateForMemory(*value, astTy);
       } else {
         errorNYI(initExpr->getSourceRange(), "non-constant initializer");
       }
-      varOp.setInitialValueAttr(initializer);
+    } else {
+      initializer = builder.getZeroInitAttr(convertType(astTy));
     }
 
+    varOp.setInitialValueAttr(initializer);
+
     // Set CIR's linkage type as appropriate.
     cir::GlobalLinkageKind linkage =
         getCIRLinkageVarDefinition(vd, /*IsConstant=*/false);

diff  --git a/clang/test/CIR/CodeGen/array.cpp 
b/clang/test/CIR/CodeGen/array.cpp
index a59880352e050..1e74275eab058 100644
--- a/clang/test/CIR/CodeGen/array.cpp
+++ b/clang/test/CIR/CodeGen/array.cpp
@@ -1,16 +1,16 @@
 // RUN: %clang_cc1 -std=c++20 -triple x86_64-unknown-linux-gnu -fclangir 
-emit-cir %s -o - 2>&1 | FileCheck %s
 
 int a[10];
-// CHECK: cir.global external @a : !cir.array<!s32i x 10>
+// CHECK: cir.global external @a = #cir.zero : !cir.array<!s32i x 10>
 
 int aa[10][5];
-// CHECK: cir.global external @aa : !cir.array<!cir.array<!s32i x 5> x 10>
+// CHECK: cir.global external @aa = #cir.zero : !cir.array<!cir.array<!s32i x 
5> x 10>
 
 extern int b[10];
-// CHECK: cir.global external @b : !cir.array<!s32i x 10>
+// CHECK: cir.global external @b = #cir.zero : !cir.array<!s32i x 10>
 
 extern int bb[10][5];
-// CHECK: cir.global external @bb : !cir.array<!cir.array<!s32i x 5> x 10>
+// CHECK: cir.global external @bb = #cir.zero : !cir.array<!cir.array<!s32i x 
5> x 10>
 
 int c[10] = {};
 // CHECK: cir.global external @c = #cir.zero : !cir.array<!s32i x 10>

diff  --git a/clang/test/CIR/Lowering/array.cpp 
b/clang/test/CIR/Lowering/array.cpp
index 763980b9124a3..4fb996aefe79e 100644
--- a/clang/test/CIR/Lowering/array.cpp
+++ b/clang/test/CIR/Lowering/array.cpp
@@ -1,16 +1,16 @@
 // RUN: %clang_cc1 -std=c++20 -triple x86_64-unknown-linux-gnu -fclangir 
-emit-llvm %s -o - 2>&1 | FileCheck %s
 
 int a[10];
-// CHECK: @a = external dso_local global [10 x i32]
+// CHECK: @a = dso_local global [10 x i32] zeroinitializer
 
 int aa[10][5];
-// CHECK: @aa = external dso_local global [10 x [5 x i32]]
+// CHECK: @aa = dso_local global [10 x [5 x i32]] zeroinitializer
 
 extern int b[10];
-// CHECK: @b = external dso_local global [10 x i32]
+// CHECK: @b = dso_local global [10 x i32] zeroinitializer
 
 extern int bb[10][5];
-// CHECK: @bb = external dso_local global [10 x [5 x i32]]
+// CHECK: @bb = dso_local global [10 x [5 x i32]] zeroinitializer
 
 int c[10] = {};
 // CHECK: @c = dso_local global [10 x i32] zeroinitializer

diff  --git a/clang/test/CIR/Lowering/global-var-simple.cpp 
b/clang/test/CIR/Lowering/global-var-simple.cpp
index ab8c6660a311b..33b418430d478 100644
--- a/clang/test/CIR/Lowering/global-var-simple.cpp
+++ b/clang/test/CIR/Lowering/global-var-simple.cpp
@@ -1,21 +1,19 @@
 // Global variables of intergal types
-// RUN: %clang_cc1 -std=c++20 -triple x86_64-unknown-linux-gnu -fclangir 
-emit-llvm %s -o -  | FileCheck %s
+// RUN: %clang_cc1 -std=c++20 -triple x86_64-unknown-linux-gnu -fclangir 
-emit-llvm %s -o - | FileCheck %s
 
-// Note: Currently unsupported features include default zero-initialization
-//       and alignment. The fact that "external" is only printed for globals
-//       without an initializer is a quirk of the LLVM AsmWriter.
+// Note: Currently unsupported features include alignment..
 
 char c;
-// CHECK: @c = external dso_local global i8
+// CHECK: @c = dso_local global i8 0
 
 signed char sc;
-// CHECK: @sc = external dso_local global i8
+// CHECK: @sc = dso_local global i8 0
 
 unsigned char uc;
-// CHECK: @uc = external dso_local global i8
+// CHECK: @uc = dso_local global i8 0
 
 short ss;
-// CHECK: @ss = external dso_local global i16
+// CHECK: @ss = dso_local global i16 0
 
 unsigned short us = 100;
 // CHECK: @us = dso_local global i16 100
@@ -24,82 +22,82 @@ int si = 42;
 // CHECK: @si = dso_local global i32 42
 
 unsigned ui;
-// CHECK: @ui = external dso_local global i32
+// CHECK: @ui = dso_local global i32 0
 
 long sl;
-// CHECK: @sl = external dso_local global i64
+// CHECK: @sl = dso_local global i64 0
 
 unsigned long ul;
-// CHECK: @ul = external dso_local global i64
+// CHECK: @ul = dso_local global i64 0
 
 long long sll;
-// CHECK: @sll = external dso_local global i64
+// CHECK: @sll = dso_local global i64 0
 
 unsigned long long ull = 123456;
 // CHECK: @ull = dso_local global i64 123456
 
 __int128 s128;
-// CHECK: @s128 = external dso_local global i128
+// CHECK: @s128 = dso_local global i128 0
 
 unsigned __int128 u128;
-// CHECK: @u128 = external dso_local global i128
+// CHECK: @u128 = dso_local global i128 0
 
 wchar_t wc;
-// CHECK: @wc = external dso_local global i32
+// CHECK: @wc = dso_local global i32 0
 
 char8_t c8;
-// CHECK: @c8 = external dso_local global i8
+// CHECK: @c8 = dso_local global i8 0
 
 char16_t c16;
-// CHECK: @c16 = external dso_local global i16
+// CHECK: @c16 = dso_local global i16 0
 
 char32_t c32;
-// CHECK: @c32 = external dso_local global i32
+// CHECK: @c32 = dso_local global i32 0
 
 _BitInt(20) sb20;
-// CHECK: @sb20 = external dso_local global i20
+// CHECK: @sb20 = dso_local global i20 0
 
 unsigned _BitInt(48) ub48;
-// CHECK: @ub48 = external dso_local global i48
+// CHECK: @ub48 = dso_local global i48 0
 
 bool boolfalse = false;
 // CHECK: @boolfalse = dso_local global i8 0
 
 _Float16 f16;
-// CHECK: @f16 = external dso_local global half
+// CHECK: @f16 = dso_local global half
 
 __bf16 bf16;
-// CHECK: @bf16 = external dso_local global bfloat
+// CHECK: @bf16 = dso_local global bfloat
 
 float f;
-// CHECK: @f = external dso_local global float
+// CHECK: @f = dso_local global float 0.000000e+00
 
 double d = 1.25;
 // CHECK: @d = dso_local global double 1.250000e+00
 
 long double ld;
-// CHECK: @ld = external dso_local global x86_fp80
+// CHECK: @ld = dso_local global x86_fp80 0xK00
 
 __float128 f128;
-// CHECK: @f128 = external dso_local global fp128
+// CHECK: @f128 = dso_local global fp128 0xL00
 
 void *vp;
-// CHECK: @vp = external dso_local global ptr{{$}}
+// CHECK: @vp = dso_local global ptr null
 
 int *ip = 0;
 // CHECK: @ip = dso_local global ptr null
 
 double *dp;
-// CHECK: @dp = external dso_local global ptr{{$}}
+// CHECK: @dp = dso_local global ptr null
 
 char **cpp;
-// CHECK: @cpp = external dso_local global ptr{{$}}
+// CHECK: @cpp = dso_local global ptr null
 
 void (*fp)();
-// CHECK: @fp = external dso_local global ptr{{$}}
+// CHECK: @fp = dso_local global ptr null
 
 int (*fpii)(int) = 0;
 // CHECK: @fpii = dso_local global ptr null
 
 void (*fpvar)(int, ...);
-// CHECK: @fpvar = external dso_local global ptr{{$}}
+// CHECK: @fpvar = dso_local global ptr null

diff  --git a/clang/test/CIR/Lowering/hello.c b/clang/test/CIR/Lowering/hello.c
index ff78b6e6f6a5e..f45beafdcb533 100644
--- a/clang/test/CIR/Lowering/hello.c
+++ b/clang/test/CIR/Lowering/hello.c
@@ -3,7 +3,7 @@
 
 int a;
 
-// CHECK: @a = external dso_local global i32
+// CHECK: @a = dso_local global i32 0
 
 int b = 2;
 

diff  --git a/clang/test/CIR/global-var-simple.cpp 
b/clang/test/CIR/global-var-simple.cpp
index 020ef5f09c650..9a52925303504 100644
--- a/clang/test/CIR/global-var-simple.cpp
+++ b/clang/test/CIR/global-var-simple.cpp
@@ -2,16 +2,16 @@
 // RUN: %clang_cc1 -std=c++20 -triple x86_64-unknown-linux-gnu -fclangir 
-emit-cir %s -o -  | FileCheck %s
 
 char c;
-// CHECK: cir.global external @c : !s8i
+// CHECK: cir.global external @c = #cir.int<0> : !s8i
 
 signed char sc;
-// CHECK: cir.global external @sc : !s8i
+// CHECK: cir.global external @sc = #cir.int<0> : !s8i
 
 unsigned char uc;
-// CHECK: cir.global external @uc : !u8i
+// CHECK: cir.global external @uc = #cir.int<0> : !u8i
 
 short ss;
-// CHECK: cir.global external @ss : !s16i
+// CHECK: cir.global external @ss = #cir.int<0> : !s16i
 
 unsigned short us = 100;
 // CHECK: cir.global external @us = #cir.int<100> : !u16i
@@ -20,82 +20,82 @@ int si = 42;
 // CHECK: cir.global external @si = #cir.int<42> : !s32i
 
 unsigned ui;
-// CHECK: cir.global external @ui : !u32i
+// CHECK: cir.global external @ui = #cir.int<0> : !u32i
 
 long sl;
-// CHECK: cir.global external @sl : !s64i
+// CHECK: cir.global external @sl = #cir.int<0> : !s64i
 
 unsigned long ul;
-// CHECK: cir.global external @ul : !u64i
+// CHECK: cir.global external @ul = #cir.int<0> : !u64i
 
 long long sll;
-// CHECK: cir.global external @sll : !s64i
+// CHECK: cir.global external @sll = #cir.int<0> : !s64i
 
 unsigned long long ull = 123456;
 // CHECK: cir.global external @ull = #cir.int<123456> : !u64i
 
 __int128 s128;
-// CHECK: cir.global external @s128 : !s128i
+// CHECK: cir.global external @s128 = #cir.int<0> : !s128i
 
 unsigned __int128 u128;
-// CHECK: cir.global external @u128 : !u128i
+// CHECK: cir.global external @u128 = #cir.int<0> : !u128i
 
 wchar_t wc;
-// CHECK: cir.global external @wc : !s32i
+// CHECK: cir.global external @wc = #cir.int<0> : !s32i
 
 char8_t c8;
-// CHECK: cir.global external @c8 : !u8i
+// CHECK: cir.global external @c8 = #cir.int<0> : !u8i
 
 char16_t c16;
-// CHECK: cir.global external @c16 : !u16i
+// CHECK: cir.global external @c16 = #cir.int<0> : !u16i
 
 char32_t c32;
-// CHECK: cir.global external @c32 : !u32i
+// CHECK: cir.global external @c32 = #cir.int<0> : !u32i
 
 _BitInt(20) sb20;
-// CHECK: cir.global external @sb20 : !cir.int<s, 20>
+// CHECK: cir.global external @sb20 = #cir.int<0> : !cir.int<s, 20>
 
 unsigned _BitInt(48) ub48;
-// CHECK: cir.global external @ub48 : !cir.int<u, 48>
+// CHECK: cir.global external @ub48 = #cir.int<0> : !cir.int<u, 48>
 
 bool boolfalse = false;
 // CHECK: cir.global external @boolfalse = #false
 
 _Float16 f16;
-// CHECK: cir.global external @f16 : !cir.f16
+// CHECK: cir.global external @f16 = #cir.fp<0.000000e+00> : !cir.f16
 
 __bf16 bf16;
-// CHECK: cir.global external @bf16 : !cir.bf16
+// CHECK: cir.global external @bf16 = #cir.fp<0.000000e+00> : !cir.bf16
 
 float f;
-// CHECK: cir.global external @f : !cir.float
+// CHECK: cir.global external @f = #cir.fp<0.000000e+00>  : !cir.float
 
 double d = 1.25;
 // CHECK: cir.global external @d = #cir.fp<1.250000e+00> : !cir.double
 
 long double ld;
-// CHECK: cir.global external @ld : !cir.long_double<!cir.f80>
+// CHECK: cir.global external @ld = #cir.fp<0.000000e+00> : 
!cir.long_double<!cir.f80>
 
 __float128 f128;
-// CHECK: cir.global external @f128 : !cir.f128
+// CHECK: cir.global external @f128 = #cir.fp<0.000000e+00> : !cir.f128
 
 void *vp;
-// CHECK: cir.global external @vp : !cir.ptr<!void>
+// CHECK: cir.global external @vp = #cir.ptr<null> : !cir.ptr<!void>
 
 int *ip = 0;
 // CHECK: cir.global external @ip = #cir.ptr<null> : !cir.ptr<!s32i>
 
 double *dp;
-// CHECK: cir.global external @dp : !cir.ptr<!cir.double>
+// CHECK: cir.global external @dp = #cir.ptr<null> : !cir.ptr<!cir.double>
 
 char **cpp;
-// CHECK: cir.global external @cpp : !cir.ptr<!cir.ptr<!s8i>>
+// CHECK: cir.global external @cpp = #cir.ptr<null> : !cir.ptr<!cir.ptr<!s8i>>
 
 void (*fp)();
-// CHECK: cir.global external @fp : !cir.ptr<!cir.func<()>>
+// CHECK: cir.global external @fp = #cir.ptr<null> : !cir.ptr<!cir.func<()>>
 
 int (*fpii)(int) = 0;
 // CHECK: cir.global external @fpii = #cir.ptr<null> : 
!cir.ptr<!cir.func<(!s32i) -> !s32i>>
 
 void (*fpvar)(int, ...);
-// CHECK: cir.global external @fpvar : !cir.ptr<!cir.func<(!s32i, ...)>>
+// CHECK: cir.global external @fpvar = #cir.ptr<null> : 
!cir.ptr<!cir.func<(!s32i, ...)>>


        
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to