Search in sources :

Example 1 with TypeConformanceComputationArgument

use of org.eclipse.xtext.xbase.typesystem.conformance.TypeConformanceComputationArgument in project xtext-xtend by eclipse.

the class DispatchMethodCompileStrategy method apply.

@Override
public void apply(/* @Nullable */
ITreeAppendable a) {
    if (a == null)
        throw new IllegalArgumentException("a is never null");
    boolean needsElse = true;
    int parameterCount = dispatchOperation.getParameters().size();
    List<JvmOperation> sortedDispatchOperations = sorter.getAllDispatchCases(dispatchOperation);
    boolean[] allCasesSameType = new boolean[parameterCount];
    for (int i = 0; i < parameterCount; i++) {
        allCasesSameType[i] = true;
        JvmTypeReference dispatchParameterType = dispatchOperation.getParameters().get(i).getParameterType();
        for (JvmOperation operation : sortedDispatchOperations) {
            JvmFormalParameter parameter = operation.getParameters().get(i);
            JvmTypeReference caseParameterType = parameter.getParameterType();
            if (!Strings.equal(dispatchParameterType.getIdentifier(), caseParameterType.getIdentifier())) {
                allCasesSameType[i] = false;
                break;
            }
        }
    }
    ITypeReferenceOwner owner = new StandardTypeReferenceOwner(services, dispatchOperation);
    for (JvmOperation operation : sortedDispatchOperations) {
        ITreeAppendable operationAppendable = treeAppendableUtil.traceSignificant(a, operation, true);
        final List<Later> laters = newArrayList();
        for (int i = 0; i < parameterCount; i++) {
            final JvmFormalParameter dispatchParam = dispatchOperation.getParameters().get(i);
            final LightweightTypeReference dispatchParamType = owner.toLightweightTypeReference(dispatchParam.getParameterType());
            final JvmFormalParameter caseParam = operation.getParameters().get(i);
            final LightweightTypeReference caseParamType = owner.toLightweightTypeReference(caseParam.getParameterType());
            final String name = getVarName(dispatchParam, operationAppendable);
            if (caseParamType.isType(Void.class)) {
                laters.add(new Later() {

                    @Override
                    public void exec(ITreeAppendable appendable) {
                        appendable.append(name).append(" == null");
                    }
                });
            } else if (!allCasesSameType[i]) {
                laters.add(new Later() {

                    @Override
                    public void exec(ITreeAppendable appendable) {
                        if (caseParamType.isAssignableFrom(dispatchParamType, new TypeConformanceComputationArgument(true, false, true, true, false, false)) && !dispatchParamType.isPrimitive()) {
                            appendable.append(name).append(" != null");
                        } else {
                            appendable.append(name).append(" instanceof ");
                            JvmType type = caseParamType.getWrapperTypeIfPrimitive().getType();
                            if (type == null) {
                                throw new IllegalStateException(String.valueOf(caseParamType));
                            }
                            appendable.append(type);
                        }
                    }
                });
            }
        }
        // if it's not the first if append an 'else'
        if (sortedDispatchOperations.get(0) != operation) {
            operationAppendable.append(" else ");
        }
        if (laters.isEmpty()) {
            needsElse = false;
            if (sortedDispatchOperations.size() != 1) {
                operationAppendable.append("{").increaseIndentation();
                operationAppendable.newLine();
            }
        } else {
            operationAppendable.append("if (");
            operationAppendable.increaseIndentation().increaseIndentation();
            Iterator<Later> iterator = laters.iterator();
            while (iterator.hasNext()) {
                iterator.next().exec(operationAppendable);
                if (iterator.hasNext()) {
                    operationAppendable.newLine().append(" && ");
                }
            }
            operationAppendable.decreaseIndentation().decreaseIndentation();
            operationAppendable.append(") {").increaseIndentation();
            operationAppendable.newLine();
        }
        final boolean isCurrentVoid = typeReferences.is(operation.getReturnType(), Void.TYPE);
        final boolean isDispatchVoid = typeReferences.is(dispatchOperation.getReturnType(), Void.TYPE);
        if (isDispatchVoid) {
            generateActualDispatchCall(dispatchOperation, operation, operationAppendable, owner);
            // we generate a redundant return statement here to get a better debugging experience
            operationAppendable.append(";").newLine().append("return;");
        } else {
            if (isCurrentVoid) {
                generateActualDispatchCall(dispatchOperation, operation, operationAppendable, owner);
                operationAppendable.append(";").newLine().append("return null");
            } else {
                operationAppendable.append("return ");
                generateActualDispatchCall(dispatchOperation, operation, operationAppendable, owner);
            }
            operationAppendable.append(";");
        }
        if (sortedDispatchOperations.size() != 1) {
            operationAppendable.decreaseIndentation();
            a.newLine().append("}");
        }
    }
    if (needsElse) {
        a.append(" else {").increaseIndentation();
        a.newLine();
        a.increaseIndentation();
        a.append("throw new IllegalArgumentException(\"Unhandled parameter types: \" +").newLine();
        JvmType jvmType = typeReferences.findDeclaredType("java.util.Arrays", dispatchOperation);
        if (jvmType != null) {
            a.append(jvmType);
        } else {
            a.append(Arrays.class.getSimpleName());
        }
        a.append(".<Object>asList(");
        Iterator<JvmFormalParameter> iterator = dispatchOperation.getParameters().iterator();
        while (iterator.hasNext()) {
            JvmFormalParameter parameter = iterator.next();
            final String name = getVarName(parameter, a);
            a.append(name);
            if (iterator.hasNext()) {
                a.append(", ");
            }
        }
        a.append(").toString());");
        a.decreaseIndentation();
        a.decreaseIndentation().newLine().append("}");
    }
}
Also used : LightweightTypeReference(org.eclipse.xtext.xbase.typesystem.references.LightweightTypeReference) TypeConformanceComputationArgument(org.eclipse.xtext.xbase.typesystem.conformance.TypeConformanceComputationArgument) JvmType(org.eclipse.xtext.common.types.JvmType) ITypeReferenceOwner(org.eclipse.xtext.xbase.typesystem.references.ITypeReferenceOwner) ITreeAppendable(org.eclipse.xtext.xbase.compiler.output.ITreeAppendable) JvmOperation(org.eclipse.xtext.common.types.JvmOperation) Later(org.eclipse.xtext.xbase.compiler.Later) JvmFormalParameter(org.eclipse.xtext.common.types.JvmFormalParameter) JvmTypeReference(org.eclipse.xtext.common.types.JvmTypeReference) Arrays(java.util.Arrays) StandardTypeReferenceOwner(org.eclipse.xtext.xbase.typesystem.references.StandardTypeReferenceOwner)

