Example usage for org.eclipse.jdt.internal.compiler.lookup TypeBinding dimensions

List of usage examples for org.eclipse.jdt.internal.compiler.lookup TypeBinding dimensions

Introduction

In this page you can find the example usage for org.eclipse.jdt.internal.compiler.lookup TypeBinding dimensions.

Prototype

public int dimensions() 

Source Link

Usage

From source file:lombok.eclipse.agent.PatchDelegate.java

License:Open Source License

private static String typeBindingToSignature(TypeBinding binding) {
    binding = binding.erasure();// ww  w  . j ava 2  s.  co  m
    if (binding != null && binding.isBaseType()) {
        return new String(binding.sourceName());
    } else if (binding instanceof ReferenceBinding) {
        String pkg = binding.qualifiedPackageName() == null ? "" : new String(binding.qualifiedPackageName());
        String qsn = binding.qualifiedSourceName() == null ? "" : new String(binding.qualifiedSourceName());
        return pkg.isEmpty() ? qsn : (pkg + "." + qsn);
    } else if (binding instanceof ArrayBinding) {
        StringBuilder out = new StringBuilder();
        out.append(typeBindingToSignature(binding.leafComponentType()));
        for (int i = 0; i < binding.dimensions(); i++)
            out.append("[]");
        return out.toString();
    }

    return "";
}

From source file:lombok.eclipse.handlers.EclipseHandlerUtil.java

License:Open Source License

public static TypeReference makeType(TypeBinding binding, ASTNode pos, boolean allowCompound) {
    int dims = binding.dimensions();
    binding = binding.leafComponentType();

    // Primitives

    char[] base = null;

    switch (binding.id) {
    case TypeIds.T_int:
        base = TypeConstants.INT;//from ww w  .j a  va2s.com
        break;
    case TypeIds.T_long:
        base = TypeConstants.LONG;
        break;
    case TypeIds.T_short:
        base = TypeConstants.SHORT;
        break;
    case TypeIds.T_byte:
        base = TypeConstants.BYTE;
        break;
    case TypeIds.T_double:
        base = TypeConstants.DOUBLE;
        break;
    case TypeIds.T_float:
        base = TypeConstants.FLOAT;
        break;
    case TypeIds.T_boolean:
        base = TypeConstants.BOOLEAN;
        break;
    case TypeIds.T_char:
        base = TypeConstants.CHAR;
        break;
    case TypeIds.T_void:
        base = TypeConstants.VOID;
        break;
    case TypeIds.T_null:
        return null;
    }

    if (base != null) {
        if (dims > 0) {
            TypeReference result = new ArrayTypeReference(base, dims, pos(pos));
            setGeneratedBy(result, pos);
            return result;
        }
        TypeReference result = new SingleTypeReference(base, pos(pos));
        setGeneratedBy(result, pos);
        return result;
    }

    if (binding.isAnonymousType()) {
        ReferenceBinding ref = (ReferenceBinding) binding;
        ReferenceBinding[] supers = ref.superInterfaces();
        if (supers == null || supers.length == 0)
            supers = new ReferenceBinding[] { ref.superclass() };
        if (supers[0] == null) {
            TypeReference result = new QualifiedTypeReference(TypeConstants.JAVA_LANG_OBJECT, poss(pos, 3));
            setGeneratedBy(result, pos);
            return result;
        }
        return makeType(supers[0], pos, false);
    }

    if (binding instanceof CaptureBinding) {
        return makeType(((CaptureBinding) binding).wildcard, pos, allowCompound);
    }

    if (binding.isUnboundWildcard()) {
        if (!allowCompound) {
            TypeReference result = new QualifiedTypeReference(TypeConstants.JAVA_LANG_OBJECT, poss(pos, 3));
            setGeneratedBy(result, pos);
            return result;
        } else {
            Wildcard out = new Wildcard(Wildcard.UNBOUND);
            setGeneratedBy(out, pos);
            out.sourceStart = pos.sourceStart;
            out.sourceEnd = pos.sourceEnd;
            return out;
        }
    }

    if (binding.isWildcard()) {
        WildcardBinding wildcard = (WildcardBinding) binding;
        if (wildcard.boundKind == Wildcard.EXTENDS) {
            if (!allowCompound) {
                return makeType(wildcard.bound, pos, false);
            } else {
                Wildcard out = new Wildcard(Wildcard.EXTENDS);
                setGeneratedBy(out, pos);
                out.bound = makeType(wildcard.bound, pos, false);
                out.sourceStart = pos.sourceStart;
                out.sourceEnd = pos.sourceEnd;
                return out;
            }
        } else if (allowCompound && wildcard.boundKind == Wildcard.SUPER) {
            Wildcard out = new Wildcard(Wildcard.SUPER);
            setGeneratedBy(out, pos);
            out.bound = makeType(wildcard.bound, pos, false);
            out.sourceStart = pos.sourceStart;
            out.sourceEnd = pos.sourceEnd;
            return out;
        } else {
            TypeReference result = new QualifiedTypeReference(TypeConstants.JAVA_LANG_OBJECT, poss(pos, 3));
            setGeneratedBy(result, pos);
            return result;
        }
    }

    // Keep moving up via 'binding.enclosingType()' and gather generics from each binding. We stop after a local type, or a static type, or a top-level type.
    // Finally, add however many nullTypeArgument[] arrays as that are missing, inverse the list, toArray it, and use that as PTR's typeArgument argument.

    List<TypeReference[]> params = new ArrayList<TypeReference[]>();
    /* Calculate generics */ {
        TypeBinding b = binding;
        while (true) {
            boolean isFinalStop = b.isLocalType() || !b.isMemberType() || b.enclosingType() == null;

            TypeReference[] tyParams = null;
            if (b instanceof ParameterizedTypeBinding) {
                ParameterizedTypeBinding paramized = (ParameterizedTypeBinding) b;
                if (paramized.arguments != null) {
                    tyParams = new TypeReference[paramized.arguments.length];
                    for (int i = 0; i < tyParams.length; i++) {
                        tyParams[i] = makeType(paramized.arguments[i], pos, true);
                    }
                }
            }

            params.add(tyParams);
            if (isFinalStop)
                break;
            b = b.enclosingType();
        }
    }

    char[][] parts;

    if (binding.isTypeVariable()) {
        parts = new char[][] { binding.shortReadableName() };
    } else if (binding.isLocalType()) {
        parts = new char[][] { binding.sourceName() };
    } else {
        String[] pkg = new String(binding.qualifiedPackageName()).split("\\.");
        String[] name = new String(binding.qualifiedSourceName()).split("\\.");
        if (pkg.length == 1 && pkg[0].isEmpty())
            pkg = new String[0];
        parts = new char[pkg.length + name.length][];
        int ptr;
        for (ptr = 0; ptr < pkg.length; ptr++)
            parts[ptr] = pkg[ptr].toCharArray();
        for (; ptr < pkg.length + name.length; ptr++)
            parts[ptr] = name[ptr - pkg.length].toCharArray();
    }

    while (params.size() < parts.length)
        params.add(null);
    Collections.reverse(params);

    boolean isParamized = false;

    for (TypeReference[] tyParams : params) {
        if (tyParams != null) {
            isParamized = true;
            break;
        }
    }
    if (isParamized) {
        if (parts.length > 1) {
            TypeReference[][] typeArguments = params.toArray(new TypeReference[0][]);
            TypeReference result = new ParameterizedQualifiedTypeReference(parts, typeArguments, dims,
                    poss(pos, parts.length));
            setGeneratedBy(result, pos);
            return result;
        }
        TypeReference result = new ParameterizedSingleTypeReference(parts[0], params.get(0), dims, pos(pos));
        setGeneratedBy(result, pos);
        return result;
    }

    if (dims > 0) {
        if (parts.length > 1) {
            TypeReference result = new ArrayQualifiedTypeReference(parts, dims, poss(pos, parts.length));
            setGeneratedBy(result, pos);
            return result;
        }
        TypeReference result = new ArrayTypeReference(parts[0], dims, pos(pos));
        setGeneratedBy(result, pos);
        return result;
    }

    if (parts.length > 1) {
        TypeReference result = new QualifiedTypeReference(parts, poss(pos, parts.length));
        setGeneratedBy(result, pos);
        return result;
    }
    TypeReference result = new SingleTypeReference(parts[0], pos(pos));
    setGeneratedBy(result, pos);
    return result;
}

