source.pass.cpp 6.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241
  1. //===----------------------------------------------------------------------===//
  2. //
  3. // The LLVM Compiler Infrastructure
  4. //
  5. // This file is dual licensed under the MIT and the University of Illinois Open
  6. // Source Licenses. See LICENSE.TXT for details.
  7. //
  8. //===----------------------------------------------------------------------===//
  9. // UNSUPPORTED: c++98, c++03
  10. // <experimental/filesystem>
  11. // class path
  12. // template <class Source>
  13. // path& operator=(Source const&);
  14. // path& operator=(string_type&&);
  15. // template <class Source>
  16. // path& assign(Source const&);
  17. // template <class InputIterator>
  18. // path& assign(InputIterator first, InputIterator last);
  19. #include "filesystem_include.hpp"
  20. #include <type_traits>
  21. #include <string_view>
  22. #include <cassert>
  23. #include "test_macros.h"
  24. #include "test_iterators.h"
  25. #include "count_new.hpp"
  26. #include "filesystem_test_helper.hpp"
  27. #include <iostream>
  28. template <class CharT>
  29. void RunTestCase(MultiStringType const& MS) {
  30. using namespace fs;
  31. const char* Expect = MS;
  32. const CharT* TestPath = MS;
  33. const CharT* TestPathEnd = StrEnd(TestPath);
  34. const std::size_t Size = TestPathEnd - TestPath;
  35. const std::size_t SSize = StrEnd(Expect) - Expect;
  36. assert(Size == SSize);
  37. //////////////////////////////////////////////////////////////////////////////
  38. // basic_string<Char, Traits, Alloc>
  39. {
  40. const std::basic_string<CharT> S(TestPath);
  41. path p; PathReserve(p, S.length() + 1);
  42. {
  43. // string provides a contiguous iterator. No allocation needed.
  44. DisableAllocationGuard g;
  45. path& pref = (p = S);
  46. assert(&pref == &p);
  47. }
  48. assert(p.native() == Expect);
  49. assert(p.string<CharT>() == TestPath);
  50. assert(p.string<CharT>() == S);
  51. }
  52. {
  53. const std::basic_string<CharT> S(TestPath);
  54. path p; PathReserve(p, S.length() + 1);
  55. {
  56. DisableAllocationGuard g;
  57. path& pref = p.assign(S);
  58. assert(&pref == &p);
  59. }
  60. assert(p.native() == Expect);
  61. assert(p.string<CharT>() == TestPath);
  62. assert(p.string<CharT>() == S);
  63. }
  64. // basic_string<Char, Traits, Alloc>
  65. {
  66. const std::basic_string_view<CharT> S(TestPath);
  67. path p; PathReserve(p, S.length() + 1);
  68. {
  69. // string provides a contiguous iterator. No allocation needed.
  70. DisableAllocationGuard g;
  71. path& pref = (p = S);
  72. assert(&pref == &p);
  73. }
  74. assert(p.native() == Expect);
  75. assert(p.string<CharT>() == TestPath);
  76. assert(p.string<CharT>() == S);
  77. }
  78. {
  79. const std::basic_string_view<CharT> S(TestPath);
  80. path p; PathReserve(p, S.length() + 1);
  81. {
  82. DisableAllocationGuard g;
  83. path& pref = p.assign(S);
  84. assert(&pref == &p);
  85. }
  86. assert(p.native() == Expect);
  87. assert(p.string<CharT>() == TestPath);
  88. assert(p.string<CharT>() == S);
  89. }
  90. //////////////////////////////////////////////////////////////////////////////
  91. // Char* pointers
  92. {
  93. path p; PathReserve(p, Size + 1);
  94. {
  95. // char* pointers are contiguous and can be used with code_cvt directly.
  96. // no allocations needed.
  97. DisableAllocationGuard g;
  98. path& pref = (p = TestPath);
  99. assert(&pref == &p);
  100. }
  101. assert(p.native() == Expect);
  102. assert(p.string<CharT>() == TestPath);
  103. }
  104. {
  105. path p; PathReserve(p, Size + 1);
  106. {
  107. DisableAllocationGuard g;
  108. path& pref = p.assign(TestPath);
  109. assert(&pref == &p);
  110. }
  111. assert(p.native() == Expect);
  112. assert(p.string<CharT>() == TestPath);
  113. }
  114. {
  115. path p; PathReserve(p, Size + 1);
  116. {
  117. DisableAllocationGuard g;
  118. path& pref = p.assign(TestPath, TestPathEnd);
  119. assert(&pref == &p);
  120. }
  121. assert(p.native() == Expect);
  122. assert(p.string<CharT>() == TestPath);
  123. }
  124. //////////////////////////////////////////////////////////////////////////////
  125. // Iterators
  126. {
  127. using It = input_iterator<const CharT*>;
  128. path p; PathReserve(p, Size + 1);
  129. It it(TestPath);
  130. {
  131. // Iterators cannot be used with code_cvt directly. This assignment
  132. // may allocate if it's larger than a "short-string".
  133. path& pref = (p = it);
  134. assert(&pref == &p);
  135. }
  136. assert(p.native() == Expect);
  137. assert(p.string<CharT>() == TestPath);
  138. }
  139. {
  140. using It = input_iterator<const CharT*>;
  141. path p; PathReserve(p, Size + 1);
  142. It it(TestPath);
  143. {
  144. path& pref = p.assign(it);
  145. assert(&pref == &p);
  146. }
  147. assert(p.native() == Expect);
  148. assert(p.string<CharT>() == TestPath);
  149. }
  150. {
  151. using It = input_iterator<const CharT*>;
  152. path p; PathReserve(p, Size + 1);
  153. It it(TestPath);
  154. It e(TestPathEnd);
  155. {
  156. path& pref = p.assign(it, e);
  157. assert(&pref == &p);
  158. }
  159. assert(p.native() == Expect);
  160. assert(p.string<CharT>() == TestPath);
  161. }
  162. }
  163. template <class It, class = decltype(fs::path{}.assign(std::declval<It>()))>
  164. constexpr bool has_assign(int) { return true; }
  165. template <class It>
  166. constexpr bool has_assign(long) { return false; }
  167. template <class It>
  168. constexpr bool has_assign() { return has_assign<It>(0); }
  169. void test_sfinae() {
  170. using namespace fs;
  171. {
  172. using It = const char* const;
  173. static_assert(std::is_assignable<path, It>::value, "");
  174. static_assert(has_assign<It>(), "");
  175. }
  176. {
  177. using It = input_iterator<const char*>;
  178. static_assert(std::is_assignable<path, It>::value, "");
  179. static_assert(has_assign<It>(), "");
  180. }
  181. {
  182. struct Traits {
  183. using iterator_category = std::input_iterator_tag;
  184. using value_type = const char;
  185. using pointer = const char*;
  186. using reference = const char&;
  187. using difference_type = std::ptrdiff_t;
  188. };
  189. using It = input_iterator<const char*, Traits>;
  190. static_assert(std::is_assignable<path, It>::value, "");
  191. static_assert(has_assign<It>(), "");
  192. }
  193. {
  194. using It = output_iterator<const char*>;
  195. static_assert(!std::is_assignable<path, It>::value, "");
  196. static_assert(!has_assign<It>(), "");
  197. }
  198. {
  199. static_assert(!std::is_assignable<path, int*>::value, "");
  200. static_assert(!has_assign<int*>(), "");
  201. }
  202. }
  203. void RunStringMoveTest(const char* Expect) {
  204. using namespace fs;
  205. std::string ss(Expect);
  206. path p;
  207. {
  208. DisableAllocationGuard g; ((void)g);
  209. path& pr = (p = std::move(ss));
  210. assert(&pr == &p);
  211. }
  212. assert(p == Expect);
  213. {
  214. // Signature test
  215. ASSERT_NOEXCEPT(p = std::move(ss));
  216. }
  217. }
  218. int main() {
  219. for (auto const& MS : PathList) {
  220. RunTestCase<char>(MS);
  221. RunTestCase<wchar_t>(MS);
  222. RunTestCase<char16_t>(MS);
  223. RunTestCase<char32_t>(MS);
  224. RunStringMoveTest(MS);
  225. }
  226. test_sfinae();
  227. }