Commit 8ee0e773 authored by Chris Palmer's avatar Chris Palmer Committed by Commit Bot

[Partition Alloc] Probabilistically poison memory on free.

We do it unconditionally in DCHECK builds to catch bugs, but let's occasionally
do it in release builds too. Frequency is tunable.

This is a re-land of
https://chromium-review.googlesource.com/c/chromium/src/+/1761578, which was
reverted in https://chromium-review.googlesource.com/c/chromium/src/+/1797642.

Bug: 984742
TBR: haraken
Change-Id: I8f9a36389b2d58f6a11b324b59dd47727e4b91fb
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/1808181Reviewed-by: default avatarChris Palmer <palmer@chromium.org>
Reviewed-by: default avatarKentaro Hara <haraken@chromium.org>
Commit-Queue: Chris Palmer <palmer@chromium.org>
Cr-Commit-Position: refs/heads/master@{#697013}
parent 7c800e5d
......@@ -11,6 +11,7 @@
#include "base/allocator/partition_allocator/partition_bucket.h"
#include "base/allocator/partition_allocator/partition_cookie.h"
#include "base/allocator/partition_allocator/partition_freelist_entry.h"
#include "base/allocator/partition_allocator/random.h"
#include "base/logging.h"
namespace base {
......@@ -201,19 +202,28 @@ ALWAYS_INLINE size_t PartitionPage::get_raw_size() const {
}
ALWAYS_INLINE void PartitionPage::Free(void* ptr) {
#if DCHECK_IS_ON()
size_t slot_size = this->bucket->slot_size;
const size_t raw_size = get_raw_size();
if (raw_size) {
slot_size = raw_size;
}
#if DCHECK_IS_ON()
// If these asserts fire, you probably corrupted memory.
PartitionCookieCheckValue(ptr);
PartitionCookieCheckValue(reinterpret_cast<char*>(ptr) + slot_size -
kCookieSize);
memset(ptr, kFreedByte, slot_size);
#else
// Probabilistically poison the memory. The goal is to do it often enough to
// catch bugs in production, but not so often that it significantly affects
// performance. Set fewer bits in the mask to increase the probability of
// poisoning; set more to reduce the performance effect.
constexpr uint32_t kProbabilityMask = 0x3f;
if (kProbabilityMask == (RandomValue() & kProbabilityMask)) {
memset(ptr, kFreedByte, slot_size);
}
#endif
DCHECK(this->num_allocated_slots);
......
......@@ -15,7 +15,7 @@ namespace base {
// `base::RandUint64` which is very unpredictable, but which is expensive due to
// the need to call into the kernel. Therefore this generator uses a fast,
// entirely user-space function after initialization.
uint32_t RandomValue();
BASE_EXPORT uint32_t RandomValue();
// Sets the seed for the random number generator to a known value, to cause the
// RNG to generate a predictable sequence of outputs. May be called multiple
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment