1f7b43230SLouis Dionne //===----------------------------------------------------------------------===//
2f7b43230SLouis Dionne //
3f7b43230SLouis Dionne // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4f7b43230SLouis Dionne // See https://llvm.org/LICENSE.txt for license information.
5f7b43230SLouis Dionne // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6f7b43230SLouis Dionne //
7f7b43230SLouis Dionne //===----------------------------------------------------------------------===//
8f7b43230SLouis Dionne 
9*ac8c9f1eSLouis Dionne // UNSUPPORTED: c++03, c++11, c++14
10c352fa74SLouis Dionne // UNSUPPORTED: availability-filesystem-missing
11f7b43230SLouis Dionne 
1288ffc727SLouis Dionne // These tests require locale for non-char paths
13a7f9895cSLouis Dionne // UNSUPPORTED: no-localization
1488ffc727SLouis Dionne 
15f7b43230SLouis Dionne // <filesystem>
16f7b43230SLouis Dionne 
17f7b43230SLouis Dionne // class path
18f7b43230SLouis Dionne 
19f7b43230SLouis Dionne // template <class Source>
20f7b43230SLouis Dionne //      path(const Source& source);
21f7b43230SLouis Dionne // template <class InputIterator>
22f7b43230SLouis Dionne //      path(InputIterator first, InputIterator last);
23f7b43230SLouis Dionne 
24*ac8c9f1eSLouis Dionne #include <filesystem>
25f7b43230SLouis Dionne #include <type_traits>
26f7b43230SLouis Dionne #include <cassert>
27f7b43230SLouis Dionne 
28c352fa74SLouis Dionne #include "../../path_helper.h"
29c352fa74SLouis Dionne #include "make_string.h"
30f7b43230SLouis Dionne #include "min_allocator.h"
31c352fa74SLouis Dionne #include "test_iterators.h"
32c352fa74SLouis Dionne #include "test_macros.h"
33*ac8c9f1eSLouis Dionne namespace fs = std::filesystem;
34f7b43230SLouis Dionne 
35f7b43230SLouis Dionne template <class CharT, class ...Args>
RunTestCaseImpl(MultiStringType const & MS,Args...args)36f7b43230SLouis Dionne void RunTestCaseImpl(MultiStringType const& MS, Args... args) {
37f7b43230SLouis Dionne   using namespace fs;
383784bdf2SMartin Storsjö   const fs::path::value_type* Expect = MS;
39f7b43230SLouis Dionne   const CharT* TestPath = MS;
40f7b43230SLouis Dionne   const CharT* TestPathEnd = StrEnd(TestPath);
41f7b43230SLouis Dionne   const std::size_t Size = TestPathEnd - TestPath;
42f7b43230SLouis Dionne   const std::size_t SSize = StrEnd(Expect) - Expect;
43f7b43230SLouis Dionne   assert(Size == SSize);
44f7b43230SLouis Dionne   // StringTypes
45f7b43230SLouis Dionne   {
46f7b43230SLouis Dionne     const std::basic_string<CharT> S(TestPath);
47f7b43230SLouis Dionne     path p(S, args...);
48f7b43230SLouis Dionne     assert(p.native() == Expect);
49f7b43230SLouis Dionne     assert(p.string<CharT>() == TestPath);
50f7b43230SLouis Dionne     assert(p.string<CharT>() == S);
51f7b43230SLouis Dionne   }
52f7b43230SLouis Dionne   {
53f7b43230SLouis Dionne     const std::basic_string_view<CharT> S(TestPath);
54f7b43230SLouis Dionne     path p(S, args...);
55f7b43230SLouis Dionne     assert(p.native() == Expect);
56f7b43230SLouis Dionne     assert(p.string<CharT>() == TestPath);
57f7b43230SLouis Dionne     assert(p.string<CharT>() == S);
58f7b43230SLouis Dionne   }
59f7b43230SLouis Dionne   // Char* pointers
60f7b43230SLouis Dionne   {
61f7b43230SLouis Dionne     path p(TestPath, args...);
62f7b43230SLouis Dionne     assert(p.native() == Expect);
63f7b43230SLouis Dionne     assert(p.string<CharT>() == TestPath);
64f7b43230SLouis Dionne   }
65f7b43230SLouis Dionne   {
66f7b43230SLouis Dionne     path p(TestPath, TestPathEnd, args...);
67f7b43230SLouis Dionne     assert(p.native() == Expect);
68f7b43230SLouis Dionne     assert(p.string<CharT>() == TestPath);
69f7b43230SLouis Dionne   }
70f7b43230SLouis Dionne   // Iterators
71f7b43230SLouis Dionne   {
72773ae441SChristopher Di Bella     using It = cpp17_input_iterator<const CharT*>;
73f7b43230SLouis Dionne     path p(It{TestPath}, args...);
74f7b43230SLouis Dionne     assert(p.native() == Expect);
75f7b43230SLouis Dionne     assert(p.string<CharT>() == TestPath);
76f7b43230SLouis Dionne   }
77f7b43230SLouis Dionne   {
78773ae441SChristopher Di Bella     using It = cpp17_input_iterator<const CharT*>;
79f7b43230SLouis Dionne     path p(It{TestPath}, It{TestPathEnd}, args...);
80f7b43230SLouis Dionne     assert(p.native() == Expect);
81f7b43230SLouis Dionne     assert(p.string<CharT>() == TestPath);
82f7b43230SLouis Dionne   }
83f7b43230SLouis Dionne }
84f7b43230SLouis Dionne 
85f7b43230SLouis Dionne template <class CharT, class ...Args>
RunTestCase(MultiStringType const & MS)86f7b43230SLouis Dionne void RunTestCase(MultiStringType const& MS) {
87f7b43230SLouis Dionne   RunTestCaseImpl<CharT>(MS);
88f7b43230SLouis Dionne   RunTestCaseImpl<CharT>(MS, fs::path::format::auto_format);
89f7b43230SLouis Dionne   RunTestCaseImpl<CharT>(MS, fs::path::format::native_format);
90f7b43230SLouis Dionne   RunTestCaseImpl<CharT>(MS, fs::path::format::generic_format);
9126005c78SMartin Storsjö   RunTestCaseImpl<CharT>(MS, fs::path::auto_format);
9226005c78SMartin Storsjö   RunTestCaseImpl<CharT>(MS, fs::path::native_format);
9326005c78SMartin Storsjö   RunTestCaseImpl<CharT>(MS, fs::path::generic_format);
94f7b43230SLouis Dionne }
95f7b43230SLouis Dionne 
test_sfinae()96f7b43230SLouis Dionne void test_sfinae() {
97f7b43230SLouis Dionne   using namespace fs;
98f7b43230SLouis Dionne   {
99f7b43230SLouis Dionne     using It = const char* const;
100f7b43230SLouis Dionne     static_assert(std::is_constructible<path, It>::value, "");
101f7b43230SLouis Dionne   }
102f7b43230SLouis Dionne   {
103773ae441SChristopher Di Bella     using It = cpp17_input_iterator<const char*>;
104f7b43230SLouis Dionne     static_assert(std::is_constructible<path, It>::value, "");
105f7b43230SLouis Dionne   }
106f7b43230SLouis Dionne   {
107f7b43230SLouis Dionne     struct Traits {
108f7b43230SLouis Dionne       using iterator_category = std::input_iterator_tag;
109f7b43230SLouis Dionne       using value_type = const char;
110f7b43230SLouis Dionne       using pointer = const char*;
111f7b43230SLouis Dionne       using reference = const char&;
112f7b43230SLouis Dionne       using difference_type = std::ptrdiff_t;
113f7b43230SLouis Dionne     };
114773ae441SChristopher Di Bella     using It = cpp17_input_iterator<const char*, Traits>;
115f7b43230SLouis Dionne     static_assert(std::is_constructible<path, It>::value, "");
116f7b43230SLouis Dionne   }
117f7b43230SLouis Dionne   {
1185e97d37bSMark de Wever     using It = cpp17_output_iterator<const char*>;
119f7b43230SLouis Dionne     static_assert(!std::is_constructible<path, It>::value, "");
120f7b43230SLouis Dionne 
121f7b43230SLouis Dionne   }
122f7b43230SLouis Dionne   {
123f7b43230SLouis Dionne     static_assert(!std::is_constructible<path, int*>::value, "");
124f7b43230SLouis Dionne   }
125f7b43230SLouis Dionne }
126f7b43230SLouis Dionne 
main(int,char **)127f7b43230SLouis Dionne int main(int, char**) {
128f7b43230SLouis Dionne   for (auto const& MS : PathList) {
129f7b43230SLouis Dionne     RunTestCase<char>(MS);
1306be11e35SMartin Storsjö #if TEST_STD_VER > 17 && defined(__cpp_char8_t)
1316be11e35SMartin Storsjö     RunTestCase<char8_t>(MS);
1326be11e35SMartin Storsjö #endif
133f4c1258dSLouis Dionne #ifndef TEST_HAS_NO_WIDE_CHARACTERS
134f7b43230SLouis Dionne     RunTestCase<wchar_t>(MS);
135f4c1258dSLouis Dionne #endif
136f7b43230SLouis Dionne     RunTestCase<char16_t>(MS);
137f7b43230SLouis Dionne     RunTestCase<char32_t>(MS);
138f7b43230SLouis Dionne   }
139f7b43230SLouis Dionne   test_sfinae();
140f7b43230SLouis Dionne 
141f7b43230SLouis Dionne   return 0;
142f7b43230SLouis Dionne }
143