From source file:org.eclipse.jdt.internal.compiler.lookup.Scope.java

License:Open Source License

/**
 * Returns a type where either all variables or specific ones got discarded.
 * e.g. List<E> (discarding <E extends Enum<E>) will return:  List<? extends Enum<?>>
 *///w w  w  .j ava 2 s  .co m
public static TypeBinding convertEliminatingTypeVariables(TypeBinding originalType,
        ReferenceBinding genericType, int rank, Set eliminatedVariables) {
    if ((originalType.tagBits & TagBits.HasTypeVariable) != 0) {
        switch (originalType.kind()) {
        case Binding.ARRAY_TYPE:
            ArrayBinding originalArrayType = (ArrayBinding) originalType;
            TypeBinding originalLeafComponentType = originalArrayType.leafComponentType;
            TypeBinding substitute = convertEliminatingTypeVariables(originalLeafComponentType, genericType,
                    rank, eliminatedVariables); // substitute could itself be array type
            if (substitute != originalLeafComponentType) {
                return originalArrayType.environment.createArrayType(substitute.leafComponentType(),
                        substitute.dimensions() + originalArrayType.dimensions());
            }
            break;
        case Binding.PARAMETERIZED_TYPE:
            ParameterizedTypeBinding paramType = (ParameterizedTypeBinding) originalType;
            ReferenceBinding originalEnclosing = paramType.enclosingType();
            ReferenceBinding substitutedEnclosing = originalEnclosing;
            if (originalEnclosing != null) {
                substitutedEnclosing = (ReferenceBinding) convertEliminatingTypeVariables(originalEnclosing,
                        genericType, rank, eliminatedVariables);
            }
            TypeBinding[] originalArguments = paramType.arguments;
            TypeBinding[] substitutedArguments = originalArguments;
            for (int i = 0, length = originalArguments == null ? 0
                    : originalArguments.length; i < length; i++) {
                TypeBinding originalArgument = originalArguments[i];
                TypeBinding substitutedArgument = convertEliminatingTypeVariables(originalArgument,
                        paramType.genericType(), i, eliminatedVariables);
                if (substitutedArgument != originalArgument) {
                    if (substitutedArguments == originalArguments) {
                        System.arraycopy(originalArguments, 0, substitutedArguments = new TypeBinding[length],
                                0, i);
                    }
                    substitutedArguments[i] = substitutedArgument;
                } else if (substitutedArguments != originalArguments) {
                    substitutedArguments[i] = originalArgument;
                }
            }
            if (originalEnclosing != substitutedEnclosing || originalArguments != substitutedArguments) {
                return paramType.environment.createParameterizedType(paramType.genericType(),
                        substitutedArguments, substitutedEnclosing);
            }
            break;
        case Binding.TYPE_PARAMETER:
            if (genericType == null) {
                break;
            }
            TypeVariableBinding originalVariable = (TypeVariableBinding) originalType;
            if (eliminatedVariables != null && eliminatedVariables.contains(originalType)) {
                return originalVariable.environment.createWildcard(genericType, rank, null, null,
                        Wildcard.UNBOUND);
            }
            TypeBinding originalUpperBound = originalVariable.upperBound();
            if (eliminatedVariables == null) {
                eliminatedVariables = new HashSet(2);
            }
            eliminatedVariables.add(originalVariable);
            TypeBinding substitutedUpperBound = convertEliminatingTypeVariables(originalUpperBound, genericType,
                    rank, eliminatedVariables);
            eliminatedVariables.remove(originalVariable);
            return originalVariable.environment.createWildcard(genericType, rank, substitutedUpperBound, null,
                    Wildcard.EXTENDS);
        case Binding.RAW_TYPE:
            break;
        case Binding.GENERIC_TYPE:
            ReferenceBinding currentType = (ReferenceBinding) originalType;
            originalEnclosing = currentType.enclosingType();
            substitutedEnclosing = originalEnclosing;
            if (originalEnclosing != null) {
                substitutedEnclosing = (ReferenceBinding) convertEliminatingTypeVariables(originalEnclosing,
                        genericType, rank, eliminatedVariables);
            }
            originalArguments = currentType.typeVariables();
            substitutedArguments = originalArguments;
            for (int i = 0, length = originalArguments == null ? 0
                    : originalArguments.length; i < length; i++) {
                TypeBinding originalArgument = originalArguments[i];
                TypeBinding substitutedArgument = convertEliminatingTypeVariables(originalArgument, currentType,
                        i, eliminatedVariables);
                if (substitutedArgument != originalArgument) {
                    if (substitutedArguments == originalArguments) {
                        System.arraycopy(originalArguments, 0, substitutedArguments = new TypeBinding[length],
                                0, i);
                    }
                    substitutedArguments[i] = substitutedArgument;
                } else if (substitutedArguments != originalArguments) {
                    substitutedArguments[i] = originalArgument;
                }
            }
            if (originalEnclosing != substitutedEnclosing || originalArguments != substitutedArguments) {
                return ((TypeVariableBinding) originalArguments[0]).environment
                        .createParameterizedType(genericType, substitutedArguments, substitutedEnclosing);
            }
            break;
        case Binding.WILDCARD_TYPE:
            WildcardBinding wildcard = (WildcardBinding) originalType;
            TypeBinding originalBound = wildcard.bound;
            TypeBinding substitutedBound = originalBound;
            if (originalBound != null) {
                substitutedBound = convertEliminatingTypeVariables(originalBound, genericType, rank,
                        eliminatedVariables);
                if (substitutedBound != originalBound) {
                    return wildcard.environment.createWildcard(wildcard.genericType, wildcard.rank,
                            substitutedBound, null, wildcard.boundKind);
                }
            }
            break;
        case Binding.INTERSECTION_TYPE:
            WildcardBinding intersection = (WildcardBinding) originalType;
            originalBound = intersection.bound;
            substitutedBound = originalBound;
            if (originalBound != null) {
                substitutedBound = convertEliminatingTypeVariables(originalBound, genericType, rank,
                        eliminatedVariables);
            }
            TypeBinding[] originalOtherBounds = intersection.otherBounds;
            TypeBinding[] substitutedOtherBounds = originalOtherBounds;
            for (int i = 0, length = originalOtherBounds == null ? 0
                    : originalOtherBounds.length; i < length; i++) {
                TypeBinding originalOtherBound = originalOtherBounds[i];
                TypeBinding substitutedOtherBound = convertEliminatingTypeVariables(originalOtherBound,
                        genericType, rank, eliminatedVariables);
                if (substitutedOtherBound != originalOtherBound) {
                    if (substitutedOtherBounds == originalOtherBounds) {
                        System.arraycopy(originalOtherBounds, 0,
                                substitutedOtherBounds = new TypeBinding[length], 0, i);
                    }
                    substitutedOtherBounds[i] = substitutedOtherBound;
                } else if (substitutedOtherBounds != originalOtherBounds) {
                    substitutedOtherBounds[i] = originalOtherBound;
                }
            }
            if (substitutedBound != originalBound || substitutedOtherBounds != originalOtherBounds) {
                return intersection.environment.createWildcard(intersection.genericType, intersection.rank,
                        substitutedBound, substitutedOtherBounds, intersection.boundKind);
            }
            break;
        }
    }
    return originalType;
}

