115 lines
4.5 KiB
C++
115 lines
4.5 KiB
C++
// The test is check we couldn't export a redeclaration which isn't exported previously and
|
|
// check it is OK to redeclare no matter exported nor not if is the previous declaration is exported.
|
|
// RUN: %clang_cc1 -std=c++20 %s -verify
|
|
|
|
export module X;
|
|
|
|
struct S { // expected-note {{previous declaration is here}}
|
|
int n;
|
|
};
|
|
typedef S S;
|
|
export typedef S S; // OK, does not redeclare an entity
|
|
export struct S; // expected-error {{cannot export redeclaration 'S' here since the previous declaration has module linkage}}
|
|
|
|
namespace A {
|
|
struct X; // expected-note {{previous declaration is here}}
|
|
export struct Y;
|
|
} // namespace A
|
|
|
|
namespace A {
|
|
export struct X; // expected-error {{cannot export redeclaration 'X' here since the previous declaration has module linkage}}
|
|
export struct Y; // OK
|
|
struct Z; // expected-note {{previous declaration is here}}
|
|
export struct Z; // expected-error {{cannot export redeclaration 'Z' here since the previous declaration has module linkage}}
|
|
} // namespace A
|
|
|
|
namespace A {
|
|
struct B; // expected-note {{previous declaration is here}}
|
|
struct C {}; // expected-note {{previous declaration is here}}
|
|
} // namespace A
|
|
|
|
namespace A {
|
|
export struct B {}; // expected-error {{cannot export redeclaration 'B' here since the previous declaration has module linkage}}
|
|
export struct C; // expected-error {{cannot export redeclaration 'C' here since the previous declaration has module linkage}}
|
|
} // namespace A
|
|
|
|
template <typename T>
|
|
struct TemplS; // expected-note {{previous declaration is here}}
|
|
|
|
export template <typename T>
|
|
struct TemplS {}; // expected-error {{cannot export redeclaration 'TemplS' here since the previous declaration has module linkage}}
|
|
|
|
template <typename T>
|
|
struct TemplS2; // expected-note {{previous declaration is here}}
|
|
|
|
export template <typename U>
|
|
struct TemplS2 {}; // expected-error {{cannot export redeclaration 'TemplS2' here since the previous declaration has module linkage}}
|
|
|
|
void baz(); // expected-note {{previous declaration is here}}
|
|
export void baz(); // expected-error {{cannot export redeclaration 'baz' here since the previous declaration has module linkage}}
|
|
|
|
namespace A {
|
|
export void foo();
|
|
void bar(); // expected-note {{previous declaration is here}}
|
|
export void bar(); // expected-error {{cannot export redeclaration 'bar' here since the previous declaration has module linkage}}
|
|
void f1(); // expected-note {{previous declaration is here}}
|
|
} // namespace A
|
|
|
|
// OK
|
|
//
|
|
// [module.interface]/p6
|
|
// A redeclaration of an entity X is implicitly exported if X was introduced by an exported declaration
|
|
void A::foo();
|
|
|
|
// The compiler couldn't export A::f1() here since A::f1() is declared above without exported.
|
|
// See [module.interface]/p6 for details.
|
|
export void A::f1(); // expected-error {{cannot export redeclaration 'f1' here since the previous declaration has module linkage}}
|
|
|
|
template <typename T>
|
|
void TemplFunc(); // expected-note {{previous declaration is here}}
|
|
|
|
export template <typename T>
|
|
void TemplFunc() { // expected-error {{cannot export redeclaration 'TemplFunc' here since the previous declaration has module linkage}}
|
|
}
|
|
|
|
namespace A {
|
|
template <typename T>
|
|
void TemplFunc2(); // expected-note {{previous declaration is here}}
|
|
export template <typename T>
|
|
void TemplFunc2() {} // expected-error {{cannot export redeclaration 'TemplFunc2' here since the previous declaration has module linkage}}
|
|
template <typename T>
|
|
void TemplFunc3(); // expected-note {{previous declaration is here}}
|
|
} // namespace A
|
|
|
|
export template <typename T>
|
|
void A::TemplFunc3() {} // expected-error {{cannot export redeclaration 'TemplFunc3' here since the previous declaration has module linkage}}
|
|
|
|
int var; // expected-note {{previous declaration is here}}
|
|
export int var; // expected-error {{cannot export redeclaration 'var' here since the previous declaration has module linkage}}
|
|
|
|
template <typename T>
|
|
T TemplVar; // expected-note {{previous declaration is here}}
|
|
export template <typename T>
|
|
T TemplVar; // expected-error {{cannot export redeclaration 'TemplVar' here since the previous declaration has module linkage}}
|
|
|
|
// Test the compiler wouldn't complain about the redeclaration of friend in exported class.
|
|
namespace Friend {
|
|
template <typename T>
|
|
class bar;
|
|
class gua;
|
|
template <typename T>
|
|
void hello();
|
|
void hi();
|
|
export class foo;
|
|
bool operator<(const foo &a, const foo &b);
|
|
export class foo {
|
|
template <typename T>
|
|
friend class bar;
|
|
friend class gua;
|
|
template <typename T>
|
|
friend void hello();
|
|
friend void hi();
|
|
friend bool operator<(const foo &a, const foo &b);
|
|
};
|
|
} // namespace Friend
|