diff options
Diffstat (limited to 'libstdc++-v3/testsuite')
16 files changed, 372 insertions, 16 deletions
diff --git a/libstdc++-v3/testsuite/17_intro/headers/c++2011/42319.cc b/libstdc++-v3/testsuite/17_intro/headers/c++2011/42319.cc index cd576ca..350a548 100644 --- a/libstdc++-v3/testsuite/17_intro/headers/c++2011/42319.cc +++ b/libstdc++-v3/testsuite/17_intro/headers/c++2011/42319.cc @@ -1,5 +1,5 @@ // { dg-do compile } -// { dg-options "-std=gnu++11" } +// { dg-add-options no_pch } // Copyright (C) 2009-2025 Free Software Foundation, Inc. // @@ -19,4 +19,4 @@ // <http://www.gnu.org/licenses/>. // libstdc++/42319 -#include <bits/char_traits.h> +#include <ios> diff --git a/libstdc++-v3/testsuite/20_util/is_implicit_lifetime/value.cc b/libstdc++-v3/testsuite/20_util/is_implicit_lifetime/value.cc new file mode 100644 index 0000000..d8cb181 --- /dev/null +++ b/libstdc++-v3/testsuite/20_util/is_implicit_lifetime/value.cc @@ -0,0 +1,129 @@ +// Copyright (C) 2025 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library is free +// software; you can redistribute it and/or modify it under the +// terms of the GNU General Public License as published by the +// Free Software Foundation; either version 3, or (at your option) +// any later version. + +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// You should have received a copy of the GNU General Public License along +// with this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++23 } } +// { dg-add-options no_pch } + +#include <type_traits> + +#ifndef __cpp_lib_is_implicit_lifetime +# error "Feature test macro for is_implicit_lifetime is missing in <type_traits>" +#elif __cpp_lib_is_implicit_lifetime < 202302L +# error "Feature test macro for is_implicit_lifetime has wrong value in <type_traits>" +#endif + +#include <testsuite_tr1.h> + +template<typename T> + concept Is_implicit_lifetime + = __gnu_test::test_category<std::is_implicit_lifetime, T>(true); + +static_assert( ! Is_implicit_lifetime<void> ); +static_assert( ! Is_implicit_lifetime<const void> ); +static_assert( ! Is_implicit_lifetime<volatile void> ); +static_assert( Is_implicit_lifetime<char> ); +static_assert( Is_implicit_lifetime<signed char> ); +static_assert( Is_implicit_lifetime<const unsigned char> ); +static_assert( Is_implicit_lifetime<short> ); +static_assert( Is_implicit_lifetime<volatile unsigned short> ); +static_assert( Is_implicit_lifetime<int> ); +static_assert( Is_implicit_lifetime<unsigned int> ); +static_assert( Is_implicit_lifetime<const volatile long> ); +static_assert( Is_implicit_lifetime<unsigned long> ); +static_assert( Is_implicit_lifetime<long long> ); +static_assert( Is_implicit_lifetime<unsigned long long> ); +static_assert( Is_implicit_lifetime<float> ); +static_assert( Is_implicit_lifetime<double> ); +static_assert( Is_implicit_lifetime<long double volatile> ); +enum W { W1 }; +static_assert( Is_implicit_lifetime<W> ); +enum class X : int { X1 }; +static_assert( Is_implicit_lifetime<const volatile X> ); +static_assert( Is_implicit_lifetime<int *> ); +static_assert( Is_implicit_lifetime<int (*) (int)> ); +struct Y { int g; int foo (int); }; +static_assert( Is_implicit_lifetime<int (Y::*)> ); +static_assert( Is_implicit_lifetime<int (Y::*) (int)> ); +static_assert( ! Is_implicit_lifetime<int &> ); +static_assert( ! Is_implicit_lifetime<char &&> ); +static_assert( Is_implicit_lifetime<int []> ); +static_assert( Is_implicit_lifetime<int [1]> ); +static_assert( Is_implicit_lifetime<const Y [42]> ); +static_assert( ! Is_implicit_lifetime<int ()> ); +static_assert( ! Is_implicit_lifetime<int () &> ); +static_assert( ! Is_implicit_lifetime<int () const> ); +static_assert( ! Is_implicit_lifetime<int (&) ()> ); +struct Z; +static_assert( Is_implicit_lifetime<Z []> ); +static_assert( Is_implicit_lifetime<Z [5]> ); +struct A { int a, b, c; }; +static_assert( Is_implicit_lifetime<A> ); +class B { static int a; private: static int b; public: int c; }; +static_assert( Is_implicit_lifetime<B> ); +struct C { C () {} int a, b, c; }; +static_assert( Is_implicit_lifetime<C> ); +struct D { explicit D (int) {} int a, b, c; }; +static_assert( Is_implicit_lifetime<D> ); +struct E : public A { int d, e, f; }; +static_assert( Is_implicit_lifetime<E> ); +struct F : public C { using C::C; int d, e, f; }; +static_assert( Is_implicit_lifetime<F> ); +class G { int a, b; }; +static_assert( Is_implicit_lifetime<G> ); +struct H { private: int a, b; }; +static_assert( Is_implicit_lifetime<H> ); +struct I { protected: int a, b; }; +static_assert( Is_implicit_lifetime<I> ); +struct J { int a, b; void foo (); }; +static_assert( Is_implicit_lifetime<J> ); +struct K { int a, b; virtual void foo (); }; +static_assert( ! Is_implicit_lifetime<K> ); +struct L : virtual public A { int d, e; }; +static_assert( ! Is_implicit_lifetime<L> ); +struct M : protected A { int d, e; }; +static_assert( Is_implicit_lifetime<M> ); +struct N : private A { int d, e; }; +static_assert( Is_implicit_lifetime<N> ); +struct O { O () = delete; int a, b, c; }; +static_assert( Is_implicit_lifetime<O> ); +struct P { P () = default; int a, b, c; }; +static_assert( Is_implicit_lifetime<P> ); +struct Q { Q (); Q (const Q &); int a, b, c; }; +static_assert( ! Is_implicit_lifetime<Q> ); +struct R { R (); R (const R &); R (R &&) = default; int a, b, c; }; +static_assert( Is_implicit_lifetime<R> ); +struct S { S (); ~S (); int a, b, c; }; +static_assert( ! Is_implicit_lifetime<S> ); +static_assert( Is_implicit_lifetime<S [3]> ); +struct T { T (); ~T () = default; int a, b, c; }; +static_assert( Is_implicit_lifetime<T> ); +struct U { U (); U (const U &) = default; int a, b, c; }; +static_assert( Is_implicit_lifetime<U> ); +struct V { V () = default; V (const V &); int a, b, c; }; +static_assert( Is_implicit_lifetime<V> ); +struct AA { Q a; Q b; }; +static_assert( Is_implicit_lifetime<AA> ); +struct AB { Q a; Q b; ~AB () = default; }; +static_assert( Is_implicit_lifetime<AB> ); +struct AC { Q a; Q b; ~AC () {} }; +static_assert( ! Is_implicit_lifetime<AC> ); +struct AD : public Q {}; +static_assert( Is_implicit_lifetime<AD> ); +struct AE : public Q { ~AE () = default; }; +static_assert( Is_implicit_lifetime<AE> ); +struct AF : public Q { ~AF () {} }; +static_assert( ! Is_implicit_lifetime<AF> ); diff --git a/libstdc++-v3/testsuite/20_util/is_implicit_lifetime/version.cc b/libstdc++-v3/testsuite/20_util/is_implicit_lifetime/version.cc new file mode 100644 index 0000000..ed90b47 --- /dev/null +++ b/libstdc++-v3/testsuite/20_util/is_implicit_lifetime/version.cc @@ -0,0 +1,27 @@ +// Copyright (C) 2025 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library is free +// software; you can redistribute it and/or modify it under the +// terms of the GNU General Public License as published by the +// Free Software Foundation; either version 3, or (at your option) +// any later version. + +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// You should have received a copy of the GNU General Public License along +// with this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++23 } } +// { dg-add-options no_pch } + +#include <version> + +#ifndef __cpp_lib_is_implicit_lifetime +# error "Feature test macro for is_implicit_lifetime is missing in <version>" +#elif __cpp_lib_is_implicit_lifetime < 202302L +# error "Feature test macro for is_implicit_lifetime has wrong value in <version>" +#endif diff --git a/libstdc++-v3/testsuite/20_util/shared_ptr/atomic/pr118757.cc b/libstdc++-v3/testsuite/20_util/shared_ptr/atomic/pr118757.cc index d54abd8..f49ae38 100644 --- a/libstdc++-v3/testsuite/20_util/shared_ptr/atomic/pr118757.cc +++ b/libstdc++-v3/testsuite/20_util/shared_ptr/atomic/pr118757.cc @@ -1,4 +1,5 @@ // { dg-do run { target c++20 } } +// { dg-additional-options "-pthread" { target pthread } } // { dg-require-gthreads "" } // { dg-require-effective-target hosted } diff --git a/libstdc++-v3/testsuite/20_util/tuple/requirements/empty_trivial.cc b/libstdc++-v3/testsuite/20_util/tuple/requirements/empty_trivial.cc new file mode 100644 index 0000000..ee18bb3 --- /dev/null +++ b/libstdc++-v3/testsuite/20_util/tuple/requirements/empty_trivial.cc @@ -0,0 +1,17 @@ +// { dg-do compile { target c++11 } } + +#include <tuple> +#include <type_traits> + +// Check that tuple<> has the expected trivial properties +static_assert(std::is_trivially_copyable<std::tuple<>>::value, + "tuple<> should be trivially copyable"); +static_assert(std::is_trivially_copy_constructible<std::tuple<>>::value, + "tuple<> should be trivially copy constructible"); +static_assert(std::is_trivially_move_constructible<std::tuple<>>::value, + "tuple<> should be trivially move constructible"); +static_assert(std::is_trivially_copy_assignable<std::tuple<>>::value, + "tuple<> should be trivially copy assignable"); +static_assert(std::is_trivially_move_assignable<std::tuple<>>::value, + "tuple<> should be trivially move assignable"); + diff --git a/libstdc++-v3/testsuite/20_util/weak_ptr/pr118757.cc b/libstdc++-v3/testsuite/20_util/weak_ptr/pr118757.cc index f048f13..77757f3 100644 --- a/libstdc++-v3/testsuite/20_util/weak_ptr/pr118757.cc +++ b/libstdc++-v3/testsuite/20_util/weak_ptr/pr118757.cc @@ -1,4 +1,5 @@ // { dg-do run { target c++20 } } +// { dg-additional-options "-pthread" { target pthread } } // { dg-require-gthreads "" } // { dg-require-effective-target hosted } diff --git a/libstdc++-v3/testsuite/23_containers/tuple/cons/119721.cc b/libstdc++-v3/testsuite/23_containers/tuple/cons/119721.cc new file mode 100644 index 0000000..1d15238 --- /dev/null +++ b/libstdc++-v3/testsuite/23_containers/tuple/cons/119721.cc @@ -0,0 +1,121 @@ +// { dg-do run { target c++23 } } + +// Test for PR libstdc++/119721: tuple<> construction/assignment with array<T, 0> + +#include <tuple> +#include <array> +#include <memory> +#include <testsuite_hooks.h> + +constexpr void +test01() +{ + std::array<int, 0> a{}; + + // Constructor from array<int, 0> + std::tuple<> t1(a); + std::tuple<> t2(std::move(a)); + + // Assignment from array<int, 0> + std::tuple<> t3; + t3 = a; + t3 = std::move(a); + + VERIFY( t1 == a ); + VERIFY( t2 == a ); + VERIFY( t3 == a ); +} + +constexpr void +test02() +{ + // Test with non-comparable element type + struct NonComparable + { + void operator==(const NonComparable&) const = delete; + void operator<=>(const NonComparable&) const = delete; + }; + + std::array<NonComparable, 0> a{}; + + std::tuple<> t1(a); + std::tuple<> t2(std::move(a)); + + std::tuple<> t3; + t3 = a; + t3 = std::move(a); + + VERIFY( t1 == a ); +} + +constexpr void +test03() +{ + // Test assignment return type (non-const assignment) + std::tuple<> t, u; + std::tuple<>& r1 = (t = u); + VERIFY( &r1 == &t ); + + std::tuple<>& r2 = (t = {}); + VERIFY( &r2 == &t ); + + std::array<int, 0> a{}; + std::tuple<>& r3 = (t = a); + VERIFY( &r3 == &t ); +} + +constexpr void +test04() +{ + std::array<int, 0> a{}; + const std::tuple<> t1; + + // Const assignment from array + std::tuple<> t2; + const std::tuple<>& r1 = (t1 = t2); + VERIFY( &r1 == &t1 ); + const std::tuple<>& r2 = (t1 = std::move(t2)); + VERIFY( &r2 == &t1 ); + + const std::tuple<>& r3 = (t1 = {}); + VERIFY( &r3 == &t1 ); + + // Const assignment from array + const std::tuple<>& r4 = (t1 = a); + VERIFY( &r4 == &t1 ); + const std::tuple<>& r5 = (t1 = std::move(a)); + VERIFY( &r5 == &t1 ); +} + +void +test05() +{ + std::array<int, 0> a{}; + std::allocator<int> alloc; + + // Allocator constructor from array + std::tuple<> t1(std::allocator_arg, alloc, a); + std::tuple<> t2(std::allocator_arg, alloc, std::move(a)); + + VERIFY( t1 == a ); + VERIFY( t2 == a ); +} + +int main() +{ + auto test_all = [] { + test01(); + test02(); + test03(); + test04(); + return true; + }; + + test_all(); + static_assert( test_all() ); + + // allocator test is not constexpr + test05(); + return 0; +} + diff --git a/libstdc++-v3/testsuite/26_numerics/valarray/108951.cc b/libstdc++-v3/testsuite/26_numerics/valarray/108951.cc new file mode 100644 index 0000000..929a1d4 --- /dev/null +++ b/libstdc++-v3/testsuite/26_numerics/valarray/108951.cc @@ -0,0 +1,22 @@ +// { dg-do run { target c++11 } } +// { dg-additional-options "-faligned-new" { target c++14_down } } + +#include <valarray> +#include <cstdint> +#include <testsuite_hooks.h> + +struct alignas(64) Num +{ + Num() + { + VERIFY(reinterpret_cast<std::uintptr_t>(this) % alignof(*this) == 0); + } + + double val{}; +}; + +int main() +{ + std::valarray<Num> v(2); + v.resize(4, {}); +} diff --git a/libstdc++-v3/testsuite/30_threads/condition_variable/members/116586.cc b/libstdc++-v3/testsuite/30_threads/condition_variable/members/116586.cc index 7114007..e8c3e16 100644 --- a/libstdc++-v3/testsuite/30_threads/condition_variable/members/116586.cc +++ b/libstdc++-v3/testsuite/30_threads/condition_variable/members/116586.cc @@ -1,4 +1,7 @@ // { dg-do run { target c++11 } } +// { dg-additional-options "-pthread" { target pthread } } +// { dg-require-gthreads "" } +// { dg-require-effective-target hosted } #include <condition_variable> #include <chrono> diff --git a/libstdc++-v3/testsuite/30_threads/future/members/116586.cc b/libstdc++-v3/testsuite/30_threads/future/members/116586.cc index b7cd12c..82f1e5c 100644 --- a/libstdc++-v3/testsuite/30_threads/future/members/116586.cc +++ b/libstdc++-v3/testsuite/30_threads/future/members/116586.cc @@ -1,4 +1,7 @@ // { dg-do run { target c++11 } } +// { dg-additional-options "-pthread" { target pthread } } +// { dg-require-gthreads "" } +// { dg-require-effective-target hosted } #include <future> #include <chrono> diff --git a/libstdc++-v3/testsuite/30_threads/recursive_timed_mutex/try_lock_until/116586.cc b/libstdc++-v3/testsuite/30_threads/recursive_timed_mutex/try_lock_until/116586.cc index 941f3af..25a78e7 100644 --- a/libstdc++-v3/testsuite/30_threads/recursive_timed_mutex/try_lock_until/116586.cc +++ b/libstdc++-v3/testsuite/30_threads/recursive_timed_mutex/try_lock_until/116586.cc @@ -1,4 +1,7 @@ // { dg-do run { target c++11 } } +// { dg-additional-options "-pthread" { target pthread } } +// { dg-require-gthreads "" } +// { dg-require-effective-target hosted } #include <mutex> #include <chrono> diff --git a/libstdc++-v3/testsuite/30_threads/shared_timed_mutex/try_lock_until/116586.cc b/libstdc++-v3/testsuite/30_threads/shared_timed_mutex/try_lock_until/116586.cc index cebbb3a..5736b7d 100644 --- a/libstdc++-v3/testsuite/30_threads/shared_timed_mutex/try_lock_until/116586.cc +++ b/libstdc++-v3/testsuite/30_threads/shared_timed_mutex/try_lock_until/116586.cc @@ -1,4 +1,7 @@ // { dg-do run { target c++14 } } +// { dg-additional-options "-pthread" { target pthread } } +// { dg-require-gthreads "" } +// { dg-require-effective-target hosted } #include <shared_mutex> #include <chrono> @@ -8,10 +11,18 @@ namespace chrono = std::chrono; -// thread.timedmutex.requirements.general: +// [thread.timedmutex.requirements.general]: // If abs_time has already passed, the function attempts to obtain // ownership without blocking (as if by calling try_lock()). +// C++14 [thread.sharedtimedmutex.class] 3.2 says it's undefined for a thread +// to attempt to recursively gain any ownership of a shared_timed_mutex. +// This isn't just theoretical, as Glibc's pthread_rwlock_timedrdlock will +// return EDEADLK if called on the same thread that already holds the +// exclusive (write) lock. +#define VERIFY_IN_NEW_THREAD(X) \ + (void) std::async(std::launch::async, [&] { VERIFY(X); }) + template <typename Clock> void test_exclusive_absolute(chrono::nanoseconds offset) @@ -19,7 +30,7 @@ test_exclusive_absolute(chrono::nanoseconds offset) std::shared_timed_mutex stm; chrono::time_point<Clock> tp(offset); VERIFY(stm.try_lock_until(tp)); - VERIFY(!stm.try_lock_until(tp)); + VERIFY_IN_NEW_THREAD(!stm.try_lock_until(tp)); } template <typename Clock> @@ -32,15 +43,7 @@ test_shared_absolute(chrono::nanoseconds offset) stm.unlock_shared(); VERIFY(stm.try_lock_for(chrono::seconds{10})); - - { - // NPTL will give us EDEADLK if pthread_rwlock_timedrdlock() is called on - // the same thread that already holds the exclusive (write) lock, so let's - // arrange for a different thread to try to acquire the shared lock. - auto t = std::async(std::launch::async, [&stm, tp]() { - VERIFY(!stm.try_lock_shared_until(tp)); - }); - } + VERIFY_IN_NEW_THREAD(!stm.try_lock_shared_until(tp)); } // The type of clock used for the actual wait depends on whether @@ -53,7 +56,7 @@ test_exclusive_relative(chrono::nanoseconds offset) std::shared_timed_mutex stm; const auto d = -Clock::now().time_since_epoch() + offset; VERIFY(stm.try_lock_for(d)); - VERIFY(!stm.try_lock_for(d)); + VERIFY_IN_NEW_THREAD(!stm.try_lock_for(d)); } template <typename Clock> @@ -66,7 +69,7 @@ test_shared_relative(chrono::nanoseconds offset) stm.unlock_shared(); // Should complete immediately VERIFY(stm.try_lock_for(chrono::seconds{10})); - VERIFY(!stm.try_lock_shared_for(d)); + VERIFY_IN_NEW_THREAD(!stm.try_lock_shared_for(d)); } int main() diff --git a/libstdc++-v3/testsuite/30_threads/thread/swap/1.cc b/libstdc++-v3/testsuite/30_threads/thread/swap/1.cc index 9616b15..b1fde09 100644 --- a/libstdc++-v3/testsuite/30_threads/thread/swap/1.cc +++ b/libstdc++-v3/testsuite/30_threads/thread/swap/1.cc @@ -23,7 +23,7 @@ #include <thread> #include <system_error> -#include <bits/move.h> // std::move +#include <utility> // std::move #include <testsuite_hooks.h> void f() { } diff --git a/libstdc++-v3/testsuite/30_threads/timed_mutex/try_lock_until/116586.cc b/libstdc++-v3/testsuite/30_threads/timed_mutex/try_lock_until/116586.cc index dcba7aa..1566228 100644 --- a/libstdc++-v3/testsuite/30_threads/timed_mutex/try_lock_until/116586.cc +++ b/libstdc++-v3/testsuite/30_threads/timed_mutex/try_lock_until/116586.cc @@ -1,4 +1,7 @@ // { dg-do run { target c++11 } } +// { dg-additional-options "-pthread" { target pthread } } +// { dg-require-gthreads "" } +// { dg-require-effective-target hosted } #include <chrono> #include <mutex> diff --git a/libstdc++-v3/testsuite/ext/iotaarray.cc b/libstdc++-v3/testsuite/ext/iotaarray.cc new file mode 100644 index 0000000..b259602 --- /dev/null +++ b/libstdc++-v3/testsuite/ext/iotaarray.cc @@ -0,0 +1,20 @@ +// { dg-do compile { target c++26 } } + +#include <utility> +#include <type_traits> + +template<auto N> +void test() +{ + constexpr auto [id0, ...ids] = std::_IotaArray<N>; + static_assert( std::is_same_v<decltype(id0), const decltype(N)> ); + static_assert( sizeof...(ids) == N - 1 ); + static_assert( (id0 + ... + ids) == N*(N-1)/2 ); +} + +int main() +{ + test<1>(); + test<4u>(); + test<8ull>(); +} diff --git a/libstdc++-v3/testsuite/util/testsuite_iterators.h b/libstdc++-v3/testsuite/util/testsuite_iterators.h index 5bf2e70..41fbcaa 100644 --- a/libstdc++-v3/testsuite/util/testsuite_iterators.h +++ b/libstdc++-v3/testsuite/util/testsuite_iterators.h @@ -674,6 +674,9 @@ namespace __gnu_test template <class T, template<class TT> class ItType> struct test_container { + typedef ItType<T> iterator; + typedef typename iterator::value_type value_type; + typename ItType<T>::ContainerType bounds; _GLIBCXX_CONSTEXPR |
