Search in sources :

Example 11 with AnnotationBinding

use of org.eclipse.jdt.internal.compiler.lookup.AnnotationBinding in project bazel-jdt-java-toolchain by salesforce.

the class ReferenceExpression method checkNullAnnotations.

protected void checkNullAnnotations(BlockScope scope) {
    CompilerOptions compilerOptions = scope.compilerOptions();
    if (compilerOptions.isAnnotationBasedNullAnalysisEnabled) {
        if (this.expectedType == null || !NullAnnotationMatching.hasContradictions(this.expectedType)) {
            // otherwise assume it has been reported and we can do nothing here
            ImplicitNullAnnotationVerifier.ensureNullnessIsKnown(this.binding, scope);
            // TODO: simplify by using this.freeParameters?
            int len;
            int expectedlen = this.binding.parameters.length;
            int providedLen = this.descriptor.parameters.length;
            if (this.receiverPrecedesParameters) {
                // one parameter is 'consumed' as the receiver
                providedLen--;
                TypeBinding descriptorParameter = this.descriptor.parameters[0];
                if ((descriptorParameter.tagBits & TagBits.AnnotationNullable) != 0) {
                    // Note: normal dereferencing of 'unchecked' values is not reported, either
                    final TypeBinding receiver = scope.environment().createAnnotatedType(this.binding.declaringClass, new AnnotationBinding[] { scope.environment().getNonNullAnnotation() });
                    scope.problemReporter().referenceExpressionArgumentNullityMismatch(this, receiver, descriptorParameter, this.descriptor, -1, NullAnnotationMatching.NULL_ANNOTATIONS_MISMATCH);
                }
            }
            boolean isVarArgs = false;
            if (this.binding.isVarargs()) {
                isVarArgs = (providedLen == expectedlen) ? !this.descriptor.parameters[expectedlen - 1].isCompatibleWith(this.binding.parameters[expectedlen - 1]) : true;
                // binding parameters will be padded from InferenceContext18.getParameter()
                len = providedLen;
            } else {
                len = Math.min(expectedlen, providedLen);
            }
            for (int i = 0; i < len; i++) {
                TypeBinding descriptorParameter = this.descriptor.parameters[i + (this.receiverPrecedesParameters ? 1 : 0)];
                TypeBinding bindingParameter = InferenceContext18.getParameter(this.binding.parameters, i, isVarArgs);
                TypeBinding bindingParameterToCheck;
                if (bindingParameter.isPrimitiveType() && !descriptorParameter.isPrimitiveType()) {
                    // replace primitive types by boxed equivalent for checking, e.g. int -> @NonNull Integer
                    bindingParameterToCheck = scope.environment().createAnnotatedType(scope.boxing(bindingParameter), new AnnotationBinding[] { scope.environment().getNonNullAnnotation() });
                } else {
                    bindingParameterToCheck = bindingParameter;
                }
                NullAnnotationMatching annotationStatus = NullAnnotationMatching.analyse(bindingParameterToCheck, descriptorParameter, FlowInfo.UNKNOWN);
                if (annotationStatus.isAnyMismatch()) {
                    // immediate reporting:
                    scope.problemReporter().referenceExpressionArgumentNullityMismatch(this, bindingParameter, descriptorParameter, this.descriptor, i, annotationStatus);
                }
            }
            TypeBinding returnType = this.binding.returnType;
            if (!returnType.isPrimitiveType()) {
                if (this.binding.isConstructor()) {
                    returnType = scope.environment().createAnnotatedType(this.receiverType, new AnnotationBinding[] { scope.environment().getNonNullAnnotation() });
                }
                NullAnnotationMatching annotationStatus = NullAnnotationMatching.analyse(this.descriptor.returnType, returnType, FlowInfo.UNKNOWN);
                if (annotationStatus.isAnyMismatch()) {
                    scope.problemReporter().illegalReturnRedefinition(this, this.descriptor, annotationStatus.isUnchecked(), returnType);
                }
            }
        }
    }
}
Also used : AnnotationBinding(org.eclipse.jdt.internal.compiler.lookup.AnnotationBinding) ParameterizedTypeBinding(org.eclipse.jdt.internal.compiler.lookup.ParameterizedTypeBinding) TypeBinding(org.eclipse.jdt.internal.compiler.lookup.TypeBinding) SourceTypeBinding(org.eclipse.jdt.internal.compiler.lookup.SourceTypeBinding) PolyTypeBinding(org.eclipse.jdt.internal.compiler.lookup.PolyTypeBinding) LocalTypeBinding(org.eclipse.jdt.internal.compiler.lookup.LocalTypeBinding) CompilerOptions(org.eclipse.jdt.internal.compiler.impl.CompilerOptions)

Example 12 with AnnotationBinding

use of org.eclipse.jdt.internal.compiler.lookup.AnnotationBinding in project bazel-jdt-java-toolchain by salesforce.

the class AnnotationMirrorImpl method convertJDTArrayToReflectionArray.

/**
 * Convert an array of JDT types as obtained from ElementValuePair.getValue()
 * (e.g., an Object[] containing IntConstant elements) to the type expected by
 * a reflective method invocation (e.g., int[]).
 * <p>
 * This does not handle arrays of Class, but it does handle primitives, enum constants,
 * and types such as String.
 * @param jdtValue the actual value returned by ElementValuePair.getValue() or MethodBinding.getDefault()
 * @param jdtType the return type of the annotation method binding
 * @param expectedType the type that the invoker of the method is expecting; must be an array type
 * @return an Object which is, e.g., an int[]; or null, if an array cannot be created.
 */
private Object convertJDTArrayToReflectionArray(Object jdtValue, TypeBinding jdtType, Class<?> expectedType) {
    assert null != expectedType && expectedType.isArray();
    if (!jdtType.isArrayType()) {
        // that there's some sort of syntax error.
        return null;
    }
    Object[] jdtArray;
    // See bug 261969: it's legal to pass a solo element for an array-typed value
    if (jdtValue != null && !(jdtValue instanceof Object[])) {
        // Create an array of the expected type
        jdtArray = (Object[]) Array.newInstance(jdtValue.getClass(), 1);
        jdtArray[0] = jdtValue;
    } else {
        jdtArray = (Object[]) jdtValue;
    }
    TypeBinding jdtLeafType = jdtType.leafComponentType();
    Class<?> expectedLeafType = expectedType.getComponentType();
    final int length = jdtArray.length;
    final Object returnArray = Array.newInstance(expectedLeafType, length);
    for (int i = 0; i < length; ++i) {
        Object jdtElementValue = jdtArray[i];
        if (expectedLeafType.isPrimitive() || String.class.equals(expectedLeafType)) {
            if (jdtElementValue instanceof Constant) {
                if (boolean.class.equals(expectedLeafType)) {
                    Array.setBoolean(returnArray, i, ((Constant) jdtElementValue).booleanValue());
                } else if (byte.class.equals(expectedLeafType)) {
                    Array.setByte(returnArray, i, ((Constant) jdtElementValue).byteValue());
                } else if (char.class.equals(expectedLeafType)) {
                    Array.setChar(returnArray, i, ((Constant) jdtElementValue).charValue());
                } else if (double.class.equals(expectedLeafType)) {
                    Array.setDouble(returnArray, i, ((Constant) jdtElementValue).doubleValue());
                } else if (float.class.equals(expectedLeafType)) {
                    Array.setFloat(returnArray, i, ((Constant) jdtElementValue).floatValue());
                } else if (int.class.equals(expectedLeafType)) {
                    Array.setInt(returnArray, i, ((Constant) jdtElementValue).intValue());
                } else if (long.class.equals(expectedLeafType)) {
                    Array.setLong(returnArray, i, ((Constant) jdtElementValue).longValue());
                } else if (short.class.equals(expectedLeafType)) {
                    Array.setShort(returnArray, i, ((Constant) jdtElementValue).shortValue());
                } else if (String.class.equals(expectedLeafType)) {
                    Array.set(returnArray, i, ((Constant) jdtElementValue).stringValue());
                }
            } else {
                // Primitive or string is expected, but our actual value cannot be coerced into one.
                // TODO: if the actual value is an array of primitives, should we unpack the first one?
                Factory.setArrayMatchingDummyValue(returnArray, i, expectedLeafType);
            }
        } else if (expectedLeafType.isEnum()) {
            Object returnVal = null;
            if (jdtLeafType != null && jdtLeafType.isEnum() && jdtElementValue instanceof FieldBinding) {
                FieldBinding binding = (FieldBinding) jdtElementValue;
                try {
                    Field returnedField = null;
                    returnedField = expectedLeafType.getField(new String(binding.name));
                    if (null != returnedField) {
                        returnVal = returnedField.get(null);
                    }
                } catch (NoSuchFieldException nsfe) {
                // return null
                } catch (IllegalAccessException iae) {
                // return null
                }
            }
            Array.set(returnArray, i, returnVal);
        } else if (expectedLeafType.isAnnotation()) {
            // member value is expected to be an annotation type.  Wrap it in an Annotation proxy.
            Object returnVal = null;
            if (jdtLeafType.isAnnotationType() && jdtElementValue instanceof AnnotationBinding) {
                AnnotationMirrorImpl annoMirror = (AnnotationMirrorImpl) _env.getFactory().newAnnotationMirror((AnnotationBinding) jdtElementValue);
                returnVal = Proxy.newProxyInstance(expectedLeafType.getClassLoader(), new Class[] { expectedLeafType }, annoMirror);
            }
            Array.set(returnArray, i, returnVal);
        } else {
            Array.set(returnArray, i, null);
        }
    }
    return returnArray;
}
Also used : TypeBinding(org.eclipse.jdt.internal.compiler.lookup.TypeBinding) Constant(org.eclipse.jdt.internal.compiler.impl.Constant) Field(java.lang.reflect.Field) AnnotationBinding(org.eclipse.jdt.internal.compiler.lookup.AnnotationBinding) FieldBinding(org.eclipse.jdt.internal.compiler.lookup.FieldBinding)

Example 13 with AnnotationBinding

use of org.eclipse.jdt.internal.compiler.lookup.AnnotationBinding in project bazel-jdt-java-toolchain by salesforce.

the class ElementsImpl method getAllAnnotationMirrors.

/**
 * Return all the annotation mirrors on this element, including inherited annotations.
 * Annotations are inherited only if the annotation type is meta-annotated with @Inherited,
 * and the annotation is on a class: e.g., annotations are not inherited for interfaces, methods,
 * or fields.
 */
@Override
public List<? extends AnnotationMirror> getAllAnnotationMirrors(Element e) {
    // if e is a class, walk up its superclass hierarchy looking for @Inherited annotations not already in the list
    if (e.getKind() == ElementKind.CLASS && e instanceof TypeElementImpl) {
        List<AnnotationBinding> annotations = new ArrayList<>();
        // A class can only have one annotation of a particular annotation type.
        Set<ReferenceBinding> annotationTypes = new HashSet<>();
        ReferenceBinding binding = (ReferenceBinding) ((TypeElementImpl) e)._binding;
        boolean checkIfInherited = false;
        while (null != binding) {
            if (binding instanceof ParameterizedTypeBinding) {
                binding = ((ParameterizedTypeBinding) binding).genericType();
            }
            for (AnnotationBinding annotation : Factory.getPackedAnnotationBindings(binding.getAnnotations())) {
                if (annotation == null)
                    continue;
                ReferenceBinding annotationType = annotation.getAnnotationType();
                if (checkIfInherited && (annotationType.getAnnotationTagBits() & TagBits.AnnotationInherited) == 0)
                    continue;
                if (!annotationTypes.contains(annotationType)) {
                    annotationTypes.add(annotationType);
                    annotations.add(annotation);
                }
            }
            binding = binding.superclass();
            checkIfInherited = true;
        }
        List<AnnotationMirror> list = new ArrayList<>(annotations.size());
        for (AnnotationBinding annotation : annotations) {
            list.add(_env.getFactory().newAnnotationMirror(annotation));
        }
        return Collections.unmodifiableList(list);
    } else {
        return e.getAnnotationMirrors();
    }
}
Also used : ParameterizedTypeBinding(org.eclipse.jdt.internal.compiler.lookup.ParameterizedTypeBinding) AnnotationMirror(javax.lang.model.element.AnnotationMirror) AnnotationBinding(org.eclipse.jdt.internal.compiler.lookup.AnnotationBinding) ArrayList(java.util.ArrayList) ReferenceBinding(org.eclipse.jdt.internal.compiler.lookup.ReferenceBinding) HashSet(java.util.HashSet) LinkedHashSet(java.util.LinkedHashSet)

Example 14 with AnnotationBinding

use of org.eclipse.jdt.internal.compiler.lookup.AnnotationBinding in project bazel-jdt-java-toolchain by salesforce.

the class RoundEnvImpl method collectAnnotations.

