1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153
|
// Copyright 2024 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// Cross platform methods for FilePathWatcher. See the various platform
// specific implementation files, too.
#include "content/browser/file_system_access/file_path_watcher/file_path_watcher.h"
#include <memory>
#include <utility>
#include "base/check.h"
#include "base/files/file_path.h"
#include "build/build_config.h"
#include "content/browser/file_system_access/features.h"
namespace content {
// static
size_t FilePathWatcher::quota_limit_override_for_testing_ = 0;
FilePathWatcher::ChangeInfo::ChangeInfo() = default;
FilePathWatcher::ChangeInfo::ChangeInfo(
FilePathWatcher::FilePathType file_path_type,
FilePathWatcher::ChangeType change_type,
base::FilePath modified_path)
: file_path_type(file_path_type),
change_type(change_type),
modified_path(modified_path) {}
FilePathWatcher::ChangeInfo::ChangeInfo(
FilePathWatcher::FilePathType file_path_type,
FilePathWatcher::ChangeType change_type,
base::FilePath modified_path,
std::optional<base::FilePath> moved_from_path)
: file_path_type(file_path_type),
change_type(change_type),
modified_path(modified_path),
moved_from_path(moved_from_path) {}
FilePathWatcher::ChangeInfo::~ChangeInfo() = default;
FilePathWatcher::ChangeInfo::ChangeInfo(const FilePathWatcher::ChangeInfo&) =
default;
FilePathWatcher::ChangeInfo::ChangeInfo(FilePathWatcher::ChangeInfo&&) =
default;
FilePathWatcher::ChangeInfo& FilePathWatcher::ChangeInfo::operator=(
const FilePathWatcher::ChangeInfo&) = default;
FilePathWatcher::ChangeInfo& FilePathWatcher::ChangeInfo::operator=(
FilePathWatcher::ChangeInfo&&) noexcept = default;
FilePathWatcher::~FilePathWatcher() {
DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
impl_->Cancel();
}
// static
bool FilePathWatcher::RecursiveWatchAvailable() {
#if BUILDFLAG(IS_MAC) || BUILDFLAG(IS_WIN) || BUILDFLAG(IS_LINUX) || \
BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(IS_FUCHSIA) || BUILDFLAG(IS_AIX)
return true;
#else
// FSEvents isn't available on iOS.
return false;
#endif
}
FilePathWatcher::PlatformDelegate::PlatformDelegate() = default;
FilePathWatcher::PlatformDelegate::~PlatformDelegate() {
DCHECK(is_cancelled());
}
size_t FilePathWatcher::PlatformDelegate::current_usage() const {
return 0;
}
bool FilePathWatcher::Watch(const base::FilePath& path,
Type type,
const Callback& callback) {
DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
DCHECK(path.IsAbsolute());
return impl_->Watch(path, type, callback);
}
bool FilePathWatcher::WatchWithOptions(const base::FilePath& path,
const WatchOptions& options,
const Callback& callback) {
DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
DCHECK(path.IsAbsolute());
return impl_->WatchWithOptions(path, options, callback);
}
std::optional<size_t> FilePathWatcher::WatchWithChangeInfo(
const base::FilePath& path,
const WatchOptions& options,
const CallbackWithChangeInfo& callback,
const UsageChangeCallback& usage_callback) {
DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
DCHECK(path.IsAbsolute());
if (impl_->WatchWithChangeInfo(path, options, callback, usage_callback)) {
return impl_->current_usage();
}
return std::nullopt;
}
bool FilePathWatcher::PlatformDelegate::WatchWithOptions(
const base::FilePath& path,
const WatchOptions& options,
const Callback& callback) {
return Watch(path, options.type, callback);
}
bool FilePathWatcher::PlatformDelegate::WatchWithChangeInfo(
const base::FilePath& path,
const WatchOptions& options,
const CallbackWithChangeInfo& callback,
const UsageChangeCallback& usage_callback) {
return Watch(path, options.type, base::BindRepeating(callback, ChangeInfo()));
}
FilePathWatcher::FilePathWatcher(std::unique_ptr<PlatformDelegate> delegate) {
DETACH_FROM_SEQUENCE(sequence_checker_);
impl_ = std::move(delegate);
}
#if BUILDFLAG(IS_WIN)
base::Lock& FilePathWatcher::GetWatchThreadLockForTest() {
return impl_->GetWatchThreadLockForTest(); // IN-TEST
}
#endif
size_t FilePathWatcher::current_usage() const {
return impl_->current_usage();
}
// static
size_t FilePathWatcher::quota_limit() {
if (FilePathWatcher::quota_limit_override_for_testing_ > 0) {
return FilePathWatcher::quota_limit_override_for_testing_;
}
if (base::FeatureList::IsEnabled(
features::kFileSystemAccessObserverQuotaLimit)) {
return GetQuotaLimitImpl();
}
return std::numeric_limits<size_t>::max();
}
} // namespace content
|