Chromium Code Reviews| Index: chrome/browser/enumerate_modules_model_win.cc |
| =================================================================== |
| --- chrome/browser/enumerate_modules_model_win.cc (revision 66602) |
| +++ chrome/browser/enumerate_modules_model_win.cc (working copy) |
| @@ -20,6 +20,7 @@ |
| #include "base/utf_string_conversions.h" |
| #include "base/values.h" |
| #include "base/version.h" |
| +#include "base/win/registry.h" |
| #include "chrome/browser/net/service_providers_win.h" |
| #include "chrome/common/chrome_constants.h" |
| #include "chrome/common/chrome_switches.h" |
| @@ -30,6 +31,10 @@ |
| // incompatible modules exist. |
| static const int kModuleCheckDelayMs = 60 * 1000; |
| +// The path to the Shell Extension key in the Windows registry. |
| +static const wchar_t kRegPath[] = |
| + L"Software\\Microsoft\\Windows\\CurrentVersion\\Shell Extensions\\Approved"; |
| + |
| // A sort method that sorts by ModuleType ordinal (loaded module at the top), |
| // then by full name (including path). |
| static bool ModuleSort(const ModuleEnumerator::Module& a, |
| @@ -226,6 +231,22 @@ |
| // Make sure the path mapping vector is setup so we can collapse paths. |
| PreparePathMappings(); |
| + EnumerateLoadedModules(); |
| + EnumerateShellExtensions(); |
| + EnumerateWinsockModule(); |
| + |
| + MatchAgainstBlacklist(); |
| + |
| + std::sort(enumerated_modules_->begin(), |
| + enumerated_modules_->end(), ModuleSort); |
| + |
| + // Send a reply back on the UI thread. |
| + BrowserThread::PostTask( |
| + callback_thread_id_, FROM_HERE, |
| + NewRunnableMethod(this, &ModuleEnumerator::ReportBack)); |
| +} |
| + |
| +void ModuleEnumerator::EnumerateLoadedModules() { |
| // Get all modules in the current process. |
| ScopedHandle snap(::CreateToolhelp32Snapshot(TH32CS_SNAPMODULE, |
| ::GetCurrentProcessId())); |
| @@ -244,31 +265,46 @@ |
| Module entry; |
| entry.type = LOADED_MODULE; |
| - entry.status = NOT_MATCHED; |
| - entry.normalized = false; |
| entry.location = module.szExePath; |
| - entry.digital_signer = |
| - GetSubjectNameFromDigitalSignature(FilePath(entry.location)); |
| - entry.recommended_action = NONE; |
| - scoped_ptr<FileVersionInfo> version_info( |
| - FileVersionInfo::CreateFileVersionInfo(FilePath(entry.location))); |
| - if (version_info.get()) { |
| - FileVersionInfoWin* version_info_win = |
| - static_cast<FileVersionInfoWin*>(version_info.get()); |
| + PopulateModuleInformation(&entry); |
| - VS_FIXEDFILEINFO* fixed_file_info = version_info_win->fixed_file_info(); |
| - if (fixed_file_info) { |
| - entry.description = version_info_win->file_description(); |
| - entry.version = version_info_win->file_version(); |
| - entry.product_name = version_info_win->product_name(); |
| - } |
| + NormalizeModule(&entry); |
| + CollapsePath(&entry); |
| + enumerated_modules_->push_back(entry); |
| + } while (::Module32Next(snap.Get(), &module)); |
| +} |
| + |
| +void ModuleEnumerator::EnumerateShellExtensions() { |
| + base::win::RegistryValueIterator registration(HKEY_LOCAL_MACHINE, kRegPath); |
|
huanr
2010/11/18 22:01:13
Do you need to enumerate keys under HKCU?
|
| + while (registration.Valid()) { |
| + std::wstring key(std::wstring(L"CLSID\\") + registration.Name() + |
| + L"\\InProcServer32"); |
| + base::win::RegKey clsid; |
| + if (!clsid.Open(HKEY_CLASSES_ROOT, key.c_str(), KEY_READ)) { |
| + ++registration; |
| + continue; |
| } |
| + string16 dll; |
| + if (!clsid.ReadValue(L"", &dll)) { |
| + ++registration; |
| + continue; |
| + } |
| + clsid.Close(); |
| + Module entry; |
| + entry.type = SHELL_EXTENSION; |
| + entry.location = dll; |
| + PopulateModuleInformation(&entry); |
| + |
| NormalizeModule(&entry); |
| CollapsePath(&entry); |
| enumerated_modules_->push_back(entry); |
| - } while (::Module32Next(snap.Get(), &module)); |
| + ++registration; |
| + } |
| +} |
| + |
| +void ModuleEnumerator::EnumerateWinsockModule() { |
| // Add to this list the Winsock LSP DLLs. |
| WinsockLayeredServiceProviderList layered_providers; |
| GetWinsockLayeredServiceProviders(&layered_providers); |
| @@ -294,16 +330,27 @@ |
| NormalizeModule(&entry); |
| enumerated_modules_->push_back(entry); |
| } |
| +} |
| - MatchAgainstBlacklist(); |
| +void ModuleEnumerator::PopulateModuleInformation(Module* module) { |
| + module->status = NOT_MATCHED; |
| + module->normalized = false; |
| + module->digital_signer = |
| + GetSubjectNameFromDigitalSignature(FilePath(module->location)); |
| + module->recommended_action = NONE; |
| + scoped_ptr<FileVersionInfo> version_info( |
| + FileVersionInfo::CreateFileVersionInfo(FilePath(module->location))); |
| + if (version_info.get()) { |
| + FileVersionInfoWin* version_info_win = |
| + static_cast<FileVersionInfoWin*>(version_info.get()); |
| - std::sort(enumerated_modules_->begin(), |
| - enumerated_modules_->end(), ModuleSort); |
| - |
| - // Send a reply back on the UI thread. |
| - BrowserThread::PostTask( |
| - callback_thread_id_, FROM_HERE, |
| - NewRunnableMethod(this, &ModuleEnumerator::ReportBack)); |
| + VS_FIXEDFILEINFO* fixed_file_info = version_info_win->fixed_file_info(); |
| + if (fixed_file_info) { |
| + module->description = version_info_win->file_description(); |
| + module->version = version_info_win->file_version(); |
| + module->product_name = version_info_win->product_name(); |
| + } |
| + } |
| } |
| void ModuleEnumerator::PreparePathMappings() { |
| @@ -498,9 +545,17 @@ |
| module != enumerated_modules_.end(); ++module) { |
| DictionaryValue* data = new DictionaryValue(); |
| data->SetInteger("type", module->type); |
| - data->SetString("type_description", |
| - (module->type == ModuleEnumerator::WINSOCK_MODULE_REGISTRATION) ? |
| - ASCIIToWide("Winsock") : ASCIIToWide("")); |
| + switch (module->type) { |
| + case ModuleEnumerator::SHELL_EXTENSION: |
| + data->SetString("type_description", ASCIIToWide("Shell Extension")); |
| + break; |
| + case ModuleEnumerator::WINSOCK_MODULE_REGISTRATION: |
| + data->SetString("type_description", ASCIIToWide("Winsock")); |
| + break; |
| + default: |
| + data->SetString("type_description", ASCIIToWide("")); |
| + break; |
| + } |
| data->SetInteger("status", module->status); |
| data->SetString("location", module->location); |
| data->SetString("name", module->name); |