| Index: chrome/common/conflicts/module_watcher_win_unittest.cc
|
| diff --git a/chrome/common/conflicts/module_watcher_win_unittest.cc b/chrome/common/conflicts/module_watcher_win_unittest.cc
|
| new file mode 100644
|
| index 0000000000000000000000000000000000000000..02bea081bc52566ce5d3c13bc03673e3b2e5e5fc
|
| --- /dev/null
|
| +++ b/chrome/common/conflicts/module_watcher_win_unittest.cc
|
| @@ -0,0 +1,119 @@
|
| +// Copyright 2016 The Chromium Authors. All rights reserved.
|
| +// Use of this source code is governed by a BSD-style license that can be
|
| +// found in the LICENSE file.
|
| +
|
| +#include "chrome/common/conflicts/module_watcher_win.h"
|
| +
|
| +#include <memory>
|
| +
|
| +#include "base/bind.h"
|
| +#include "testing/gtest/include/gtest/gtest.h"
|
| +
|
| +class ModuleWatcherTest : public testing::Test {
|
| + public:
|
| + ModuleWatcherTest()
|
| + : module_(nullptr),
|
| + module_event_count_(0),
|
| + module_already_loaded_event_count_(0),
|
| + module_loaded_event_count_(0),
|
| + module_unloaded_event_count_(0) {}
|
| +
|
| + void OnModuleEvent(const mojom::ModuleEvent& event) {
|
| + ++module_event_count_;
|
| + switch (event.event_type) {
|
| + case mojom::ModuleEventType::MODULE_ALREADY_LOADED:
|
| + ++module_already_loaded_event_count_;
|
| + break;
|
| + case mojom::ModuleEventType::MODULE_LOADED:
|
| + ++module_loaded_event_count_;
|
| + break;
|
| + case mojom::ModuleEventType::MODULE_UNLOADED:
|
| + ++module_unloaded_event_count_;
|
| + break;
|
| + }
|
| + }
|
| +
|
| + void TearDown() override { UnloadModule(); }
|
| +
|
| + void LoadModule() {
|
| + if (module_)
|
| + return;
|
| + // This module should not be a static dependency of the unit-test
|
| + // executable, but should be a build-system dependency or a module that is
|
| + // present on any Windows machine.
|
| + static constexpr wchar_t kModuleName[] = L"conflicts_dll.dll";
|
| + // The module should not already be loaded.
|
| + ASSERT_FALSE(::GetModuleHandle(kModuleName));
|
| + // It should load successfully.
|
| + module_ = ::LoadLibrary(kModuleName);
|
| + ASSERT_TRUE(module_);
|
| + }
|
| +
|
| + void UnloadModule() {
|
| + if (!module_)
|
| + return;
|
| + ::FreeLibrary(module_);
|
| + module_ = nullptr;
|
| + }
|
| +
|
| + std::unique_ptr<ModuleWatcher> Create() {
|
| + return ModuleWatcher::Create(
|
| + base::Bind(&ModuleWatcherTest::OnModuleEvent, base::Unretained(this)));
|
| + }
|
| +
|
| + // Holds a handle to a loaded module.
|
| + HMODULE module_;
|
| +
|
| + // Total number of module events seen.
|
| + int module_event_count_;
|
| + // Total number of MODULE_ALREADY_LOADED events seen.
|
| + int module_already_loaded_event_count_;
|
| + // Total number of MODULE_LOADED events seen.
|
| + int module_loaded_event_count_;
|
| + // Total number of MODULE_UNLOADED events seen.
|
| + int module_unloaded_event_count_;
|
| +
|
| + private:
|
| + DISALLOW_COPY_AND_ASSIGN(ModuleWatcherTest);
|
| +};
|
| +
|
| +TEST_F(ModuleWatcherTest, SingleModuleWatcherOnly) {
|
| + std::unique_ptr<ModuleWatcher> mw1(Create());
|
| + EXPECT_TRUE(mw1.get());
|
| +
|
| + std::unique_ptr<ModuleWatcher> mw2(Create());
|
| + EXPECT_FALSE(mw2.get());
|
| +}
|
| +
|
| +TEST_F(ModuleWatcherTest, ModuleEvents) {
|
| + // Create the module watcher. This should immediately enumerate all already
|
| + // loaded modules.
|
| + std::unique_ptr<ModuleWatcher> mw(Create());
|
| + EXPECT_LT(0, module_event_count_);
|
| + EXPECT_LT(0, module_already_loaded_event_count_);
|
| + EXPECT_EQ(0, module_loaded_event_count_);
|
| + EXPECT_EQ(0, module_unloaded_event_count_);
|
| +
|
| + // Dynamically load a module and ensure a notification is received for it.
|
| + int previous_module_loaded_event_count = module_loaded_event_count_;
|
| + LoadModule();
|
| + EXPECT_LT(previous_module_loaded_event_count, module_loaded_event_count_);
|
| +
|
| + // Unload the module and ensure another notification is received.
|
| + int previous_module_unloaded_event_count = module_unloaded_event_count_;
|
| + UnloadModule();
|
| + EXPECT_LT(previous_module_unloaded_event_count, module_unloaded_event_count_);
|
| +
|
| + // Dynamically load a module and ensure a notification is received for it.
|
| + previous_module_loaded_event_count = module_loaded_event_count_;
|
| + LoadModule();
|
| + EXPECT_LT(previous_module_loaded_event_count, module_loaded_event_count_);
|
| +
|
| + // Destroy the module watcher.
|
| + mw.reset();
|
| +
|
| + // Unload the module and ensure no notification is received this time.
|
| + previous_module_unloaded_event_count = module_unloaded_event_count_;
|
| + UnloadModule();
|
| + EXPECT_EQ(previous_module_unloaded_event_count, module_unloaded_event_count_);
|
| +}
|
|
|