From source file:org.eclipse.jdt.internal.compiler.lookup.Scope.java

License:Open Source License

/**
 * Returns a type, where original type was substituted using the receiver
 * parameterized type.//from   w  w w. jav a 2 s .  c  o m
 * In raw mode, all parameterized type denoting same original type are converted
 * to raw types. e.g.
 * class X <T> {
 *   X<T> foo;
 *   X<String> bar;
 * } when used in raw fashion, then type of both foo and bar is raw type X.
 *
 */
public static TypeBinding substitute(Substitution substitution, TypeBinding originalType) {
    if (originalType == null)
        return null;
    switch (originalType.kind()) {

    case Binding.TYPE_PARAMETER:
        return substitution.substitute((TypeVariableBinding) originalType);

    case Binding.PARAMETERIZED_TYPE:
        ParameterizedTypeBinding originalParameterizedType = (ParameterizedTypeBinding) originalType;
        ReferenceBinding originalEnclosing = originalType.enclosingType();
        ReferenceBinding substitutedEnclosing = originalEnclosing;
        if (originalEnclosing != null) {
            substitutedEnclosing = (ReferenceBinding) substitute(substitution, originalEnclosing);
        }
        TypeBinding[] originalArguments = originalParameterizedType.arguments;
        TypeBinding[] substitutedArguments = originalArguments;
        if (originalArguments != null) {
            if (substitution.isRawSubstitution()) {
                return originalParameterizedType.environment
                        .createRawType(originalParameterizedType.genericType(), substitutedEnclosing);
            }
            substitutedArguments = substitute(substitution, originalArguments);
        }
        if (substitutedArguments != originalArguments || substitutedEnclosing != originalEnclosing) {
            return originalParameterizedType.environment.createParameterizedType(
                    originalParameterizedType.genericType(), substitutedArguments, substitutedEnclosing);
        }
        break;

    case Binding.ARRAY_TYPE:
        ArrayBinding originalArrayType = (ArrayBinding) originalType;
        TypeBinding originalLeafComponentType = originalArrayType.leafComponentType;
        TypeBinding substitute = substitute(substitution, originalLeafComponentType); // substitute could itself be array type
        if (substitute != originalLeafComponentType) {
            return originalArrayType.environment.createArrayType(substitute.leafComponentType(),
                    substitute.dimensions() + originalType.dimensions());
        }
        break;

    case Binding.WILDCARD_TYPE:
    case Binding.INTERSECTION_TYPE:
        WildcardBinding wildcard = (WildcardBinding) originalType;
        if (wildcard.boundKind != Wildcard.UNBOUND) {
            TypeBinding originalBound = wildcard.bound;
            TypeBinding substitutedBound = substitute(substitution, originalBound);
            TypeBinding[] originalOtherBounds = wildcard.otherBounds;
            TypeBinding[] substitutedOtherBounds = substitute(substitution, originalOtherBounds);
            if (substitutedBound != originalBound || originalOtherBounds != substitutedOtherBounds) {
                if (originalOtherBounds != null) {
                    /* https://bugs.eclipse.org/bugs/show_bug.cgi?id=347145: the constituent intersecting types have changed
                       in the last round of substitution. Reevaluate the composite intersection type, as there is a possibility
                       of the intersection collapsing into one of the constituents, the other being fully subsumed.
                    */
                    TypeBinding[] bounds = new TypeBinding[1 + substitutedOtherBounds.length];
                    bounds[0] = substitutedBound;
                    System.arraycopy(substitutedOtherBounds, 0, bounds, 1, substitutedOtherBounds.length);
                    TypeBinding[] glb = Scope.greaterLowerBound(bounds); // re-evaluate
                    if (glb != null && glb != bounds) {
                        substitutedBound = glb[0];
                        if (glb.length == 1) {
                            substitutedOtherBounds = null;
                        } else {
                            System.arraycopy(glb, 1, substitutedOtherBounds = new TypeBinding[glb.length - 1],
                                    0, glb.length - 1);
                        }
                    }
                }
                return wildcard.environment.createWildcard(wildcard.genericType, wildcard.rank,
                        substitutedBound, substitutedOtherBounds, wildcard.boundKind);
            }
        }
        break;

    case Binding.TYPE:
        if (!originalType.isMemberType())
            break;
        ReferenceBinding originalReferenceType = (ReferenceBinding) originalType;
        originalEnclosing = originalType.enclosingType();
        substitutedEnclosing = originalEnclosing;
        if (originalEnclosing != null) {
            substitutedEnclosing = (ReferenceBinding) substitute(substitution, originalEnclosing);
        }

        // treat as if parameterized with its type variables (non generic type gets 'null' arguments)
        if (substitutedEnclosing != originalEnclosing) {
            return substitution.isRawSubstitution()
                    ? substitution.environment().createRawType(originalReferenceType, substitutedEnclosing)
                    : substitution.environment().createParameterizedType(originalReferenceType, null,
                            substitutedEnclosing);
        }
        break;
    case Binding.GENERIC_TYPE:
        originalReferenceType = (ReferenceBinding) originalType;
        originalEnclosing = originalType.enclosingType();
        substitutedEnclosing = originalEnclosing;
        if (originalEnclosing != null) {
            substitutedEnclosing = (ReferenceBinding) substitute(substitution, originalEnclosing);
        }

        if (substitution.isRawSubstitution()) {
            return substitution.environment().createRawType(originalReferenceType, substitutedEnclosing);
        }
        // treat as if parameterized with its type variables (non generic type gets 'null' arguments)
        originalArguments = originalReferenceType.typeVariables();
        substitutedArguments = substitute(substitution, originalArguments);
        return substitution.environment().createParameterizedType(originalReferenceType, substitutedArguments,
                substitutedEnclosing);
    }
    return originalType;
}

From source file:org.eclipse.jdt.internal.compiler.lookup.Scope.java

License:Open Source License

private TypeBinding leastContainingInvocation(TypeBinding mec, Object invocationData, List lubStack) {
    if (invocationData == null)
        return mec; // no alternate invocation
    if (invocationData instanceof TypeBinding) { // only one invocation, simply return it (array only allocated if more than one)
        return (TypeBinding) invocationData;
    }//from   ww  w.  j a v  a2  s.  co m
    TypeBinding[] invocations = (TypeBinding[]) invocationData;

    // if mec is an array type, intersect invocation leaf component types, then promote back to array
    int dim = mec.dimensions();
    mec = mec.leafComponentType();

    int argLength = mec.typeVariables().length;
    if (argLength == 0)
        return mec; // should be caught by no invocation check

    // infer proper parameterized type from invocations
    TypeBinding[] bestArguments = new TypeBinding[argLength];
    for (int i = 0, length = invocations.length; i < length; i++) {
        TypeBinding invocation = invocations[i].leafComponentType();
        switch (invocation.kind()) {
        case Binding.GENERIC_TYPE:
            TypeVariableBinding[] invocationVariables = invocation.typeVariables();
            for (int j = 0; j < argLength; j++) {
                TypeBinding bestArgument = leastContainingTypeArgument(bestArguments[j], invocationVariables[j],
                        (ReferenceBinding) mec, j, lubStack);
                if (bestArgument == null)
                    return null;
                bestArguments[j] = bestArgument;
            }
            break;
        case Binding.PARAMETERIZED_TYPE:
            ParameterizedTypeBinding parameterizedType = (ParameterizedTypeBinding) invocation;
            for (int j = 0; j < argLength; j++) {
                TypeBinding bestArgument = leastContainingTypeArgument(bestArguments[j],
                        parameterizedType.arguments[j], (ReferenceBinding) mec, j, lubStack);
                if (bestArgument == null)
                    return null;
                bestArguments[j] = bestArgument;
            }
            break;
        case Binding.RAW_TYPE:
            return dim == 0 ? invocation : environment().createArrayType(invocation, dim); // raw type is taking precedence
        }
    }
    TypeBinding least = environment().createParameterizedType((ReferenceBinding) mec.erasure(), bestArguments,
            mec.enclosingType());
    return dim == 0 ? least : environment().createArrayType(least, dim);
}

From source file:org.eclipse.jdt.internal.compiler.lookup.Scope.java

License:Open Source License

private TypeBinding lowerUpperBound(TypeBinding[] types, List lubStack) {

    int typeLength = types.length;
    if (typeLength == 1) {
        TypeBinding type = types[0];/*from   w w  w .j ava  2 s  .c  om*/
        return type == null ? TypeBinding.VOID : type;
    }
    // cycle detection
    int stackLength = lubStack.size();
    nextLubCheck: for (int i = 0; i < stackLength; i++) {
        TypeBinding[] lubTypes = (TypeBinding[]) lubStack.get(i);
        int lubTypeLength = lubTypes.length;
        if (lubTypeLength < typeLength)
            continue nextLubCheck;
        nextTypeCheck: for (int j = 0; j < typeLength; j++) {
            TypeBinding type = types[j];
            if (type == null)
                continue nextTypeCheck; // ignore
            for (int k = 0; k < lubTypeLength; k++) {
                TypeBinding lubType = lubTypes[k];
                if (lubType == null)
                    continue; // ignore
                if (lubType == type || lubType.isEquivalentTo(type))
                    continue nextTypeCheck; // type found, jump to next one
            }
            continue nextLubCheck; // type not found in current lubTypes
        }
        // all types are included in some lub, cycle detected - stop recursion by answering special value (int)
        return TypeBinding.INT;
    }

    lubStack.add(types);
    Map invocations = new HashMap(1);
    TypeBinding[] mecs = minimalErasedCandidates(types, invocations);
    if (mecs == null)
        return null;
    int length = mecs.length;
    if (length == 0)
        return TypeBinding.VOID;
    int count = 0;
    TypeBinding firstBound = null;
    int commonDim = -1;
    for (int i = 0; i < length; i++) {
        TypeBinding mec = mecs[i];
        if (mec == null)
            continue;
        mec = leastContainingInvocation(mec, invocations.get(mec), lubStack);
        if (mec == null)
            return null;
        int dim = mec.dimensions();
        if (commonDim == -1) {
            commonDim = dim;
        } else if (dim != commonDim) { // not all types have same dimension
            return null;
        }
        if (firstBound == null && !mec.leafComponentType().isInterface())
            firstBound = mec.leafComponentType();
        mecs[count++] = mec; // recompact them to the front
    }
    switch (count) {
    case 0:
        return TypeBinding.VOID;
    case 1:
        return mecs[0];
    case 2:
        if ((commonDim == 0 ? mecs[1].id : mecs[1].leafComponentType().id) == TypeIds.T_JavaLangObject)
            return mecs[0];
        if ((commonDim == 0 ? mecs[0].id : mecs[0].leafComponentType().id) == TypeIds.T_JavaLangObject)
            return mecs[1];
    }
    TypeBinding[] otherBounds = new TypeBinding[count - 1];
    int rank = 0;
    for (int i = 0; i < count; i++) {
        TypeBinding mec = commonDim == 0 ? mecs[i] : mecs[i].leafComponentType();
        if (mec.isInterface()) {
            otherBounds[rank++] = mec;
        }
    }
    TypeBinding intersectionType = environment().createWildcard(null, 0, firstBound, otherBounds,
            Wildcard.EXTENDS);
    return commonDim == 0 ? intersectionType : environment().createArrayType(intersectionType, commonDim);
}

