mirror of
https://github.com/konsoletyper/teavm.git
synced 2024-11-21 01:00:54 +08:00
wasm gc: support writing debug info, support it in disassembler
This commit is contained in:
parent
7aec0763fa
commit
c2eb11e056
@ -0,0 +1,22 @@
|
||||
/*
|
||||
* Copyright 2024 Alexey Andreev.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.teavm.backend.wasm;
|
||||
|
||||
public enum WasmDebugInfoLevel {
|
||||
NONE,
|
||||
DEOBFUSCATION,
|
||||
FULL
|
||||
}
|
@ -0,0 +1,21 @@
|
||||
/*
|
||||
* Copyright 2024 Alexey Andreev.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.teavm.backend.wasm;
|
||||
|
||||
public enum WasmDebugInfoLocation {
|
||||
EMBEDDED,
|
||||
EXTERNAL
|
||||
}
|
@ -21,6 +21,9 @@ import java.util.Comparator;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import org.teavm.backend.wasm.debug.DebugLines;
|
||||
import org.teavm.backend.wasm.debug.ExternalDebugFile;
|
||||
import org.teavm.backend.wasm.debug.GCDebugInfoBuilder;
|
||||
import org.teavm.backend.wasm.gc.TeaVMWasmGCHost;
|
||||
import org.teavm.backend.wasm.gc.WasmGCDependencies;
|
||||
import org.teavm.backend.wasm.generate.gc.WasmGCDeclarationsGenerator;
|
||||
@ -63,6 +66,8 @@ public class WasmGCTarget implements TeaVMTarget, TeaVMWasmGCHost {
|
||||
private BoundCheckInsertion boundCheckInsertion = new BoundCheckInsertion();
|
||||
private boolean strict;
|
||||
private boolean obfuscated;
|
||||
private WasmDebugInfoLocation debugLocation;
|
||||
private WasmDebugInfoLevel debugLevel;
|
||||
private List<WasmGCIntrinsicFactory> intrinsicFactories = new ArrayList<>();
|
||||
private Map<MethodReference, WasmGCIntrinsic> customIntrinsics = new HashMap<>();
|
||||
private List<WasmGCCustomTypeMapperFactory> customTypeMapperFactories = new ArrayList<>();
|
||||
@ -77,6 +82,14 @@ public class WasmGCTarget implements TeaVMTarget, TeaVMWasmGCHost {
|
||||
this.strict = strict;
|
||||
}
|
||||
|
||||
public void setDebugLevel(WasmDebugInfoLevel debugLevel) {
|
||||
this.debugLevel = debugLevel;
|
||||
}
|
||||
|
||||
public void setDebugLocation(WasmDebugInfoLocation debugLocation) {
|
||||
this.debugLocation = debugLocation;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void addIntrinsicFactory(WasmGCIntrinsicFactory intrinsicFactory) {
|
||||
intrinsicFactories.add(intrinsicFactory);
|
||||
@ -172,6 +185,7 @@ public class WasmGCTarget implements TeaVMTarget, TeaVMWasmGCHost {
|
||||
customGeneratorFactories, customCustomGenerators,
|
||||
controller.getProperties());
|
||||
var intrinsics = new WasmGCIntrinsics(classes, controller.getServices(), intrinsicFactories, customIntrinsics);
|
||||
var debugInfoBuilder = new GCDebugInfoBuilder();
|
||||
var declarationsGenerator = new WasmGCDeclarationsGenerator(
|
||||
module,
|
||||
classes,
|
||||
@ -231,7 +245,7 @@ public class WasmGCTarget implements TeaVMTarget, TeaVMWasmGCHost {
|
||||
customGenerators.contributeToModule(module);
|
||||
adjustModuleMemory(module);
|
||||
|
||||
emitWasmFile(module, buildTarget, outputName);
|
||||
emitWasmFile(module, buildTarget, outputName, debugInfoBuilder);
|
||||
}
|
||||
|
||||
private void adjustModuleMemory(WasmModule module) {
|
||||
@ -248,13 +262,22 @@ public class WasmGCTarget implements TeaVMTarget, TeaVMWasmGCHost {
|
||||
module.setMaxMemorySize(pages);
|
||||
}
|
||||
|
||||
private void emitWasmFile(WasmModule module, BuildTarget buildTarget, String outputName) throws IOException {
|
||||
private void emitWasmFile(WasmModule module, BuildTarget buildTarget, String outputName,
|
||||
GCDebugInfoBuilder debugInfoBuilder) throws IOException {
|
||||
var binaryWriter = new WasmBinaryWriter();
|
||||
DebugLines debugLines = null;
|
||||
if (debugLevel != WasmDebugInfoLevel.NONE) {
|
||||
debugLines = debugInfoBuilder.lines();
|
||||
}
|
||||
var binaryRenderer = new WasmBinaryRenderer(binaryWriter, WasmBinaryVersion.V_0x1, obfuscated,
|
||||
null, null, null, null, WasmBinaryStatsCollector.EMPTY);
|
||||
null, null, debugLines, null, WasmBinaryStatsCollector.EMPTY);
|
||||
optimizeIndexes(module);
|
||||
module.prepareForRendering();
|
||||
binaryRenderer.render(module);
|
||||
if (debugLocation == WasmDebugInfoLocation.EMBEDDED) {
|
||||
binaryRenderer.render(module, debugInfoBuilder::build);
|
||||
} else {
|
||||
binaryRenderer.render(module);
|
||||
}
|
||||
var data = binaryWriter.getData();
|
||||
if (!outputName.endsWith(".wasm")) {
|
||||
outputName += ".wasm";
|
||||
@ -262,6 +285,14 @@ public class WasmGCTarget implements TeaVMTarget, TeaVMWasmGCHost {
|
||||
try (var output = buildTarget.createResource(outputName)) {
|
||||
output.write(data);
|
||||
}
|
||||
if (debugLocation == WasmDebugInfoLocation.EXTERNAL) {
|
||||
var debugInfoData = ExternalDebugFile.write(debugInfoBuilder.build());
|
||||
if (debugInfoData != null) {
|
||||
try (var output = buildTarget.createResource(outputName + ".tdbg")) {
|
||||
output.write(debugInfoData);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void optimizeIndexes(WasmModule module) {
|
||||
|
@ -0,0 +1,41 @@
|
||||
/*
|
||||
* Copyright 2024 Alexey Andreev.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.teavm.backend.wasm.debug;
|
||||
|
||||
import java.util.List;
|
||||
import org.teavm.backend.wasm.model.WasmCustomSection;
|
||||
import org.teavm.backend.wasm.render.WasmBinaryWriter;
|
||||
|
||||
public final class ExternalDebugFile {
|
||||
private ExternalDebugFile() {
|
||||
}
|
||||
|
||||
public static byte[] write(List<WasmCustomSection> sections) {
|
||||
if (sections.isEmpty()) {
|
||||
return null;
|
||||
}
|
||||
var writer = new WasmBinaryWriter();
|
||||
writer.writeInt32(0x67626474);
|
||||
writer.writeInt32(1);
|
||||
for (var section : sections) {
|
||||
var data = section.getData();
|
||||
writer.writeAsciiString(section.getName());
|
||||
writer.writeLEB(data.length);
|
||||
writer.writeBytes(data);
|
||||
}
|
||||
return writer.getData();
|
||||
}
|
||||
}
|
@ -0,0 +1,80 @@
|
||||
/*
|
||||
* Copyright 2024 Alexey Andreev.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.teavm.backend.wasm.debug;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import org.teavm.backend.wasm.model.WasmCustomSection;
|
||||
|
||||
public class GCDebugInfoBuilder {
|
||||
private DebugStringsBuilder strings;
|
||||
private DebugFilesBuilder files;
|
||||
private DebugPackagesBuilder packages;
|
||||
private DebugClassesBuilder classes;
|
||||
private DebugMethodsBuilder methods;
|
||||
private DebugLinesBuilder lines;
|
||||
|
||||
public GCDebugInfoBuilder() {
|
||||
strings = new DebugStringsBuilder();
|
||||
files = new DebugFilesBuilder(strings);
|
||||
packages = new DebugPackagesBuilder(strings);
|
||||
classes = new DebugClassesBuilder(packages, strings);
|
||||
methods = new DebugMethodsBuilder(classes, strings);
|
||||
lines = new DebugLinesBuilder(files, methods);
|
||||
}
|
||||
|
||||
public DebugStrings strings() {
|
||||
return strings;
|
||||
}
|
||||
|
||||
public DebugFiles files() {
|
||||
return files;
|
||||
}
|
||||
|
||||
public DebugPackages packages() {
|
||||
return packages;
|
||||
}
|
||||
|
||||
public DebugClasses classes() {
|
||||
return classes;
|
||||
}
|
||||
|
||||
public DebugMethods methods() {
|
||||
return methods;
|
||||
}
|
||||
|
||||
public DebugLines lines() {
|
||||
return lines;
|
||||
}
|
||||
|
||||
public List<WasmCustomSection> build() {
|
||||
var result = new ArrayList<WasmCustomSection>();
|
||||
addSection(result, strings);
|
||||
addSection(result, files);
|
||||
addSection(result, packages);
|
||||
addSection(result, classes);
|
||||
addSection(result, methods);
|
||||
addSection(result, lines);
|
||||
return result;
|
||||
}
|
||||
|
||||
private void addSection(List<WasmCustomSection> sections, DebugSectionBuilder builder) {
|
||||
if (builder.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
sections.add(new WasmCustomSection(builder.name(), builder.build()));
|
||||
}
|
||||
}
|
@ -21,7 +21,17 @@ import java.io.FileOutputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.PrintWriter;
|
||||
import java.nio.file.Files;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.function.Consumer;
|
||||
import org.teavm.backend.wasm.debug.info.LineInfo;
|
||||
import org.teavm.backend.wasm.debug.parser.DebugClassParser;
|
||||
import org.teavm.backend.wasm.debug.parser.DebugFileParser;
|
||||
import org.teavm.backend.wasm.debug.parser.DebugLinesParser;
|
||||
import org.teavm.backend.wasm.debug.parser.DebugMethodParser;
|
||||
import org.teavm.backend.wasm.debug.parser.DebugPackageParser;
|
||||
import org.teavm.backend.wasm.debug.parser.DebugSectionParser;
|
||||
import org.teavm.backend.wasm.debug.parser.DebugStringParser;
|
||||
import org.teavm.backend.wasm.parser.AddressListener;
|
||||
import org.teavm.backend.wasm.parser.CodeSectionParser;
|
||||
import org.teavm.backend.wasm.parser.FunctionSectionListener;
|
||||
@ -41,9 +51,27 @@ public final class Disassembler {
|
||||
private WasmHollowFunctionType[] functionTypes;
|
||||
private int[] functionTypeRefs;
|
||||
private int importFunctionCount;
|
||||
private Map<String, DebugSectionParser> debugSectionParsers = new HashMap<>();
|
||||
private DebugLinesParser debugLines;
|
||||
private LineInfo lineInfo;
|
||||
|
||||
public Disassembler(DisassemblyWriter writer) {
|
||||
this.writer = writer;
|
||||
installDebugParsers();
|
||||
}
|
||||
|
||||
private void installDebugParsers() {
|
||||
var strings = addDebugSection(new DebugStringParser());
|
||||
var files = addDebugSection(new DebugFileParser(strings));
|
||||
var packages = addDebugSection(new DebugPackageParser(strings));
|
||||
var classes = addDebugSection(new DebugClassParser(strings, packages));
|
||||
var methods = addDebugSection(new DebugMethodParser(strings, classes));
|
||||
debugLines = addDebugSection(new DebugLinesParser(files, methods));
|
||||
}
|
||||
|
||||
private <T extends DebugSectionParser> T addDebugSection(T section) {
|
||||
debugSectionParsers.put(section.name(), section);
|
||||
return section;
|
||||
}
|
||||
|
||||
public void startModule() {
|
||||
@ -65,18 +93,25 @@ public final class Disassembler {
|
||||
public void read(byte[] bytes) {
|
||||
var nameAccumulator = new NameAccumulatingSectionListener();
|
||||
var input = new ByteArrayAsyncInputStream(bytes);
|
||||
var nameParser = createNameParser(input, nameAccumulator);
|
||||
input.readFully(nameParser::parse);
|
||||
var preparationParser = createPreparationParser(input, nameAccumulator);
|
||||
input.readFully(preparationParser::parse);
|
||||
lineInfo = debugLines.getLineInfo();
|
||||
|
||||
input = new ByteArrayAsyncInputStream(bytes);
|
||||
var parser = createParser(input, nameAccumulator.buildProvider());
|
||||
input.readFully(parser::parse);
|
||||
}
|
||||
|
||||
public ModuleParser createNameParser(AsyncInputStream input, NameSectionListener listener) {
|
||||
public ModuleParser createPreparationParser(AsyncInputStream input, NameSectionListener listener) {
|
||||
return new ModuleParser(input) {
|
||||
@Override
|
||||
protected Consumer<byte[]> getSectionConsumer(int code, int pos, String name) {
|
||||
if (code == 0) {
|
||||
var debugSection = debugSectionParsers.get(name);
|
||||
if (debugSection != null) {
|
||||
return debugSection::parse;
|
||||
}
|
||||
}
|
||||
return Disassembler.this.getNameSectionConsumer(code, name, listener);
|
||||
}
|
||||
};
|
||||
@ -139,11 +174,14 @@ public final class Disassembler {
|
||||
disassembler.setFunctionTypes(functionTypes);
|
||||
disassembler.setFunctionTypeRefs(functionTypeRefs);
|
||||
writer.setAddressOffset(pos);
|
||||
writer.setDebugLines(lineInfo);
|
||||
writer.startSection();
|
||||
writer.write("(; code section size: " + bytes.length + " ;)").eol();
|
||||
var sectionParser = new CodeSectionParser(disassembler);
|
||||
sectionParser.setFunctionIndexOffset(importFunctionCount);
|
||||
sectionParser.parse(writer.addressListener, bytes);
|
||||
writer.flush();
|
||||
writer.setDebugLines(null);
|
||||
};
|
||||
} else {
|
||||
return null;
|
||||
|
@ -24,7 +24,11 @@ public class DisassemblyHTMLWriter extends DisassemblyWriter {
|
||||
|
||||
@Override
|
||||
public DisassemblyWriter prologue() {
|
||||
return writeExact("<html><body><pre>");
|
||||
writeExact("<html>\n<head>");
|
||||
writeExact("<style>\n");
|
||||
writeExact("em { color: gray; }\n");
|
||||
writeExact("</style></head>\n");
|
||||
return writeExact("<body><pre>");
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -82,4 +86,14 @@ public class DisassemblyHTMLWriter extends DisassemblyWriter {
|
||||
writeExact(s);
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void startAnnotation() {
|
||||
writeExact("<em>");
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void endAnnotation() {
|
||||
writeExact("</em>");
|
||||
}
|
||||
}
|
||||
|
@ -16,16 +16,27 @@
|
||||
package org.teavm.backend.wasm.disasm;
|
||||
|
||||
import java.io.PrintWriter;
|
||||
import org.teavm.backend.wasm.debug.info.LineInfo;
|
||||
import org.teavm.backend.wasm.debug.info.LineInfoCommandVisitor;
|
||||
import org.teavm.backend.wasm.debug.info.LineInfoEnterCommand;
|
||||
import org.teavm.backend.wasm.debug.info.LineInfoExitCommand;
|
||||
import org.teavm.backend.wasm.debug.info.LineInfoFileCommand;
|
||||
import org.teavm.backend.wasm.debug.info.LineInfoLineCommand;
|
||||
import org.teavm.backend.wasm.parser.AddressListener;
|
||||
|
||||
public abstract class DisassemblyWriter {
|
||||
private PrintWriter out;
|
||||
private boolean withAddress;
|
||||
private int indentLevel;
|
||||
private int addressWithinSection;
|
||||
private int address;
|
||||
private boolean hasAddress;
|
||||
private boolean lineStarted;
|
||||
private int addressOffset;
|
||||
private LineInfo debugLines;
|
||||
private int currentSequenceIndex;
|
||||
private int currentCommandIndex = -1;
|
||||
private int lineInfoIndent;
|
||||
|
||||
public DisassemblyWriter(PrintWriter out) {
|
||||
this.out = out;
|
||||
@ -39,6 +50,15 @@ public abstract class DisassemblyWriter {
|
||||
this.addressOffset = addressOffset;
|
||||
}
|
||||
|
||||
public void setDebugLines(LineInfo debugLines) {
|
||||
this.debugLines = debugLines;
|
||||
}
|
||||
|
||||
public void startSection() {
|
||||
addressWithinSection = -1;
|
||||
currentSequenceIndex = 0;
|
||||
}
|
||||
|
||||
public DisassemblyWriter address() {
|
||||
hasAddress = true;
|
||||
return this;
|
||||
@ -63,6 +83,9 @@ public abstract class DisassemblyWriter {
|
||||
private void startLine() {
|
||||
if (!lineStarted) {
|
||||
lineStarted = true;
|
||||
if (debugLines != null) {
|
||||
printDebugLine();
|
||||
}
|
||||
if (withAddress) {
|
||||
if (hasAddress) {
|
||||
hasAddress = false;
|
||||
@ -77,6 +100,85 @@ public abstract class DisassemblyWriter {
|
||||
}
|
||||
}
|
||||
|
||||
private void printDebugLine() {
|
||||
if (currentSequenceIndex >= debugLines.sequences().size()) {
|
||||
return;
|
||||
}
|
||||
var force = false;
|
||||
if (currentCommandIndex < 0) {
|
||||
if (addressWithinSection < debugLines.sequences().get(currentSequenceIndex).startAddress()) {
|
||||
return;
|
||||
}
|
||||
currentCommandIndex = 0;
|
||||
force = true;
|
||||
} else {
|
||||
if (addressWithinSection >= debugLines.sequences().get(currentSequenceIndex).endAddress()) {
|
||||
printSingleDebugAnnotation("<end debug line sequence>");
|
||||
++currentSequenceIndex;
|
||||
currentCommandIndex = -1;
|
||||
lineInfoIndent = 0;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
var sequence = debugLines.sequences().get(currentSequenceIndex);
|
||||
if (currentCommandIndex >= sequence.commands().size()) {
|
||||
return;
|
||||
}
|
||||
var command = sequence.commands().get(currentCommandIndex);
|
||||
if (!force) {
|
||||
if (currentCommandIndex + 1 < sequence.commands().size()
|
||||
&& addressWithinSection >= sequence.commands().get(currentCommandIndex + 1).address()) {
|
||||
command = sequence.commands().get(++currentCommandIndex);
|
||||
} else {
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
command.acceptVisitor(new LineInfoCommandVisitor() {
|
||||
@Override
|
||||
public void visit(LineInfoEnterCommand command) {
|
||||
printSingleDebugAnnotation(" at " + command.method().fullName());
|
||||
++lineInfoIndent;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visit(LineInfoExitCommand command) {
|
||||
--lineInfoIndent;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visit(LineInfoFileCommand command) {
|
||||
if (command.file() == null) {
|
||||
printSingleDebugAnnotation("at <unknown>:" + command.line());
|
||||
} else {
|
||||
printSingleDebugAnnotation(" at " + command.file().name() + ":" + command.line());
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visit(LineInfoLineCommand command) {
|
||||
printSingleDebugAnnotation(" at " + command.line());
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void printSingleDebugAnnotation(String text) {
|
||||
out.print(" ");
|
||||
for (int i = 0; i < indentLevel; ++i) {
|
||||
out.print(" ");
|
||||
}
|
||||
for (int i = 0; i < lineInfoIndent; ++i) {
|
||||
out.print(" ");
|
||||
}
|
||||
startAnnotation();
|
||||
out.print("(;");
|
||||
write(text);
|
||||
out.print(" ;)");
|
||||
endAnnotation();
|
||||
out.print("\n");
|
||||
}
|
||||
|
||||
private void printAddress() {
|
||||
out.print("(; ");
|
||||
for (int i = 7; i >= 0; --i) {
|
||||
@ -108,15 +210,20 @@ public abstract class DisassemblyWriter {
|
||||
|
||||
public abstract DisassemblyWriter epilogue();
|
||||
|
||||
protected void startAnnotation() {
|
||||
}
|
||||
|
||||
protected void endAnnotation() {
|
||||
}
|
||||
|
||||
public void flush() {
|
||||
out.flush();
|
||||
}
|
||||
|
||||
|
||||
|
||||
public final AddressListener addressListener = new AddressListener() {
|
||||
@Override
|
||||
public void address(int address) {
|
||||
addressWithinSection = address;
|
||||
DisassemblyWriter.this.address = address + addressOffset;
|
||||
}
|
||||
};
|
||||
|
@ -32,6 +32,8 @@ import java.util.Map;
|
||||
import java.util.StringTokenizer;
|
||||
import java.util.function.Consumer;
|
||||
import java.util.function.Supplier;
|
||||
import org.teavm.backend.wasm.WasmDebugInfoLevel;
|
||||
import org.teavm.backend.wasm.WasmDebugInfoLocation;
|
||||
import org.teavm.backend.wasm.WasmGCTarget;
|
||||
import org.teavm.backend.wasm.disasm.Disassembler;
|
||||
import org.teavm.backend.wasm.disasm.DisassemblyHTMLWriter;
|
||||
@ -69,6 +71,8 @@ class WebAssemblyGCPlatformSupport extends TestPlatformSupport<WasmGCTarget> {
|
||||
var target = new WasmGCTarget();
|
||||
target.setObfuscated(false);
|
||||
target.setStrict(true);
|
||||
target.setDebugLevel(WasmDebugInfoLevel.DEOBFUSCATION);
|
||||
target.setDebugLocation(WasmDebugInfoLocation.EMBEDDED);
|
||||
var sourceDirs = System.getProperty(SOURCE_DIRS);
|
||||
if (sourceDirs != null) {
|
||||
var dirs = new ArrayList<File>();
|
||||
|
Loading…
Reference in New Issue
Block a user