Search in sources :

Example 6 with ArrayType

use of org.robovm.compiler.llvm.ArrayType in project robovm by robovm.

the class BridgeMethodCompilerTest method testCreateBridgeCWrapperComplexNestedStructByValReturnAndParameter.

@Test
public void testCreateBridgeCWrapperComplexNestedStructByValReturnAndParameter() {
    StructureType structType = new StructureType(new StructureType(I8, I16), new StructureType(I32, I64), new StructureType(FLOAT, DOUBLE), new ArrayType(100, I32), new ArrayType(10, new StructureType(FLOAT, FLOAT)), new ArrayType(5, new ArrayType(10, I32)), new StructureType(I8_PTR, new PointerType(new StructureType(I32))));
    FunctionType functionType = new FunctionType(structType, structType);
    assertEquals("void f(void* target, void* ret, void* p0) {\n" + "    struct f_0001_0006 {void* m0;void* m1;};\n" + "    struct f_0001_0004 {float m0;float m1;};\n" + "    struct f_0001_0002 {float m0;double m1;};\n" + "    struct f_0001_0001 {int m0;long long m1;};\n" + "    struct f_0001_0000 {char m0;short m1;};\n" + "    struct f_0001 {struct f_0001_0000 m0;struct f_0001_0001 m1;struct f_0001_0002 m2;int m3[100];struct f_0001_0004 m4[10];int m5[5][10];struct f_0001_0006 m6;};\n" + "    struct f_0000_0006 {void* m0;void* m1;};\n" + "    struct f_0000_0004 {float m0;float m1;};\n" + "    struct f_0000_0002 {float m0;double m1;};\n" + "    struct f_0000_0001 {int m0;long long m1;};\n" + "    struct f_0000_0000 {char m0;short m1;};\n" + "    struct f_0000 {struct f_0000_0000 m0;struct f_0000_0001 m1;struct f_0000_0002 m2;int m3[100];struct f_0000_0004 m4[10];int m5[5][10];struct f_0000_0006 m6;};\n" + "    *((struct f_0000*)ret) = ((struct f_0000 (*)(struct f_0001)) target)(*((struct f_0001*)p0));\n" + "}\n", BridgeMethodCompiler.createBridgeCWrapper(functionType.getReturnType(), functionType.getParameterTypes(), functionType.getParameterTypes(), "f"));
}
Also used : ArrayType(org.robovm.compiler.llvm.ArrayType) StructureType(org.robovm.compiler.llvm.StructureType) FunctionType(org.robovm.compiler.llvm.FunctionType) PointerType(org.robovm.compiler.llvm.PointerType) Test(org.junit.Test)

Example 7 with ArrayType

use of org.robovm.compiler.llvm.ArrayType in project robovm by robovm.

the class BroMethodCompiler method mergeStructMemberTypes.

static Type mergeStructMemberTypes(DataLayout dataLayout, Type t1, Type t2) {
    int align1 = dataLayout.getAlignment(t1);
    int align2 = dataLayout.getAlignment(t2);
    int size1 = dataLayout.getStoreSize(t1);
    int size2 = dataLayout.getStoreSize(t2);
    Type result = align1 < align2 ? t2 : t1;
    int size = align1 < align2 ? size2 : size1;
    int pad = Math.max(size1, size2) - size;
    if (pad > 0) {
        return new StructureType(result, new ArrayType(pad, I8));
    } else {
        return result;
    }
}
Also used : ArrayType(org.robovm.compiler.llvm.ArrayType) RefType(soot.RefType) IntegerType(org.robovm.compiler.llvm.IntegerType) StructureType(org.robovm.compiler.llvm.StructureType) ArrayType(org.robovm.compiler.llvm.ArrayType) PointerType(org.robovm.compiler.llvm.PointerType) DoubleType(soot.DoubleType) FloatType(soot.FloatType) LongType(soot.LongType) Type(org.robovm.compiler.llvm.Type) AggregateType(org.robovm.compiler.llvm.AggregateType) PrimitiveType(org.robovm.compiler.llvm.PrimitiveType) PrimType(soot.PrimType) VoidType(soot.VoidType) FunctionType(org.robovm.compiler.llvm.FunctionType) StructureType(org.robovm.compiler.llvm.StructureType) Ptrtoint(org.robovm.compiler.llvm.Ptrtoint)

