]> git.ipfire.org Git - thirdparty/gcc.git/blob - libstdc++-v3/testsuite/27_io/filesystem/path/append/source.cc
Update copyright years.
[thirdparty/gcc.git] / libstdc++-v3 / testsuite / 27_io / filesystem / path / append / source.cc
1 // { dg-options "-std=gnu++17 -lstdc++fs" }
2 // { dg-do run { target c++17 } }
3 // { dg-require-filesystem-ts "" }
4
5 // Copyright (C) 2018-2019 Free Software Foundation, Inc.
6 //
7 // This file is part of the GNU ISO C++ Library. This library is free
8 // software; you can redistribute it and/or modify it under the
9 // terms of the GNU General Public License as published by the
10 // Free Software Foundation; either version 3, or (at your option)
11 // any later version.
12
13 // This library is distributed in the hope that it will be useful,
14 // but WITHOUT ANY WARRANTY; without even the implied warranty of
15 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 // GNU General Public License for more details.
17
18 // You should have received a copy of the GNU General Public License along
19 // with this library; see the file COPYING3. If not see
20 // <http://www.gnu.org/licenses/>.
21
22 // C++17 30.10.8.4.3 path appends [fs.path.append]
23
24 #include <filesystem>
25 #include <string_view>
26 #include <testsuite_fs.h>
27 #include <testsuite_iterators.h>
28
29 using std::filesystem::path;
30 using __gnu_test::compare_paths;
31
32 // path::operator/=(const Source& source)
33 // path::append(const Source& source)
34 // Equivalent to: return operator/=(path(source));
35
36 // path::append(InputIterator first, InputIterator last)
37 // Equivalent to: return operator/=(path(first, last));
38
39 template<typename Char>
40 void test(const path& p, const Char* s)
41 {
42 path expected = p;
43 expected /= path(s);
44
45 path oper = p;
46 oper /= s;
47
48 path func = p;
49 func.append(s);
50
51 __gnu_test::test_container<const Char, __gnu_test::input_iterator_wrapper>
52 input_range(s, s + std::char_traits<Char>::length(s));
53 path range = p;
54 range.append(input_range.begin(), input_range.end());
55
56 compare_paths( oper, expected );
57 compare_paths( func, expected );
58 compare_paths( range, expected );
59 }
60
61 void
62 test01()
63 {
64 test( "/foo/bar", "/foo/" );
65
66 test( "baz", "baz" );
67 test( "baz/", "baz" );
68 test( "baz", "/foo/bar" );
69 test( "baz/", "/foo/bar" );
70
71 test( "", "" );
72 test( "", "rel" );
73
74 test( "dir/", "/file" );
75 test( "dir/", "file" );
76 }
77
78 void
79 test02()
80 {
81 // C++17 [fs.path.append] p4
82 test( "//host", "foo" );
83 test( "//host/", "foo" );
84 test( "foo", "" );
85 test( "foo", "/bar" );
86 test( "foo", "c:/bar" );
87 test( "foo", "c:" );
88 test( "c:", "" );
89 test( "c:foo", "/bar" );
90 test( "foo", "c:\\bar" );
91 }
92
93 void
94 test03()
95 {
96 for (const path& p : __gnu_test::test_paths)
97 for (const path& q : __gnu_test::test_paths)
98 {
99 test(p, q.c_str());
100 if constexpr (!std::is_same_v<path::value_type, char>)
101 test(p, q.string().c_str());
102 }
103 }
104
105 void
106 test04()
107 {
108 #ifdef _GLIBCXX_USE_WCHAR_T
109 test( "foo", L"/bar" );
110 test( L"foo", "/bar" );
111 test( L"foo", L"/bar" );
112 #endif
113 }
114
115 void
116 test05()
117 {
118 std::basic_string_view<path::value_type> s;
119
120 path p = "0/1/2/3/4/5/6";
121 // The string_view aliases the path's internal string:
122 s = p.native();
123 path::string_type expected(s);
124 expected += path::preferred_separator;
125 expected += s;
126 // Append that string_view, which must work correctly even though the
127 // internal string will be reallocated during the operation:
128 p /= s;
129 compare_paths(p, expected);
130
131 // Same again with a trailing slash:
132 path p2 = "0/1/2/3/4/5/";
133 s = p2.native();
134 expected = s;
135 expected += s;
136 p2 /= s;
137 compare_paths(p2, expected);
138
139 // And aliasing one of the components of the path:
140 path p3 = "0/123456789/a";
141 path::iterator second = std::next(p3.begin());
142 s = second->native();
143 expected = p3.native() + path::preferred_separator;
144 expected += s;
145 p3 /= s;
146 compare_paths(p3, expected);
147 }
148
149 void
150 test06()
151 {
152 const std::string s0 = "a/b/c";
153 path p = s0;
154 std::string s;
155 for (int i = 0; i < 10; ++i)
156 s += "0/1/2/3/4/5/6/7/8/9/";
157 // append a long string with many components
158 test(p, s.c_str());
159
160 // Same again but with a trailing slash on the left operand:
161 path p2 = s0 + '/';
162 test(p2, s.c_str());
163 }
164
165 int
166 main()
167 {
168 test01();
169 test02();
170 test03();
171 test04();
172 test05();
173 test06();
174 }