Skip to content

Commit 6e6cb8e

Browse files
committed
Test, formatting and fixes.
1 parent 1fea8e1 commit 6e6cb8e

File tree

2 files changed

+104
-2
lines changed

2 files changed

+104
-2
lines changed

libcxx/include/__filesystem/directory_entry.h

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -242,7 +242,8 @@ class directory_entry {
242242
return __data;
243243
}
244244

245-
_LIBCPP_HIDE_FROM_ABI static __cached_data __create_iter_cached_result(file_type __ft, uintmax_t __size, perms __perm, file_time_type __write_time) {
245+
_LIBCPP_HIDE_FROM_ABI static __cached_data
246+
__create_iter_cached_result(file_type __ft, uintmax_t __size, perms __perm, file_time_type __write_time) {
246247
__cached_data __data;
247248
__data.__type_ = __ft;
248249
__data.__size_ = __size;
@@ -428,10 +429,10 @@ class directory_entry {
428429
case _Empty:
429430
case _IterNonSymlink:
430431
case _IterSymlink:
432+
case _IterCachedSymlink:
431433
case _RefreshSymlinkUnresolved:
432434
return filesystem::__last_write_time(__p_, __ec);
433435
case _IterCachedNonSymlink:
434-
case _IterCachedSymlink:
435436
case _RefreshSymlink:
436437
case _RefreshNonSymlink: {
437438
error_code __m_ec;
Lines changed: 101 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,101 @@
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+
// REQUIRES: can-create-symlinks
10+
// UNSUPPORTED: c++03, c++11, c++14
11+
// UNSUPPORTED: no-filesystem
12+
// UNSUPPORTED: availability-filesystem-missing
13+
14+
// <filesystem>
15+
16+
// recursive_directory_iterator
17+
18+
#include <filesystem>
19+
#include <type_traits>
20+
#include <set>
21+
#include <cassert>
22+
23+
#include "test_macros.h"
24+
#include "filesystem_test_helper.h"
25+
namespace fs = std::filesystem;
26+
using namespace fs;
27+
28+
#if defined(_WIN32)
29+
static void set_last_write_time_in_iteration(const fs::path& dir)
30+
{
31+
// Windows can postpone updating last write time for file especially for
32+
// directory because last write time of directory depends of its childs.
33+
// See
34+
// https://learn.microsoft.com/en-us/windows/win32/sysinfo/file-times
35+
// To force updating file entries calls "last_write_time" with own value.
36+
const recursive_directory_iterator endIt{};
37+
38+
std::error_code ec;
39+
recursive_directory_iterator it(dir, ec);
40+
assert(!ec);
41+
42+
file_time_type now_time = file_time_type::clock::now();
43+
for ( ; it != endIt; ++it) {
44+
const path entry = *it;
45+
last_write_time(entry, now_time, ec);
46+
assert(!ec);
47+
}
48+
49+
assert(it == endIt);
50+
}
51+
#endif
52+
53+
static void test_cache_and_refresh_in_iteration()
54+
{
55+
static_test_env static_env;
56+
const path testDir = static_env.Dir;
57+
#if defined(_WIN32)
58+
set_last_write_time_in_iteration(testDir);
59+
#endif
60+
const std::set<path> dir_contents(static_env.RecDirIterationList.begin(),
61+
static_env.RecDirIterationList.end());
62+
const recursive_directory_iterator endIt{};
63+
64+
std::error_code ec;
65+
recursive_directory_iterator it(testDir, ec);
66+
assert(!ec);
67+
68+
std::set<path> unseen_entries = dir_contents;
69+
while (!unseen_entries.empty()) {
70+
assert(it != endIt);
71+
const directory_entry& entry = *it;
72+
73+
assert(unseen_entries.erase(entry.path()) == 1);
74+
75+
file_status symlink_status = entry.symlink_status();
76+
file_status status = entry.status();
77+
std::uintmax_t file_size = entry.is_regular_file() ? entry.file_size() : 0;
78+
file_time_type last_write_time = entry.last_write_time();
79+
80+
directory_entry mutable_entry = *it;
81+
mutable_entry.refresh();
82+
file_status upd_symlink_status = mutable_entry.symlink_status();
83+
file_status upd_status = mutable_entry.status();
84+
std::uintmax_t upd_file_size = mutable_entry.is_regular_file() ? mutable_entry.file_size() : 0;
85+
file_time_type upd_last_write_time = mutable_entry.last_write_time();
86+
assert(upd_symlink_status == symlink_status);
87+
assert(upd_status == status);
88+
assert(upd_file_size == file_size);
89+
assert(upd_last_write_time == last_write_time);
90+
91+
recursive_directory_iterator& it_ref = it.increment(ec);
92+
assert(!ec);
93+
assert(&it_ref == &it);
94+
}
95+
}
96+
97+
int main(int, char**) {
98+
test_cache_and_refresh_in_iteration();
99+
100+
return 0;
101+
}

0 commit comments

Comments
 (0)