Example 8 with ArrayType

use of org.robovm.compiler.llvm.ArrayType in project robovm by robovm.

the class BroMethodCompiler method loadValueForGetter.

protected Value loadValueForGetter(SootMethod method, Function fn, Type memberType, Value memberPtr, Value env, boolean dereference, long flags) {
    soot.Type type = method.getReturnType();
    Value result = null;
    if (memberType instanceof StructureType) {
        // The member is a child struct contained in the current struct
        result = memberPtr;
    } else if (memberType instanceof ArrayType) {
        // The member is an array contained in the current struct
        result = memberPtr;
    } else if (dereference) {
        Variable tmp = fn.newVariable(memberType);
        fn.add(new Load(tmp, memberPtr));
        result = tmp.ref();
    } else {
        // Do not dereference the pointer but use it as is. This is needed for
        // global values such as _dispatch_main_q which is a struct and not a
        // pointer which we should load. We want the address of the struct.
        Variable tmp = fn.newVariable(memberType);
        fn.add(new Bitcast(tmp, memberPtr, tmp.getType()));
        result = tmp.ref();
    }
    if (needsMarshaler(type)) {
        MarshalerMethod marshalerMethod = config.getMarshalerLookup().findMarshalerMethod(new MarshalSite(method));
        String targetClassName = getInternalName(type);
        if (memberType instanceof PrimitiveType) {
            // Value type wrapping a primitive value (e.g. Enum, Integer and Bits)
            result = marshalNativeToValueObject(fn, marshalerMethod, env, targetClassName, result, flags);
        } else {
            if (memberType instanceof ArrayType) {
                // Array
                result = marshalNativeToArray(fn, marshalerMethod, env, targetClassName, result, flags, getArrayDimensions(method));
            } else {
                result = marshalNativeToObject(fn, marshalerMethod, null, env, targetClassName, result, flags);
            }
        }
    } else {
        result = marshalNativeToPrimitive(fn, method, result);
    }
    return result;
}
Also used : ArrayType(org.robovm.compiler.llvm.ArrayType) MarshalSite(org.robovm.compiler.MarshalerLookup.MarshalSite) Load(org.robovm.compiler.llvm.Load) Variable(org.robovm.compiler.llvm.Variable) Bitcast(org.robovm.compiler.llvm.Bitcast) ConstantBitcast(org.robovm.compiler.llvm.ConstantBitcast) StructureType(org.robovm.compiler.llvm.StructureType) Value(org.robovm.compiler.llvm.Value) PrimitiveType(org.robovm.compiler.llvm.PrimitiveType) MarshalerMethod(org.robovm.compiler.MarshalerLookup.MarshalerMethod) ValueMarshalerMethod(org.robovm.compiler.MarshalerLookup.ValueMarshalerMethod) ArrayMarshalerMethod(org.robovm.compiler.MarshalerLookup.ArrayMarshalerMethod)

Example 9 with ArrayType

use of org.robovm.compiler.llvm.ArrayType in project robovm by robovm.

the class BroMethodCompiler method getStructMemberType.

