Optimize FileFd.get_size/get_real_size on Windows.
GitOrigin-RevId: e39efbecdd6882bf4465b17dad556b585633b56e
This commit is contained in:
parent
db7573769f
commit
75ecd9c692
@ -22,6 +22,7 @@
|
||||
#include <cstring>
|
||||
#include <mutex>
|
||||
#include <unordered_set>
|
||||
#include <utility>
|
||||
|
||||
#if TD_PORT_POSIX
|
||||
#include <fcntl.h>
|
||||
@ -475,23 +476,57 @@ NativeFd FileFd::move_as_native_fd() {
|
||||
return res;
|
||||
}
|
||||
|
||||
#if TD_PORT_WINDOWS
|
||||
namespace {
|
||||
|
||||
uint64 filetime_to_unix_time_nsec(LONGLONG filetime) {
|
||||
const auto FILETIME_UNIX_TIME_DIFF = 116444736000000000ll;
|
||||
return static_cast<uint64>((filetime - FILETIME_UNIX_TIME_DIFF) * 100);
|
||||
}
|
||||
|
||||
struct FileSize {
|
||||
int64 size_;
|
||||
int64 real_size_;
|
||||
};
|
||||
|
||||
Result<FileSize> get_file_size(const FileFd &file_fd) {
|
||||
FILE_STANDARD_INFO standard_info;
|
||||
if (!GetFileInformationByHandleEx(file_fd.get_native_fd().fd(), FileStandardInfo, &standard_info,
|
||||
sizeof(standard_info))) {
|
||||
return OS_ERROR("Get FileStandardInfo failed");
|
||||
}
|
||||
FileSize res;
|
||||
res.size_ = standard_info.EndOfFile.QuadPart;
|
||||
res.real_size_ = standard_info.AllocationSize.QuadPart;
|
||||
|
||||
if (res.size_ > 0 && res.real_size_ <= 0) {
|
||||
res.real_size_ = res.size_; // just in case
|
||||
}
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
} // namespace
|
||||
#endif
|
||||
|
||||
Result<int64> FileFd::get_size() const {
|
||||
#if TD_PORT_POSIX
|
||||
TRY_RESULT(s, stat());
|
||||
#else if TD_PORT_WINDOWS
|
||||
TRY_RESULT(s, get_file_size(*this));
|
||||
#endif
|
||||
return s.size_;
|
||||
}
|
||||
|
||||
Result<int64> FileFd::get_real_size() const {
|
||||
#if TD_PORT_POSIX
|
||||
TRY_RESULT(s, stat());
|
||||
#else if TD_PORT_WINDOWS
|
||||
TRY_RESULT(s, get_file_size(*this));
|
||||
#endif
|
||||
return s.real_size_;
|
||||
}
|
||||
|
||||
#if TD_PORT_WINDOWS
|
||||
static uint64 filetime_to_unix_time_nsec(LONGLONG filetime) {
|
||||
const auto FILETIME_UNIX_TIME_DIFF = 116444736000000000ll;
|
||||
return static_cast<uint64>((filetime - FILETIME_UNIX_TIME_DIFF) * 100);
|
||||
}
|
||||
#endif
|
||||
|
||||
Result<Stat> FileFd::stat() const {
|
||||
CHECK(!empty());
|
||||
#if TD_PORT_POSIX
|
||||
@ -509,17 +544,9 @@ Result<Stat> FileFd::stat() const {
|
||||
res.is_dir_ = (basic_info.FileAttributes & FILE_ATTRIBUTE_DIRECTORY) != 0;
|
||||
res.is_reg_ = !res.is_dir_; // TODO this is still wrong
|
||||
|
||||
FILE_STANDARD_INFO standard_info;
|
||||
status = GetFileInformationByHandleEx(get_native_fd().fd(), FileStandardInfo, &standard_info, sizeof(standard_info));
|
||||
if (!status) {
|
||||
return OS_ERROR("Get FileStandardInfo failed");
|
||||
}
|
||||
res.size_ = standard_info.EndOfFile.QuadPart;
|
||||
res.real_size_ = standard_info.AllocationSize.QuadPart;
|
||||
|
||||
if (res.size_ != 0 && res.real_size_ <= 0 ) {
|
||||
res.real_size_ = res.size_; // just in case
|
||||
}
|
||||
TRY_RESULT(file_size, get_file_size(*this));
|
||||
res.size_ = file_size.size_;
|
||||
res.real_size_ = file_size.real_size_;
|
||||
|
||||
return res;
|
||||
#endif
|
||||
|
Reference in New Issue
Block a user