mirror of
https://github.com/Eaglercraft-TeaVM-Fork/eagler-teavm.git
synced 2024-12-22 08:14:09 -08:00
wasm gc: support imported functions in disassembler
This commit is contained in:
parent
0057bbd00d
commit
a5212fb9ca
|
@ -27,7 +27,6 @@ import org.teavm.backend.wasm.parser.CodeSectionParser;
|
|||
import org.teavm.backend.wasm.parser.FunctionSectionListener;
|
||||
import org.teavm.backend.wasm.parser.FunctionSectionParser;
|
||||
import org.teavm.backend.wasm.parser.GlobalSectionParser;
|
||||
import org.teavm.backend.wasm.parser.ImportSectionListener;
|
||||
import org.teavm.backend.wasm.parser.ImportSectionParser;
|
||||
import org.teavm.backend.wasm.parser.ModuleParser;
|
||||
import org.teavm.backend.wasm.parser.NameSectionListener;
|
||||
|
@ -41,6 +40,7 @@ public final class Disassembler {
|
|||
private DisassemblyWriter writer;
|
||||
private WasmHollowFunctionType[] functionTypes;
|
||||
private int[] functionTypeRefs;
|
||||
private int importFunctionCount;
|
||||
|
||||
public Disassembler(DisassemblyWriter writer) {
|
||||
this.writer = writer;
|
||||
|
@ -91,17 +91,6 @@ public final class Disassembler {
|
|||
};
|
||||
}
|
||||
|
||||
ImportListenerImpl importListener = new ImportListenerImpl();
|
||||
|
||||
static class ImportListenerImpl implements ImportSectionListener {
|
||||
int count;
|
||||
|
||||
@Override
|
||||
public void function(int typeIndex) {
|
||||
++count;
|
||||
}
|
||||
}
|
||||
|
||||
public Consumer<byte[]> getSectionConsumer(int code, int pos, NameProvider nameProvider) {
|
||||
if (code == 1) {
|
||||
return bytes -> {
|
||||
|
@ -115,13 +104,15 @@ public final class Disassembler {
|
|||
};
|
||||
} else if (code == 2) {
|
||||
return bytes -> {
|
||||
var importListener = new DisassemblyImportSectionListener(writer, nameProvider, functionTypes);
|
||||
var parser = new ImportSectionParser(importListener);
|
||||
parser.parse(AddressListener.EMPTY, bytes);
|
||||
importFunctionCount = importListener.functionCount();
|
||||
};
|
||||
} else if (code == 3) {
|
||||
return bytes -> {
|
||||
var signatures = new IntArrayList();
|
||||
for (var i = 0; i < importListener.count; ++i) {
|
||||
for (var i = 0; i < importFunctionCount; ++i) {
|
||||
signatures.add(0);
|
||||
}
|
||||
var parser = new FunctionSectionParser(new FunctionSectionListener() {
|
||||
|
@ -150,7 +141,7 @@ public final class Disassembler {
|
|||
writer.setAddressOffset(pos);
|
||||
writer.write("(; code section size: " + bytes.length + " ;)").eol();
|
||||
var sectionParser = new CodeSectionParser(disassembler);
|
||||
sectionParser.setFunctionIndexOffset(importListener.count);
|
||||
sectionParser.setFunctionIndexOffset(importFunctionCount);
|
||||
sectionParser.parse(writer.addressListener, bytes);
|
||||
writer.flush();
|
||||
};
|
||||
|
|
|
@ -0,0 +1,84 @@
|
|||
/*
|
||||
* 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.disasm;
|
||||
|
||||
import org.teavm.backend.wasm.parser.ImportSectionListener;
|
||||
import org.teavm.backend.wasm.parser.WasmHollowFunctionType;
|
||||
|
||||
public class DisassemblyImportSectionListener extends BaseDisassemblyListener implements ImportSectionListener {
|
||||
private WasmHollowFunctionType[] functionTypes;
|
||||
private String currentModule;
|
||||
private String currentName;
|
||||
private int functionIndex;
|
||||
|
||||
public DisassemblyImportSectionListener(DisassemblyWriter writer, NameProvider nameProvider,
|
||||
WasmHollowFunctionType[] functionTypes) {
|
||||
super(writer, nameProvider);
|
||||
this.functionTypes = functionTypes;
|
||||
}
|
||||
|
||||
public int functionCount() {
|
||||
return functionIndex;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void startEntry(String module, String name) {
|
||||
currentModule = module;
|
||||
currentName = name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void function(int typeIndex) {
|
||||
writer.address().write("(import \"").write(currentModule).write("\" \"")
|
||||
.write(currentName).write("\" ");
|
||||
writer.write("(func ");
|
||||
writer.startLinkTarget("f" + functionIndex).write("(; " + functionIndex + " ;)");
|
||||
var name = nameProvider.function(functionIndex);
|
||||
if (name != null) {
|
||||
writer.write(" $").write(name);
|
||||
}
|
||||
writer.endLinkTarget();
|
||||
|
||||
writer.write(" (type ");
|
||||
writeTypeRef(typeIndex);
|
||||
writer.write(")");
|
||||
writer.indent().eol();
|
||||
|
||||
var type = typeIndex < functionTypes.length ? functionTypes[typeIndex] : null;
|
||||
if (type != null) {
|
||||
for (var i = 0; i < type.parameterTypes.length; ++i) {
|
||||
writer.write("(param ");
|
||||
writer.startLinkTarget("l" + functionIndex + "." + i).write(" (; " + i + " ;)");
|
||||
var paramName = nameProvider.local(functionIndex, i);
|
||||
if (paramName != null) {
|
||||
writer.write(" $").write(paramName);
|
||||
}
|
||||
writer.endLinkTarget();
|
||||
writer.write(" ");
|
||||
writeType(type.parameterTypes[i]);
|
||||
writer.write(")").eol();
|
||||
}
|
||||
for (var i = 0; i < type.returnTypes.length; ++i) {
|
||||
writer.write("(result ");
|
||||
writeType(type.returnTypes[i]);
|
||||
writer.write(")").eol();
|
||||
}
|
||||
}
|
||||
writer.outdent().write("))").eol();
|
||||
|
||||
functionIndex++;
|
||||
}
|
||||
}
|
|
@ -112,6 +112,8 @@ public abstract class DisassemblyWriter {
|
|||
out.flush();
|
||||
}
|
||||
|
||||
|
||||
|
||||
public final AddressListener addressListener = new AddressListener() {
|
||||
@Override
|
||||
public void address(int address) {
|
||||
|
|
|
@ -462,7 +462,7 @@ public class WasmBinaryRenderer {
|
|||
|
||||
WasmBinaryWriter functionsSubsection = new WasmBinaryWriter();
|
||||
var functions = module.functions.stream()
|
||||
.filter(f -> f.getName() != null && f.getImportName() == null)
|
||||
.filter(f -> f.getName() != null)
|
||||
.collect(Collectors.toList());
|
||||
functionsSubsection.writeLEB(functions.size());
|
||||
|
||||
|
|
Loading…
Reference in New Issue
Block a user