public Type getStructMemberType(SootMethod method) {
    String methodType = hasStructMemberAnnotation(method) ? "@StructMember" : "@GlobalValue";
    SootMethod getter = method.getParameterCount() == 0 ? method : null;
    SootMethod setter = getter == null ? method : null;
    soot.Type type = getter != null ? getter.getReturnType() : setter.getParameterType(0);
    Type memberType = null;
    if (getter != null && hasPointerAnnotation(getter) || setter != null && hasPointerAnnotation(setter, 0)) {
        memberType = I8_PTR;
    } else if (getter != null && hasMachineSizedFloatAnnotation(getter) || setter != null && hasMachineSizedFloatAnnotation(setter, 0)) {
        memberType = config.getArch().is32Bit() ? FLOAT : DOUBLE;
    } else if (getter != null && (hasMachineSizedSIntAnnotation(getter) || hasMachineSizedUIntAnnotation(getter)) || setter != null && (hasMachineSizedSIntAnnotation(setter, 0) || hasMachineSizedUIntAnnotation(setter, 0))) {
        memberType = config.getArch().is32Bit() ? I32 : I64;
    } else if (type instanceof PrimType) {
        memberType = getType(type);
    } else if (getter != null && hasArrayAnnotation(getter) || setter != null && hasArrayAnnotation(setter, 0)) {
        int[] dimensions = getter != null ? getArrayDimensions(getter) : getArrayDimensions(setter, 0);
        if (dimensions == null || dimensions.length == 0) {
            throw new IllegalArgumentException("No dimensions specified for @Array annotation on " + methodType + " " + (getter != null ? "getter" : "setter") + " " + method);
        }
        if (type instanceof soot.ArrayType && ((soot.ArrayType) type).numDimensions != dimensions.length) {
            throw new IllegalArgumentException("Mismatch in number of dimennsions for @Array annotation " + "and type on " + methodType + " " + (getter != null ? "getter" : "setter") + " " + method);
        }
        Type baseType = null;
        if (type instanceof soot.ArrayType) {
            soot.ArrayType arrayType = (soot.ArrayType) type;
            if (isStruct(arrayType.baseType)) {
                // ByVal is implied for arrays of structs
                try {
                    baseType = getStructType(arrayType.baseType);
                } catch (StackOverflowError e) {
                    throw new IllegalArgumentException("Struct type " + type + " refers to itself");
                }
            } else {
                baseType = getType(arrayType.baseType);
            }
        } else if (isStruct(type)) {
            // ByVal is implied
            try {
                baseType = getStructType(type);
            } catch (StackOverflowError e) {
                throw new IllegalArgumentException("Struct type " + type + " refers to itself");
            }
        } else if (type instanceof RefType) {
            MarshalerMethod marshalerMethod = config.getMarshalerLookup().findMarshalerMethod(getter != null ? new MarshalSite(getter) : new MarshalSite(setter, 0));
            baseType = getType(((ArrayMarshalerMethod) marshalerMethod).getBaseType());
        }
        if (baseType == null) {
            throw new IllegalArgumentException("Arrays of " + type + " is not supported");
        }
        long total = dimensions[0];
        for (int i = 1; i < dimensions.length; i++) {
            total *= dimensions[i];
        }
        memberType = new ArrayType(total, baseType);
    } else if (isStruct(type)) {
        boolean byVal = getter != null ? isPassByValue(getter) : isPassByValue(setter, 0);
        if (!byVal) {
            // NOTE: We use i8* instead of <StructType>* to support pointers to recursive structs
            memberType = I8_PTR;
        } else {
            try {
                memberType = getStructType(type);
            } catch (StackOverflowError e) {
                throw new IllegalArgumentException("Struct type " + type + " refers to itself");
            }
        }
    } else if (isNativeObject(type)) {
        memberType = I8_PTR;
    } else {
        MarshalerMethod marshalerMethod = config.getMarshalerLookup().findMarshalerMethod(getter != null ? new MarshalSite(getter) : new MarshalSite(setter, 0));
        if (marshalerMethod instanceof ValueMarshalerMethod) {
            memberType = ((ValueMarshalerMethod) marshalerMethod).getNativeType(config.getArch());
        } else {
            memberType = I8_PTR;
        }
    }
    return memberType;
}
Also used : MarshalSite(org.robovm.compiler.MarshalerLookup.MarshalSite) ValueMarshalerMethod(org.robovm.compiler.MarshalerLookup.ValueMarshalerMethod) Ptrtoint(org.robovm.compiler.llvm.Ptrtoint) ArrayType(org.robovm.compiler.llvm.ArrayType) RefType(soot.RefType) RefType(soot.RefType) IntegerType(org.robovm.compiler.llvm.IntegerType) StructureType(org.robovm.compiler.llvm.StructureType) ArrayType(org.robovm.compiler.llvm.ArrayType) PointerType(org.robovm.compiler.llvm.PointerType) DoubleType(soot.DoubleType) FloatType(soot.FloatType) LongType(soot.LongType) Type(org.robovm.compiler.llvm.Type) AggregateType(org.robovm.compiler.llvm.AggregateType) PrimitiveType(org.robovm.compiler.llvm.PrimitiveType) PrimType(soot.PrimType) VoidType(soot.VoidType) FunctionType(org.robovm.compiler.llvm.FunctionType) SootMethod(soot.SootMethod) PrimType(soot.PrimType) MarshalerMethod(org.robovm.compiler.MarshalerLookup.MarshalerMethod) ValueMarshalerMethod(org.robovm.compiler.MarshalerLookup.ValueMarshalerMethod) ArrayMarshalerMethod(org.robovm.compiler.MarshalerLookup.ArrayMarshalerMethod) ArrayMarshalerMethod(org.robovm.compiler.MarshalerLookup.ArrayMarshalerMethod)

