123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172 |
- diff --git a/include/__filesystem/directory_entry.h b/include/__filesystem/directory_entry.h
- index bb7a061..a839bcf 100644
- --- a/include/__filesystem/directory_entry.h
- +++ b/include/__filesystem/directory_entry.h
- @@ -271,6 +271,8 @@ private:
- _Empty,
- _IterSymlink,
- _IterNonSymlink,
- + _IterCachedSymlink,
- + _IterCachedNonSymlink,
- _RefreshSymlink,
- _RefreshSymlinkUnresolved,
- _RefreshNonSymlink
- @@ -315,6 +317,30 @@ private:
- return __data;
- }
-
- + _LIBCPP_INLINE_VISIBILITY
- + static __cached_data __create_iter_cached_result(file_type __ft, uintmax_t __size,
- + perms __perm, file_time_type __write_time) {
- + __cached_data __data;
- + __data.__type_ = __ft;
- + __data.__size_ = __size;
- + __data.__write_time_ = __write_time;
- + if (__ft == file_type::symlink)
- + __data.__sym_perms_ = __perm;
- + else
- + __data.__non_sym_perms_ = __perm;
- + __data.__cache_type_ = [&]() {
- + switch (__ft) {
- + case file_type::none:
- + return _Empty;
- + case file_type::symlink:
- + return _IterCachedSymlink;
- + default:
- + return _IterCachedNonSymlink;
- + }
- + }();
- + return __data;
- + }
- +
- _LIBCPP_INLINE_VISIBILITY
- void __assign_iter_entry(_Path&& __p, __cached_data __dt) {
- __p_ = _VSTD::move(__p);
- @@ -359,12 +385,14 @@ private:
- case _Empty:
- return __symlink_status(__p_, __ec).type();
- case _IterSymlink:
- + case _IterCachedSymlink:
- case _RefreshSymlink:
- case _RefreshSymlinkUnresolved:
- if (__ec)
- __ec->clear();
- return file_type::symlink;
- case _IterNonSymlink:
- + case _IterCachedNonSymlink:
- case _RefreshNonSymlink:
- file_status __st(__data_.__type_);
- if (__ec && !_VSTD_FS::exists(__st))
- @@ -381,9 +409,11 @@ private:
- switch (__data_.__cache_type_) {
- case _Empty:
- case _IterSymlink:
- + case _IterCachedSymlink:
- case _RefreshSymlinkUnresolved:
- return __status(__p_, __ec).type();
- case _IterNonSymlink:
- + case _IterCachedNonSymlink:
- case _RefreshNonSymlink:
- case _RefreshSymlink: {
- file_status __st(__data_.__type_);
- @@ -403,8 +433,10 @@ private:
- case _Empty:
- case _IterNonSymlink:
- case _IterSymlink:
- + case _IterCachedSymlink:
- case _RefreshSymlinkUnresolved:
- return __status(__p_, __ec);
- + case _IterCachedNonSymlink:
- case _RefreshNonSymlink:
- case _RefreshSymlink:
- return file_status(__get_ft(__ec), __data_.__non_sym_perms_);
- @@ -419,8 +451,10 @@ private:
- case _IterNonSymlink:
- case _IterSymlink:
- return __symlink_status(__p_, __ec);
- + case _IterCachedNonSymlink:
- case _RefreshNonSymlink:
- return file_status(__get_sym_ft(__ec), __data_.__non_sym_perms_);
- + case _IterCachedSymlink:
- case _RefreshSymlink:
- case _RefreshSymlinkUnresolved:
- return file_status(__get_sym_ft(__ec), __data_.__sym_perms_);
- @@ -434,8 +468,10 @@ private:
- case _Empty:
- case _IterNonSymlink:
- case _IterSymlink:
- + case _IterCachedSymlink:
- case _RefreshSymlinkUnresolved:
- return _VSTD_FS::__file_size(__p_, __ec);
- + case _IterCachedNonSymlink:
- case _RefreshSymlink:
- case _RefreshNonSymlink: {
- error_code __m_ec;
- @@ -459,6 +495,8 @@ private:
- case _Empty:
- case _IterNonSymlink:
- case _IterSymlink:
- + case _IterCachedNonSymlink:
- + case _IterCachedSymlink:
- case _RefreshSymlinkUnresolved:
- return _VSTD_FS::__hard_link_count(__p_, __ec);
- case _RefreshSymlink:
- @@ -480,6 +518,8 @@ private:
- case _IterSymlink:
- case _RefreshSymlinkUnresolved:
- return _VSTD_FS::__last_write_time(__p_, __ec);
- + case _IterCachedNonSymlink:
- + case _IterCachedSymlink:
- case _RefreshSymlink:
- case _RefreshNonSymlink: {
- error_code __m_ec;
- diff --git a/src/filesystem/directory_iterator.cpp b/src/filesystem/directory_iterator.cpp
- index 151fb2f..cf9d631 100644
- --- a/src/filesystem/directory_iterator.cpp
- +++ b/src/filesystem/directory_iterator.cpp
- @@ -80,14 +80,12 @@ public:
- bool assign() {
- if (!wcscmp(__data_.cFileName, L".") || !wcscmp(__data_.cFileName, L".."))
- return false;
- - // FIXME: Cache more of this
- - //directory_entry::__cached_data cdata;
- - //cdata.__type_ = get_file_type(__data_);
- - //cdata.__size_ = get_file_size(__data_);
- - //cdata.__write_time_ = get_write_time(__data_);
- __entry_.__assign_iter_entry(
- __root_ / __data_.cFileName,
- - directory_entry::__create_iter_result(detail::get_file_type(__data_)));
- + directory_entry::__create_iter_cached_result(detail::get_file_type(__data_),
- + detail::get_file_size(__data_),
- + detail::get_file_perm(__data_),
- + detail::get_write_time(__data_)));
- return true;
- }
-
- diff --git a/src/filesystem/file_descriptor.h b/src/filesystem/file_descriptor.h
- index d3a668f..7bc0a4d 100644
- --- a/src/filesystem/file_descriptor.h
- +++ b/src/filesystem/file_descriptor.h
- @@ -99,11 +99,18 @@ inline uintmax_t get_file_size(const WIN32_FIND_DATAW& data) {
- return (static_cast<uint64_t>(data.nFileSizeHigh) << 32) + data.nFileSizeLow;
- }
- inline file_time_type get_write_time(const WIN32_FIND_DATAW& data) {
- - ULARGE_INTEGER tmp;
- + using detail::fs_time;
- const FILETIME& time = data.ftLastWriteTime;
- - tmp.u.LowPart = time.dwLowDateTime;
- - tmp.u.HighPart = time.dwHighDateTime;
- - return file_time_type(file_time_type::duration(tmp.QuadPart));
- + auto ts = filetime_to_timespec(time);
- + if (!fs_time::is_representable(ts))
- + return file_time_type::min();
- + return fs_time::convert_from_timespec(ts);
- +}
- +inline perms get_file_perm(const WIN32_FIND_DATAW& data) {
- + unsigned st_mode = 0555; // Read-only
- + if (!(data.dwFileAttributes & FILE_ATTRIBUTE_READONLY))
- + st_mode |= 0222; // Write
- + return static_cast<perms>(st_mode) & perms::mask;
- }
-
- #endif // !_LIBCPP_WIN32API
|