Search in sources :

Example 6 with ElementUtils.findAnnotationMirror

use of com.oracle.truffle.dsl.processor.java.ElementUtils.findAnnotationMirror in project graal by oracle.

the class ExportsParser method initializeExportedMethod.

private void initializeExportedMethod(Map<String, NodeData> parsedNodeCache, ExportsData model, ExportMessageData exportedElement) {
    ExecutableElement exportedMethod = (ExecutableElement) exportedElement.getMessageElement();
    LibraryMessage message = exportedElement.getResolvedMessage();
    ExportsLibrary exportsLibrary = exportedElement.getExportsLibrary();
    if (ElementUtils.getVisibility(exportedMethod.getModifiers()) == Modifier.PRIVATE) {
        exportedElement.addError("The exported method must not be private. " + "Increase visibility to resolve this.");
        return;
    }
    List<TypeMirror> cachedAnnotations = NodeParser.getCachedAnnotations();
    List<VariableElement> cachedNodes = new ArrayList<>();
    List<VariableElement> cachedLibraries = new ArrayList<>();
    int realParameterCount = 0;
    parameters: for (VariableElement exportParameter : exportedMethod.getParameters()) {
        AnnotationMirror cachedMirror = null;
        for (TypeMirror cachedAnnotation : cachedAnnotations) {
            AnnotationMirror found = ElementUtils.findAnnotationMirror(exportParameter.getAnnotationMirrors(), cachedAnnotation);
            if (found == null) {
                continue;
            }
            if (cachedMirror == null) {
                cachedMirror = found;
            } else {
                StringBuilder b = new StringBuilder();
                String sep = "";
                for (TypeMirror stringCachedAnnotation : cachedAnnotations) {
                    b.append(sep);
                    b.append("@");
                    b.append(ElementUtils.getSimpleName(stringCachedAnnotation));
                    sep = ", ";
                }
                exportedElement.addError(exportParameter, "The following annotations are mutually exclusive for a parameter: %s.", b.toString());
                continue parameters;
            }
        }
        AnnotationMirror cachedLibraryMirror = findAnnotationMirror(exportParameter.getAnnotationMirrors(), types.CachedLibrary);
        if (cachedLibraryMirror != null) {
            cachedLibraries.add(exportParameter);
        } else if (cachedMirror != null) {
            cachedNodes.add(exportParameter);
        } else {
            realParameterCount++;
        }
    }
    verifyMethodSignature(model.getTemplateType(), message, exportedElement, exportedMethod, exportsLibrary.getReceiverType(), realParameterCount, true);
    boolean aotExcluded = ElementUtils.findAnnotationMirror(exportedMethod, types.GenerateAOT_Exclude) != null;
    if (aotExcluded && message.getName().equals("accepts")) {
        exportedElement.addError("Cannot use with @%s.%s with the accepts message. The accepts message must always be usable for AOT.", getSimpleName(types.GenerateAOT), getSimpleName(types.GenerateAOT_Exclude));
    }
    if (exportedElement.hasErrors()) {
        return;
    }
    if (!cachedNodes.isEmpty() || !cachedLibraries.isEmpty()) {
        String nodeName = firstLetterUpperCase(exportedMethod.getSimpleName().toString()) + "Node_";
        CodeTypeElement type = GeneratorUtils.createClass(model, null, modifiers(PUBLIC, STATIC), nodeName, types.Node);
        AnnotationMirror importStatic = findAnnotationMirror(model.getMessageElement(), types.ImportStatic);
        if (importStatic != null) {
            type.getAnnotationMirrors().add(importStatic);
        }
        type.getAnnotationMirrors().add(exportedElement.getMessageAnnotation());
        CodeExecutableElement element = CodeExecutableElement.clone(exportedMethod);
        element.getParameters().clear();
        element.getParameters().addAll(exportedMethod.getParameters());
        DeclaredType specializationType = types.Specialization;
        CodeAnnotationMirror specialization = new CodeAnnotationMirror(specializationType);
        specialization.setElementValue(ElementUtils.findExecutableElement(specializationType, "limit"), ElementUtils.getAnnotationValue(exportedElement.getMessageAnnotation(), "limit", false));
        element.getAnnotationMirrors().clear();
        element.addAnnotationMirror(specialization);
        if (aotExcluded) {
            element.getAnnotationMirrors().add(new CodeAnnotationMirror(types.GenerateAOT_Exclude));
        }
        boolean isStatic = element.getModifiers().contains(Modifier.STATIC);
        if (!isStatic) {
            element.getParameters().add(0, new CodeVariableElement(exportedElement.getReceiverType(), "this"));
            element.getModifiers().add(Modifier.STATIC);
        }
        type.add(element);
        NodeData parsedNodeData = parseNode(parsedNodeCache, type, exportedElement, Collections.emptyList());
        if (parsedNodeData == null) {
            exportedElement.addError("Error could not parse synthetic node: %s", element);
        }
        element.setEnclosingElement(exportedMethod.getEnclosingElement());
        exportedElement.setSpecializedNode(parsedNodeData);
    }
    if (exportsLibrary.isExplicitReceiver() && !exportedMethod.getModifiers().contains(STATIC)) {
        exportedElement.addError("Exported method must be static. @%s annotated types with explcit receiverClass must only contain static methods.", types.ExportLibrary.asElement().getSimpleName().toString());
    }
}
Also used : CodeAnnotationMirror(com.oracle.truffle.dsl.processor.java.model.CodeAnnotationMirror) CodeExecutableElement(com.oracle.truffle.dsl.processor.java.model.CodeExecutableElement) CodeExecutableElement(com.oracle.truffle.dsl.processor.java.model.CodeExecutableElement) ExecutableElement(javax.lang.model.element.ExecutableElement) ArrayList(java.util.ArrayList) CodeVariableElement(com.oracle.truffle.dsl.processor.java.model.CodeVariableElement) VariableElement(javax.lang.model.element.VariableElement) NodeData(com.oracle.truffle.dsl.processor.model.NodeData) ElementUtils.findAnnotationMirror(com.oracle.truffle.dsl.processor.java.ElementUtils.findAnnotationMirror) CodeAnnotationMirror(com.oracle.truffle.dsl.processor.java.model.CodeAnnotationMirror) AnnotationMirror(javax.lang.model.element.AnnotationMirror) ElementUtils.fromTypeMirror(com.oracle.truffle.dsl.processor.java.ElementUtils.fromTypeMirror) TypeMirror(javax.lang.model.type.TypeMirror) CodeTypeElement(com.oracle.truffle.dsl.processor.java.model.CodeTypeElement) CodeVariableElement(com.oracle.truffle.dsl.processor.java.model.CodeVariableElement) DeclaredType(javax.lang.model.type.DeclaredType)

