1 // Copyright 2020 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #ifndef BASE_ALLOCATOR_PARTITION_ALLOCATOR_PARTITION_ALLOC_FEATURES_H_ 6 #define BASE_ALLOCATOR_PARTITION_ALLOCATOR_PARTITION_ALLOC_FEATURES_H_ 7 8 #include "base/allocator/buildflags.h" 9 #include "base/allocator/partition_allocator/partition_alloc_constants.h" 10 #include "base/base_export.h" 11 #include "base/feature_list.h" 12 #include "base/metrics/field_trial_params.h" 13 #include "build/build_config.h" 14 15 #if defined(OS_WIN) 16 // VersionHelpers.h depends on Windows.h. 17 #include <Windows.h> 18 // For IsWindows8Point1OrGreater(). 19 #include <VersionHelpers.h> 20 #endif 21 22 #define ALLOW_ENABLING_PCSCAN 0 23 24 namespace base { 25 26 struct Feature; 27 28 namespace features { 29 30 extern const BASE_EXPORT Feature kPartitionAllocGigaCage; 31 extern const BASE_EXPORT Feature kPartitionAllocPCScan; 32 IsPartitionAllocGigaCageEnabled()33ALWAYS_INLINE bool IsPartitionAllocGigaCageEnabled() { 34 #if defined(PA_HAS_64_BITS_POINTERS) && defined(OS_WIN) 35 // Lots of crashes (at PartitionAddressSpace::Init) occur 36 // when enabling GigaCage on Windows whose version is smaller than 8.1, 37 // because PTEs for reserved memory counts against commit limit. See 38 // https://crbug.com/1101421. 39 // TODO(tasak): this windows version check is the same as GetRandomPageBase() 40 // (address_space_randomization.cc). Refactor the code to avoid the 41 // duplication. 42 static bool is_windows_version_checked = false; 43 // Don't assign directly IsWindows8Point1OrGreater() to a static local 44 // variable, because the initial value is not trivial and the assignment needs 45 // thread-safe static-local initializer on Windows. (i.e. Init_thread_header) 46 // This causes issues when used on the allocation path (see 47 // crbug.com/1126432). As we don't use atomics here, this may end up querying 48 // the version multiple times, which is fine, as this operation is idempotent, 49 // with no side-effects. 50 static bool recent_enough_windows_version = false; 51 if (!is_windows_version_checked) { 52 recent_enough_windows_version = IsWindows8Point1OrGreater(); 53 is_windows_version_checked = true; 54 } 55 if (!recent_enough_windows_version) 56 return false; 57 #endif // defined(PA_HAS_64_BITS_POINTERS) && defined(OS_WIN) 58 #if BUILDFLAG(USE_PARTITION_ALLOC_AS_MALLOC) 59 return true; 60 #else 61 return FeatureList::IsEnabled(kPartitionAllocGigaCage); 62 #endif // BUILDFLAG(USE_PARTITION_ALLOC_AS_MALLOC) 63 } 64 IsPartitionAllocPCScanEnabled()65ALWAYS_INLINE bool IsPartitionAllocPCScanEnabled() { 66 #if !defined(PA_HAS_64_BITS_POINTERS) || !ALLOW_ENABLING_PCSCAN 67 return false; 68 #endif 69 // TODO(bikineev): Calling this function can allocate which can cause 70 // reentrancy for the 'PA as malloc' configuration. 71 return FeatureList::IsEnabled(kPartitionAllocPCScan); 72 } 73 74 } // namespace features 75 } // namespace base 76 77 #endif // BASE_ALLOCATOR_PARTITION_ALLOCATOR_PARTITION_ALLOC_FEATURES_H_ 78