diff options
author | Evan Brown <ezb@google.com> | 2024-07-10 12:44:39 -0700 |
---|---|---|
committer | Copybara-Service <copybara-worker@google.com> | 2024-07-10 12:45:28 -0700 |
commit | 5b6285e7c5548adf74396650c473efb163363705 (patch) | |
tree | 969d74ba9f19d4a4b563de511aea870d629c926a /absl/base/internal/poison.h | |
parent | bb50cad0adb77f6afdab1d50c093aae2b36d0522 (diff) |
Roll forward poisoned pointer API and fix portability issues.
Also, return the middle of the poisoned block.
PiperOrigin-RevId: 651119057
Change-Id: Iae0fc3dcb40e32cd449f469d9b8d62c37f3773f4
Diffstat (limited to 'absl/base/internal/poison.h')
-rw-r--r-- | absl/base/internal/poison.h | 59 |
1 files changed, 59 insertions, 0 deletions
diff --git a/absl/base/internal/poison.h b/absl/base/internal/poison.h new file mode 100644 index 00000000..28113bdd --- /dev/null +++ b/absl/base/internal/poison.h @@ -0,0 +1,59 @@ +// Copyright 2024 The Abseil Authors +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#ifndef ABSL_BASE_INTERNAL_POISON_H_ +#define ABSL_BASE_INTERNAL_POISON_H_ + +#include <cstdint> + +#include "absl/base/config.h" + +namespace absl { +ABSL_NAMESPACE_BEGIN +namespace base_internal { + +inline void* GetBadPointerInternal() { + // A likely bad pointer. Pointers are required to have high bits that are all + // zero or all one for certain 64-bit CPUs. This pointer value will hopefully + // cause a crash on dereference and also be clearly recognizable as invalid. + constexpr uint64_t kBadPtr = 0xBAD0BAD0BAD0BAD0; + auto ret = reinterpret_cast<void*>(static_cast<uintptr_t>(kBadPtr)); +#ifndef _MSC_VER // MSVC doesn't support inline asm with `volatile`. + // Try to prevent the compiler from optimizing out the undefined behavior. + asm volatile("" : : "r"(ret) :); // NOLINT +#endif + return ret; +} + +void* InitializePoisonedPointerInternal(); + +inline void* get_poisoned_pointer() { +#if defined(NDEBUG) && !defined(ABSL_HAVE_ADDRESS_SANITIZER) && \ + !defined(ABSL_HAVE_MEMORY_SANITIZER) + // In optimized non-sanitized builds, avoid the function-local static because + // of the codegen and runtime cost. + return GetBadPointerInternal(); +#else + // Non-optimized builds may use more robust implementation. Note that we can't + // use a static global because Chromium doesn't allow non-constinit globals. + static void* ptr = InitializePoisonedPointerInternal(); + return ptr; +#endif +} + +} // namespace base_internal +ABSL_NAMESPACE_END +} // namespace absl + +#endif // ABSL_BASE_INTERNAL_POISON_H_ |