diff --git a/clang/lib/Sema/SemaTemplateInstantiateDecl.cpp b/clang/lib/Sema/SemaTemplateInstantiateDecl.cpp --- a/clang/lib/Sema/SemaTemplateInstantiateDecl.cpp +++ b/clang/lib/Sema/SemaTemplateInstantiateDecl.cpp @@ -3625,6 +3625,13 @@ if (InsertPos) VarTemplate->AddSpecialization(Var, InsertPos); + // FIXME: This may not be the best approach, as the correct type (including + // address space) is available in D, but the type in D may not be reliable + // in every situation. + // This approach was copied from TemplateDeclInstantiator::VisitVarDecl + if (SemaRef.getLangOpts().OpenCL) + SemaRef.deduceOpenCLAddressSpace(Var); + // Substitute the nested name specifier, if any. if (SubstQualifier(D, Var)) return nullptr; @@ -4803,6 +4810,13 @@ // Instantiate the initializer. InstantiateVariableInitializer(VarSpec, PatternDecl, TemplateArgs); + // FIXME: This may not be the best approach, as the correct type (including + // address space) is available in PatternDecl, but this type may not be + // reliable in every situation. + // This approach was copied from TemplateDeclInstantiator::VisitVarDecl + if (getLangOpts().OpenCL) + deduceOpenCLAddressSpace(VarSpec); + return VarSpec; } diff --git a/clang/test/SemaOpenCLCXX/address-space-deduction.cl b/clang/test/SemaOpenCLCXX/address-space-deduction.cl --- a/clang/test/SemaOpenCLCXX/address-space-deduction.cl +++ b/clang/test/SemaOpenCLCXX/address-space-deduction.cl @@ -5,6 +5,10 @@ //CHECK: |-VarDecl {{.*}} foo 'const __global int' constexpr int foo = 0; +//CHECK: `-VarTemplateSpecializationDecl {{.*}} used foo1 '__global long':'__global long' cinit +template +T foo1 = 0; + class c { public: //CHECK: `-VarDecl {{.*}} foo2 'const __global int' @@ -111,4 +115,5 @@ t3(&x); t4(&p); t5(&p); + long f1 = foo1; }