package com.oracle.truffle.tools.chromeinspector.types;
import java.util.List;
import com.oracle.truffle.tools.utils.json.JSONArray;
import com.oracle.truffle.tools.utils.json.JSONObject;
import com.oracle.truffle.api.debug.DebugStackTraceElement;
import com.oracle.truffle.api.source.Source;
import com.oracle.truffle.api.source.SourceSection;
import com.oracle.truffle.tools.chromeinspector.InspectorExecutionContext;
import com.oracle.truffle.tools.chromeinspector.ScriptsHandler;
public final class StackTrace {
private final JSONObject jsonObject;
public StackTrace(InspectorExecutionContext context, List<List<DebugStackTraceElement>> stacks) {
jsonObject = new JSONObject();
JSONObject jsonStack = jsonObject;
JSONObject jsonParentStack = null;
for (List<DebugStackTraceElement> frames : stacks) {
if (jsonParentStack != null) {
jsonStack.put("parent", jsonParentStack);
jsonStack = jsonParentStack;
}
JSONArray callFrames = new JSONArray();
for (DebugStackTraceElement frame : frames) {
SourceSection sourceSection = frame.getSourceSection();
if (sourceSection == null) {
continue;
}
if (!context.isInspectInternal() && frame.isInternal()) {
continue;
}
Source source = sourceSection.getSource();
if (!context.isInspectInternal() && source.isInternal()) {
continue;
}
JSONObject callFrame = new JSONObject();
callFrame.put("functionName", frame.getName());
ScriptsHandler sch = context.acquireScriptsHandler();
try {
int scriptId = sch.assureLoaded(source);
if (scriptId != -1) {
callFrame.put("scriptId", Integer.toString(scriptId));
callFrame.put("url", sch.getScript(scriptId).getUrl());
callFrame.put("lineNumber", sourceSection.getStartLine() - 1);
callFrame.put("columnNumber", sourceSection.getStartColumn() - 1);
callFrames.put(callFrame);
}
} finally {
context.releaseScriptsHandler();
}
}
jsonStack.put("callFrames", callFrames);
jsonParentStack = new JSONObject();
}
}
public JSONObject toJSON() {
return jsonObject;
}
}