mirror of
https://github.com/capstone-engine/llvm-capstone.git
synced 2025-05-13 17:37:00 +00:00

This a test for https://github.com/llvm/llvm-project/pull/76774. In the review comments, we're concerning about the case that ODRHash may produce the different hash values for semantical same template arguments. For example, if the template argument in a specialization is not qualified and the semantical same template argument in the instantiation point is qualified, we should be able to select that template specialization. And this patch tests this behavior: we should be able to select the correct specialization with semantical same template arguments.
134 lines
3.0 KiB
C++
134 lines
3.0 KiB
C++
// Testing that the compiler can select the correct template specialization
|
|
// from different template aliasing.
|
|
//
|
|
// RUN: rm -rf %t
|
|
// RUN: split-file %s %t
|
|
// RUN: cd %t
|
|
//
|
|
// RUN: %clang_cc1 -std=c++20 %t/a.cppm -emit-module-interface -o %t/a.pcm
|
|
// RUN: %clang_cc1 -std=c++20 %t/b.cpp -fprebuilt-module-path=%t \
|
|
// RUN: -fsyntax-only -verify
|
|
|
|
//--- a.cppm
|
|
|
|
// For template type parameters
|
|
export module a;
|
|
export template <class C>
|
|
struct S {
|
|
static constexpr bool selected = false;
|
|
};
|
|
|
|
export struct A {};
|
|
|
|
export template <>
|
|
struct S<A> {
|
|
static constexpr bool selected = true;
|
|
};
|
|
|
|
export using B = A;
|
|
|
|
// For template template parameters
|
|
|
|
export template <template<typename> typename C>
|
|
struct V {
|
|
static constexpr bool selected = false;
|
|
};
|
|
|
|
export template <>
|
|
struct V<S> {
|
|
static constexpr bool selected = true;
|
|
};
|
|
|
|
// For template non type parameters
|
|
export template <int X>
|
|
struct Numbers {
|
|
static constexpr bool selected = false;
|
|
static constexpr int value = X;
|
|
};
|
|
|
|
export template<>
|
|
struct Numbers<43> {
|
|
static constexpr bool selected = true;
|
|
static constexpr int value = 43;
|
|
};
|
|
|
|
export template <const int *>
|
|
struct Pointers {
|
|
static constexpr bool selected = false;
|
|
};
|
|
|
|
export int IntegralValue = 0;
|
|
export template<>
|
|
struct Pointers<&IntegralValue> {
|
|
static constexpr bool selected = true;
|
|
};
|
|
|
|
export template <void *>
|
|
struct NullPointers {
|
|
static constexpr bool selected = false;
|
|
};
|
|
|
|
export template<>
|
|
struct NullPointers<nullptr> {
|
|
static constexpr bool selected = true;
|
|
};
|
|
|
|
export template<int (&)[5]>
|
|
struct Array {
|
|
static constexpr bool selected = false;
|
|
};
|
|
|
|
export int array[5];
|
|
export template<>
|
|
struct Array<array> {
|
|
static constexpr bool selected = true;
|
|
};
|
|
|
|
//--- b.cpp
|
|
// expected-no-diagnostics
|
|
import a;
|
|
|
|
// Testing for different qualifiers
|
|
static_assert(S<B>::selected);
|
|
static_assert(S<::B>::selected);
|
|
static_assert(::S<B>::selected);
|
|
static_assert(::S<::B>::selected);
|
|
typedef A C;
|
|
static_assert(S<C>::selected);
|
|
static_assert(S<::C>::selected);
|
|
static_assert(::S<C>::selected);
|
|
static_assert(::S<::C>::selected);
|
|
|
|
namespace D {
|
|
C getAType();
|
|
typedef C E;
|
|
}
|
|
|
|
static_assert(S<D::E>::selected);
|
|
static_assert(S<decltype(D::getAType())>::selected);
|
|
|
|
// Testing we can select the correct specialization for different
|
|
// template template argument alising.
|
|
|
|
static_assert(V<S>::selected);
|
|
static_assert(V<::S>::selected);
|
|
static_assert(::V<S>::selected);
|
|
static_assert(::V<::S>::selected);
|
|
|
|
// Testing for template non type parameters
|
|
static_assert(Numbers<43>::selected);
|
|
static_assert(Numbers<21 * 2 + 1>::selected);
|
|
static_assert(Numbers<42 + 1>::selected);
|
|
static_assert(Numbers<44 - 1>::selected);
|
|
static_assert(Numbers<Numbers<43>::value>::selected);
|
|
static_assert(!Numbers<44>::selected);
|
|
|
|
static_assert(Pointers<&IntegralValue>::selected);
|
|
static_assert(!Pointers<nullptr>::selected);
|
|
static_assert(NullPointers<nullptr>::selected);
|
|
static_assert(!NullPointers<(void*)&IntegralValue>::selected);
|
|
|
|
static_assert(Array<array>::selected);
|
|
int another_array[5];
|
|
static_assert(!Array<another_array>::selected);
|