Example 7 with ElementUtils.findAnnotationMirror

use of com.oracle.truffle.dsl.processor.java.ElementUtils.findAnnotationMirror in project graal by oracle.

the class NodeParser method parseFields.

private List<NodeFieldData> parseFields(List<TypeElement> typeHierarchy, List<? extends Element> elements) {
    Set<String> names = new HashSet<>();
    List<NodeFieldData> fields = new ArrayList<>();
    for (VariableElement field : ElementFilter.fieldsIn(elements)) {
        if (field.getModifiers().contains(Modifier.STATIC)) {
            continue;
        } else if (ElementUtils.findAnnotationMirror(field, types.Executed) != null) {
            continue;
        }
        if (field.getModifiers().contains(Modifier.PUBLIC) || field.getModifiers().contains(Modifier.PROTECTED)) {
            String name = field.getSimpleName().toString();
            fields.add(new NodeFieldData(field, null, field, false));
            names.add(name);
        }
    }
    List<TypeElement> reversedTypeHierarchy = new ArrayList<>(typeHierarchy);
    Collections.reverse(reversedTypeHierarchy);
    for (TypeElement typeElement : reversedTypeHierarchy) {
        AnnotationMirror nodeChildrenMirror = findAnnotationMirror(typeElement, types.NodeFields);
        List<AnnotationMirror> children = collectAnnotations(nodeChildrenMirror, "value", typeElement, types.NodeField);
        for (AnnotationMirror mirror : children) {
            String name = firstLetterLowerCase(getAnnotationValue(String.class, mirror, "name"));
            TypeMirror type = getAnnotationValue(TypeMirror.class, mirror, "type");
            if (type != null) {
                NodeFieldData field = new NodeFieldData(typeElement, mirror, new CodeVariableElement(type, name), true);
                if (name.isEmpty()) {
                    field.addError(getAnnotationValue(mirror, "name"), "Field name cannot be empty.");
                } else if (names.contains(name)) {
                    field.addError(getAnnotationValue(mirror, "name"), "Duplicate field name '%s'.", name);
                }
                names.add(name);
                fields.add(field);
            } else {
            // Type is null here. This indicates that the type could not be resolved.
            // The Java compiler will subsequently raise the appropriate error.
            }
        }
    }
    for (NodeFieldData nodeFieldData : fields) {
        nodeFieldData.setGetter(findGetter(elements, nodeFieldData.getName(), nodeFieldData.getType()));
        nodeFieldData.setSetter(findSetter(elements, nodeFieldData.getName(), nodeFieldData.getType()));
    }
    return fields;
}
Also used : TypeElement(javax.lang.model.element.TypeElement) CodeTypeElement(com.oracle.truffle.dsl.processor.java.model.CodeTypeElement) ArrayList(java.util.ArrayList) VariableElement(javax.lang.model.element.VariableElement) CodeVariableElement(com.oracle.truffle.dsl.processor.java.model.CodeVariableElement) ElementUtils.findAnnotationMirror(com.oracle.truffle.dsl.processor.java.ElementUtils.findAnnotationMirror) AnnotationMirror(javax.lang.model.element.AnnotationMirror) NodeFieldData(com.oracle.truffle.dsl.processor.model.NodeFieldData) ElementUtils.fromTypeMirror(com.oracle.truffle.dsl.processor.java.ElementUtils.fromTypeMirror) CodeTypeMirror(com.oracle.truffle.dsl.processor.java.model.CodeTypeMirror) ArrayCodeTypeMirror(com.oracle.truffle.dsl.processor.java.model.CodeTypeMirror.ArrayCodeTypeMirror) TypeMirror(javax.lang.model.type.TypeMirror) CodeVariableElement(com.oracle.truffle.dsl.processor.java.model.CodeVariableElement) LinkedHashSet(java.util.LinkedHashSet) HashSet(java.util.HashSet)