From source file:org.eclipse.jdt.internal.compiler.lookup.Scope.java

License:Open Source License

/**
 * Returns the most specific set of types compatible with all given types.
 * (i.e. most specific common super types)
 * If no types is given, will return an empty array. If not compatible
 * reference type is found, returns null. In other cases, will return an array
 * of minimal erased types, where some nulls may appear (and must simply be
 * ignored).//from  w w  w  .  j  av a  2  s  .  c  o m
 */
protected TypeBinding[] minimalErasedCandidates(TypeBinding[] types, Map allInvocations) {
    int length = types.length;
    int indexOfFirst = -1, actualLength = 0;
    for (int i = 0; i < length; i++) {
        TypeBinding type = types[i];
        if (type == null)
            continue;
        if (type.isBaseType())
            return null;
        if (indexOfFirst < 0)
            indexOfFirst = i;
        actualLength++;
    }
    switch (actualLength) {
    case 0:
        return Binding.NO_TYPES;
    case 1:
        return types;
    }
    TypeBinding firstType = types[indexOfFirst];
    if (firstType.isBaseType())
        return null;

    // record all supertypes of type
    // intersect with all supertypes of otherType
    ArrayList typesToVisit = new ArrayList(5);

    int dim = firstType.dimensions();
    TypeBinding leafType = firstType.leafComponentType();
    // do not allow type variables/intersection types to match with erasures for free
    TypeBinding firstErasure;
    switch (leafType.kind()) {
    case Binding.PARAMETERIZED_TYPE:
    case Binding.RAW_TYPE:
    case Binding.ARRAY_TYPE:
        firstErasure = firstType.erasure();
        break;
    default:
        firstErasure = firstType;
        break;
    }
    if (firstErasure != firstType) {
        allInvocations.put(firstErasure, firstType);
    }
    typesToVisit.add(firstType);
    int max = 1;
    ReferenceBinding currentType;
    for (int i = 0; i < max; i++) {
        TypeBinding typeToVisit = (TypeBinding) typesToVisit.get(i);
        dim = typeToVisit.dimensions();
        if (dim > 0) {
            leafType = typeToVisit.leafComponentType();
            switch (leafType.id) {
            case TypeIds.T_JavaLangObject:
                if (dim > 1) { // Object[][] supertype is Object[]
                    TypeBinding elementType = ((ArrayBinding) typeToVisit).elementsType();
                    if (!typesToVisit.contains(elementType)) {
                        typesToVisit.add(elementType);
                        max++;
                    }
                    continue;
                }
                //$FALL-THROUGH$
            case TypeIds.T_byte:
            case TypeIds.T_short:
            case TypeIds.T_char:
            case TypeIds.T_boolean:
            case TypeIds.T_int:
            case TypeIds.T_long:
            case TypeIds.T_float:
            case TypeIds.T_double:
                TypeBinding superType = getJavaIoSerializable();
                if (!typesToVisit.contains(superType)) {
                    typesToVisit.add(superType);
                    max++;
                }
                superType = getJavaLangCloneable();
                if (!typesToVisit.contains(superType)) {
                    typesToVisit.add(superType);
                    max++;
                }
                superType = getJavaLangObject();
                if (!typesToVisit.contains(superType)) {
                    typesToVisit.add(superType);
                    max++;
                }
                continue;

            default:
            }
            typeToVisit = leafType;
        }
        currentType = (ReferenceBinding) typeToVisit;
        if (currentType.isCapture()) {
            TypeBinding firstBound = ((CaptureBinding) currentType).firstBound;
            if (firstBound != null && firstBound.isArrayType()) {
                TypeBinding superType = dim == 0 ? firstBound
                        : (TypeBinding) environment().createArrayType(firstBound, dim); // recreate array if needed
                if (!typesToVisit.contains(superType)) {
                    typesToVisit.add(superType);
                    max++;
                    TypeBinding superTypeErasure = (firstBound.isTypeVariable()
                            || firstBound.isWildcard() /*&& !itsInterface.isCapture()*/) ? superType
                                    : superType.erasure();
                    if (superTypeErasure != superType) {
                        allInvocations.put(superTypeErasure, superType);
                    }
                }
                continue;
            }
        }
        // inject super interfaces prior to superclass
        ReferenceBinding[] itsInterfaces = currentType.superInterfaces();
        if (itsInterfaces != null) { // can be null during code assist operations that use LookupEnvironment.completeTypeBindings(parsedUnit, buildFieldsAndMethods)
            for (int j = 0, count = itsInterfaces.length; j < count; j++) {
                TypeBinding itsInterface = itsInterfaces[j];
                TypeBinding superType = dim == 0 ? itsInterface
                        : (TypeBinding) environment().createArrayType(itsInterface, dim); // recreate array if needed
                if (!typesToVisit.contains(superType)) {
                    typesToVisit.add(superType);
                    max++;
                    TypeBinding superTypeErasure = (itsInterface.isTypeVariable()
                            || itsInterface.isWildcard() /*&& !itsInterface.isCapture()*/) ? superType
                                    : superType.erasure();
                    if (superTypeErasure != superType) {
                        allInvocations.put(superTypeErasure, superType);
                    }
                }
            }
        }
        TypeBinding itsSuperclass = currentType.superclass();
        if (itsSuperclass != null) {
            TypeBinding superType = dim == 0 ? itsSuperclass
                    : (TypeBinding) environment().createArrayType(itsSuperclass, dim); // recreate array if needed
            if (!typesToVisit.contains(superType)) {
                typesToVisit.add(superType);
                max++;
                TypeBinding superTypeErasure = (itsSuperclass.isTypeVariable()
                        || itsSuperclass.isWildcard() /*&& !itsSuperclass.isCapture()*/) ? superType
                                : superType.erasure();
                if (superTypeErasure != superType) {
                    allInvocations.put(superTypeErasure, superType);
                }
            }
        }
    }
    int superLength = typesToVisit.size();
    TypeBinding[] erasedSuperTypes = new TypeBinding[superLength];
    int rank = 0;
    for (Iterator iter = typesToVisit.iterator(); iter.hasNext();) {
        TypeBinding type = (TypeBinding) iter.next();
        leafType = type.leafComponentType();
        erasedSuperTypes[rank++] = (leafType.isTypeVariable()
                || leafType.isWildcard() /*&& !leafType.isCapture()*/) ? type : type.erasure();
    }
    // intersecting first type supertypes with other types' ones, nullifying non matching supertypes
    int remaining = superLength;
    nextOtherType: for (int i = indexOfFirst + 1; i < length; i++) {
        TypeBinding otherType = types[i];
        if (otherType == null)
            continue nextOtherType;
        if (otherType.isArrayType()) {
            nextSuperType: for (int j = 0; j < superLength; j++) {
                TypeBinding erasedSuperType = erasedSuperTypes[j];
                if (erasedSuperType == null || erasedSuperType == otherType)
                    continue nextSuperType;
                TypeBinding match;
                if ((match = otherType.findSuperTypeOriginatingFrom(erasedSuperType)) == null) {
                    erasedSuperTypes[j] = null;
                    if (--remaining == 0)
                        return null;
                    continue nextSuperType;
                }
                // record invocation
                Object invocationData = allInvocations.get(erasedSuperType);
                if (invocationData == null) {
                    allInvocations.put(erasedSuperType, match); // no array for singleton
                } else if (invocationData instanceof TypeBinding) {
                    if (match != invocationData) {
                        // using an array to record invocations in order (188103)
                        TypeBinding[] someInvocations = { (TypeBinding) invocationData, match, };
                        allInvocations.put(erasedSuperType, someInvocations);
                    }
                } else { // using an array to record invocations in order (188103)
                    TypeBinding[] someInvocations = (TypeBinding[]) invocationData;
                    checkExisting: {
                        int invocLength = someInvocations.length;
                        for (int k = 0; k < invocLength; k++) {
                            if (someInvocations[k] == match)
                                break checkExisting;
                        }
                        System.arraycopy(someInvocations, 0, someInvocations = new TypeBinding[invocLength + 1],
                                0, invocLength);
                        allInvocations.put(erasedSuperType, someInvocations);
                        someInvocations[invocLength] = match;
                    }
                }
            }
            continue nextOtherType;
        }
        nextSuperType: for (int j = 0; j < superLength; j++) {
            TypeBinding erasedSuperType = erasedSuperTypes[j];
            if (erasedSuperType == null)
                continue nextSuperType;
            TypeBinding match;
            if (erasedSuperType == otherType
                    || erasedSuperType.id == TypeIds.T_JavaLangObject && otherType.isInterface()) {
                match = erasedSuperType;
            } else {
                if (erasedSuperType.isArrayType()) {
                    match = null;
                } else {
                    match = otherType.findSuperTypeOriginatingFrom(erasedSuperType);
                }
                if (match == null) { // incompatible super type
                    erasedSuperTypes[j] = null;
                    if (--remaining == 0)
                        return null;
                    continue nextSuperType;
                }
            }
            // record invocation
            Object invocationData = allInvocations.get(erasedSuperType);
            if (invocationData == null) {
                allInvocations.put(erasedSuperType, match); // no array for singleton
            } else if (invocationData instanceof TypeBinding) {
                if (match != invocationData) {
                    // using an array to record invocations in order (188103)
                    TypeBinding[] someInvocations = { (TypeBinding) invocationData, match, };
                    allInvocations.put(erasedSuperType, someInvocations);
                }
            } else { // using an array to record invocations in order (188103)
                TypeBinding[] someInvocations = (TypeBinding[]) invocationData;
                checkExisting: {
                    int invocLength = someInvocations.length;
                    for (int k = 0; k < invocLength; k++) {
                        if (someInvocations[k] == match)
                            break checkExisting;
                    }
                    System.arraycopy(someInvocations, 0, someInvocations = new TypeBinding[invocLength + 1], 0,
                            invocLength);
                    allInvocations.put(erasedSuperType, someInvocations);
                    someInvocations[invocLength] = match;
                }
            }
        }
    }
    // eliminate non minimal super types
    if (remaining > 1) {
        nextType: for (int i = 0; i < superLength; i++) {
            TypeBinding erasedSuperType = erasedSuperTypes[i];
            if (erasedSuperType == null)
                continue nextType;
            nextOtherType: for (int j = 0; j < superLength; j++) {
                if (i == j)
                    continue nextOtherType;
                TypeBinding otherType = erasedSuperTypes[j];
                if (otherType == null)
                    continue nextOtherType;
                if (erasedSuperType instanceof ReferenceBinding) {
                    if (otherType.id == TypeIds.T_JavaLangObject && erasedSuperType.isInterface())
                        continue nextOtherType; // keep Object for an interface
                    if (erasedSuperType.findSuperTypeOriginatingFrom(otherType) != null) {
                        erasedSuperTypes[j] = null; // discard non minimal supertype
                        remaining--;
                    }
                } else if (erasedSuperType.isArrayType()) {
                    if (otherType.isArrayType() // keep Object[...] for an interface array (same dimensions)
                            && otherType.leafComponentType().id == TypeIds.T_JavaLangObject
                            && otherType.dimensions() == erasedSuperType.dimensions()
                            && erasedSuperType.leafComponentType().isInterface())
                        continue nextOtherType;
                    if (erasedSuperType.findSuperTypeOriginatingFrom(otherType) != null) {
                        erasedSuperTypes[j] = null; // discard non minimal supertype
                        remaining--;
                    }
                }
            }
        }
    }
    return erasedSuperTypes;
}

