[inspector] store stack frame in struct instead of JSObject

JSObject is slow: creating strings for keys and storing values by these keys after takes significant amount of time.
With this CL console methods (most of them collect top stack frame to calculate source location) are ~33% faster.
V8Debugger::captureStackTrace is ~50% faster.

BUG=v8:6189
R=yangguo@chromium.org
TBR=bmeurer@chromium.org

Review-Url: https://codereview.chromium.org/2789073002
Cr-Commit-Position: refs/heads/master@{#44344}
This commit is contained in:
kozyatinskiy 2017-04-03 07:58:49 -07:00 committed by Commit bot
parent 32d4d8e93d
commit dc662e5b74
14 changed files with 164 additions and 186 deletions

View File

@ -8646,8 +8646,8 @@ class Internals {
static const int kNodeIsIndependentShift = 3;
static const int kNodeIsActiveShift = 4;
static const int kJSApiObjectType = 0xba;
static const int kJSObjectType = 0xbb;
static const int kJSApiObjectType = 0xbb;
static const int kJSObjectType = 0xbc;
static const int kFirstNonstringType = 0x80;
static const int kOddballType = 0x82;
static const int kForeignType = 0x86;

View File

@ -2846,8 +2846,8 @@ Local<StackFrame> StackTrace::GetFrame(uint32_t index) const {
EscapableHandleScope scope(reinterpret_cast<Isolate*>(isolate));
auto self = Utils::OpenHandle(this);
auto obj = i::JSReceiver::GetElement(isolate, self, index).ToHandleChecked();
auto jsobj = i::Handle<i::JSObject>::cast(obj);
return scope.Escape(Utils::StackFrameToLocal(jsobj));
auto info = i::Handle<i::StackFrameInfo>::cast(obj);
return scope.Escape(Utils::StackFrameToLocal(info));
}
@ -2875,77 +2875,59 @@ Local<StackTrace> StackTrace::CurrentStackTrace(
// --- S t a c k F r a m e ---
static int getIntProperty(const StackFrame* f, const char* propertyName,
int defaultValue) {
i::Isolate* isolate = Utils::OpenHandle(f)->GetIsolate();
ENTER_V8_NO_SCRIPT_NO_EXCEPTION(isolate);
i::HandleScope scope(isolate);
i::Handle<i::JSObject> self = Utils::OpenHandle(f);
i::Handle<i::Object> obj =
i::JSReceiver::GetProperty(isolate, self, propertyName).ToHandleChecked();
return obj->IsSmi() ? i::Smi::cast(*obj)->value() : defaultValue;
}
int StackFrame::GetLineNumber() const {
return getIntProperty(this, "lineNumber", Message::kNoLineNumberInfo);
int v = Utils::OpenHandle(this)->line_number();
return v ? v : Message::kNoLineNumberInfo;
}
int StackFrame::GetColumn() const {
return getIntProperty(this, "column", Message::kNoColumnInfo);
int v = Utils::OpenHandle(this)->column_number();
return v ? v : Message::kNoLineNumberInfo;
}
int StackFrame::GetScriptId() const {
return getIntProperty(this, "scriptId", Message::kNoScriptIdInfo);
int v = Utils::OpenHandle(this)->script_id();
return v ? v : Message::kNoScriptIdInfo;
}
static Local<String> getStringProperty(const StackFrame* f,
const char* propertyName) {
i::Isolate* isolate = Utils::OpenHandle(f)->GetIsolate();
ENTER_V8_NO_SCRIPT_NO_EXCEPTION(isolate);
Local<String> StackFrame::GetScriptName() const {
i::Isolate* isolate = Utils::OpenHandle(this)->GetIsolate();
EscapableHandleScope scope(reinterpret_cast<Isolate*>(isolate));
i::Handle<i::JSObject> self = Utils::OpenHandle(f);
i::Handle<i::Object> obj =
i::JSReceiver::GetProperty(isolate, self, propertyName).ToHandleChecked();
i::Handle<i::StackFrameInfo> self = Utils::OpenHandle(this);
i::Handle<i::Object> obj(self->script_name(), isolate);
return obj->IsString()
? scope.Escape(Local<String>::Cast(Utils::ToLocal(obj)))
: Local<String>();
}
Local<String> StackFrame::GetScriptName() const {
return getStringProperty(this, "scriptName");
}
Local<String> StackFrame::GetScriptNameOrSourceURL() const {
return getStringProperty(this, "scriptNameOrSourceURL");
i::Isolate* isolate = Utils::OpenHandle(this)->GetIsolate();
EscapableHandleScope scope(reinterpret_cast<Isolate*>(isolate));
i::Handle<i::StackFrameInfo> self = Utils::OpenHandle(this);
i::Handle<i::Object> obj(self->script_name_or_source_url(), isolate);
return obj->IsString()
? scope.Escape(Local<String>::Cast(Utils::ToLocal(obj)))
: Local<String>();
}
Local<String> StackFrame::GetFunctionName() const {
return getStringProperty(this, "functionName");
i::Isolate* isolate = Utils::OpenHandle(this)->GetIsolate();
EscapableHandleScope scope(reinterpret_cast<Isolate*>(isolate));
i::Handle<i::StackFrameInfo> self = Utils::OpenHandle(this);
i::Handle<i::Object> obj(self->function_name(), isolate);
return obj->IsString()
? scope.Escape(Local<String>::Cast(Utils::ToLocal(obj)))
: Local<String>();
}
static bool getBoolProperty(const StackFrame* f, const char* propertyName) {
i::Isolate* isolate = Utils::OpenHandle(f)->GetIsolate();
ENTER_V8_NO_SCRIPT_NO_EXCEPTION(isolate);
i::HandleScope scope(isolate);
i::Handle<i::JSObject> self = Utils::OpenHandle(f);
i::Handle<i::Object> obj =
i::JSReceiver::GetProperty(isolate, self, propertyName).ToHandleChecked();
return obj->IsTrue(isolate);
}
bool StackFrame::IsEval() const { return getBoolProperty(this, "isEval"); }
bool StackFrame::IsEval() const { return Utils::OpenHandle(this)->is_eval(); }
bool StackFrame::IsConstructor() const {
return getBoolProperty(this, "isConstructor");
return Utils::OpenHandle(this)->is_constructor();
}

View File

@ -106,7 +106,7 @@ class RegisteredExtension {
V(Context, Context) \
V(External, Object) \
V(StackTrace, JSArray) \
V(StackFrame, JSObject) \
V(StackFrame, StackFrameInfo) \
V(Proxy, JSProxy) \
V(NativeWeakMap, JSWeakMap) \
V(debug::GeneratorObject, JSGeneratorObject) \
@ -188,7 +188,7 @@ class Utils {
static inline Local<StackTrace> StackTraceToLocal(
v8::internal::Handle<v8::internal::JSArray> obj);
static inline Local<StackFrame> StackFrameToLocal(
v8::internal::Handle<v8::internal::JSObject> obj);
v8::internal::Handle<v8::internal::StackFrameInfo> obj);
static inline Local<Number> NumberToLocal(
v8::internal::Handle<v8::internal::Object> obj);
static inline Local<Integer> IntegerToLocal(
@ -318,7 +318,7 @@ MAKE_TO_LOCAL(AccessorSignatureToLocal, FunctionTemplateInfo, AccessorSignature)
MAKE_TO_LOCAL(MessageToLocal, Object, Message)
MAKE_TO_LOCAL(PromiseToLocal, JSObject, Promise)
MAKE_TO_LOCAL(StackTraceToLocal, JSArray, StackTrace)
MAKE_TO_LOCAL(StackFrameToLocal, JSObject, StackFrame)
MAKE_TO_LOCAL(StackFrameToLocal, StackFrameInfo, StackFrame)
MAKE_TO_LOCAL(NumberToLocal, Object, Number)
MAKE_TO_LOCAL(IntegerToLocal, Object, Integer)
MAKE_TO_LOCAL(Uint32ToLocal, Object, Uint32)

View File

@ -312,6 +312,7 @@ AstType::bitset AstBitsetType::Lub(i::Map* map) {
case ALIASED_ARGUMENTS_ENTRY_TYPE:
case DEBUG_INFO_TYPE:
case BREAK_POINT_INFO_TYPE:
case STACK_FRAME_INFO_TYPE:
case CELL_TYPE:
case WEAK_CELL_TYPE:
case PROTOTYPE_INFO_TYPE:

View File

@ -320,6 +320,7 @@ Type::bitset BitsetType::Lub(i::Map* map) {
case PROMISE_REACTION_JOB_INFO_TYPE:
case DEBUG_INFO_TYPE:
case BREAK_POINT_INFO_TYPE:
case STACK_FRAME_INFO_TYPE:
case CELL_TYPE:
case WEAK_CELL_TYPE:
case PROTOTYPE_INFO_TYPE:

View File

@ -4203,6 +4203,7 @@ Handle<Object> TranslatedState::MaterializeCapturedObjectAt(
case PROMISE_REACTION_JOB_INFO_TYPE:
case DEBUG_INFO_TYPE:
case BREAK_POINT_INFO_TYPE:
case STACK_FRAME_INFO_TYPE:
case CELL_TYPE:
case WEAK_CELL_TYPE:
case PROTOTYPE_INFO_TYPE:

View File

@ -2592,6 +2592,19 @@ Handle<BreakPointInfo> Factory::NewBreakPointInfo(int source_position) {
return new_break_point_info;
}
Handle<StackFrameInfo> Factory::NewStackFrameInfo() {
Handle<StackFrameInfo> stack_frame_info =
Handle<StackFrameInfo>::cast(NewStruct(STACK_FRAME_INFO_TYPE));
stack_frame_info->set_line_number(0);
stack_frame_info->set_column_number(0);
stack_frame_info->set_script_id(0);
stack_frame_info->set_script_name(Smi::kZero);
stack_frame_info->set_script_name_or_source_url(Smi::kZero);
stack_frame_info->set_function_name(Smi::kZero);
stack_frame_info->set_flag(0);
return stack_frame_info;
}
Handle<JSObject> Factory::NewArgumentsObject(Handle<JSFunction> callee,
int length) {
bool strict_mode_callee = is_strict(callee->shared()->language_mode()) ||

View File

@ -321,6 +321,7 @@ class V8_EXPORT_PRIVATE Factory final {
Handle<Script> NewScript(Handle<String> source);
Handle<BreakPointInfo> NewBreakPointInfo(int source_position);
Handle<StackFrameInfo> NewStackFrameInfo();
// Foreign objects are pretenured when allocated by the bootstrapper.
Handle<Foreign> NewForeign(Address addr,

View File

@ -614,169 +614,85 @@ class CaptureStackTraceHelper {
public:
CaptureStackTraceHelper(Isolate* isolate,
StackTrace::StackTraceOptions options)
: isolate_(isolate) {
if (options & StackTrace::kColumnOffset) {
column_key_ =
factory()->InternalizeOneByteString(STATIC_CHAR_VECTOR("column"));
}
if (options & StackTrace::kLineNumber) {
line_key_ =
factory()->InternalizeOneByteString(STATIC_CHAR_VECTOR("lineNumber"));
}
if (options & StackTrace::kScriptId) {
script_id_key_ =
factory()->InternalizeOneByteString(STATIC_CHAR_VECTOR("scriptId"));
}
if (options & StackTrace::kScriptName) {
script_name_key_ =
factory()->InternalizeOneByteString(STATIC_CHAR_VECTOR("scriptName"));
}
if (options & StackTrace::kScriptNameOrSourceURL) {
script_name_or_source_url_key_ = factory()->InternalizeOneByteString(
STATIC_CHAR_VECTOR("scriptNameOrSourceURL"));
}
if (options & StackTrace::kFunctionName) {
function_key_ = factory()->InternalizeOneByteString(
STATIC_CHAR_VECTOR("functionName"));
}
if (options & StackTrace::kIsEval) {
eval_key_ =
factory()->InternalizeOneByteString(STATIC_CHAR_VECTOR("isEval"));
}
if (options & StackTrace::kIsConstructor) {
constructor_key_ = factory()->InternalizeOneByteString(
STATIC_CHAR_VECTOR("isConstructor"));
}
}
: isolate_(isolate), options_(options) {}
Handle<JSObject> NewStackFrameObject(FrameSummary& summ) {
Handle<StackFrameInfo> NewStackFrameObject(FrameSummary& summ) {
if (summ.IsJavaScript()) return NewStackFrameObject(summ.AsJavaScript());
if (summ.IsWasm()) return NewStackFrameObject(summ.AsWasm());
UNREACHABLE();
return Handle<JSObject>::null();
return factory()->NewStackFrameInfo();
}
Handle<JSObject> NewStackFrameObject(
Handle<StackFrameInfo> NewStackFrameObject(
const FrameSummary::JavaScriptFrameSummary& summ) {
Handle<JSObject> stack_frame =
factory()->NewJSObject(isolate_->object_function());
Handle<StackFrameInfo> frame = factory()->NewStackFrameInfo();
Handle<Script> script = Handle<Script>::cast(summ.script());
if (!line_key_.is_null()) {
if (options_ & StackTrace::kLineNumber) {
Script::PositionInfo info;
bool valid_pos = Script::GetPositionInfo(script, summ.SourcePosition(),
&info, Script::WITH_OFFSET);
if (!column_key_.is_null() && valid_pos) {
JSObject::AddProperty(stack_frame, column_key_,
handle(Smi::FromInt(info.column + 1), isolate_),
NONE);
if (valid_pos) {
frame->set_line_number(info.line + 1);
if (options_ & StackTrace::kColumnOffset) {
frame->set_column_number(info.column + 1);
}
}
JSObject::AddProperty(stack_frame, line_key_,
handle(Smi::FromInt(info.line + 1), isolate_),
NONE);
}
if (!script_id_key_.is_null()) {
JSObject::AddProperty(stack_frame, script_id_key_,
handle(Smi::FromInt(script->id()), isolate_), NONE);
if (options_ & StackTrace::kScriptId) frame->set_script_id(script->id());
if (options_ & StackTrace::kScriptName) {
frame->set_script_name(script->name());
}
if (!script_name_key_.is_null()) {
JSObject::AddProperty(stack_frame, script_name_key_,
handle(script->name(), isolate_), NONE);
if (options_ & StackTrace::kScriptNameOrSourceURL) {
frame->set_script_name_or_source_url(script->GetNameOrSourceURL());
}
if (!script_name_or_source_url_key_.is_null()) {
Handle<Object> result(script->GetNameOrSourceURL(), isolate_);
JSObject::AddProperty(stack_frame, script_name_or_source_url_key_, result,
NONE);
if (options_ & StackTrace::kIsEval) {
frame->set_is_eval(script->compilation_type() ==
Script::COMPILATION_TYPE_EVAL);
}
if (!eval_key_.is_null()) {
Handle<Object> is_eval = factory()->ToBoolean(
script->compilation_type() == Script::COMPILATION_TYPE_EVAL);
JSObject::AddProperty(stack_frame, eval_key_, is_eval, NONE);
if (options_ & StackTrace::kFunctionName) {
Handle<String> name = summ.FunctionName();
frame->set_function_name(*name);
}
if (!function_key_.is_null()) {
Handle<String> fun_name = summ.FunctionName();
JSObject::AddProperty(stack_frame, function_key_, fun_name, NONE);
if (options_ & StackTrace::kIsConstructor) {
frame->set_is_constructor(summ.is_constructor());
}
if (!constructor_key_.is_null()) {
Handle<Object> is_constructor_obj =
factory()->ToBoolean(summ.is_constructor());
JSObject::AddProperty(stack_frame, constructor_key_, is_constructor_obj,
NONE);
}
return stack_frame;
return frame;
}
Handle<JSObject> NewStackFrameObject(BuiltinExitFrame* frame) {
Handle<JSObject> stack_frame =
factory()->NewJSObject(isolate_->object_function());
Handle<JSFunction> fun = handle(frame->function(), isolate_);
if (!function_key_.is_null()) {
Handle<Object> fun_name = JSFunction::GetDebugName(fun);
JSObject::AddProperty(stack_frame, function_key_, fun_name, NONE);
}
// We don't have a script and hence cannot set line and col positions.
DCHECK(!fun->shared()->script()->IsScript());
return stack_frame;
}
Handle<JSObject> NewStackFrameObject(
Handle<StackFrameInfo> NewStackFrameObject(
const FrameSummary::WasmFrameSummary& summ) {
Handle<JSObject> stack_frame =
factory()->NewJSObject(isolate_->object_function());
Handle<StackFrameInfo> info = factory()->NewStackFrameInfo();
if (!function_key_.is_null()) {
if (options_ & StackTrace::kFunctionName) {
Handle<WasmCompiledModule> compiled_module(
summ.wasm_instance()->compiled_module(), isolate_);
Handle<String> name = WasmCompiledModule::GetFunctionName(
isolate_, compiled_module, summ.function_index());
JSObject::AddProperty(stack_frame, function_key_, name, NONE);
info->set_function_name(*name);
}
// Encode the function index as line number (1-based).
if (!line_key_.is_null()) {
JSObject::AddProperty(
stack_frame, line_key_,
isolate_->factory()->NewNumberFromInt(summ.function_index() + 1),
NONE);
if (options_ & StackTrace::kLineNumber) {
info->set_line_number(summ.function_index() + 1);
}
// Encode the byte offset as column (1-based).
if (!column_key_.is_null()) {
if (options_ & StackTrace::kColumnOffset) {
int position = summ.byte_offset();
// Make position 1-based.
if (position >= 0) ++position;
JSObject::AddProperty(stack_frame, column_key_,
isolate_->factory()->NewNumberFromInt(position),
NONE);
info->set_column_number(position);
}
if (!script_id_key_.is_null()) {
int script_id = summ.script()->id();
JSObject::AddProperty(stack_frame, script_id_key_,
handle(Smi::FromInt(script_id), isolate_), NONE);
if (options_ & StackTrace::kScriptId) {
info->set_script_id(summ.script()->id());
}
return stack_frame;
return info;
}
private:
inline Factory* factory() { return isolate_->factory(); }
Isolate* isolate_;
Handle<String> column_key_;
Handle<String> line_key_;
Handle<String> script_id_key_;
Handle<String> script_name_key_;
Handle<String> script_name_or_source_url_key_;
Handle<String> function_key_;
Handle<String> eval_key_;
Handle<String> constructor_key_;
StackTrace::StackTraceOptions options_;
};
Handle<JSArray> Isolate::CaptureCurrentStackTrace(
@ -803,7 +719,8 @@ Handle<JSArray> Isolate::CaptureCurrentStackTrace(
if (!(options & StackTrace::kExposeFramesAcrossSecurityOrigins) &&
!this->context()->HasSameSecurityTokenAs(*frames[i].native_context()))
continue;
Handle<JSObject> new_frame_obj = helper.NewStackFrameObject(frames[i]);
Handle<StackFrameInfo> new_frame_obj =
helper.NewStackFrameObject(frames[i]);
stack_trace_elems->set(frames_seen, *new_frame_obj);
frames_seen++;
}

View File

@ -1302,6 +1302,13 @@ void BreakPointInfo::BreakPointInfoVerify() {
CHECK(IsBreakPointInfo());
VerifyPointer(break_point_objects());
}
void StackFrameInfo::StackFrameInfoVerify() {
CHECK(IsStackFrameInfo());
VerifyPointer(script_name());
VerifyPointer(script_name_or_source_url());
VerifyPointer(function_name());
}
#endif // VERIFY_HEAP
#ifdef DEBUG

View File

@ -5797,6 +5797,17 @@ Code* DebugInfo::DebugCode() {
SMI_ACCESSORS(BreakPointInfo, source_position, kSourcePositionIndex)
ACCESSORS(BreakPointInfo, break_point_objects, Object, kBreakPointObjectsIndex)
SMI_ACCESSORS(StackFrameInfo, line_number, kLineNumberIndex)
SMI_ACCESSORS(StackFrameInfo, column_number, kColumnNumberIndex)
SMI_ACCESSORS(StackFrameInfo, script_id, kScriptIdIndex)
ACCESSORS(StackFrameInfo, script_name, Object, kScriptNameIndex)
ACCESSORS(StackFrameInfo, script_name_or_source_url, Object,
kScriptNameOrSourceUrlIndex)
ACCESSORS(StackFrameInfo, function_name, Object, kFunctionNameIndex)
SMI_ACCESSORS(StackFrameInfo, flag, kFlagIndex)
BOOL_ACCESSORS(StackFrameInfo, flag, is_eval, kIsEvalBit)
BOOL_ACCESSORS(StackFrameInfo, flag, is_constructor, kIsConstructorBit)
ACCESSORS(SharedFunctionInfo, name, Object, kNameOffset)
ACCESSORS(SharedFunctionInfo, optimized_code_map, FixedArray,
kOptimizedCodeMapOffset)

View File

@ -1472,6 +1472,19 @@ void BreakPointInfo::BreakPointInfoPrint(std::ostream& os) { // NOLINT
os << "\n";
}
void StackFrameInfo::StackFrameInfoPrint(std::ostream& os) { // NOLINT
HeapObject::PrintHeader(os, "StackFrame");
os << "\n - line_number: " << line_number();
os << "\n - column_number: " << column_number();
os << "\n - script_id: " << script_id();
os << "\n - script_name: " << Brief(script_name());
os << "\n - script_name_or_source_url: "
<< Brief(script_name_or_source_url());
os << "\n - function_name: " << Brief(function_name());
os << "\n - is_eval: " << (is_eval() ? "true" : "false");
os << "\n - is_constructor: " << (is_constructor() ? "true" : "false");
os << "\n";
}
static void PrintBitMask(std::ostream& os, uint32_t value) { // NOLINT
for (int i = 0; i < 32; i++) {

View File

@ -144,6 +144,7 @@
// - Script
// - DebugInfo
// - BreakPointInfo
// - StackFrameInfo
// - CodeCache
// - PrototypeInfo
// - Module
@ -357,6 +358,7 @@ const int kStubMinorKeyBits = kSmiValueSize - kStubMajorKeyBits - 1;
V(PROMISE_REACTION_JOB_INFO_TYPE) \
V(DEBUG_INFO_TYPE) \
V(BREAK_POINT_INFO_TYPE) \
V(STACK_FRAME_INFO_TYPE) \
V(PROTOTYPE_INFO_TYPE) \
V(TUPLE2_TYPE) \
V(TUPLE3_TYPE) \
@ -528,6 +530,7 @@ const int kStubMinorKeyBits = kSmiValueSize - kStubMajorKeyBits - 1;
promise_reaction_job_info) \
V(DEBUG_INFO, DebugInfo, debug_info) \
V(BREAK_POINT_INFO, BreakPointInfo, break_point_info) \
V(STACK_FRAME_INFO, StackFrameInfo, stack_frame_info) \
V(PROTOTYPE_INFO, PrototypeInfo, prototype_info) \
V(TUPLE2, Tuple2, tuple2) \
V(TUPLE3, Tuple3, tuple3) \
@ -699,6 +702,7 @@ enum InstanceType {
PROMISE_REACTION_JOB_INFO_TYPE,
DEBUG_INFO_TYPE,
BREAK_POINT_INFO_TYPE,
STACK_FRAME_INFO_TYPE,
PROTOTYPE_INFO_TYPE,
TUPLE2_TYPE,
TUPLE3_TYPE,
@ -11283,6 +11287,42 @@ class BreakPointInfo: public Struct {
DISALLOW_IMPLICIT_CONSTRUCTORS(BreakPointInfo);
};
class StackFrameInfo : public Struct {
public:
DECL_INT_ACCESSORS(line_number)
DECL_INT_ACCESSORS(column_number)
DECL_INT_ACCESSORS(script_id)
DECL_ACCESSORS(script_name, Object)
DECL_ACCESSORS(script_name_or_source_url, Object)
DECL_ACCESSORS(function_name, Object)
DECL_BOOLEAN_ACCESSORS(is_eval)
DECL_BOOLEAN_ACCESSORS(is_constructor)
DECL_INT_ACCESSORS(flag)
DECLARE_CAST(StackFrameInfo)
// Dispatched behavior.
DECLARE_PRINTER(StackFrameInfo)
DECLARE_VERIFIER(StackFrameInfo)
static const int kLineNumberIndex = Struct::kHeaderSize;
static const int kColumnNumberIndex = kLineNumberIndex + kPointerSize;
static const int kScriptIdIndex = kColumnNumberIndex + kPointerSize;
static const int kScriptNameIndex = kScriptIdIndex + kPointerSize;
static const int kScriptNameOrSourceUrlIndex =
kScriptNameIndex + kPointerSize;
static const int kFunctionNameIndex =
kScriptNameOrSourceUrlIndex + kPointerSize;
static const int kFlagIndex = kFunctionNameIndex + kPointerSize;
static const int kSize = kFlagIndex + kPointerSize;
private:
// Bit position in the flag, from least significant bit position.
static const int kIsEvalBit = 0;
static const int kIsConstructorBit = 1;
DISALLOW_IMPLICIT_CONSTRUCTORS(StackFrameInfo);
};
#define VISITOR_SYNCHRONIZATION_TAGS_LIST(V) \
V(kStringTable, "string_table", "(Internalized strings)") \

View File

@ -103,19 +103,10 @@ Object* ThrowRuntimeError(Isolate* isolate, int message_id, int byte_offset,
Handle<FixedArray> stack_elements(
FixedArray::cast(JSArray::cast(*detailed_stack_trace_obj)->elements()));
DCHECK_GE(stack_elements->length(), 1);
Handle<JSObject> top_frame(JSObject::cast(stack_elements->get(0)));
Handle<String> wasm_offset_key =
isolate->factory()->InternalizeOneByteString(
STATIC_CHAR_VECTOR("column"));
LookupIterator it(top_frame, wasm_offset_key, top_frame,
LookupIterator::PROTOTYPE_CHAIN_SKIP_INTERCEPTOR);
if (it.IsFound()) {
DCHECK(JSReceiver::GetDataProperty(&it)->IsSmi());
// Make column number 1-based here.
Maybe<bool> data_set = JSReceiver::SetDataProperty(
&it, handle(Smi::FromInt(byte_offset + 1), isolate));
DCHECK(data_set.IsJust() && data_set.FromJust() == true);
USE(data_set);
Handle<StackFrameInfo> top_frame(
StackFrameInfo::cast(stack_elements->get(0)));
if (top_frame->column_number()) {
top_frame->set_column_number(byte_offset + 1);
}
}