/* * Copyright (C) 2012 RoboVM AB * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License * as published by the Free Software Foundation; either version 2 * of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see <http://www.gnu.org/licenses/gpl-2.0.html>. */ package org.robovm.compiler; import static org.junit.Assert.*; import static org.robovm.compiler.Types.*; import static org.robovm.compiler.llvm.Type.*; import org.junit.Before; import org.junit.Test; import org.robovm.compiler.config.Arch; import org.robovm.compiler.config.OS; import org.robovm.compiler.llvm.FunctionType; import org.robovm.compiler.llvm.StructureType; import org.robovm.llvm.Context; import org.robovm.llvm.Module; import org.robovm.llvm.Target; import org.robovm.llvm.TargetMachine; import soot.Scene; import soot.SootClass; import soot.options.Options; /** * Tests {@link Types}. */ public class TypesTest { @Before public void initializeSoot() { soot.G.reset(); Options.v().set_output_format(Options.output_format_jimple); Options.v().set_include_all(true); Options.v().set_print_tags_in_output(true); Options.v().set_allow_phantom_refs(true); Options.v().set_soot_classpath(System.getProperty("sun.boot.class.path") + ":" + System.getProperty("java.class.path")); Scene.v().loadNecessaryClasses(); } private SootClass getSootClass(String name) { return Scene.v().loadClassAndSupport(name); } @Test public void testGetFunctionTypeFromDescriptor() { FunctionType type = null; type = getFunctionType("()V", true); assertEquals(VOID, type.getReturnType()); assertEquals(1, type.getParameterTypes().length); assertEquals(ENV_PTR, type.getParameterTypes()[0]); type = getFunctionType("()V", false); assertEquals(VOID, type.getReturnType()); assertEquals(2, type.getParameterTypes().length); assertEquals(ENV_PTR, type.getParameterTypes()[0]); assertEquals(OBJECT_PTR, type.getParameterTypes()[1]); type = getFunctionType("(Ljava/lang/Object;)Ljava/lang/String;", true); assertEquals(OBJECT_PTR, type.getReturnType()); assertEquals(2, type.getParameterTypes().length); assertEquals(ENV_PTR, type.getParameterTypes()[0]); assertEquals(OBJECT_PTR, type.getParameterTypes()[1]); type = getFunctionType("(Ljava/lang/Object;)Ljava/lang/String;", false); assertEquals(OBJECT_PTR, type.getReturnType()); assertEquals(3, type.getParameterTypes().length); assertEquals(ENV_PTR, type.getParameterTypes()[0]); assertEquals(OBJECT_PTR, type.getParameterTypes()[1]); assertEquals(OBJECT_PTR, type.getParameterTypes()[2]); } public static class A { byte A_c, A_b; Object A_a; } public static class B extends A { byte B_c; Object B_a; } public static class C extends B { byte C_a; } public static class D extends C { final long D_d = 0; Object D_a, D_b, D_c; } @Test public void testGetInstanceType() throws Exception { StructureType type = Types.getInstanceType(OS.ios, Arch.thumbv7, getSootClass(D.class.getName())); int size = getAllocSize(type, "thumbv7-unknown-ios"); assertEquals(48, size); } private int getAllocSize(StructureType type, String triple) { Context context = null; Module module = null; TargetMachine targetMachine = null; try { context = new Context(); module = Module.parseIR(context, "%Object = type {i8*, i8*}\n%DataObject = type {%Object}\n%t = type " + type, null); Target target = Target.lookupTarget(triple); targetMachine = target.createTargetMachine(triple); return (int) targetMachine.getDataLayout().getTypeAllocSize(module.getTypeByName("t")); } finally { if (module != null) { module.dispose(); } if (context != null) { context.dispose(); } if (targetMachine != null) { targetMachine.dispose(); } } } }