From source file:org.eclipse.objectteams.otdt.internal.core.compiler.ast.CallinMappingDeclaration.java

License:Open Source License

/**
 * Check all parameters in methodSpec against the resolved role method.
 * Also record which parameters (including result) need translation (lifting/lowering).
 *
 * Pre: not called if parameter mappings are present.
 * @param methodSpec//w  w w.j  a v  a 2s. c om
 */
protected boolean internalCheckParametersCompatibility(MethodSpec methodSpec, TypeBinding[] roleParams,
        TypeBinding[] baseParams) {
    if (baseParams.length < roleParams.length) {
        this.scope.problemReporter().tooFewArgumentsInMethodMapping(this.roleMethodSpec, methodSpec,
                false/*callout*/);
        this.binding.tagBits |= TagBits.HasMappingIncompatibility;
        return false;
    } else {
        // before modifying the parameters array copy it:
        System.arraycopy(this.roleMethodSpec.parameters, 0,
                this.roleMethodSpec.parameters = new TypeBinding[roleParams.length], 0, roleParams.length);
        for (int j = 0; j < roleParams.length; j++) {
            TypeBinding baseParam = baseParams[j];
            TypeBinding roleParam = roleParams[j];
            if (baseParam.dimensions() != roleParam.dimensions()) {
                this.scope.problemReporter().incompatibleMappedArgument(baseParam, roleParam,
                        this.roleMethodSpec, j, /*callout*/false);
                this.binding.tagBits |= TagBits.HasMappingIncompatibility;
                continue; // no real type checking needed.
            }
            TypeBinding baseLeaf = baseParam.leafComponentType();
            TypeBinding roleLeaf = roleParam.leafComponentType();
            ASTNode location = (methodSpec.hasSignature) ? (ASTNode) methodSpec.arguments[j] : methodSpec;
            boolean compatibilityViaBaseAnchor = false;
            boolean hasReportedError = false;
            boolean isTypeVariable = false;
            try { // capture continue exits

                // unbound type variable matches everything:
                if (roleParam.isTypeVariable()) {
                    TypeVariableBinding typeVariableBinding = (TypeVariableBinding) roleParam;
                    if (typeVariableBinding.firstBound == null)
                        continue;
                    // use bound for type checking below, yet need not check two-way compatibility:
                    isTypeVariable = true;
                    roleLeaf = typeVariableBinding.firstBound.leafComponentType();
                }

                int dimensions = roleParam.dimensions();
                if (baseLeaf.isCompatibleWith(roleLeaf)) {
                    this.roleMethodSpec.parameters[j] = roleParam;
                    continue;
                }
                if (RoleTypeCreator.isCompatibleViaBaseAnchor(this.scope, baseLeaf, roleLeaf,
                        TokenNameBINDIN)) {
                    this.roleMethodSpec.parameters[j] = roleParam;
                    compatibilityViaBaseAnchor = true;
                    continue;
                }

                TypeBinding roleToLiftTo = null;
                if (isReplaceCallin()) {
                    TypeBinding roleSideType = roleLeaf;
                    if (roleSideType.isRole()) {
                        ReferenceBinding roleRef = (ReferenceBinding) roleSideType;
                        roleRef = (ReferenceBinding) TeamModel
                                .strengthenRoleType(this.scope.enclosingReceiverType(), roleRef);
                        if (TypeBinding.equalsEquals(roleRef.baseclass(), baseLeaf)) {
                            if (dimensions > 0) {
                                if (roleRef instanceof DependentTypeBinding)
                                    roleToLiftTo = ((DependentTypeBinding) roleRef).getArrayType(dimensions);
                                else
                                    roleToLiftTo = this.scope.createArrayType(roleRef, dimensions); // FIXME(SH): is this OK?
                            } else {
                                roleToLiftTo = roleRef;
                            }
                        }
                    }
                } else {
                    // this uses OTJLD 2.3.3(a) adaptation which is not reversible, ie., not usable for replace:
                    roleToLiftTo = TeamModel.getRoleToLiftTo(this.scope, baseParam, roleParam, false, location);
                }
                if (roleToLiftTo != null) {
                    // success by translation
                    methodSpec.argNeedsTranslation[j] = true;
                    this.roleMethodSpec.argNeedsTranslation[j] = true;
                    this.roleMethodSpec.parameters[j] = roleToLiftTo; // this applies to all bindings

                    // still need to check for ambiguity/abstract role:
                    ReferenceBinding enclosingTeam = this.scope.enclosingSourceType().enclosingType();
                    int iProblem = enclosingTeam.getTeamModel()
                            .canLiftingFail((ReferenceBinding) roleToLiftTo.leafComponentType());
                    if (iProblem > 0)
                        addRoleLiftingProblem((ReferenceBinding) roleToLiftTo.leafComponentType(), iProblem);

                    continue;
                }
                // check auto(un)boxing:
                if (this.scope.isBoxingCompatibleWith(baseLeaf, roleLeaf))
                    continue;

                if (roleParam instanceof ReferenceBinding) {
                    ReferenceBinding roleRef = (ReferenceBinding) roleParam;
                    if (roleRef.isRole() && roleRef.baseclass() != null) {
                        this.scope.problemReporter().typeMismatchErrorPotentialLift(location, baseParam,
                                roleParam, roleRef.baseclass());
                        hasReportedError = true;
                        continue;
                    }
                }
                // no compatibility detected:
                this.scope.problemReporter().incompatibleMappedArgument(baseParam, roleParam,
                        this.roleMethodSpec, j, /*callout*/false);
                hasReportedError = true;
            } finally {
                if (hasReportedError)
                    this.binding.tagBits |= TagBits.HasMappingIncompatibility;
                // regardless of continue, check this last because it is the least precise message:
                if (!hasReportedError && baseLeaf.isCompatibleWith(roleLeaf)) {
                    if (isReplaceCallin() && !isTypeVariable) {
                        boolean twowayCompatible = compatibilityViaBaseAnchor
                                ? RoleTypeCreator.isCompatibleViaBaseAnchor(this.scope, baseLeaf, roleLeaf,
                                        TokenNameBINDOUT)
                                : roleLeaf.isCompatibleWith(baseLeaf);
                        if (!twowayCompatible) {
                            // requires two-way compatibility (see additional paragraph in 4.5(d))
                            this.scope.problemReporter().typesNotTwowayCompatibleInReplace(baseParam, roleParam,
                                    location, j);
                        }
                    }
                }
            }
        }
    }
    return true; // unused in the callin case
}

