From 6c494adc387f6793f02a55d5a5f811eaa22357b4 Mon Sep 17 00:00:00 2001 From: "Henrik G. Olsson" Date: Mon, 7 Jul 2025 12:16:42 -0700 Subject: [PATCH] [Modules] Don't const eval VarDecls with dependent type EvaluateAsInitializer does not support evaluating values with dependent types. This was previously guarded with a check for the initializer expression, but it is possible for the VarDecl to have a dependent type without the initializer having a dependent type, when the initializer is a specialized template type and the VarDecl has the unspecialized type. This adds a guard checking for dependence in the VarDecl type as well. --- clang/lib/AST/Decl.cpp | 3 ++- .../var-init-side-effects-templated.cpp | 20 +++++++++++++++++++ 2 files changed, 22 insertions(+), 1 deletion(-) create mode 100644 clang/test/Modules/var-init-side-effects-templated.cpp diff --git a/clang/lib/AST/Decl.cpp b/clang/lib/AST/Decl.cpp index e0362245d6ecd..8855d0107daca 100644 --- a/clang/lib/AST/Decl.cpp +++ b/clang/lib/AST/Decl.cpp @@ -2450,7 +2450,8 @@ bool VarDecl::hasInitWithSideEffects() const { ES->HasSideEffects = E->HasSideEffects(getASTContext()) && // We can get a value-dependent initializer during error recovery. - (E->isValueDependent() || !evaluateValue()); + (E->isValueDependent() || getType()->isDependentType() || + !evaluateValue()); ES->CheckedForSideEffects = true; } return ES->HasSideEffects; diff --git a/clang/test/Modules/var-init-side-effects-templated.cpp b/clang/test/Modules/var-init-side-effects-templated.cpp new file mode 100644 index 0000000000000..542ca270429b6 --- /dev/null +++ b/clang/test/Modules/var-init-side-effects-templated.cpp @@ -0,0 +1,20 @@ +// Tests referencing variable with initializer containing side effect across module boundary + +// RUN: %clang_cc1 -std=c++20 -emit-module-interface %s -o %t + +export module Foo; + +export template +struct Wrapper { + double value; +}; + +export constexpr Wrapper Compute() { + return Wrapper{1.0}; +} + +export template +Wrapper ComputeInFloat() { + const Wrapper a = Compute(); + return a; +}