llvm-project/clang/test/Modules/merge-concepts-redefinition-error.cpp
Ilya Biryukov 59179d72b2 [Sema] Merge C++20 concept definitions from different modules in same TU
Currently the C++20 concepts are only merged in `ASTReader`, i.e. when
coming from different TU. This can causes ambiguious reference errors when
trying to access the same concept that should otherwise be merged.

Please see the added test for an example.

Note that we currently use `ASTContext::isSameEntity` to check for ODR
violations. However, it will not check that concept requirements match.
The same issue holds for mering concepts from different TUs, I added a
FIXME and filed a GH issue to track this:
https://github.com/llvm/llvm-project/issues/56310

Reviewed By: ChuanqiXu

Differential Revision: https://reviews.llvm.org/D128921
2022-07-25 14:43:38 +02:00

58 lines
1.5 KiB
C++

// RUN: rm -rf %t
// RUN: mkdir %t
// RUN: split-file %s %t
//
// RUN: %clang_cc1 -xc++ -std=c++20 -fmodules -fmodule-name=library \
// RUN: -emit-module %t/modules.map \
// RUN: -o %t/module.pcm \
// RUN: -verify
//
//--- modules.map
module "library" {
export *
module "concepts" {
export *
header "concepts.h"
}
module "conflicting" {
export *
header "conflicting.h"
}
}
//--- concepts.h
#ifndef CONCEPTS_H_
#define CONCEPTS_H_
template <class T>
concept ConflictingConcept = true;
template <class T, class U>
concept same_as = __is_same(T, U);
template<class T> concept truec = true;
int var;
#endif // SAMEAS_CONCEPTS_H
//--- conflicting.h
#ifndef CONFLICTING_H
#define CONFLICTING_H
#include "concepts.h"
template <class T, class U = int>
concept ConflictingConcept = true; // expected-error {{redefinition of concept 'ConflictingConcept' with different template}}
// expected-note@* {{previous definition}}
int same_as; // expected-error {{redefinition of 'same_as' as different kind of symbol}}
// expected-note@* {{previous definition}}
template<class T> concept var = false; // expected-error {{redefinition of 'var' as different kind of symbol}}
// expected-note@* {{previous definition}}
template<class T> concept truec = true; // expected-error {{redefinition of 'truec'}}
// expected-note@* {{previous definition}}
#endif // CONFLICTING_H