Richard Smith | b5b37d1 | 2012-10-23 00:32:41 +0000 | [diff] [blame] | 1 | // RUN: %clang_cc1 -fsyntax-only %s -std=c++11 -verify |
| 2 | |
| 3 | // This is a test for an egregious hack in Clang that works around |
| 4 | // an issue with GCC's <type_traits> implementation. std::common_type |
| 5 | // relies on pre-standard rules for decltype(), in which it doesn't |
| 6 | // produce reference types so frequently. |
| 7 | |
| 8 | #ifdef BE_THE_HEADER |
| 9 | |
| 10 | #pragma GCC system_header |
| 11 | namespace std { |
| 12 | template<typename T> T &&declval(); |
| 13 | |
| 14 | template<typename...Ts> struct common_type {}; |
| 15 | template<typename A, typename B> struct common_type<A, B> { |
| 16 | // Under the rules in the standard, this always produces a |
| 17 | // reference type. |
| 18 | typedef decltype(true ? declval<A>() : declval<B>()) type; |
| 19 | }; |
| 20 | } |
| 21 | |
| 22 | #else |
| 23 | |
| 24 | #define BE_THE_HEADER |
| 25 | #include "libstdcxx_common_type_hack.cpp" |
| 26 | |
| 27 | using T = int; |
| 28 | using T = std::common_type<int, int>::type; |
| 29 | |
| 30 | using U = int; // expected-note {{here}} |
| 31 | using U = decltype(true ? std::declval<int>() : std::declval<int>()); // expected-error {{different types}} |
| 32 | |
| 33 | #endif |