C: fix generation of virtual tables inheriting interface default methods

This commit is contained in:
Alexey Andreev 2019-05-16 18:50:03 +03:00
parent b3b324d73c
commit f5c2cf0fa3
3 changed files with 19 additions and 7 deletions

View File

@ -114,6 +114,9 @@ public class CallSiteGenerator {
} }
private void generateLocations() { private void generateLocations() {
if (locations.isEmpty()) {
return;
}
includes.includeClass(CALL_SITE_LOCATION); includes.includeClass(CALL_SITE_LOCATION);
writer.print("static ").print(callSiteLocationName).print(" callSiteLocations_" + callSitesName writer.print("static ").print(callSiteLocationName).print(" callSiteLocations_" + callSitesName
+ "[" + locations.size() + "] = {").indent(); + "[" + locations.size() + "] = {").indent();
@ -147,6 +150,9 @@ public class CallSiteGenerator {
} }
private void generateHandlers() { private void generateHandlers() {
if (exceptionHandlers.isEmpty()) {
return;
}
includes.includeClass(EXCEPTION_HANDLER); includes.includeClass(EXCEPTION_HANDLER);
writer.print("static ").print(exceptionHandlerName).print(" exceptionHandlers_" + callSitesName + "[" writer.print("static ").print(exceptionHandlerName).print(" exceptionHandlers_" + callSitesName + "["
+ exceptionHandlers.size() + "] = {").indent(); + exceptionHandlers.size() + "] = {").indent();

View File

@ -613,7 +613,6 @@ public class ClassGenerator {
codeWriter.println(".superclass = " + parent + ","); codeWriter.println(".superclass = " + parent + ",");
codeWriter.println(".superinterfaceCount = " + superinterfaceCount + ","); codeWriter.println(".superinterfaceCount = " + superinterfaceCount + ",");
codeWriter.println(".superinterfaces = " + superinterfaces + ","); codeWriter.println(".superinterfaces = " + superinterfaces + ",");
codeWriter.println(".enumValues = NULL,");
codeWriter.println(".layout = " + layout + ","); codeWriter.println(".layout = " + layout + ",");
codeWriter.println(".enumValues = " + enumConstants + ","); codeWriter.println(".enumValues = " + enumConstants + ",");
codeWriter.println(".init = " + initFunction); codeWriter.println(".init = " + initFunction);

View File

@ -69,12 +69,11 @@ public class VirtualTableProvider {
} }
if (cls.getParent() != null) { if (cls.getParent() != null) {
fillClass(cls.getParent(), methodCalledVirtually); fillClass(cls.getParent(), methodCalledVirtually);
VirtualTable parentTable = virtualTables.get(cls.getParent()); copyEntriesFromSupertype(table, virtualTables.get(cls.getParent()));
for (VirtualTableEntry parentEntry : parentTable.entries.values()) {
VirtualTableEntry entry = new VirtualTableEntry(table, parentEntry.getMethod(),
parentEntry.getImplementor(), parentEntry.getIndex());
table.entries.put(entry.getMethod(), entry);
} }
for (String itf : cls.getInterfaces()) {
fillClass(itf, methodCalledVirtually);
copyEntriesFromSupertype(table, virtualTables.get(itf));
} }
Set<MethodDescriptor> newDescriptors = virtualMethodMap.get(className); Set<MethodDescriptor> newDescriptors = virtualMethodMap.get(className);
@ -106,6 +105,14 @@ public class VirtualTableProvider {
} }
} }
private void copyEntriesFromSupertype(VirtualTable table, VirtualTable supertypeTable) {
for (VirtualTableEntry parentEntry : supertypeTable.entries.values()) {
VirtualTableEntry entry = new VirtualTableEntry(table, parentEntry.getMethod(),
parentEntry.getImplementor(), parentEntry.getIndex());
table.entries.put(entry.getMethod(), entry);
}
}
public VirtualTableEntry lookup(MethodReference method) { public VirtualTableEntry lookup(MethodReference method) {
VirtualTable vtable = virtualTables.get(interfaceMapping.mapClass(method.getClassName())); VirtualTable vtable = virtualTables.get(interfaceMapping.mapClass(method.getClassName()));
if (vtable == null) { if (vtable == null) {