Example 10 with ArrayType

use of org.robovm.compiler.llvm.ArrayType in project robovm by robovm.

the class BroMethodCompiler method storeValueForSetter.

protected void storeValueForSetter(SootMethod method, Function function, Type memberType, Value memberPtr, Value env, Value value, long flags) {
    soot.Type type = method.getParameterType(0);
    if (needsMarshaler(type)) {
        MarshalerMethod marshalerMethod = config.getMarshalerLookup().findMarshalerMethod(new MarshalSite(method, 0));
        if (memberType instanceof PrimitiveType) {
            value = marshalValueObjectToNative(function, marshalerMethod, memberType, env, value, flags);
        } else {
            if (memberType instanceof StructureType || memberType instanceof ArrayType) {
                // The parameter must not be null. We assume that Structs 
                // never have a NULL handle so we just check that the Java
                // Object isn't null.
                call(function, CHECK_NULL, env, value);
            }
            if (memberType instanceof ArrayType) {
                // Array
                marshalArrayToNative(function, marshalerMethod, env, value, memberPtr, flags, getArrayDimensions(method, 0));
                value = null;
            } else {
                value = marshalObjectToNative(function, marshalerMethod, null, memberType, env, value, flags);
            }
        }
    } else {
        value = marshalPrimitiveToNative(function, method, 0, value);
    }
    if (value != null) {
        function.add(new Store(value, memberPtr));
    }
}
Also used : MarshalSite(org.robovm.compiler.MarshalerLookup.MarshalSite) ArrayType(org.robovm.compiler.llvm.ArrayType) StructureType(org.robovm.compiler.llvm.StructureType) Store(org.robovm.compiler.llvm.Store) PrimitiveType(org.robovm.compiler.llvm.PrimitiveType) MarshalerMethod(org.robovm.compiler.MarshalerLookup.MarshalerMethod) ValueMarshalerMethod(org.robovm.compiler.MarshalerLookup.ValueMarshalerMethod) ArrayMarshalerMethod(org.robovm.compiler.MarshalerLookup.ArrayMarshalerMethod)

Aggregations

ArrayType (org.robovm.compiler.llvm.ArrayType)10 StructureType (org.robovm.compiler.llvm.StructureType)8 PointerType (org.robovm.compiler.llvm.PointerType)7 FunctionType (org.robovm.compiler.llvm.FunctionType)6 PrimitiveType (org.robovm.compiler.llvm.PrimitiveType)5 Type (org.robovm.compiler.llvm.Type)5 IntegerType (org.robovm.compiler.llvm.IntegerType)4 Value (org.robovm.compiler.llvm.Value)4 PrimType (soot.PrimType)4 ArrayMarshalerMethod (org.robovm.compiler.MarshalerLookup.ArrayMarshalerMethod)3 MarshalSite (org.robovm.compiler.MarshalerLookup.MarshalSite)3 MarshalerMethod (org.robovm.compiler.MarshalerLookup.MarshalerMethod)3 ValueMarshalerMethod (org.robovm.compiler.MarshalerLookup.ValueMarshalerMethod)3 AggregateType (org.robovm.compiler.llvm.AggregateType)3 IntegerConstant (org.robovm.compiler.llvm.IntegerConstant)3 Ptrtoint (org.robovm.compiler.llvm.Ptrtoint)3 Variable (org.robovm.compiler.llvm.Variable)3 ArrayList (java.util.ArrayList)2 Test (org.junit.Test)2 Bitcast (org.robovm.compiler.llvm.Bitcast)2