1 //===----------------------------------------------------------------------===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 9 // <array> 10 11 // implicitly generated array constructors / assignment operators 12 13 #include <array> 14 #include <type_traits> 15 #include <cassert> 16 #include "test_macros.h" 17 18 // std::array is explicitly allowed to be initialized with A a = { init-list };. 19 // Disable the missing braces warning for this reason. 20 #include "disable_missing_braces_warning.h" 21 22 // In C++03 the copy assignment operator is not deleted when the implicitly 23 // generated operator would be ill-formed; like in the case of a struct with a 24 // const member. 25 #if TEST_STD_VER < 11 26 # define TEST_NOT_COPY_ASSIGNABLE(T) ((void)0) 27 #else 28 # define TEST_NOT_COPY_ASSIGNABLE(T) static_assert(!std::is_copy_assignable<T>::value, "") 29 #endif 30 31 struct NoDefault { 32 TEST_CONSTEXPR NoDefault(int) { } 33 }; 34 35 struct NonTrivialCopy { 36 TEST_CONSTEXPR NonTrivialCopy() { } 37 TEST_CONSTEXPR NonTrivialCopy(NonTrivialCopy const&) { } 38 TEST_CONSTEXPR_CXX14 NonTrivialCopy& operator=(NonTrivialCopy const&) { return *this; } 39 }; 40 41 TEST_CONSTEXPR_CXX14 bool tests() 42 { 43 { 44 typedef std::array<double, 3> Array; 45 Array array = {1.1, 2.2, 3.3}; 46 Array copy = array; 47 copy = array; 48 static_assert(std::is_copy_constructible<Array>::value, ""); 49 static_assert(std::is_copy_assignable<Array>::value, ""); 50 } 51 { 52 typedef std::array<double const, 3> Array; 53 Array array = {1.1, 2.2, 3.3}; 54 Array copy = array; (void)copy; 55 static_assert(std::is_copy_constructible<Array>::value, ""); 56 TEST_NOT_COPY_ASSIGNABLE(Array); 57 } 58 { 59 typedef std::array<double, 0> Array; 60 Array array = {}; 61 Array copy = array; 62 copy = array; 63 static_assert(std::is_copy_constructible<Array>::value, ""); 64 static_assert(std::is_copy_assignable<Array>::value, ""); 65 } 66 { 67 // const arrays of size 0 should disable the implicit copy assignment operator. 68 typedef std::array<double const, 0> Array; 69 Array array = {}; 70 Array copy = array; (void)copy; 71 static_assert(std::is_copy_constructible<Array>::value, ""); 72 TEST_NOT_COPY_ASSIGNABLE(Array); 73 } 74 { 75 typedef std::array<NoDefault, 0> Array; 76 Array array = {}; 77 Array copy = array; 78 copy = array; 79 static_assert(std::is_copy_constructible<Array>::value, ""); 80 static_assert(std::is_copy_assignable<Array>::value, ""); 81 } 82 { 83 typedef std::array<NoDefault const, 0> Array; 84 Array array = {}; 85 Array copy = array; (void)copy; 86 static_assert(std::is_copy_constructible<Array>::value, ""); 87 TEST_NOT_COPY_ASSIGNABLE(Array); 88 } 89 90 // Make sure we can implicitly copy a std::array of a non-trivially copyable type 91 { 92 typedef std::array<NonTrivialCopy, 0> Array; 93 Array array = {}; 94 Array copy = array; 95 copy = array; 96 static_assert(std::is_copy_constructible<Array>::value, ""); 97 } 98 { 99 typedef std::array<NonTrivialCopy, 1> Array; 100 Array array = {}; 101 Array copy = array; 102 copy = array; 103 static_assert(std::is_copy_constructible<Array>::value, ""); 104 } 105 { 106 typedef std::array<NonTrivialCopy, 2> Array; 107 Array array = {}; 108 Array copy = array; 109 copy = array; 110 static_assert(std::is_copy_constructible<Array>::value, ""); 111 } 112 113 return true; 114 } 115 116 int main(int, char**) 117 { 118 tests(); 119 #if TEST_STD_VER >= 14 120 static_assert(tests(), ""); 121 #endif 122 return 0; 123 } 124