Search in sources :

Example 1 with MarshalInfo

use of sharpen.xobotos.api.interop.marshal.MarshalInfo in project XobotOS by xamarin.

the class NativeMethodBuilder method resolve.

public boolean resolve(IMarshalContext context) {
    if (_resolveFailed)
        return false;
    if (_resolved)
        return true;
    _binding = _node.resolveBinding();
    ITypeBinding returnType = _binding.getReturnType();
    ITypeBinding[] paramTypes = _binding.getParameterTypes();
    _methodName = BindingUtils.qualifiedSignature(_binding);
    final Signature signature = getNativeMethod().getSignature();
    final Kind kind = _native.getKind();
    MarshalInfo returnInfo = null;
    if (isVoid(returnType) && (kind == Kind.CONSTRUCTOR)) {
        ReturnInfo info = signature.getReturnInfo();
        if ((info != null) && (info.marshal != null))
            returnInfo = info.marshal.resolve(null);
        if (returnInfo == null) {
            Sharpen.Log(Level.SEVERE, "Missing marshal info for return type of constructor '%s'", _methodName);
            _resolveFailed = true;
        }
    } else if (!isVoid(returnType) && !getNativeMethod().returnVoid()) {
        ReturnInfo info = signature.getReturnInfo();
        if (info != null) {
            if (info.marshal != null)
                returnInfo = info.marshal.resolve(returnType);
            else
                returnInfo = context.getMarshalInfo(returnType);
        } else {
            returnInfo = context.getMarshalInfo(returnType);
        }
        if (returnInfo == null) {
            Sharpen.Log(Level.SEVERE, "Missing marshal info for return type '%s' of method '%s'", BindingUtils.qualifiedName(returnType), _methodName);
            _resolveFailed = true;
        }
    }
    if (kind == Kind.CONSTRUCTOR) {
        if (returnInfo == null) {
            Sharpen.Log(Level.SEVERE, "Missing marshal info for return type '%s' of constructor '%s'", BindingUtils.qualifiedName(returnType), _methodName);
            _resolveFailed = true;
        } else if (!(returnInfo instanceof MarshalAsClass)) {
            Sharpen.Log(Level.SEVERE, "Return type '%s' of constructor '%s' must have MarshalAsClass marshal info", BindingUtils.qualifiedName(returnType), _methodName);
            _resolveFailed = true;
        }
    }
    if (kind == Kind.DESTRUCTOR) {
        if (_returnInfo != null) {
            Sharpen.Log(Level.SEVERE, "Destructor '%s' cannot return a value.", _methodName);
            _resolveFailed = true;
        } else if (paramTypes.length != 1) {
            Sharpen.Log(Level.SEVERE, "Destructor '%s' must take one single argument.", _methodName);
            _resolveFailed = true;
        } else if (_nativeHandle == null) {
            Sharpen.Log(Level.SEVERE, "Destructor '%s' must have a native handle", _methodName);
            _resolveFailed = true;
        }
    }
    if (_resolveFailed)
        return false;
    if (returnInfo != null) {
        if (!returnInfo.resolve(context, returnType)) {
            Sharpen.Log(Level.SEVERE, "Cannot resolve return value in '%s'.", _methodName);
            _resolveFailed = true;
        } else {
            _returnInfo = new ElementInfo(returnType, returnInfo, Mode.OUT, null);
        }
    }
    if (kind == Kind.DESTRUCTOR) {
        _paramInfo = new ElementInfo[1];
        if (_nativeHandle == null) {
            Sharpen.Log(Level.SEVERE, "Missing 'native-handle' for destructor '%s'.", _methodName);
            _resolveFailed = true;
        } else {
            MarshalInfo info = new MarshalAsClass(paramTypes[0], null, _nativeHandle.getTemplate());
            VariableDeclaration vdecl = (VariableDeclaration) _node.parameters().get(0);
            IVariableBinding vbinding = vdecl.resolveBinding();
            ITypeBinding vtype = vbinding.getType();
            if (!info.resolve(context, vtype)) {
                Sharpen.Log(Level.SEVERE, "Cannot resolve marshal info for destructor '%s'.", _methodName);
                _resolveFailed = true;
            } else {
                _paramInfo[0] = new ElementInfo(vtype, info, null, null);
            }
        }
    } else {
        _paramInfo = new ElementInfo[paramTypes.length];
        for (int i = 0; i < paramTypes.length; i++) {
            final ParameterInfo info = signature.getParameterInfo(i);
            if ((info == null) || (info.mode == Mode.REMOVE))
                continue;
            MarshalInfo marshal;
            if (info.marshal != null)
                marshal = info.marshal.resolve(paramTypes[i]);
            else
                marshal = context.getMarshalInfo(paramTypes[i]);
            if (marshal == null) {
                Sharpen.Log(Level.SEVERE, "Missing marshal info for type '%s' in method '%s'", BindingUtils.qualifiedName(paramTypes[i]), _methodName);
                _resolveFailed = true;
                continue;
            }
            VariableDeclaration vdecl = (VariableDeclaration) _node.parameters().get(i);
            IVariableBinding vbinding = vdecl.resolveBinding();
            ITypeBinding vtype = vbinding.getType();
            boolean isInstanceArg;
            if ((kind == Kind.INSTANCE) || (kind == Kind.PROXY))
                isInstanceArg = (i == 0) && !signature.implicitInstance();
            else
                isInstanceArg = false;
            if (isInstanceArg) {
                _paramInfo[0] = new ElementInfo(vtype, marshal, Mode.REF, null);
                if (!marshal.resolve(context, vtype)) {
                    Sharpen.Log(Level.SEVERE, "Cannot resolve instance parameter of method '%s'.", _methodName);
                    _resolveFailed = true;
                }
            } else {
                _paramInfo[i] = new ElementInfo(vtype, marshal, info.mode, info.flags);
                if (!marshal.resolve(context, vtype)) {
                    Sharpen.Log(Level.SEVERE, "Cannot resolve parameter %d of method '%s'.", i, _methodName);
                    _resolveFailed = true;
                }
            }
        }
    }
    if (signature.implicitInstance()) {
        if (_nativeHandle == null) {
            Sharpen.Log(Level.SEVERE, "Cannot use <add-instance> without <native-handle> in '%s'", _methodName);
            _resolveFailed = true;
            return false;
        }
        String fieldName = _nativeHandle.getTemplate().getField();
        _implicitInstance = findField(_binding, fieldName);
        if (_implicitInstance == null) {
            Sharpen.Log(Level.SEVERE, "No such field '%s' in type '%s'", fieldName, BindingUtils.qualifiedName(_binding.getDeclaringClass()));
            _resolveFailed = true;
            return false;
        }
    }
    if (_resolveFailed)
        return false;
    _resolved = true;
    return true;
}
Also used : MarshalAsClass(sharpen.xobotos.api.interop.marshal.MarshalAsClass) ParameterInfo(sharpen.xobotos.api.interop.Signature.ParameterInfo) IVariableBinding(org.eclipse.jdt.core.dom.IVariableBinding) MarshalInfo(sharpen.xobotos.api.interop.marshal.MarshalInfo) ITypeBinding(org.eclipse.jdt.core.dom.ITypeBinding) Kind(sharpen.xobotos.api.interop.NativeMethod.Kind) VariableDeclaration(org.eclipse.jdt.core.dom.VariableDeclaration) ReturnInfo(sharpen.xobotos.api.interop.Signature.ReturnInfo)