Example 2 with TypeConformanceComputationArgument

use of org.eclipse.xtext.xbase.typesystem.conformance.TypeConformanceComputationArgument in project xtext-xtend by eclipse.

the class RawAssignabilityTest method doIsAssignable.

@Override
public boolean doIsAssignable(final LightweightTypeReference lhs, final LightweightTypeReference rhs) {
    TypeConformanceComputationArgument _typeConformanceComputationArgument = new TypeConformanceComputationArgument(true, false, true, true, false, true);
    final int result = lhs.internalIsAssignableFrom(rhs, _typeConformanceComputationArgument);
    Assert.assertTrue(((result & ConformanceFlags.RAW_TYPE) != 0));
    return ((result & ConformanceFlags.SUCCESS) != 0);
}
Also used : TypeConformanceComputationArgument(org.eclipse.xtext.xbase.typesystem.conformance.TypeConformanceComputationArgument)

Example 3 with TypeConformanceComputationArgument

use of org.eclipse.xtext.xbase.typesystem.conformance.TypeConformanceComputationArgument in project dsl-devkit by dsldevkit.

the class CheckJavaValidator method checkFormalParameterTypeConformance.

/**
 * Checks that type of a default expression of a formal parameter actually matches the declared type.
 *
 * @param parameter
 *          to check
 */
@Check
public void checkFormalParameterTypeConformance(final FormalParameter parameter) {
    JvmTypeReference jvmType = parameter.getType();
    XExpression value = parameter.getRight();
    if (jvmType == null || value == null) {
        return;
    }
    LightweightTypeReference declaredType = toLightweightTypeReference(jvmType);
    LightweightTypeReference valueType = getActualType(value);
    if (!declaredType.isAssignableFrom(valueType, new TypeConformanceComputationArgument())) {
        error(Messages.CheckJavaValidator_FormalParameterType_Incompatibility, value, null, IssueCodes.FORMAL_PARAMETER_TYPE);
    }
}
Also used : LightweightTypeReference(org.eclipse.xtext.xbase.typesystem.references.LightweightTypeReference) JvmTypeReference(org.eclipse.xtext.common.types.JvmTypeReference) XExpression(org.eclipse.xtext.xbase.XExpression) TypeConformanceComputationArgument(org.eclipse.xtext.xbase.typesystem.conformance.TypeConformanceComputationArgument) Check(org.eclipse.xtext.validation.Check)

