1d3c4975be
If we can read an object's Map pointer but not any data from the Map itself, we may still be able to accurately describe the object's type if the Map pointer matches one of the known Maps from the snapshot. GetObjectProperties uses that data in one of two ways: - If it is sure that the Map pointer matches a known Map, then it uses the type from that Map and continues as if it read the type normally. - If the Map pointer is at the right offset within a heap page to match a known Map, but the caller didn't provide the addresses of the first pages in Map space or read-only space, then the type of that Map is just a guess and gets returned in a separate array. This gives the caller the opportunity to present guessed types to the user, and perhaps call again using the guessed type as the type hint. Bug: v8:9376 Change-Id: I187f67b77e76699863a14534a9d635b79f654124 Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/1787986 Commit-Queue: Seth Brenith <seth.brenith@microsoft.com> Reviewed-by: Jakob Gruber <jgruber@chromium.org> Reviewed-by: Michael Achenbach <machenbach@chromium.org> Reviewed-by: Tobias Tebbi <tebbi@chromium.org> Cr-Commit-Position: refs/heads/master@{#63908}
86 lines
3.0 KiB
C++
86 lines
3.0 KiB
C++
// Copyright 2019 the V8 project 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 "heap-constants.h"
|
|
#include "src/common/globals.h"
|
|
|
|
namespace d = v8::debug_helper;
|
|
|
|
namespace v8_debug_helper_internal {
|
|
|
|
std::string FindKnownObject(uintptr_t address,
|
|
const d::HeapAddresses& heap_addresses) {
|
|
uintptr_t containing_page = address & ~i::kPageAlignmentMask;
|
|
uintptr_t offset_in_page = address & i::kPageAlignmentMask;
|
|
|
|
// If there's a match with a known page, then search only that page.
|
|
if (containing_page == heap_addresses.map_space_first_page) {
|
|
return FindKnownObjectInMapSpace(offset_in_page);
|
|
}
|
|
if (containing_page == heap_addresses.old_space_first_page) {
|
|
return FindKnownObjectInOldSpace(offset_in_page);
|
|
}
|
|
if (containing_page == heap_addresses.read_only_space_first_page) {
|
|
return FindKnownObjectInReadOnlySpace(offset_in_page);
|
|
}
|
|
|
|
// For any unknown pages, compile a list of things this object might be.
|
|
std::string result;
|
|
if (heap_addresses.map_space_first_page == 0) {
|
|
std::string sub_result = FindKnownObjectInMapSpace(offset_in_page);
|
|
if (!sub_result.empty()) {
|
|
result += "maybe " + sub_result;
|
|
}
|
|
}
|
|
if (heap_addresses.old_space_first_page == 0) {
|
|
std::string sub_result = FindKnownObjectInOldSpace(offset_in_page);
|
|
if (!sub_result.empty()) {
|
|
result = (result.empty() ? "" : result + ", ") + "maybe " + sub_result;
|
|
}
|
|
}
|
|
if (heap_addresses.read_only_space_first_page == 0) {
|
|
std::string sub_result = FindKnownObjectInReadOnlySpace(offset_in_page);
|
|
if (!sub_result.empty()) {
|
|
result = (result.empty() ? "" : result + ", ") + "maybe " + sub_result;
|
|
}
|
|
}
|
|
|
|
return result;
|
|
}
|
|
|
|
KnownInstanceType FindKnownMapInstanceType(
|
|
uintptr_t address, const d::HeapAddresses& heap_addresses) {
|
|
uintptr_t containing_page = address & ~i::kPageAlignmentMask;
|
|
uintptr_t offset_in_page = address & i::kPageAlignmentMask;
|
|
|
|
// If there's a match with a known page, then search only that page.
|
|
if (containing_page == heap_addresses.map_space_first_page) {
|
|
return KnownInstanceType(
|
|
FindKnownMapInstanceTypeInMapSpace(offset_in_page));
|
|
}
|
|
if (containing_page == heap_addresses.read_only_space_first_page) {
|
|
return KnownInstanceType(
|
|
FindKnownMapInstanceTypeInReadOnlySpace(offset_in_page));
|
|
}
|
|
|
|
// For any unknown pages, compile a list of things this object might be.
|
|
KnownInstanceType result;
|
|
if (heap_addresses.map_space_first_page == 0) {
|
|
int sub_result = FindKnownMapInstanceTypeInMapSpace(offset_in_page);
|
|
if (sub_result >= 0) {
|
|
result.types.push_back(static_cast<i::InstanceType>(sub_result));
|
|
}
|
|
}
|
|
if (heap_addresses.read_only_space_first_page == 0) {
|
|
int sub_result = FindKnownMapInstanceTypeInReadOnlySpace(offset_in_page);
|
|
if (sub_result >= 0) {
|
|
result.types.push_back(static_cast<i::InstanceType>(sub_result));
|
|
}
|
|
}
|
|
|
|
return result;
|
|
}
|
|
|
|
} // namespace v8_debug_helper_internal
|