ddfc98337b
This is a reland of b6dc4dad4d
TEST=ci
Original change's description:
> [vm/aot] Avoid using most Code objects in stack traces with --dwarf-stack-traces
>
> The following changes are done in preparation for the removal of Code
> objects in AOT with --dwarf-stack-traces:
>
> * Stack trace objects are extended to hold uword PCs (which may not
> fit into Smi range).
>
> * Scanning stack frames in GC (StackFrame::VisitObjectPointers)
> now avoids using Code objects.
> In order to find CompressedStackMaps it now calls
> ReversePc::FindCompressedStackMaps.
>
> * Singleton Code object (StubCode::UnknownDartCode()) is prepared as
> a replacement for Code objects in stack traces. It has
> PayloadStart() == 0 and Size() == kUwordMax so it includes
> arbitrary PCs.
>
> * In --dwarf-stack-traces mode, most Code objects obtained from stack
> frames are replaced with StubCode::UnknownDartCode().
> This simulates future behavior of ReversePc::Lookup when Code objects
> will be removed.
>
> Issue: https://github.com/dart-lang/sdk/issues/44852
> Change-Id: I7cec7b8b9396c9cfeca3c256a412ba4e82a7e0c4
> TEST=ci
> Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/182720
> Commit-Queue: Alexander Markov <alexmarkov@google.com>
> Reviewed-by: Tess Strickland <sstrickl@google.com>
> Reviewed-by: Martin Kustermann <kustermann@google.com>
Change-Id: Ia2fc4672a085cd963b7fc103369851df3603590c
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/186202
Commit-Queue: Vyacheslav Egorov <vegorov@google.com>
Reviewed-by: Tess Strickland <sstrickl@google.com>
Reviewed-by: Martin Kustermann <kustermann@google.com>
Reviewed-by: Vyacheslav Egorov <vegorov@google.com>
102 lines
3.1 KiB
C++
102 lines
3.1 KiB
C++
// Copyright (c) 2018, the Dart project authors. Please see the AUTHORS file
|
|
// for details. All rights reserved. Use of this source code is governed by a
|
|
// BSD-style license that can be found in the LICENSE file.
|
|
|
|
#include "vm/reverse_pc_lookup_cache.h"
|
|
|
|
#include "vm/isolate.h"
|
|
#include "vm/object.h"
|
|
#include "vm/object_store.h"
|
|
|
|
namespace dart {
|
|
|
|
CodePtr ReversePc::LookupInGroup(IsolateGroup* group,
|
|
uword pc,
|
|
bool is_return_address) {
|
|
#if defined(DART_PRECOMPILED_RUNTIME)
|
|
// This can run in the middle of GC and must not allocate handles.
|
|
NoSafepointScope no_safepoint;
|
|
|
|
if (is_return_address) {
|
|
pc--;
|
|
}
|
|
|
|
// This expected number of tables is low, so we go through them linearly. If
|
|
// this changes, would could sort the table list during deserialization and
|
|
// binary search for the table.
|
|
GrowableObjectArrayPtr tables = group->object_store()->code_order_tables();
|
|
intptr_t tables_length = Smi::Value(tables->untag()->length_);
|
|
for (intptr_t i = 0; i < tables_length; i++) {
|
|
ArrayPtr table =
|
|
static_cast<ArrayPtr>(tables->untag()->data_->untag()->data()[i]);
|
|
intptr_t lo = 0;
|
|
intptr_t hi = Smi::Value(table->untag()->length_) - 1;
|
|
|
|
// Fast check if pc belongs to this table.
|
|
if (lo > hi) {
|
|
continue;
|
|
}
|
|
CodePtr first = static_cast<CodePtr>(table->untag()->data()[lo]);
|
|
if (pc < Code::PayloadStartOf(first)) {
|
|
continue;
|
|
}
|
|
CodePtr last = static_cast<CodePtr>(table->untag()->data()[hi]);
|
|
if (pc >= (Code::PayloadStartOf(last) + Code::PayloadSizeOf(last))) {
|
|
continue;
|
|
}
|
|
|
|
// Binary search within the table for the matching Code.
|
|
while (lo <= hi) {
|
|
intptr_t mid = (hi - lo + 1) / 2 + lo;
|
|
ASSERT(mid >= lo);
|
|
ASSERT(mid <= hi);
|
|
CodePtr code = static_cast<CodePtr>(table->untag()->data()[mid]);
|
|
uword code_start = Code::PayloadStartOf(code);
|
|
uword code_end = code_start + Code::PayloadSizeOf(code);
|
|
if (pc < code_start) {
|
|
hi = mid - 1;
|
|
} else if (pc >= code_end) {
|
|
lo = mid + 1;
|
|
} else {
|
|
return code;
|
|
}
|
|
}
|
|
}
|
|
#endif // defined(DART_PRECOMPILED_RUNTIME)
|
|
|
|
return Code::null();
|
|
}
|
|
|
|
CodePtr ReversePc::Lookup(IsolateGroup* group,
|
|
uword pc,
|
|
bool is_return_address) {
|
|
ASSERT(FLAG_precompiled_mode && FLAG_use_bare_instructions);
|
|
NoSafepointScope no_safepoint;
|
|
|
|
CodePtr code = LookupInGroup(group, pc, is_return_address);
|
|
if (code == Code::null()) {
|
|
code = LookupInGroup(Dart::vm_isolate_group(), pc, is_return_address);
|
|
}
|
|
return code;
|
|
}
|
|
|
|
CompressedStackMapsPtr ReversePc::FindCompressedStackMaps(
|
|
IsolateGroup* group,
|
|
uword pc,
|
|
bool is_return_address,
|
|
uword* code_start) {
|
|
ASSERT(FLAG_precompiled_mode && FLAG_use_bare_instructions);
|
|
NoSafepointScope no_safepoint;
|
|
|
|
CodePtr code = Lookup(group, pc, is_return_address);
|
|
if (code != Code::null()) {
|
|
*code_start = Code::PayloadStartOf(code);
|
|
return code->untag()->compressed_stackmaps();
|
|
}
|
|
|
|
*code_start = 0;
|
|
return CompressedStackMaps::null();
|
|
}
|
|
|
|
} // namespace dart
|