Example 4 with TypeConformanceComputationArgument

use of org.eclipse.xtext.xbase.typesystem.conformance.TypeConformanceComputationArgument in project xtext-xtend by eclipse.

the class DispatchMethodCompileStrategy method generateActualDispatchCall.

protected void generateActualDispatchCall(JvmOperation dispatchOperation, JvmOperation actualOperationToCall, ITreeAppendable a, ITypeReferenceOwner owner) {
    a.append(actualOperationToCall.getSimpleName()).append("(");
    Iterator<JvmFormalParameter> iter1 = dispatchOperation.getParameters().iterator();
    for (Iterator<JvmFormalParameter> iter2 = actualOperationToCall.getParameters().iterator(); iter2.hasNext(); ) {
        JvmFormalParameter p1 = iter1.next();
        JvmFormalParameter p2 = iter2.next();
        LightweightTypeReference type1 = owner.toLightweightTypeReference(p1.getParameterType());
        LightweightTypeReference type2 = owner.toLightweightTypeReference(p2.getParameterType());
        if (!type2.isAssignableFrom(type1, new TypeConformanceComputationArgument(true, false, true, true, false, false))) {
            a.append("(").append(type2.getWrapperTypeIfPrimitive()).append(")");
        }
        if (typeReferences.is(p2.getParameterType(), Void.class)) {
            a.append("null");
        } else {
            a.append(getVarName(p1, a));
        }
        if (iter2.hasNext()) {
            a.append(", ");
        }
    }
    a.append(")");
}
Also used : LightweightTypeReference(org.eclipse.xtext.xbase.typesystem.references.LightweightTypeReference) JvmFormalParameter(org.eclipse.xtext.common.types.JvmFormalParameter) TypeConformanceComputationArgument(org.eclipse.xtext.xbase.typesystem.conformance.TypeConformanceComputationArgument)

Example 5 with TypeConformanceComputationArgument

use of org.eclipse.xtext.xbase.typesystem.conformance.TypeConformanceComputationArgument in project xtext-xtend by eclipse.

the class AssignabilityTest method doIsAssignable.

@Override
public boolean doIsAssignable(final LightweightTypeReference lhs, final LightweightTypeReference rhs) {
    TypeConformanceComputationArgument _typeConformanceComputationArgument = new TypeConformanceComputationArgument(false, false, true, true, false, true);
    final int result = lhs.internalIsAssignableFrom(rhs, _typeConformanceComputationArgument);
    Assert.assertTrue(((result & ConformanceFlags.RAW_TYPE) == 0));
    return ((result & ConformanceFlags.SUCCESS) != 0);
}
Also used : TypeConformanceComputationArgument(org.eclipse.xtext.xbase.typesystem.conformance.TypeConformanceComputationArgument)

Aggregations

TypeConformanceComputationArgument (org.eclipse.xtext.xbase.typesystem.conformance.TypeConformanceComputationArgument)6 LightweightTypeReference (org.eclipse.xtext.xbase.typesystem.references.LightweightTypeReference)3 JvmFormalParameter (org.eclipse.xtext.common.types.JvmFormalParameter)2 JvmTypeReference (org.eclipse.xtext.common.types.JvmTypeReference)2 Arrays (java.util.Arrays)1 JvmOperation (org.eclipse.xtext.common.types.JvmOperation)1 JvmType (org.eclipse.xtext.common.types.JvmType)1 Check (org.eclipse.xtext.validation.Check)1 XExpression (org.eclipse.xtext.xbase.XExpression)1 Later (org.eclipse.xtext.xbase.compiler.Later)1 ITreeAppendable (org.eclipse.xtext.xbase.compiler.output.ITreeAppendable)1 ITypeReferenceOwner (org.eclipse.xtext.xbase.typesystem.references.ITypeReferenceOwner)1 StandardTypeReferenceOwner (org.eclipse.xtext.xbase.typesystem.references.StandardTypeReferenceOwner)1