diff options
-rw-r--r-- | base/BUILD.gn | 3 | ||||
-rw-r--r-- | base/allocator/allocator_check.cc | 38 | ||||
-rw-r--r-- | base/allocator/allocator_check.h | 18 | ||||
-rw-r--r-- | base/allocator/allocator_shim_win.cc | 7 | ||||
-rw-r--r-- | base/base.gypi | 2 | ||||
-rw-r--r-- | content/app/content_main_runner.cc | 7 | ||||
-rw-r--r-- | third_party/tcmalloc/README.chromium | 1 | ||||
-rw-r--r-- | third_party/tcmalloc/chromium/src/gperftools/tcmalloc.h | 11 | ||||
-rw-r--r-- | third_party/tcmalloc/chromium/src/tcmalloc.cc | 8 |
9 files changed, 91 insertions, 4 deletions
diff --git a/base/BUILD.gn b/base/BUILD.gn index 946d17f..589af08 100644 --- a/base/BUILD.gn +++ b/base/BUILD.gn @@ -118,6 +118,8 @@ component("base") { component_never_use_source_set = !is_nacl_nonsfi sources = [ + "allocator/allocator_check.cc", + "allocator/allocator_check.h", "allocator/allocator_extension.cc", "allocator/allocator_extension.h", "android/animation_frame_time_histogram.cc", @@ -946,6 +948,7 @@ component("base") { configs += [ ":base_flags", ":base_implementation", + "//base/allocator:allocator_shim_define", # for allocator_check.cc. "//build/config:precompiled_headers", ] diff --git a/base/allocator/allocator_check.cc b/base/allocator/allocator_check.cc new file mode 100644 index 0000000..4220fb7 --- /dev/null +++ b/base/allocator/allocator_check.cc @@ -0,0 +1,38 @@ +// Copyright (c) 2012 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 "base/allocator/allocator_check.h" + +#include "build/build_config.h" + +#if defined(OS_LINUX) +#include <malloc.h> +#endif + +namespace base { +namespace allocator { + +// Defined in allocator_shim_win.cc . +// TODO(primiano): replace with an include once base can depend on allocator. +#if defined(OS_WIN) && defined(ALLOCATOR_SHIM) +extern bool g_is_win_shim_layer_initialized; +#endif + +bool IsAllocatorInitialized() { +#if defined(OS_WIN) && defined(ALLOCATOR_SHIM) + // Set by allocator_shim_win.cc when the shimmed _heap_init() is called. + return g_is_win_shim_layer_initialized; +#elif defined(OS_LINUX) && defined(USE_TCMALLOC) +// From third_party/tcmalloc/chromium/src/gperftools/tcmalloc.h. +// TODO(primiano): replace with an include once base can depend on allocator. +#define TC_MALLOPT_IS_OVERRIDDEN_BY_TCMALLOC 0xbeef42 + return (mallopt(TC_MALLOPT_IS_OVERRIDDEN_BY_TCMALLOC, 0) == + TC_MALLOPT_IS_OVERRIDDEN_BY_TCMALLOC); +#else + return true; +#endif +} + +} // namespace allocator +} // namespace base diff --git a/base/allocator/allocator_check.h b/base/allocator/allocator_check.h new file mode 100644 index 0000000..c3aa2cb --- /dev/null +++ b/base/allocator/allocator_check.h @@ -0,0 +1,18 @@ +// Copyright 2015 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. + +#ifndef BASE_ALLOCATOR_ALLOCATOR_ALLOCATOR_CHECK_H_ +#define BASE_ALLOCATOR_ALLOCATOR_ALLOCATOR_CHECK_H_ + +#include "base/base_export.h" + +namespace base { +namespace allocator { + +BASE_EXPORT bool IsAllocatorInitialized(); + +} // namespace allocator +} // namespace base + +#endif // BASE_ALLOCATOR_ALLOCATOR_ALLOCATOR_CHECK_H_ diff --git a/base/allocator/allocator_shim_win.cc b/base/allocator/allocator_shim_win.cc index 2c5a40f..b65544f5 100644 --- a/base/allocator/allocator_shim_win.cc +++ b/base/allocator/allocator_shim_win.cc @@ -26,6 +26,12 @@ extern "C" { void* _crtheap = reinterpret_cast<void*>(1); } +namespace base { +namespace allocator { +bool g_is_win_shim_layer_initialized = false; +} // namespace allocator +} // namespace base + namespace { const size_t kWindowsPageSize = 4096; @@ -211,6 +217,7 @@ intptr_t _get_heap_handle() { // heapinit.c int _heap_init() { + base::allocator::g_is_win_shim_layer_initialized = true; return win_heap_init() ? 1 : 0; } diff --git a/base/base.gypi b/base/base.gypi index c93d8d3..5e90823 100644 --- a/base/base.gypi +++ b/base/base.gypi @@ -16,6 +16,8 @@ ['base_target==1', { 'sources': [ '../build/build_config.h', + 'allocator/allocator_check.cc', + 'allocator/allocator_check.h', 'allocator/allocator_extension.cc', 'allocator/allocator_extension.h', 'android/animation_frame_time_histogram.cc', diff --git a/content/app/content_main_runner.cc b/content/app/content_main_runner.cc index 3b5f88a..037c79b 100644 --- a/content/app/content_main_runner.cc +++ b/content/app/content_main_runner.cc @@ -10,6 +10,7 @@ #include <string> #include <utility> +#include "base/allocator/allocator_check.h" #include "base/allocator/allocator_extension.h" #include "base/at_exit.h" #include "base/command_line.h" @@ -654,6 +655,12 @@ class ContentMainRunnerImpl : public ContentMainRunner { base::win::SetupCRT(command_line); #endif + // If we are on a platform where the default allocator is overridden (shim + // layer on windows, tcmalloc on Linux Desktop) smoke-tests that the + // overriding logic is working correctly. If not causes a hard crash, as its + // unexpected absence has security implications. + CHECK(base::allocator::IsAllocatorInitialized()); + #if defined(OS_POSIX) if (!process_type.empty()) { // When you hit Ctrl-C in a terminal running the browser diff --git a/third_party/tcmalloc/README.chromium b/third_party/tcmalloc/README.chromium index a8595da..d857d07 100644 --- a/third_party/tcmalloc/README.chromium +++ b/third_party/tcmalloc/README.chromium @@ -101,3 +101,4 @@ Modifications: - Add "ARMv8-a" to the supporting list of ARM architecture - Add generic.total_physical_bytes property to MallocExtension - Conditionally define HAVE_VDSO_SUPPORT only on linux_x86 to avoid static initializers +- Add TC_MALLOPT_IS_OVERRIDDEN_BY_TCMALLOC mallopt() arg diff --git a/third_party/tcmalloc/chromium/src/gperftools/tcmalloc.h b/third_party/tcmalloc/chromium/src/gperftools/tcmalloc.h index a3f036f..501abd6 100644 --- a/third_party/tcmalloc/chromium/src/gperftools/tcmalloc.h +++ b/third_party/tcmalloc/chromium/src/gperftools/tcmalloc.h @@ -1,10 +1,10 @@ /* Copyright (c) 2003, Google Inc. * All rights reserved. - * + * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are * met: - * + * * * Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * Redistributions in binary form must reproduce the above @@ -14,7 +14,7 @@ * * Neither the name of Google Inc. nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. - * + * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR @@ -53,6 +53,11 @@ #define TC_VERSION_PATCH "" #define TC_VERSION_STRING "gperftools 2.0" +// When passed to mallopt() as first argument causes it to return +// TC_MALLOPT_IS_OVERRIDDEN_BY_TCMALLOC. Used to detect the sanity of the +// overriding mechanisms at runtime. +#define TC_MALLOPT_IS_OVERRIDDEN_BY_TCMALLOC 0xbeef42 + // For struct mallinfo, it it's defined. #ifdef HAVE_STRUCT_MALLINFO // Malloc can be in several places on older versions of OS X. diff --git a/third_party/tcmalloc/chromium/src/tcmalloc.cc b/third_party/tcmalloc/chromium/src/tcmalloc.cc index 4709411..3077b75 100644 --- a/third_party/tcmalloc/chromium/src/tcmalloc.cc +++ b/third_party/tcmalloc/chromium/src/tcmalloc.cc @@ -1390,7 +1390,13 @@ inline void do_malloc_stats() { } inline int do_mallopt(int cmd, int value) { - return 1; // Indicates error + if (cmd == TC_MALLOPT_IS_OVERRIDDEN_BY_TCMALLOC) + return TC_MALLOPT_IS_OVERRIDDEN_BY_TCMALLOC; + + // 1 is the success return value according to man mallopt(). However (see the + // BUGS section in the manpage), most implementations return always 1. + // This code is just complying with that (buggy) expectation. + return 1; } #ifdef HAVE_STRUCT_MALLINFO |