Example 2 with MarshalInfo

use of sharpen.xobotos.api.interop.marshal.MarshalInfo in project XobotOS by xamarin.

the class StructHelperClass method resolve.

@Override
public boolean resolve(IMarshalContext context) {
    if (BindingManager.DEBUG)
        Sharpen.Debug("RESOLVE STRUCT: %s", getName());
    if (_resolved)
        return !_resolveFailed;
    final List<MemberInfo> members = _template.getMembers();
    _fieldInfo = new ElementInfo[members.size()];
    for (int i = 0; i < members.size(); i++) {
        final MemberInfo member = members.get(i);
        IVariableBinding field = findField(getType(), member.getName());
        if (field == null) {
            Sharpen.Log(Level.SEVERE, "No such field '%s' in type '%s'", member.getName(), BindingUtils.qualifiedName(getType()));
            _resolveFailed = true;
            continue;
        }
        if (member.getValue() != null)
            continue;
        MarshalInfo marshal;
        if (member.getMarshalInfo() != null)
            marshal = member.getMarshalInfo().resolve(field.getType());
        else
            marshal = context.getMarshalInfo(field.getType());
        if (marshal == null) {
            Sharpen.Log(Level.SEVERE, "Missing marshal info for type '%s' of field '%s'", BindingUtils.qualifiedName(field.getType()), member.getName());
            _resolveFailed = true;
            continue;
        }
        _fieldInfo[i] = new ElementInfo(field.getType(), marshal, null, Flags.ELEMENT);
        if (BindingManager.DEBUG)
            Sharpen.Debug("STRUCT MEMBER: %s - %s", member.getName(), BindingUtils.qualifiedName(field.getType()));
        if (!marshal.resolve(context, field.getType())) {
            Sharpen.Log(Level.SEVERE, "Failed to resolve field '%s' in '%s'", member.getName(), BindingUtils.qualifiedName(getType()));
            _resolveFailed = true;
            continue;
        }
        if (!marshal.isPrimitiveType()) {
            Sharpen.Log(Level.SEVERE, "Field '%s' in '%s' is not a primitive type", member.getName(), BindingUtils.qualifiedName(getType()));
            _resolveFailed = true;
            continue;
        }
        if (BindingManager.DEBUG)
            Sharpen.Debug("STRUCT MEMBER DONE: %s - %s", member.getName(), BindingUtils.qualifiedName(field.getType()));
    }
    if (BindingManager.DEBUG)
        Sharpen.Debug("RESOLVE STRUCT DONE: %s%s", getName(), _resolveFailed ? " - ERROR" : "");
    _resolved = true;
    return true;
}
Also used : MemberInfo(sharpen.xobotos.api.interop.NativeStruct.MemberInfo) ElementInfo(sharpen.xobotos.api.interop.NativeMethodBuilder.ElementInfo) IVariableBinding(org.eclipse.jdt.core.dom.IVariableBinding) MarshalInfo(sharpen.xobotos.api.interop.marshal.MarshalInfo)

Aggregations

IVariableBinding (org.eclipse.jdt.core.dom.IVariableBinding)2 MarshalInfo (sharpen.xobotos.api.interop.marshal.MarshalInfo)2 ITypeBinding (org.eclipse.jdt.core.dom.ITypeBinding)1 VariableDeclaration (org.eclipse.jdt.core.dom.VariableDeclaration)1 Kind (sharpen.xobotos.api.interop.NativeMethod.Kind)1 ElementInfo (sharpen.xobotos.api.interop.NativeMethodBuilder.ElementInfo)1 MemberInfo (sharpen.xobotos.api.interop.NativeStruct.MemberInfo)1 ParameterInfo (sharpen.xobotos.api.interop.Signature.ParameterInfo)1 ReturnInfo (sharpen.xobotos.api.interop.Signature.ReturnInfo)1 MarshalAsClass (sharpen.xobotos.api.interop.marshal.MarshalAsClass)1