Chromium Code Reviews| Index: chrome/browser/chrome_browser_main_win.cc | 
| diff --git a/chrome/browser/chrome_browser_main_win.cc b/chrome/browser/chrome_browser_main_win.cc | 
| index 45cb0af5b2949d6dc78d0f515be9063701558f14..84ad5b2ede955de039208eb959b819a1aa95aeff 100644 | 
| --- a/chrome/browser/chrome_browser_main_win.cc | 
| +++ b/chrome/browser/chrome_browser_main_win.cc | 
| @@ -29,6 +29,8 @@ | 
| #include "base/win/win_util.h" | 
| #include "base/win/windows_version.h" | 
| #include "base/win/wrapped_window_proc.h" | 
| +#include "chrome/browser/conflicts/module_database_win.h" | 
| +#include "chrome/browser/conflicts/module_event_sink_impl_win.h" | 
| #include "chrome/browser/first_run/first_run.h" | 
| #include "chrome/browser/install_verification/win/install_verification.h" | 
| #include "chrome/browser/profiles/profile_shortcut_manager.h" | 
| @@ -39,6 +41,7 @@ | 
| #include "chrome/browser/win/chrome_elf_init.h" | 
| #include "chrome/chrome_watcher/chrome_watcher_main_api.h" | 
| #include "chrome/common/chrome_constants.h" | 
| +#include "chrome/common/chrome_features.h" | 
| #include "chrome/common/chrome_paths.h" | 
| #include "chrome/common/chrome_result_codes.h" | 
| #include "chrome/common/chrome_switches.h" | 
| @@ -202,6 +205,42 @@ void DetectFaultTolerantHeap() { | 
| UMA_HISTOGRAM_ENUMERATION("FaultTolerantHeap", detected, FTH_FLAGS_COUNT); | 
| } | 
| +// Helper function for getting the time date stamp associated with a module in | 
| +// this process. Similar to implementation in ModuleEventSinkImpl, but doesn't | 
| +// use remote process reads. | 
| +uint32_t GetModuleTimeDateStamp(const void* module_load_address) { | 
| + auto* base = reinterpret_cast<const uint8_t*>(module_load_address); | 
| 
 
grt (UTC plus 2)
2017/01/06 09:44:57
can you use base::win::PEImage for this?
 
chrisha
2017/01/10 21:01:45
Yeah, should be fine. I forget that thing exists.
 
 | 
| + auto* dos_header = reinterpret_cast<const IMAGE_DOS_HEADER*>(base); | 
| + auto* nt_headers = | 
| + reinterpret_cast<const IMAGE_NT_HEADERS*>(base + dos_header->e_lfanew); | 
| + return nt_headers->FileHeader.TimeDateStamp; | 
| +} | 
| + | 
| +// Used as the callback for ModuleWatcher events in this process. Dispatches | 
| +// them to the ModuleDatabase. | 
| +void OnModuleEvent(uint32_t process_id, | 
| + uint64_t creation_time, | 
| + const ModuleWatcher::ModuleEvent& event) { | 
| + auto* module_database = ModuleDatabase::GetInstance(); | 
| + uintptr_t load_address = | 
| + reinterpret_cast<uintptr_t>(event.module_load_address); | 
| + | 
| + switch (event.event_type) { | 
| + case mojom::ModuleEventType::MODULE_ALREADY_LOADED: | 
| + case mojom::ModuleEventType::MODULE_LOADED: { | 
| + module_database->OnModuleLoad( | 
| + process_id, creation_time, event.module_path, event.module_size, | 
| + GetModuleTimeDateStamp(event.module_load_address), load_address); | 
| + return; | 
| + } | 
| + | 
| + case mojom::ModuleEventType::MODULE_UNLOADED: { | 
| + module_database->OnModuleUnload(process_id, creation_time, load_address); | 
| + return; | 
| + } | 
| + } | 
| +} | 
| + | 
| } // namespace | 
| void ShowCloseBrowserFirstMessageBox() { | 
| @@ -326,6 +365,25 @@ void ChromeBrowserMainPartsWin::PostProfileInit() { | 
| FROM_HERE, content::BrowserThread::GetTaskRunnerForThread( | 
| content::BrowserThread::FILE), | 
| base::Bind(base::IgnoreResult(&base::DeleteFile), path, false)); | 
| + | 
| + // Create the module database and hook up the in-process module watcher. This | 
| + // needs to be done before any child processes are initialized as the | 
| + // ModuleDatabase is an endpoint for IPC from child processes. | 
| + if (base::FeatureList::IsEnabled(features::kModuleDatabase)) { | 
| 
 
grt (UTC plus 2)
2017/01/06 09:44:57
nit: pull this out into a function in the unnamed
 
chrisha
2017/01/10 21:01:45
Done.
 
 | 
| + uint64_t creation_time = 0; | 
| 
 
grt (UTC plus 2)
2017/01/06 09:44:58
#include <stdint.h>
 
chrisha
2017/01/10 21:01:46
Done.
 
 | 
| + ModuleEventSinkImpl::GetProcessCreationTime(::GetCurrentProcess(), | 
| 
 
grt (UTC plus 2)
2017/01/06 09:44:57
TIL: base::CurrentProcessInfo::CreationTime()!
 
chrisha
2017/01/10 21:01:45
Is there any guarantee that base::Time is lossless
 
 | 
| + &creation_time); | 
| + | 
| + ModuleDatabase::SetInstance(base::MakeUnique<ModuleDatabase>( | 
| + content::BrowserThread::GetTaskRunnerForThread( | 
| + content::BrowserThread::UI))); | 
| + auto* module_database = ModuleDatabase::GetInstance(); | 
| + uint32_t process_id = ::GetCurrentProcessId(); | 
| + module_database->OnProcessStarted(process_id, creation_time, | 
| + content::PROCESS_TYPE_BROWSER); | 
| + module_watcher_ = ModuleWatcher::Create( | 
| + base::Bind(&OnModuleEvent, process_id, creation_time)); | 
| + } | 
| } | 
| void ChromeBrowserMainPartsWin::PostBrowserStart() { |