From 066d431ee3a136b9f5e0e6b83dd21de5d614912e Mon Sep 17 00:00:00 2001 From: Jonathan Wu Date: Tue, 11 Aug 2026 19:20:22 +0000 Subject: [PATCH 1/6] filesystem: refactor win32 watcher_impl to use absl mutex and fix buffer alignment Signed-off-by: Jonathan Wu --- .../common/filesystem/win32/watcher_impl.cc | 91 ++++++++++++++----- source/common/filesystem/win32/watcher_impl.h | 32 ++++++- test/common/filesystem/watcher_impl_test.cc | 40 ++++---- 3 files changed, 113 insertions(+), 50 deletions(-) diff --git a/source/common/filesystem/win32/watcher_impl.cc b/source/common/filesystem/win32/watcher_impl.cc index 2e7c0e72432e3..361bbcf32277f 100644 --- a/source/common/filesystem/win32/watcher_impl.cc +++ b/source/common/filesystem/win32/watcher_impl.cc @@ -80,7 +80,7 @@ absl::Status WatcherImpl::addWatch(absl::string_view path, uint32_t events, OnCh } else { callback_map_[fii_key] = std::make_unique(); callback_map_[fii_key]->dir_handle_ = dir_handle; - callback_map_[fii_key]->buffer_.resize(16384); + callback_map_[fii_key]->buffer_.resize(1024); callback_map_[fii_key]->watcher_ = this; // According to Microsoft docs, "the hEvent member of the OVERLAPPED structure is not used by @@ -107,7 +107,10 @@ absl::Status WatcherImpl::addWatch(absl::string_view path, uint32_t events, OnCh ENVOY_LOG(debug, "created watch for directory: '{}' handle: {}", result.directory_, dir_handle); } - callback_map_[fii_key]->watches_.push_back({file, events, cb}); + { + absl::WriterMutexLock lock(&callback_map_[fii_key]->watches_mutex_); + callback_map_[fii_key]->watches_.push_back({file, events, cb}); + } ENVOY_LOG(debug, "added watch for file '{}' in directory '{}'", result.file_, result.directory_); return absl::OkStatus(); } @@ -142,10 +145,13 @@ void WatcherImpl::issueFirstRead(ULONG_PTR param) { // a pointer to DirectoryWatch as the OVERLAPPED for ReadDirectoryChangesW. Then, the // completion routine can use its OVERLAPPED* parameter to access the DirectoryWatch see: // https://docs.microsoft.com/en-us/windows/desktop/ipc/named-pipe-server-using-completion-routines - ReadDirectoryChangesW(dir_watch->dir_handle_, &(dir_watch->buffer_[0]), - dir_watch->buffer_.capacity(), false, - FILE_NOTIFY_CHANGE_FILE_NAME | FILE_NOTIFY_CHANGE_LAST_WRITE, nullptr, - reinterpret_cast(param), &directoryChangeCompletion); + dir_watch->overlapped_.Internal = 0; + dir_watch->overlapped_.InternalHigh = 0; + const BOOL success = ReadDirectoryChangesW( + dir_watch->dir_handle_, dir_watch->buffer_.data(), dir_watch->buffer_.size() * sizeof(DWORD), + false, FILE_NOTIFY_CHANGE_FILE_NAME | FILE_NOTIFY_CHANGE_LAST_WRITE, nullptr, + reinterpret_cast(param), &directoryChangeCompletion); + RELEASE_ASSERT(success, fmt::format("ReadDirectoryChangesW failed: {}", GetLastError())); const BOOL rc = ::SetEvent(dir_watch->overlapped_.hEvent); ASSERT(rc); @@ -200,20 +206,31 @@ void WatcherImpl::directoryChangeCompletion(DWORD err, DWORD num_bytes, LPOVERLA } constexpr absl::string_view data{"a"}; - for (FileWatch& watch : dir_watch->watches_) { - if (watch.file_ == file && (watch.events_ & events)) { - ENVOY_LOG(debug, "matched callback: file: {}", watcher->wstring_converter_.to_bytes(file)); - const auto cb = watch.cb_; - const auto cb_closure = [cb, events]() -> void { cb(events); }; - watcher->active_callbacks_.push(cb_closure); - // write a byte to the other end of the socket that libevent is watching - // this tells the libevent callback to pull this callback off the active_callbacks_ - // queue. We do this so that the callbacks are executed in the main libevent loop, - // not in this completion routine - Buffer::RawSlice buffer{(void*)data.data(), 1}; - auto result = watcher->write_handle_->writev(&buffer, 1); - RELEASE_ASSERT(result.return_value_ == 1, - fmt::format("failed to write 1 byte: {}", result.err_->getErrorDetails())); + // Protect watches_ access with ReaderMutexLock + { + absl::ReaderMutexLock lock(&dir_watch->watches_mutex_); + for (FileWatch& watch : dir_watch->watches_) { + // Windows filesystems are case-insensitive. + // An empty watch.file_ matches any file change in the watched directory. + if ((watch.file_.empty() || _wcsicmp(watch.file_.c_str(), file.c_str()) == 0) && + (watch.events_ & events)) { + ENVOY_LOG(debug, "matched callback: file: {}", + watcher->wstring_converter_.to_bytes(file)); + const auto cb = watch.cb_; + const std::string file_name = watcher->wstring_converter_.to_bytes(file); + const auto cb_closure = [watcher, cb, events, file_name]() -> void { + watcher->callAndLogOnError(cb, events, file_name); + }; + watcher->active_callbacks_.push(cb_closure); + // write a byte to the other end of the socket that libevent is watching + // this tells the libevent callback to pull this callback off the active_callbacks_ + // queue. We do this so that the callbacks are executed in the main libevent loop, + // not in this completion routine + Buffer::RawSlice buffer{(void*)data.data(), 1}; + auto result = watcher->write_handle_->writev(&buffer, 1); + RELEASE_ASSERT(result.return_value_ == 1, + fmt::format("failed to write 1 byte: {}", result.err_->getErrorDetails())); + } } } @@ -226,10 +243,13 @@ void WatcherImpl::directoryChangeCompletion(DWORD err, DWORD num_bytes, LPOVERLA return; } - ReadDirectoryChangesW(dir_watch->dir_handle_, &(dir_watch->buffer_[0]), - dir_watch->buffer_.capacity(), false, - FILE_NOTIFY_CHANGE_FILE_NAME | FILE_NOTIFY_CHANGE_LAST_WRITE, nullptr, - overlapped, directoryChangeCompletion); + overlapped->Internal = 0; + overlapped->InternalHigh = 0; + const BOOL success = ReadDirectoryChangesW( + dir_watch->dir_handle_, dir_watch->buffer_.data(), dir_watch->buffer_.size() * sizeof(DWORD), + false, FILE_NOTIFY_CHANGE_FILE_NAME | FILE_NOTIFY_CHANGE_LAST_WRITE, nullptr, overlapped, + directoryChangeCompletion); + RELEASE_ASSERT(success, fmt::format("ReadDirectoryChangesW failed: {}", GetLastError())); } void WatcherImpl::watchLoop() { @@ -277,3 +297,26 @@ void WatcherImpl::watchLoop() { } // namespace Filesystem } // namespace Envoy + +void WatcherImpl::callAndLogOnError(const OnChangedCb& cb, uint32_t events, + const std::string& file) { + TRY_ASSERT_MAIN_THREAD { + const absl::Status status = cb(events); + if (!status.ok()) { + // Use ENVOY_LOG_EVERY_POW_2 to avoid log spam if a callback keeps failing. + ENVOY_LOG_EVERY_POW_2(warn, "Filesystem watch callback for '{}' returned error: {}", file, + status.message()); + } + } + END_TRY + MULTI_CATCH( + const std::exception& e, + { + ENVOY_LOG_EVERY_POW_2(warn, "Filesystem watch callback for '{}' threw exception: {}", file, + e.what()); + }, + { + ENVOY_LOG_EVERY_POW_2(warn, "Filesystem watch callback for '{}' threw unknown exception", + file); + }) +} diff --git a/source/common/filesystem/win32/watcher_impl.h b/source/common/filesystem/win32/watcher_impl.h index 5431d5f3f0a25..16c34dfbeee55 100644 --- a/source/common/filesystem/win32/watcher_impl.h +++ b/source/common/filesystem/win32/watcher_impl.h @@ -1,11 +1,10 @@ #pragma once -#include - #include #include #include #include +#include #include #include "envoy/api/api.h" @@ -21,10 +20,33 @@ #include "source/common/network/io_socket_handle_impl.h" #include "absl/container/node_hash_map.h" +#include "absl/synchronization/mutex.h" namespace Envoy { namespace Filesystem { +template class ThreadSafeQueue { +public: + void push(const T& value) { + absl::WriterMutexLock lock(&mutex_); + queue_.push(value); + } + + bool try_pop(T& value) { + absl::WriterMutexLock lock(&mutex_); + if (queue_.empty()) { + return false; + } + value = std::move(queue_.front()); + queue_.pop(); + return true; + } + +private: + absl::Mutex mutex_; + std::queue queue_; +}; + class WatcherImpl : public Watcher, Logger::Loggable { public: WatcherImpl(Event::Dispatcher& dispatcher, Filesystem::Instance& file_system); @@ -39,6 +61,7 @@ class WatcherImpl : public Watcher, Logger::Loggable { static void endDirectoryWatch(Network::IoHandle& io_handle, HANDLE hEvent); void watchLoop(); void onDirectoryEvent(); + void callAndLogOnError(const OnChangedCb& cb, uint32_t events, const std::string& file); struct FileWatch { // store the wide character string for ReadDirectoryChangesW @@ -52,8 +75,9 @@ class WatcherImpl : public Watcher, Logger::Loggable { struct DirectoryWatch { OVERLAPPED overlapped_; std::list watches_; + absl::Mutex watches_mutex_; HANDLE dir_handle_; - std::vector buffer_; + std::vector buffer_; WatcherImpl* watcher_; }; @@ -68,7 +92,7 @@ class WatcherImpl : public Watcher, Logger::Loggable { HANDLE thread_exit_event_; std::vector dir_watch_complete_events_; std::atomic keep_watching_; - concurrency::concurrent_queue active_callbacks_; + ThreadSafeQueue active_callbacks_; Api::OsSysCallsImpl& os_sys_calls_; std::wstring_convert> wstring_converter_; }; diff --git a/test/common/filesystem/watcher_impl_test.cc b/test/common/filesystem/watcher_impl_test.cc index e3c6e956f0443..e7911ecd6c358 100644 --- a/test/common/filesystem/watcher_impl_test.cc +++ b/test/common/filesystem/watcher_impl_test.cc @@ -1,5 +1,6 @@ #include #include +#include #include "envoy/common/exception.h" @@ -44,15 +45,11 @@ TEST_F(WatcherImplTest, All) { unlink(TestEnvironment::temporaryPath("envoy_test/watcher_new_link").c_str()); TestEnvironment::createPath(TestEnvironment::temporaryPath("envoy_test")); - { - std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_target")); - } + { std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_target")); } TestEnvironment::createSymlink(TestEnvironment::temporaryPath("envoy_test/watcher_target"), TestEnvironment::temporaryPath("envoy_test/watcher_link")); - { - std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_new_target")); - } + { std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_new_target")); } TestEnvironment::createSymlink(TestEnvironment::temporaryPath("envoy_test/watcher_new_target"), TestEnvironment::temporaryPath("envoy_test/watcher_new_link")); @@ -84,9 +81,7 @@ TEST_F(WatcherImplTest, Create) { unlink(TestEnvironment::temporaryPath("envoy_test/other_file").c_str()); TestEnvironment::createPath(TestEnvironment::temporaryPath("envoy_test")); - { - std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_target")); - } + { std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_target")); } WatchCallback callback; ASSERT_OK(watcher->addWatch(TestEnvironment::temporaryPath("envoy_test/watcher_link"), @@ -96,9 +91,7 @@ TEST_F(WatcherImplTest, Create) { return absl::OkStatus(); })); - { - std::ofstream file(TestEnvironment::temporaryPath("envoy_test/other_file")); - } + { std::ofstream file(TestEnvironment::temporaryPath("envoy_test/other_file")); } dispatcher_->run(Event::Dispatcher::RunType::NonBlock); EXPECT_CALL(callback, called(Watcher::Events::MovedTo)); @@ -182,9 +175,7 @@ TEST_F(WatcherImplTest, SymlinkAtomicRename) { TestEnvironment::createPath(TestEnvironment::temporaryPath("envoy_test")); TestEnvironment::createPath(TestEnvironment::temporaryPath("envoy_test/..timestamp1")); - { - std::ofstream file(TestEnvironment::temporaryPath("envoy_test/..timestamp1/watched_file")); - } + { std::ofstream file(TestEnvironment::temporaryPath("envoy_test/..timestamp1/watched_file")); } TestEnvironment::createSymlink(TestEnvironment::temporaryPath("envoy_test/..timestamp1"), TestEnvironment::temporaryPath("envoy_test/..data")); @@ -201,9 +192,7 @@ TEST_F(WatcherImplTest, SymlinkAtomicRename) { })); TestEnvironment::createPath(TestEnvironment::temporaryPath("envoy_test/..timestamp2")); - { - std::ofstream file(TestEnvironment::temporaryPath("envoy_test/..timestamp2/watched_file")); - } + { std::ofstream file(TestEnvironment::temporaryPath("envoy_test/..timestamp2/watched_file")); } TestEnvironment::createSymlink(TestEnvironment::temporaryPath("envoy_test/..timestamp2"), TestEnvironment::temporaryPath("envoy_test/..tmp")); TestEnvironment::renameFile(TestEnvironment::temporaryPath("envoy_test/..tmp"), @@ -262,7 +251,7 @@ TEST_F(WatcherImplTest, MultipleCallbacksWithErrors) { Filesystem::WatcherPtr watcher = dispatcher_->createFilesystemWatcher(); TestEnvironment::createPath(TestEnvironment::temporaryPath("envoy_test")); - std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_target")); + { std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_target")); } int callback_count = 0; ASSERT_OK(watcher->addWatch(TestEnvironment::temporaryPath("envoy_test/watcher_target"), @@ -280,12 +269,19 @@ TEST_F(WatcherImplTest, MultipleCallbacksWithErrors) { dispatcher_->run(Event::Dispatcher::RunType::NonBlock); // Trigger first modification. The first callback returns error, but watcher continues. - file << "text1" << std::flush; + { + std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_target"), std::ios::app); + file << "text1"; + } + std::this_thread::sleep_for(std::chrono::milliseconds(100)); // NO_CHECK_FORMAT(real_time) dispatcher_->run(Event::Dispatcher::RunType::NonBlock); + std::this_thread::sleep_for(std::chrono::milliseconds(100)); // NO_CHECK_FORMAT(real_time) // Trigger second modification. It should still work. - file << "text2" << std::flush; - file.close(); + { + std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_target"), std::ios::app); + file << "text2"; + } dispatcher_->run(Event::Dispatcher::RunType::Block); EXPECT_EQ(2, callback_count); From 66c493711164f4276d7184ddb2d9a0b0f1e45764 Mon Sep 17 00:00:00 2001 From: Jonathan Wu Date: Fri, 14 Aug 2026 15:15:17 -0400 Subject: [PATCH 2/6] Increase buffer size for directory watcher revert the buffer size for directory watching from 1024 to 16384 bytes. Signed-off-by: Jonathan Wu --- source/common/filesystem/win32/watcher_impl.cc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/source/common/filesystem/win32/watcher_impl.cc b/source/common/filesystem/win32/watcher_impl.cc index 361bbcf32277f..21c3619cef3f7 100644 --- a/source/common/filesystem/win32/watcher_impl.cc +++ b/source/common/filesystem/win32/watcher_impl.cc @@ -80,7 +80,7 @@ absl::Status WatcherImpl::addWatch(absl::string_view path, uint32_t events, OnCh } else { callback_map_[fii_key] = std::make_unique(); callback_map_[fii_key]->dir_handle_ = dir_handle; - callback_map_[fii_key]->buffer_.resize(1024); + callback_map_[fii_key]->buffer_.resize(16384); callback_map_[fii_key]->watcher_ = this; // According to Microsoft docs, "the hEvent member of the OVERLAPPED structure is not used by From f1fda03615faf4fdb862d70566a69f62f81289cd Mon Sep 17 00:00:00 2001 From: Jonathan Wu Date: Fri, 14 Aug 2026 19:58:31 +0000 Subject: [PATCH 3/6] fix(filesystem): move callAndLogOnError inside namespaces and fix MULTI_CATCH semicolon Signed-off-by: Jonathan Wu --- source/common/filesystem/win32/watcher_impl.cc | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/source/common/filesystem/win32/watcher_impl.cc b/source/common/filesystem/win32/watcher_impl.cc index cb256cc556568..e430095d56389 100644 --- a/source/common/filesystem/win32/watcher_impl.cc +++ b/source/common/filesystem/win32/watcher_impl.cc @@ -295,9 +295,6 @@ void WatcherImpl::watchLoop() { } } -} // namespace Filesystem -} // namespace Envoy - void WatcherImpl::callAndLogOnError(const OnChangedCb& cb, uint32_t events, const std::string& file) { TRY_ASSERT_MAIN_THREAD { @@ -318,5 +315,8 @@ void WatcherImpl::callAndLogOnError(const OnChangedCb& cb, uint32_t events, { ENVOY_LOG_EVERY_POW_2(warn, "Filesystem watch callback for '{}' threw unknown exception", file); - }) + }); } + +} // namespace Filesystem +} // namespace Envoy From 9c81372a2a75126fbcd3ce04c761ef1a4ea1a821 Mon Sep 17 00:00:00 2001 From: Jonathan Wu Date: Fri, 14 Aug 2026 19:59:01 +0000 Subject: [PATCH 4/6] revert buffer size for directory watching from 1024 to 16384 bytes Signed-off-by: Jonathan Wu --- source/common/filesystem/win32/watcher_impl.cc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/source/common/filesystem/win32/watcher_impl.cc b/source/common/filesystem/win32/watcher_impl.cc index e430095d56389..152d3a0627329 100644 --- a/source/common/filesystem/win32/watcher_impl.cc +++ b/source/common/filesystem/win32/watcher_impl.cc @@ -80,7 +80,7 @@ absl::Status WatcherImpl::addWatch(absl::string_view path, uint32_t events, OnCh } else { callback_map_[fii_key] = std::make_unique(); callback_map_[fii_key]->dir_handle_ = dir_handle; - callback_map_[fii_key]->buffer_.resize(1024); + callback_map_[fii_key]->buffer_.resize(16384); callback_map_[fii_key]->watcher_ = this; // According to Microsoft docs, "the hEvent member of the OVERLAPPED structure is not used by From a273c4cbde1a8de8e92a1cee76bc623351ae4b80 Mon Sep 17 00:00:00 2001 From: Jonathan Wu Date: Fri, 14 Aug 2026 21:02:51 +0000 Subject: [PATCH 5/6] fix(spelling): change filesystems to file systems in watcher_impl.cc Signed-off-by: Jonathan Wu --- source/common/filesystem/win32/watcher_impl.cc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/source/common/filesystem/win32/watcher_impl.cc b/source/common/filesystem/win32/watcher_impl.cc index 152d3a0627329..1b4bad1e49d90 100644 --- a/source/common/filesystem/win32/watcher_impl.cc +++ b/source/common/filesystem/win32/watcher_impl.cc @@ -210,7 +210,7 @@ void WatcherImpl::directoryChangeCompletion(DWORD err, DWORD num_bytes, LPOVERLA { absl::ReaderMutexLock lock(&dir_watch->watches_mutex_); for (FileWatch& watch : dir_watch->watches_) { - // Windows filesystems are case-insensitive. + // Windows file systems are case-insensitive. // An empty watch.file_ matches any file change in the watched directory. if ((watch.file_.empty() || _wcsicmp(watch.file_.c_str(), file.c_str()) == 0) && (watch.events_ & events)) { From 242a895b6e55e2f4a35679c3720027eb6e28d883 Mon Sep 17 00:00:00 2001 From: Jonathan Wu Date: Fri, 14 Aug 2026 21:57:28 +0000 Subject: [PATCH 6/6] fix(filesystem): include exception.h and clean up watcher_impl_test formatting Signed-off-by: Jonathan Wu --- .../common/filesystem/win32/watcher_impl.cc | 2 ++ test/common/filesystem/watcher_impl_test.cc | 28 ++++++++++++++----- 2 files changed, 23 insertions(+), 7 deletions(-) diff --git a/source/common/filesystem/win32/watcher_impl.cc b/source/common/filesystem/win32/watcher_impl.cc index 1b4bad1e49d90..d567fb545564c 100644 --- a/source/common/filesystem/win32/watcher_impl.cc +++ b/source/common/filesystem/win32/watcher_impl.cc @@ -1,5 +1,7 @@ #include "source/common/filesystem/watcher_impl.h" +#include "envoy/common/exception.h" + #include "source/common/api/os_sys_calls_impl.h" #include "source/common/common/assert.h" #include "source/common/common/fmt.h" diff --git a/test/common/filesystem/watcher_impl_test.cc b/test/common/filesystem/watcher_impl_test.cc index e7911ecd6c358..e0ee8b8d94600 100644 --- a/test/common/filesystem/watcher_impl_test.cc +++ b/test/common/filesystem/watcher_impl_test.cc @@ -45,11 +45,15 @@ TEST_F(WatcherImplTest, All) { unlink(TestEnvironment::temporaryPath("envoy_test/watcher_new_link").c_str()); TestEnvironment::createPath(TestEnvironment::temporaryPath("envoy_test")); - { std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_target")); } + { + std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_target")); + } TestEnvironment::createSymlink(TestEnvironment::temporaryPath("envoy_test/watcher_target"), TestEnvironment::temporaryPath("envoy_test/watcher_link")); - { std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_new_target")); } + { + std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_new_target")); + } TestEnvironment::createSymlink(TestEnvironment::temporaryPath("envoy_test/watcher_new_target"), TestEnvironment::temporaryPath("envoy_test/watcher_new_link")); @@ -81,7 +85,9 @@ TEST_F(WatcherImplTest, Create) { unlink(TestEnvironment::temporaryPath("envoy_test/other_file").c_str()); TestEnvironment::createPath(TestEnvironment::temporaryPath("envoy_test")); - { std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_target")); } + { + std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_target")); + } WatchCallback callback; ASSERT_OK(watcher->addWatch(TestEnvironment::temporaryPath("envoy_test/watcher_link"), @@ -91,7 +97,9 @@ TEST_F(WatcherImplTest, Create) { return absl::OkStatus(); })); - { std::ofstream file(TestEnvironment::temporaryPath("envoy_test/other_file")); } + { + std::ofstream file(TestEnvironment::temporaryPath("envoy_test/other_file")); + } dispatcher_->run(Event::Dispatcher::RunType::NonBlock); EXPECT_CALL(callback, called(Watcher::Events::MovedTo)); @@ -175,7 +183,9 @@ TEST_F(WatcherImplTest, SymlinkAtomicRename) { TestEnvironment::createPath(TestEnvironment::temporaryPath("envoy_test")); TestEnvironment::createPath(TestEnvironment::temporaryPath("envoy_test/..timestamp1")); - { std::ofstream file(TestEnvironment::temporaryPath("envoy_test/..timestamp1/watched_file")); } + { + std::ofstream file(TestEnvironment::temporaryPath("envoy_test/..timestamp1/watched_file")); + } TestEnvironment::createSymlink(TestEnvironment::temporaryPath("envoy_test/..timestamp1"), TestEnvironment::temporaryPath("envoy_test/..data")); @@ -192,7 +202,9 @@ TEST_F(WatcherImplTest, SymlinkAtomicRename) { })); TestEnvironment::createPath(TestEnvironment::temporaryPath("envoy_test/..timestamp2")); - { std::ofstream file(TestEnvironment::temporaryPath("envoy_test/..timestamp2/watched_file")); } + { + std::ofstream file(TestEnvironment::temporaryPath("envoy_test/..timestamp2/watched_file")); + } TestEnvironment::createSymlink(TestEnvironment::temporaryPath("envoy_test/..timestamp2"), TestEnvironment::temporaryPath("envoy_test/..tmp")); TestEnvironment::renameFile(TestEnvironment::temporaryPath("envoy_test/..tmp"), @@ -251,7 +263,9 @@ TEST_F(WatcherImplTest, MultipleCallbacksWithErrors) { Filesystem::WatcherPtr watcher = dispatcher_->createFilesystemWatcher(); TestEnvironment::createPath(TestEnvironment::temporaryPath("envoy_test")); - { std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_target")); } + { + std::ofstream file(TestEnvironment::temporaryPath("envoy_test/watcher_target")); + } int callback_count = 0; ASSERT_OK(watcher->addWatch(TestEnvironment::temporaryPath("envoy_test/watcher_target"),