From source file:org.eclipse.objectteams.otdt.internal.core.compiler.ast.CallinMappingDeclaration.java

License:Open Source License

/** Check whether the baseSpec has a result compatible via replace. */
public void checkResultForReplace(MethodSpec baseSpec) {
    boolean typeIdentityRequired = true; // default unless return is type variable
    // covariant return requires a fresh type parameter for the role's return type:
    if (baseSpec.covariantReturn && this.roleMethodSpec.returnType != null) {
        TypeBinding resolvedRoleReturn = this.roleMethodSpec.returnType.resolvedType;
        if (resolvedRoleReturn != null) {
            if (!resolvedRoleReturn.isTypeVariable()) {
                this.scope.problemReporter()
                        .covariantReturnRequiresTypeParameter(this.roleMethodSpec.returnType);
                this.binding.tagBits |= TagBits.HasMappingIncompatibility;
            } else {
                // is the type parameter "fresh"?
                for (Argument arg : this.roleMethodSpec.arguments) {
                    if (typeUsesTypeVariable(arg.type.resolvedType.leafComponentType(), resolvedRoleReturn)) {
                        this.scope.problemReporter().duplicateUseOfTypeVariableInCallin(
                                this.roleMethodSpec.returnType, resolvedRoleReturn);
                        this.binding.tagBits |= TagBits.HasMappingIncompatibility;
                        break;
                    }/*ww w . jav  a 2s.  co  m*/
                }
            }
        }
    }
    TypeVariableBinding returnVariable = MethodModel
            .checkedGetReturnTypeVariable(this.roleMethodSpec.resolvedMethod);
    if (returnVariable != null) {
        // unbounded type variable always matches:
        if (returnVariable.firstBound == null)
            return;
        // in case of type variable only one-way compatibility is needed even for replace:
        typeIdentityRequired = false;
    }

    // now go for the actual type checking:
    TypeBinding baseReturn = baseSpec.resolvedMethod.returnType;
    TypeBinding roleReturn = MethodModel.getReturnType(this.roleMethodSpec.resolvedMethod);
    TypeBinding roleReturnLeaf = roleReturn != null ? roleReturn.leafComponentType() : null;
    if (roleReturnLeaf instanceof ReferenceBinding && ((ReferenceBinding) roleReturnLeaf).isRole()) {
        // strengthen:
        roleReturnLeaf = TeamModel.strengthenRoleType(this.scope.enclosingSourceType(), roleReturnLeaf);
        if (roleReturnLeaf == null) { // FIXME(SH): testcase and better handling
            String roleReturnName = roleReturn != null ? new String(roleReturn.readableName())
                    : "null return type"; //$NON-NLS-1$
            throw new InternalCompilerError("role strengthening for " + roleReturnName + " -> null"); //$NON-NLS-1$ //$NON-NLS-2$
        }

        // bound roles use their topmost bound super:
        if (((ReferenceBinding) roleReturnLeaf).baseclass() != null)
            roleReturnLeaf = RoleModel.getTopmostBoundRole(this.scope, (ReferenceBinding) roleReturnLeaf);

        // need the RTB:
        if (!(roleReturnLeaf instanceof DependentTypeBinding))
            roleReturnLeaf = RoleTypeCreator.maybeWrapUnqualifiedRoleType(roleReturnLeaf,
                    this.scope.enclosingSourceType());

        // array?
        int dims = roleReturn != null ? roleReturn.dimensions() : 0;
        if (dims == 0) {
            roleReturn = roleReturnLeaf;
            this.realRoleReturn = roleReturnLeaf;
        } else {
            roleReturn = ((DependentTypeBinding) roleReturnLeaf).getArrayType(dims);
            this.realRoleReturn = ((DependentTypeBinding) roleReturnLeaf).getArrayType(dims);
        }
    }
    if (baseReturn == null || baseReturn == TypeBinding.VOID) {
        // OTJLD 4.4(b): "A callin method bound with replace
        //                to a base method returning void
        //                must not declare a non-void result."
        if (!(roleReturn == null || roleReturn == TypeBinding.VOID)) {
            this.scope.problemReporter().callinIllegalRoleReturnReturn(baseSpec, this.roleMethodSpec);
            this.binding.tagBits |= TagBits.HasMappingIncompatibility;
        }
    } else {
        if (roleReturn == null || roleReturn == TypeBinding.VOID) {
            this.baseMethodNeedingResultFromBasecall = baseSpec;
            // will be reported in checkBaseResult().
            return;
        }

        TypeBinding baseLeaf = baseReturn.leafComponentType();
        if (baseLeaf instanceof DependentTypeBinding) {
            // instantiate relative to Role._OT$base:
            ReferenceBinding enclosingRole = this.scope.enclosingSourceType();
            FieldBinding baseField = enclosingRole.getField(IOTConstants._OT_BASE, true);
            if (baseField != null && baseField.isValidBinding())
                baseReturn = baseField.getRoleTypeBinding((ReferenceBinding) baseLeaf, baseReturn.dimensions());
        }

        // check auto(un)boxing:
        if (this.scope.isBoxingCompatibleWith(roleReturn, baseReturn))
            return;

        Config oldConfig = Config.createOrResetConfig(this);
        try {
            if (!roleReturn.isCompatibleWith(baseReturn)) {
                if (typeIdentityRequired) {
                    this.scope.problemReporter().callinIncompatibleReturnType(baseSpec, this.roleMethodSpec);
                    this.binding.tagBits |= TagBits.HasMappingIncompatibility;
                    return;
                }
                // else we still needed the lowering test
            }
            // callin replace requires two way compatibility:
            baseSpec.returnNeedsTranslation = Config.getLoweringRequired();

        } finally {
            Config.removeOrRestore(oldConfig, this);
        }
        // from now on don't bother with arrays any more (dimensions have been checked):
        roleReturn = roleReturn.leafComponentType();
        baseReturn = baseReturn.leafComponentType();
        TypeBinding translatedReturn = baseSpec.returnNeedsTranslation
                ? ((ReferenceBinding) roleReturn).baseclass()
                : roleReturn;
        if (translatedReturn.isTypeVariable()) {
            TypeBinding firstBound = ((TypeVariableBinding) translatedReturn).firstBound;
            if (firstBound != null)
                translatedReturn = firstBound;
        }
        if (!baseReturn.isCompatibleWith(translatedReturn)) {
            this.scope.problemReporter().callinIncompatibleReturnTypeBaseCall(baseSpec, this.roleMethodSpec);
            this.binding.tagBits |= TagBits.HasMappingIncompatibility;
        }
    }
}

