Index: src/runtime/runtime-debug.cc |
diff --git a/src/runtime/runtime-debug.cc b/src/runtime/runtime-debug.cc |
index e3f3beb6976da53443707168c427ff0247e525ed..a7b7a1a90251ce466a78eae2b7cd9c6eba4cce3c 100644 |
--- a/src/runtime/runtime-debug.cc |
+++ b/src/runtime/runtime-debug.cc |
@@ -1501,6 +1501,105 @@ RUNTIME_FUNCTION(Runtime_GetScript) { |
return *Script::GetWrapper(found); |
} |
+RUNTIME_FUNCTION(Runtime_ScriptLineCount) { |
+ HandleScope scope(isolate); |
+ DCHECK(args.length() == 1); |
+ CONVERT_ARG_CHECKED(JSValue, script, 0); |
+ |
+ RUNTIME_ASSERT(script->value()->IsScript()); |
+ Handle<Script> script_handle = Handle<Script>(Script::cast(script->value())); |
+ |
+ Script::InitLineEnds(script_handle); |
+ |
+ FixedArray* line_ends_array = FixedArray::cast(script_handle->line_ends()); |
+ return Smi::FromInt(line_ends_array->length()); |
+} |
+ |
+RUNTIME_FUNCTION(Runtime_ScriptLineStartPosition) { |
+ HandleScope scope(isolate); |
+ DCHECK(args.length() == 2); |
+ CONVERT_ARG_CHECKED(JSValue, script, 0); |
+ CONVERT_NUMBER_CHECKED(int32_t, line, Int32, args[1]); |
+ |
+ RUNTIME_ASSERT(script->value()->IsScript()); |
+ Handle<Script> script_handle = Handle<Script>(Script::cast(script->value())); |
+ |
+ Script::InitLineEnds(script_handle); |
+ |
+ FixedArray* line_ends_array = FixedArray::cast(script_handle->line_ends()); |
+ const int line_count = line_ends_array->length(); |
+ |
+ // If line == line_count, we return the first position beyond the last line. |
+ if (line < 0 || line > line_count) { |
+ return Smi::FromInt(-1); |
+ } else if (line == 0) { |
+ return Smi::FromInt(0); |
+ } else { |
+ DCHECK(0 < line && line <= line_count); |
+ const int pos = Smi::cast(line_ends_array->get(line - 1))->value() + 1; |
+ return Smi::FromInt(pos); |
+ } |
+} |
+ |
+RUNTIME_FUNCTION(Runtime_ScriptLineEndPosition) { |
+ HandleScope scope(isolate); |
+ DCHECK(args.length() == 2); |
+ CONVERT_ARG_CHECKED(JSValue, script, 0); |
+ CONVERT_NUMBER_CHECKED(int32_t, line, Int32, args[1]); |
+ |
+ RUNTIME_ASSERT(script->value()->IsScript()); |
+ Handle<Script> script_handle = Handle<Script>(Script::cast(script->value())); |
+ |
+ Script::InitLineEnds(script_handle); |
+ |
+ FixedArray* line_ends_array = FixedArray::cast(script_handle->line_ends()); |
+ const int line_count = line_ends_array->length(); |
+ |
+ if (line < 0 || line >= line_count) { |
+ return Smi::FromInt(-1); |
+ } else { |
+ return Smi::cast(line_ends_array->get(line)); |
+ } |
+} |
+ |
+RUNTIME_FUNCTION(Runtime_ScriptPositionInfo) { |
+ HandleScope scope(isolate); |
+ DCHECK(args.length() == 3); |
+ CONVERT_ARG_CHECKED(JSValue, script, 0); |
+ CONVERT_NUMBER_CHECKED(int32_t, position, Int32, args[1]); |
+ CONVERT_BOOLEAN_ARG_CHECKED(with_offset, 2); |
+ |
+ RUNTIME_ASSERT(script->value()->IsScript()); |
+ Handle<Script> script_handle = Handle<Script>(Script::cast(script->value())); |
+ |
+ Script::PositionInfo info; |
+ const Script::OffsetFlag offset_flag = |
+ with_offset ? Script::kWithOffset : Script::kNoOffset; |
+ if (!script_handle->GetPositionInfo(position, &info, offset_flag)) { |
+ return isolate->heap()->null_value(); |
+ } |
+ |
+ Handle<String> source = |
+ handle(String::cast(script_handle->source()), isolate); |
+ Handle<String> sourceText = |
+ isolate->factory()->NewSubString(source, info.line_start, info.line_end); |
+ |
+ Handle<JSObject> jsinfo = |
+ isolate->factory()->NewJSObject(isolate->object_function()); |
+ |
+ JSObject::AddProperty(jsinfo, isolate->factory()->script_string(), |
+ script_handle, NONE); |
+ JSObject::AddProperty(jsinfo, isolate->factory()->position_string(), |
+ handle(Smi::FromInt(position), isolate), NONE); |
+ JSObject::AddProperty(jsinfo, isolate->factory()->line_string(), |
+ handle(Smi::FromInt(info.line), isolate), NONE); |
+ JSObject::AddProperty(jsinfo, isolate->factory()->column_string(), |
+ handle(Smi::FromInt(info.column), isolate), NONE); |
+ JSObject::AddProperty(jsinfo, isolate->factory()->sourceText_string(), |
+ sourceText, NONE); |
+ |
+ return *jsinfo; |
+} |
// Set one shot breakpoints for the callback function that is passed to a |
// built-in function such as Array.forEach to enable stepping into the callback, |