private void collectAnnotations(ReferenceBinding[] referenceBindings) {
    for (ReferenceBinding referenceBinding : referenceBindings) {
        // collect all annotations from the binary types
        if (referenceBinding instanceof ParameterizedTypeBinding) {
            referenceBinding = ((ParameterizedTypeBinding) referenceBinding).genericType();
        }
        AnnotationBinding[] annotationBindings = Factory.getPackedAnnotationBindings(referenceBinding.getAnnotations());
        for (AnnotationBinding annotationBinding : annotationBindings) {
            TypeElement anno = (TypeElement) _factory.newElement(annotationBinding.getAnnotationType());
            Element element = _factory.newElement(referenceBinding);
            _annoToUnit.put(anno, element);
        }
        FieldBinding[] fieldBindings = referenceBinding.fields();
        for (FieldBinding fieldBinding : fieldBindings) {
            annotationBindings = Factory.getPackedAnnotationBindings(fieldBinding.getAnnotations());
            for (AnnotationBinding annotationBinding : annotationBindings) {
                TypeElement anno = (TypeElement) _factory.newElement(annotationBinding.getAnnotationType());
                Element element = _factory.newElement(fieldBinding);
                _annoToUnit.put(anno, element);
            }
        }
        MethodBinding[] methodBindings = referenceBinding.methods();
        for (MethodBinding methodBinding : methodBindings) {
            annotationBindings = Factory.getPackedAnnotationBindings(methodBinding.getAnnotations());
            for (AnnotationBinding annotationBinding : annotationBindings) {
                TypeElement anno = (TypeElement) _factory.newElement(annotationBinding.getAnnotationType());
                Element element = _factory.newElement(methodBinding);
                _annoToUnit.put(anno, element);
            }
        }
        ReferenceBinding[] memberTypes = referenceBinding.memberTypes();
        collectAnnotations(memberTypes);
    }
}
Also used : ParameterizedTypeBinding(org.eclipse.jdt.internal.compiler.lookup.ParameterizedTypeBinding) AnnotationBinding(org.eclipse.jdt.internal.compiler.lookup.AnnotationBinding) TypeElement(javax.lang.model.element.TypeElement) Element(javax.lang.model.element.Element) TypeElement(javax.lang.model.element.TypeElement) FieldBinding(org.eclipse.jdt.internal.compiler.lookup.FieldBinding) MethodBinding(org.eclipse.jdt.internal.compiler.lookup.MethodBinding) ReferenceBinding(org.eclipse.jdt.internal.compiler.lookup.ReferenceBinding)

Example 15 with AnnotationBinding

use of org.eclipse.jdt.internal.compiler.lookup.AnnotationBinding in project j2cl by google.

the class JdtAnnotationUtils method getAnnotationBinding.

/**
 * Reflective access to {@link AnnotationBinding#binding}.
 *
 * <p>JDT dom classes like IAnnotationBinding would not provide annotation attributes if the
 * annotation class is not present in the compile (even when accessing a previously compiled class
 * file). For that reason we obtain here, using reflection, the private reference to the internal
 * representation, i.e. org.eclipse.jdt.internal.compiler.lookup.AnnotationBinding to extract the
 * attribute values.
 */
private static AnnotationBinding getAnnotationBinding(IAnnotationBinding annotationBinding) {
    try {
        // Access to the internal compiler class AnnotationBinding through the private field
        // binding in the dom class implementing IAnnotationBinding.
        Field bindingField = annotationBinding.getClass().getDeclaredField("binding");
        bindingField.setAccessible(true);
        return (AnnotationBinding) bindingField.get(annotationBinding);
    } catch (ReflectiveOperationException e) {
        throw new RuntimeException("Unexpectedly unable to access AnnotationBinding.binding via reflection", e);
    }
}
Also used : Field(java.lang.reflect.Field) AnnotationBinding(org.eclipse.jdt.internal.compiler.lookup.AnnotationBinding) IAnnotationBinding(org.eclipse.jdt.core.dom.IAnnotationBinding)

Aggregations

AnnotationBinding (org.eclipse.jdt.internal.compiler.lookup.AnnotationBinding)23 ReferenceBinding (org.eclipse.jdt.internal.compiler.lookup.ReferenceBinding)10 TypeBinding (org.eclipse.jdt.internal.compiler.lookup.TypeBinding)9 MethodBinding (org.eclipse.jdt.internal.compiler.lookup.MethodBinding)8 FieldBinding (org.eclipse.jdt.internal.compiler.lookup.FieldBinding)6 ParameterizedTypeBinding (org.eclipse.jdt.internal.compiler.lookup.ParameterizedTypeBinding)6 SourceTypeBinding (org.eclipse.jdt.internal.compiler.lookup.SourceTypeBinding)6 ArrayList (java.util.ArrayList)5 LookupEnvironment (org.eclipse.jdt.internal.compiler.lookup.LookupEnvironment)5 ParameterizedGenericMethodBinding (org.eclipse.jdt.internal.compiler.lookup.ParameterizedGenericMethodBinding)3 ParameterizedMethodBinding (org.eclipse.jdt.internal.compiler.lookup.ParameterizedMethodBinding)3 ProblemMethodBinding (org.eclipse.jdt.internal.compiler.lookup.ProblemMethodBinding)3 TypeVariableBinding (org.eclipse.jdt.internal.compiler.lookup.TypeVariableBinding)3 Field (java.lang.reflect.Field)2 TypeElement (javax.lang.model.element.TypeElement)2 ArrayBinding (org.eclipse.jdt.internal.compiler.lookup.ArrayBinding)2 Binding (org.eclipse.jdt.internal.compiler.lookup.Binding)2 BlockScope (org.eclipse.jdt.internal.compiler.lookup.BlockScope)2 ElementValuePair (org.eclipse.jdt.internal.compiler.lookup.ElementValuePair)2 LocalTypeBinding (org.eclipse.jdt.internal.compiler.lookup.LocalTypeBinding)2