From source file:org.eclipse.objectteams.otdt.internal.core.compiler.bytecode.AnchorListAttribute.java

License:Open Source License

/**
 * @param typeToWrap ReferenceBinding or array thereof
 * @param anchorName/*ww w.j  a  va  2 s. co  m*/
 * @param site
 * @param declaringMethod where to look for arguments being used as type anchor.
 * @param environment
 * @return a wrapped version of typeToWrap
 */
private TypeBinding getWrappedType(TypeBinding typeToWrap, char[] anchorName, ReferenceBinding site,
        final MethodBinding declaringMethod, LookupEnvironment environment) {
    assert !CharOperation.equals(anchorName, NO_ANCHOR) : "NO_ANCHOR should have been filtered out"; //$NON-NLS-1$

    ReferenceBinding type = (ReferenceBinding) typeToWrap.leafComponentType();
    if (CharOperation.prefixEquals(ARG_ANCHOR_PREFIX.toCharArray(), anchorName)) {
        // Type anchored to another argument:
        LocalVariableBinding anchor = new LocalVariableBinding(anchorName, type.enclosingType(), 0, true); // name is irrelevant.
        // make sure this anchor can answer `anchor.declaringScope.referenceMethodBinding()`:
        anchor.declaringScope = new CallinCalloutScope(null, null) {
            public MethodBinding referenceMethodBinding() {
                return declaringMethod;
            }
        };
        TypeBinding wrappedType = anchor.getRoleTypeBinding(type, typeToWrap.dimensions());

        // argument position is relevant:
        char[] tail = CharOperation.subarray(anchorName, ARG_ANCHOR_PREFIX.length(), -1);
        RoleTypeBinding wrappedRole = (RoleTypeBinding) wrappedType.leafComponentType();
        wrappedRole._argumentPosition = Integer.parseInt(String.valueOf(tail));
        wrappedRole._declaringMethod = new IMethodProvider() {
            public MethodBinding getMethod() {
                return declaringMethod;
            }
        };

        return wrappedType;
    } else {
        return RoleTypeCreator.wrapTypeWithAnchorFromName(typeToWrap, anchorName, site, environment);
    }
}