#include "src/heap/base/stack.h"
#include <limits>
#include "src/base/sanitizer/asan.h"
#include "src/base/sanitizer/msan.h"
#include "src/heap/base/memory-tagging.h"
#include "src/base/sanitizer/tsan.h"
namespace heap::base {
extern "C" void PushAllRegistersAndIterateStack(
Stack* stack, void* argument, Stack::IterateStackCallback callback);
bool Stack::IsOnStack(const void* slot) { … }
namespace {
#ifdef V8_USE_ADDRESS_SANITIZER
DISABLE_ASAN
DISABLE_HWASAN
DISABLE_TSAN
void IterateAsanFakeFrameIfNecessary(StackVisitor* visitor,
const Stack::Segment& segment,
const void* address) {
if (!segment.asan_fake_stack) return;
void* fake_frame_begin;
void* fake_frame_end;
void* real_stack_frame = __asan_addr_is_in_fake_stack(
const_cast<void*>(segment.asan_fake_stack), const_cast<void*>(address),
&fake_frame_begin, &fake_frame_end);
if (real_stack_frame) {
if (segment.start >= real_stack_frame && real_stack_frame >= segment.top) {
for (const void* const* current =
reinterpret_cast<const void* const*>(fake_frame_begin);
current < fake_frame_end; ++current) {
const void* address = *current;
if (address == nullptr) continue;
visitor->VisitPointer(address);
}
}
}
}
#else
void IterateAsanFakeFrameIfNecessary(StackVisitor* visitor,
const Stack::Segment& segment,
const void* address) { … }
#endif
void IteratePointersInUnsafeStackIfNecessary(StackVisitor* visitor,
const Stack::Segment& segment) { … }
V8_NOINLINE
DISABLE_ASAN
DISABLE_HWASAN
DISABLE_TSAN
void IteratePointersInStack(StackVisitor* visitor,
const Stack::Segment& segment) { … }
}
void Stack::IteratePointersForTesting(StackVisitor* visitor) { … }
void Stack::IteratePointersUntilMarker(StackVisitor* visitor) const { … }
void Stack::IterateBackgroundStacks(StackVisitor* visitor) const { … }
#ifdef DEBUG
bool Stack::IsOnCurrentStack(const void* ptr) { … }
#endif
void Stack::AddStackSegment(const void* start, const void* top) { … }
void Stack::ClearStackSegments() { … }
void Stack::TrampolineCallbackHelper(void* argument,
IterateStackCallback callback) { … }
}