Aggregations

ElementUtils.findAnnotationMirror (com.oracle.truffle.dsl.processor.java.ElementUtils.findAnnotationMirror)7 ArrayList (java.util.ArrayList)7 AnnotationMirror (javax.lang.model.element.AnnotationMirror)7 TypeMirror (javax.lang.model.type.TypeMirror)7 ElementUtils.fromTypeMirror (com.oracle.truffle.dsl.processor.java.ElementUtils.fromTypeMirror)6 CodeVariableElement (com.oracle.truffle.dsl.processor.java.model.CodeVariableElement)6 VariableElement (javax.lang.model.element.VariableElement)6 CodeTypeElement (com.oracle.truffle.dsl.processor.java.model.CodeTypeElement)5 ArrayCodeTypeMirror (com.oracle.truffle.dsl.processor.java.model.CodeTypeMirror.ArrayCodeTypeMirror)5 CodeExecutableElement (com.oracle.truffle.dsl.processor.java.model.CodeExecutableElement)4 CodeTypeMirror (com.oracle.truffle.dsl.processor.java.model.CodeTypeMirror)4 HashSet (java.util.HashSet)4 LinkedHashSet (java.util.LinkedHashSet)4 ExecutableElement (javax.lang.model.element.ExecutableElement)4 SpecializationData (com.oracle.truffle.dsl.processor.model.SpecializationData)3 List (java.util.List)3 TypeElement (javax.lang.model.element.TypeElement)3 DSLExpression (com.oracle.truffle.dsl.processor.expression.DSLExpression)2 DSLExpressionResolver (com.oracle.truffle.dsl.processor.expression.DSLExpressionResolver)2 ElementUtils.getAnnotationValue (com.oracle.truffle.dsl.processor.java.ElementUtils.getAnnotationValue)2