[clang] 4983fdf - [C++20] [Modules] Handle reachability for deduction guide

Chuanqi Xu via cfe-commits cfe-commits at lists.llvm.org
Mon Jul 18 00:46:52 PDT 2022


Author: Chuanqi Xu
Date: 2022-07-18T15:46:26+08:00
New Revision: 4983fdfec0443cf388adb87b816b7298a7bdf273

URL: https://github.com/llvm/llvm-project/commit/4983fdfec0443cf388adb87b816b7298a7bdf273
DIFF: https://github.com/llvm/llvm-project/commit/4983fdfec0443cf388adb87b816b7298a7bdf273.diff

LOG: [C++20] [Modules] Handle reachability for deduction guide

Previously, we forget to handle reachability for deduction guide.
The deduction guide is a hint to the compiler. And the deduction guide
should be able to use if the corresponding template decl is reachable.

Added: 
    clang/test/Modules/deduction-guide.cppm
    clang/test/Modules/deduction-guide2.cppm
    clang/test/Modules/deduction-guide3.cppm

Modified: 
    clang/lib/Sema/SemaLookup.cpp

Removed: 
    


################################################################################
diff  --git a/clang/lib/Sema/SemaLookup.cpp b/clang/lib/Sema/SemaLookup.cpp
index 47c7a61f8072f..aa87a33ce8ae1 100644
--- a/clang/lib/Sema/SemaLookup.cpp
+++ b/clang/lib/Sema/SemaLookup.cpp
@@ -2087,6 +2087,13 @@ bool LookupResult::isAvailableForLookup(Sema &SemaRef, NamedDecl *ND) {
   if (isVisible(SemaRef, ND))
     return true;
 
+  // Deduction guide lives in namespace scope generally, but it is just a
+  // hint to the compilers. What we actually lookup for is the generated member
+  // of the corresponding template. So it is sufficient to check the
+  // reachability of the template decl.
+  if (auto *DeductionGuide = ND->getDeclName().getCXXDeductionGuideTemplate())
+    return SemaRef.hasReachableDefinition(DeductionGuide);
+
   auto *DC = ND->getDeclContext();
   // If ND is not visible and it is at namespace scope, it shouldn't be found
   // by name lookup.

diff  --git a/clang/test/Modules/deduction-guide.cppm b/clang/test/Modules/deduction-guide.cppm
new file mode 100644
index 0000000000000..9c959a71365da
--- /dev/null
+++ b/clang/test/Modules/deduction-guide.cppm
@@ -0,0 +1,30 @@
+// RUN: rm -rf %t
+// RUN: mkdir %t
+// RUN: split-file %s %t
+//
+// RUN: %clang_cc1 -std=c++20 %t/Templ.cppm -emit-module-interface -o %t/Templ.pcm
+// RUN: %clang_cc1 -std=c++20 -fprebuilt-module-path=%t %t/Use.cpp -verify -fsyntax-only
+
+//--- foo.h
+template <typename T>
+class Templ {
+public:
+    Templ(T a) {}
+};
+
+template<typename T>
+Templ(T t) -> Templ<T>;
+
+//--- Templ.cppm
+module;
+#include "foo.h"
+export module Templ;
+export using ::Templ;
+
+//--- Use.cpp
+// expected-no-diagnostics
+import Templ;
+void func() {
+    Templ t(5);
+}
+

diff  --git a/clang/test/Modules/deduction-guide2.cppm b/clang/test/Modules/deduction-guide2.cppm
new file mode 100644
index 0000000000000..a163c36568310
--- /dev/null
+++ b/clang/test/Modules/deduction-guide2.cppm
@@ -0,0 +1,25 @@
+// RUN: rm -rf %t
+// RUN: mkdir %t
+// RUN: split-file %s %t
+//
+// RUN: %clang_cc1 -std=c++20 %t/Templ.cppm -emit-module-interface -o %t/Templ.pcm
+// RUN: %clang_cc1 -std=c++20 -fprebuilt-module-path=%t %t/Use.cpp -verify -fsyntax-only
+
+//--- Templ.cppm
+export module Templ;
+export template <typename T>
+class Templ {
+public:
+    Templ(T a) {}
+};
+
+template<typename T>
+Templ(T t) -> Templ<T>;
+
+//--- Use.cpp
+// expected-no-diagnostics
+import Templ;
+void func() {
+    Templ t(5);
+}
+

diff  --git a/clang/test/Modules/deduction-guide3.cppm b/clang/test/Modules/deduction-guide3.cppm
new file mode 100644
index 0000000000000..8fa08a0625d7c
--- /dev/null
+++ b/clang/test/Modules/deduction-guide3.cppm
@@ -0,0 +1,26 @@
+// RUN: rm -rf %t
+// RUN: mkdir %t
+// RUN: split-file %s %t
+//
+// RUN: %clang_cc1 -std=c++20 %t/Templ.cppm -emit-module-interface -o %t/Templ.pcm
+// RUN: %clang_cc1 -std=c++20 -fprebuilt-module-path=%t %t/Use.cpp -verify -fsyntax-only
+
+//--- Templ.cppm
+export module Templ;
+template <typename T>
+class Templ {
+public:
+    Templ(T a) {}
+};
+
+template<typename T>
+Templ(T t) -> Templ<T>;
+
+//--- Use.cpp
+import Templ;
+void func() {
+    Templ t(5); // expected-error {{declaration of 'Templ' must be imported from module 'Templ' before it is required}}
+                // expected-error at -1 {{unknown type name 'Templ'}}
+                // expected-note at Templ.cppm:3 {{declaration here is not visible}}
+}
+


        


More information about the cfe-commits mailing list