// Copyright (c) 2006-2008 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 "sandbox/src/sandbox_utils.h" #include #include "base/logging.h" #include "sandbox/src/internal_types.h" #include "sandbox/src/nt_internals.h" namespace sandbox { bool GetModuleHandleHelper(DWORD flags, const wchar_t* module_name, HMODULE* module) { DCHECK(module); HMODULE kernel32_base = ::GetModuleHandle(kKerneldllName); if (!kernel32_base) { NOTREACHED(); return false; } GetModuleHandleExFunction get_module_handle_ex = reinterpret_cast< GetModuleHandleExFunction>(::GetProcAddress(kernel32_base, "GetModuleHandleExW")); if (get_module_handle_ex) { BOOL ret = get_module_handle_ex(flags, module_name, module); return (ret ? true : false); } if (!flags) { *module = ::LoadLibrary(module_name); } else if (flags & GET_MODULE_HANDLE_EX_FLAG_PIN) { NOTREACHED(); return false; } else if (!(flags & GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS)) { DCHECK((flags & GET_MODULE_HANDLE_EX_FLAG_UNCHANGED_REFCOUNT) == GET_MODULE_HANDLE_EX_FLAG_UNCHANGED_REFCOUNT); *module = ::GetModuleHandle(module_name); } else { DCHECK((flags & (GET_MODULE_HANDLE_EX_FLAG_UNCHANGED_REFCOUNT | GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS)) == (GET_MODULE_HANDLE_EX_FLAG_UNCHANGED_REFCOUNT | GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS)); MEMORY_BASIC_INFORMATION info = {0}; size_t returned = VirtualQuery(module_name, &info, sizeof(info)); if (sizeof(info) != returned) return false; *module = reinterpret_cast(info.AllocationBase); } return true; } bool IsXPSP2OrLater() { OSVERSIONINFOEX version = {0}; version.dwOSVersionInfoSize = sizeof(version); if (!::GetVersionEx(reinterpret_cast(&version))) { NOTREACHED(); return false; } // Vista or later if (version.dwMajorVersion > 5) return true; // 2k, xp or 2003 if (version.dwMajorVersion == 5) { // 2003 if (version.dwMinorVersion > 1) return true; // 2000 if (version.dwMinorVersion == 0) return false; // Windows Xp Sp2 or later if (version.wServicePackMajor >= 2) return true; } return false; } void InitObjectAttribs(const std::wstring& name, ULONG attributes, HANDLE root, OBJECT_ATTRIBUTES* obj_attr, UNICODE_STRING* uni_name) { static RtlInitUnicodeStringFunction RtlInitUnicodeString; if (!RtlInitUnicodeString) { HMODULE ntdll = ::GetModuleHandle(kNtdllName); RtlInitUnicodeString = reinterpret_cast( GetProcAddress(ntdll, "RtlInitUnicodeString")); DCHECK(RtlInitUnicodeString); } RtlInitUnicodeString(uni_name, name.c_str()); InitializeObjectAttributes(obj_attr, uni_name, attributes, root, NULL); } std::string WideToMultiByte(const std::wstring& wide) { if (wide.length() == 0) return std::string(); // compute the length of the buffer we'll need int charcount = WideCharToMultiByte(CP_UTF8, 0, wide.c_str(), -1, NULL, 0, NULL, NULL); if (charcount == 0) return std::string(); std::string mb; WideCharToMultiByte(CP_UTF8, 0, wide.c_str(), -1, WriteInto(&mb, charcount), charcount, NULL, NULL); return mb; } }; // namespace sandbox