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 // reference at (size_type); // constexpr in C++17
12 
13 #include <array>
14 #include <cassert>
15 
16 #ifndef TEST_HAS_NO_EXCEPTIONS
17 #include <stdexcept>
18 #endif
19 
20 #include "test_macros.h"
21 
22 // std::array is explicitly allowed to be initialized with A a = { init-list };.
23 // Disable the missing braces warning for this reason.
24 #include "disable_missing_braces_warning.h"
25 
26 
27 TEST_CONSTEXPR_CXX17 bool tests()
28 {
29     {
30         typedef double T;
31         typedef std::array<T, 3> C;
32         C c = {1, 2, 3.5};
33         typename C::reference r1 = c.at(0);
34         assert(r1 == 1);
35         r1 = 5.5;
36         assert(c[0] == 5.5);
37 
38         typename C::reference r2 = c.at(2);
39         assert(r2 == 3.5);
40         r2 = 7.5;
41         assert(c[2] == 7.5);
42     }
43     return true;
44 }
45 
46 void test_exceptions()
47 {
48 #ifndef TEST_HAS_NO_EXCEPTIONS
49     {
50         std::array<int, 4> array = {1, 2, 3, 4};
51 
52         try {
53             TEST_IGNORE_NODISCARD array.at(4);
54             assert(false);
55         } catch (std::out_of_range const&) {
56             // pass
57         } catch (...) {
58             assert(false);
59         }
60 
61         try {
62             TEST_IGNORE_NODISCARD array.at(5);
63             assert(false);
64         } catch (std::out_of_range const&) {
65             // pass
66         } catch (...) {
67             assert(false);
68         }
69 
70         try {
71             TEST_IGNORE_NODISCARD array.at(6);
72             assert(false);
73         } catch (std::out_of_range const&) {
74             // pass
75         } catch (...) {
76             assert(false);
77         }
78 
79         try {
80             using size_type = decltype(array)::size_type;
81             TEST_IGNORE_NODISCARD array.at(static_cast<size_type>(-1));
82             assert(false);
83         } catch (std::out_of_range const&) {
84             // pass
85         } catch (...) {
86             assert(false);
87         }
88     }
89 
90     {
91         std::array<int, 0> array = {};
92 
93         try {
94             TEST_IGNORE_NODISCARD array.at(0);
95             assert(false);
96         } catch (std::out_of_range const&) {
97             // pass
98         } catch (...) {
99             assert(false);
100         }
101     }
102 #endif
103 }
104 
105 int main(int, char**)
106 {
107     tests();
108     test_exceptions();
109 
110 #if TEST_STD_VER >= 17
111     static_assert(tests(), "");
112 #endif
113     return 0;
114 }
115