private boolean hasClassesToExpose() { for (String className : classSource.getClassNames()) { ClassReader cls = classSource.get(className); if (cls.getMethods().stream().anyMatch(method -> getPublicAlias(method) != null)) { return true; } } return false; }
private void collectMethodsToCopyFromInterfaces(ClassReader cls, List<MethodReference> targetList) { Set<MethodDescriptor> implementedMethods = new HashSet<>(); implementedMethods.addAll(targetList.stream().map(method -> method.getDescriptor()) .collect(Collectors.toList())); Set<String> visitedClasses = new HashSet<>(); for (String ifaceName : cls.getInterfaces()) { ClassReader iface = classSource.get(ifaceName); if (iface != null) { collectMethodsToCopyFromInterfacesImpl(iface, targetList, implementedMethods, visitedClasses); } } }
public VirtualTableProvider(ListableClassReaderSource classSource, Set<MethodReference> virtualMethods) { this.classSource = classSource; interfaceMapping = new InterfaceToClassMapping(classSource); Set<String> classNames = new HashSet<>(classSource.getClassNames()); for (MethodReference virtualMethod : virtualMethods) { String cls = interfaceMapping.mapClass(virtualMethod.getClassName()); if (cls == null) { cls = virtualMethod.getClassName(); } classNames.add(cls); virtualMethodMap.computeIfAbsent(cls, c -> new LinkedHashSet<>()).add(virtualMethod.getDescriptor()); } for (String className : classNames) { fillClass(className); } }
@Override public boolean isApplicable(MethodReference methodReference) { MethodReader method = classSource.resolve(methodReference); if (method == null) { return false; } return method.getAnnotations().get(MetadataProvider.class.getName()) != null; }
private void addOverriddenToFamily(MethodReference methodRef) { asyncFamilyMethods.put(methodRef, true); ClassReader cls = classSource.get(methodRef.getClassName()); if (cls == null) { return; } for (MethodReference overriddenMethod : findOverriddenMethods(cls, methodRef.getDescriptor())) { addOverriddenToFamily(overriddenMethod); } }
private void generateLookup(GeneratorContext context, SourceWriter writer) throws IOException { String param = context.getParameterName(1); writer.append("switch ($rt_ustr(" + param + ")) {").softNewLine().indent(); for (String name : context.getClassSource().getClassNames()) { writer.append("case \"" + name + "\": ").appendClass(name).append(".$clinit(); ") .append("return ").appendClass(name).append(";").softNewLine(); } writer.append("default: return null;").softNewLine(); writer.outdent().append("}").softNewLine(); }
@Override public WasmExpression apply(InvocationExpr invocation, WasmIntrinsicManager manager) { MethodReader method = classSource.resolve(invocation.getMethod()); MetadataGenerator generator = MetadataUtils.createMetadataGenerator(classLoader, method, new CallLocation(invocation.getMethod()), manager.getDiagnostics()); if (generator == null) { return new WasmInt32Constant(0); } DefaultMetadataGeneratorContext metadataContext = new DefaultMetadataGeneratorContext(classSource, classLoader, properties, services); Resource resource = generator.generateMetadata(metadataContext, invocation.getMethod()); int address = writeValue(manager.getBinaryWriter(), manager.getStringPool(), resource); return new WasmInt32Constant(address); }
public InterfaceToClassMapping(ListableClassReaderSource classSource) { for (String className : classSource.getClassNames()) { ClassReader cls = classSource.get(className); if (cls.hasModifier(ElementModifier.INTERFACE)) { continue; } map.put(className, className); for (String iface : getInterfaces(classSource, className)) { String existing = map.get(iface); if (existing == null) { map.put(iface, className); } else { map.put(iface, commonSuperClass(classSource, className, existing)); } } } }
private boolean addToFamilyCacheMiss(MethodReference methodRef) { if (asyncMethods.contains(methodRef)) { return true; } ClassReader cls = classSource.get(methodRef.getClassName()); if (cls == null) { return false; } for (MethodReference overriddenMethod : findOverriddenMethods(cls, methodRef.getDescriptor())) { if (addToFamily(overriddenMethod)) { return true; } } return false; }
if (context.getClassSource().getClassNames().contains(implName)) { writer.append("[").appendClass(implName).append(", ").appendMethodBody( new MethodReference(implName, new MethodDescriptor("<init>", ValueType.VOID)))
private void printStats() { if (vm == null || vm.getWrittenClasses() == null) { return; } int classCount = vm.getWrittenClasses().getClassNames().size(); int methodCount = 0; for (String className : vm.getWrittenClasses().getClassNames()) { ClassReader cls = vm.getWrittenClasses().get(className); methodCount += cls.getMethods().size(); } log.info("Classes compiled: " + classCount); log.info("Methods compiled: " + methodCount); }
private void collectMethodsToCopyFromInterfacesImpl(ClassReader cls, List<MethodReference> targetList, Set<MethodDescriptor> visited, Set<String> visitedClasses) { if (!visitedClasses.add(cls.getName())) { return; } for (MethodReader method : cls.getMethods()) { if (!method.hasModifier(ElementModifier.STATIC) && !method.hasModifier(ElementModifier.ABSTRACT)) { if (visited.add(method.getDescriptor())) { targetList.add(method.getReference()); } } } for (String ifaceName : cls.getInterfaces()) { ClassReader iface = classSource.get(ifaceName); if (iface != null) { collectMethodsToCopyFromInterfacesImpl(iface, targetList, visited, visitedClasses); } } }
public VirtualTableProvider(ListableClassReaderSource classSource, Set<MethodReference> virtualMethods) { this.classSource = classSource; interfaceMapping = new InterfaceToClassMapping(classSource); Set<String> classNames = new HashSet<>(classSource.getClassNames()); for (MethodReference virtualMethod : virtualMethods) { String cls = interfaceMapping.mapClass(virtualMethod.getClassName()); if (cls == null) { cls = virtualMethod.getClassName(); } classNames.add(cls); virtualMethodMap.computeIfAbsent(cls, c -> new HashSet<>()).add(virtualMethod.getDescriptor()); } for (String className : classNames) { fillClass(className); } }
private void printStats(TeaVM vm, long startTime) { if (vm.getWrittenClasses() != null) { int classCount = vm.getWrittenClasses().getClassNames().size(); int methodCount = 0; for (String className : vm.getWrittenClasses().getClassNames()) { ClassReader cls = vm.getWrittenClasses().get(className); methodCount += cls.getMethods().size(); } log.info("Classes compiled: " + classCount); log.info("Methods compiled: " + methodCount); } log.info("Compilation took " + (System.currentTimeMillis() - startTime) + " ms"); }
private void findOverriddenMethods(String className, MethodDescriptor methodDesc, Set<MethodReference> result, Set<String> visited) { if (!visited.add(className)) { return; } if (methodDesc.getName().equals("<init>") || methodDesc.getName().equals("<clinit>")) { return; } ClassReader cls = classSource.get(className); if (cls == null) { return; } MethodReader method = cls.getMethod(methodDesc); if (method != null) { if (!method.hasModifier(ElementModifier.STATIC) && !method.hasModifier(ElementModifier.FINAL)) { result.add(method.getReference()); } } else { if (cls.getParent() != null) { findOverriddenMethods(cls.getParent(), methodDesc, result, visited); } for (String iface : cls.getInterfaces()) { findOverriddenMethods(iface, methodDesc, result, visited); } } }
private void generateLookup(GeneratorContext context, SourceWriter writer) throws IOException { String param = context.getParameterName(1); writer.append("switch ($rt_ustr(" + param + ")) {").softNewLine().indent(); for (String name : context.getClassSource().getClassNames()) { writer.append("case \"" + name + "\": ").appendClass(name).append(".$clinit(); ") .append("return ").appendClass(name).append(";").softNewLine(); } writer.append("default: return null;").softNewLine(); writer.outdent().append("}").softNewLine(); }
private boolean hasAsyncMethods() { boolean result = false; loop: for (String clsName : classSource.getClassNames()) { ClassReader cls = classSource.get(clsName); for (MethodReader method : cls.getMethods()) { if (!asyncMethods.contains(method.getReference()) || method.getProgram() == null) { continue; } if (hasMonitor(method)) { result = true; break loop; } } } ClassReader cls = classSource.get("java.lang.Thread"); MethodReader method = cls != null ? cls.getMethod(new MethodDescriptor("start", void.class)) : null; return result && method != null; }
private void generateSet(GeneratorContext context, SourceWriter writer) throws IOException { String array = context.getParameterName(1); String item = context.getParameterName(3); writer.append("var type = " + array + ".constructor.$meta.item;").softNewLine(); boolean first = true; for (int i = 0; i < primitives.length; ++i) { String wrapper = "java.lang." + primitiveWrappers[i]; MethodReference methodRef = new MethodReference(wrapper, primitives[i].toLowerCase() + "Value", primitiveTypes[i]); ClassReader cls = context.getClassSource().get(methodRef.getClassName()); if (cls == null || cls.getMethod(methodRef.getDescriptor()) == null) { continue; } if (!first) { writer.append(" else "); } first = false; writer.append("if (type === $rt_" + primitives[i].toLowerCase() + "cls()) {").indent().softNewLine(); writer.append(item + " = ").appendMethodBody(methodRef).append("(" + item + ");").softNewLine(); writer.outdent().append("}"); } writer.softNewLine(); writer.append(array + ".data[" + context.getParameterName(2) + "] = " + item + ";").softNewLine(); }
private List<String> sortClassNames(ListableClassReaderSource classes) { List<String> classNames = new ArrayList<>(classes.getClassNames().size()); Deque<String> stack = new ArrayDeque<>(classes.getClassNames()); ObjectByteMap<String> stateMap = new ObjectByteHashMap<>(); while (!stack.isEmpty()) { String className = stack.pop(); byte state = stateMap.getOrDefault(className, (byte) 0); switch (state) { case 0: { stateMap.put(className, (byte) 1); stack.push(className); ClassReader cls = classes.get(className); String parent = cls != null ? cls.getParent() : null; if (parent == null) { parent = RuntimeObject.class.getName(); } if (!parent.equals(Structure.class.getName()) && stateMap.getOrDefault(cls.getParent(), (byte) 0) == 0) { stack.push(parent); } break; } case 1: stateMap.put(className, (byte) 2); classNames.add(className); break; } } return classNames; }
public Injector getInjector(MethodReference ref) { InjectorHolder holder = injectorMap.get(ref); if (holder == null) { holder = new InjectorHolder(null); if (!isBootstrap()) { ClassReader cls = classSource.get(ref.getClassName()); if (cls != null) { MethodReader method = cls.getMethod(ref.getDescriptor()); if (method != null) { AnnotationReader injectedByAnnot = method.getAnnotations().get(InjectedBy.class.getName()); if (injectedByAnnot != null) { ValueType type = injectedByAnnot.getValue("value").getJavaClass(); holder = new InjectorHolder(instantiateInjector(((ValueType.Object) type).getClassName())); } } } } injectorMap.put(ref, holder); } return holder.injector; }