Search in sources :

Example 6 with NodeChildData

use of com.oracle.truffle.dsl.processor.model.NodeChildData in project graal by oracle.

the class CreateCastParser method createSpecification.

@Override
public MethodSpec createSpecification(ExecutableElement method, AnnotationMirror mirror) {
    List<String> childNames = ElementUtils.getAnnotationValueList(String.class, mirror, "value");
    NodeChildData foundChild = null;
    for (String childName : childNames) {
        foundChild = getNode().findChild(childName);
        if (foundChild != null) {
            break;
        }
    }
    TypeMirror baseType = getContext().getTruffleTypes().getNode();
    if (foundChild != null) {
        baseType = foundChild.getOriginalType();
    }
    MethodSpec spec = new MethodSpec(new ParameterSpec("child", baseType));
    addDefaultFieldMethodSpec(spec);
    ParameterSpec childSpec = new ParameterSpec("castedChild", baseType);
    childSpec.setSignature(true);
    spec.addRequired(childSpec);
    return spec;
}
Also used : NodeChildData(com.oracle.truffle.dsl.processor.model.NodeChildData) TypeMirror(javax.lang.model.type.TypeMirror) MethodSpec(com.oracle.truffle.dsl.processor.model.MethodSpec) ParameterSpec(com.oracle.truffle.dsl.processor.model.ParameterSpec)

Example 7 with NodeChildData

use of com.oracle.truffle.dsl.processor.model.NodeChildData in project graal by oracle.

the class NodeParser method initializeChildren.

@SuppressWarnings("unchecked")
private void initializeChildren(NodeData node) {
    for (NodeChildData child : node.getChildren()) {
        AnnotationValue executeWithValue1 = child.getExecuteWithValue();
        List<AnnotationValue> executeWithValues = ElementUtils.resolveAnnotationValue(List.class, executeWithValue1);
        List<NodeExecutionData> executeWith = new ArrayList<>();
        for (AnnotationValue executeWithValue : executeWithValues) {
            String executeWithString = ElementUtils.resolveAnnotationValue(String.class, executeWithValue);
            if (child.getName().equals(executeWithString)) {
                child.addError(executeWithValue1, "The child node '%s' cannot be executed with itself.", executeWithString);
                continue;
            }
            NodeExecutionData found = null;
            boolean before = true;
            for (NodeExecutionData resolveChild : node.getChildExecutions()) {
                if (resolveChild.getChild() == child) {
                    before = false;
                    continue;
                }
                if (resolveChild.getIndexedName().equals(executeWithString)) {
                    found = resolveChild;
                    break;
                }
            }
            if (found == null) {
                child.addError(executeWithValue1, "The child node '%s' cannot be executed with '%s'. The child node was not found.", child.getName(), executeWithString);
                continue;
            } else if (!before) {
                child.addError(executeWithValue1, "The child node '%s' cannot be executed with '%s'. The node %s is executed after the current node.", child.getName(), executeWithString, executeWithString);
                continue;
            }
            executeWith.add(found);
        }
        child.setExecuteWith(executeWith);
    }
    for (NodeChildData child : node.getChildren()) {
        TypeMirror nodeType = child.getNodeType();
        NodeData fieldNodeData = parseChildNodeData(node, child, ElementUtils.fromTypeMirror(nodeType));
        child.setNode(fieldNodeData);
        if (fieldNodeData == null || fieldNodeData.hasErrors()) {
            child.addError("Node type '%s' is invalid or not a subclass of Node.", ElementUtils.getQualifiedName(nodeType));
        } else {
            List<ExecutableTypeData> types = child.findGenericExecutableTypes(context);
            if (types.isEmpty()) {
                AnnotationValue executeWithValue = child.getExecuteWithValue();
                child.addError(executeWithValue, "No generic execute method found with %s evaluated arguments for node type %s and frame types %s.", child.getExecuteWith().size(), ElementUtils.getSimpleName(nodeType), ElementUtils.getUniqueIdentifiers(createAllowedChildFrameTypes(node)));
            }
        }
    }
}
Also used : ExecutableTypeData(com.oracle.truffle.dsl.processor.model.ExecutableTypeData) NodeChildData(com.oracle.truffle.dsl.processor.model.NodeChildData) NodeExecutionData(com.oracle.truffle.dsl.processor.model.NodeExecutionData) ArrayCodeTypeMirror(com.oracle.truffle.dsl.processor.java.model.CodeTypeMirror.ArrayCodeTypeMirror) TypeMirror(javax.lang.model.type.TypeMirror) ArrayList(java.util.ArrayList) AnnotationValue(javax.lang.model.element.AnnotationValue) NodeData(com.oracle.truffle.dsl.processor.model.NodeData)

Example 8 with NodeChildData

use of com.oracle.truffle.dsl.processor.model.NodeChildData in project graal by oracle.

the class NodeParser method initializeExecutableTypes.

private void initializeExecutableTypes(NodeData node) {
    List<ExecutableTypeData> allExecutes = node.getExecutableTypes();
    Set<String> inconsistentFrameTypes = new HashSet<>();
    TypeMirror frameType = null;
    for (ExecutableTypeData execute : allExecutes) {
        TypeMirror frame = execute.getFrameParameter();
        TypeMirror resolvedFrameType;
        if (frame != null) {
            resolvedFrameType = frame;
            if (frameType == null) {
                frameType = resolvedFrameType;
            } else if (!ElementUtils.typeEquals(frameType, resolvedFrameType)) {
                // found inconsistent frame types
                inconsistentFrameTypes.add(ElementUtils.getSimpleName(frameType));
                inconsistentFrameTypes.add(ElementUtils.getSimpleName(resolvedFrameType));
            }
        }
    }
    if (!inconsistentFrameTypes.isEmpty()) {
        // ensure they are sorted somehow
        List<String> inconsistentFrameTypesList = new ArrayList<>(inconsistentFrameTypes);
        Collections.sort(inconsistentFrameTypesList);
        node.addError("Invalid inconsistent frame types %s found for the declared execute methods. The frame type must be identical for all execute methods.", inconsistentFrameTypesList);
    }
    if (frameType == null) {
        frameType = context.getType(void.class);
    }
    node.setFrameType(frameType);
    boolean genericFound = false;
    for (ExecutableTypeData type : node.getExecutableTypes()) {
        if (!type.hasUnexpectedValue(context)) {
            genericFound = true;
            break;
        }
    }
    // no generic executes
    if (!genericFound) {
        node.addError("No accessible and overridable generic execute method found. Generic execute methods usually have the " + "signature 'public abstract {Type} execute(VirtualFrame)' and must not throw any checked exceptions.");
    }
    int nodeChildDeclarations = 0;
    int nodeChildDeclarationsRequired = 0;
    List<NodeExecutionData> executions = node.getChildExecutions();
    for (NodeExecutionData execution : executions) {
        if (execution.getChild() == null) {
            nodeChildDeclarationsRequired = execution.getIndex() + 1;
        } else {
            nodeChildDeclarations++;
        }
    }
    List<String> requireNodeChildDeclarations = new ArrayList<>();
    for (ExecutableTypeData type : allExecutes) {
        if (type.getEvaluatedCount() < nodeChildDeclarationsRequired) {
            requireNodeChildDeclarations.add(ElementUtils.createReferenceName(type.getMethod()));
        }
    }
    if (!requireNodeChildDeclarations.isEmpty()) {
        node.addError("Not enough child node declarations found. Please annotate the node class with addtional @NodeChild annotations or remove all execute methods that do not provide all evaluated values. " + "The following execute methods do not provide all evaluated values for the expected signature size %s: %s.", executions.size(), requireNodeChildDeclarations);
    }
    if (nodeChildDeclarations > 0 && executions.size() == node.getMinimalEvaluatedParameters()) {
        for (NodeChildData child : node.getChildren()) {
            child.addError("Unnecessary @NodeChild declaration. All evaluated child values are provided as parameters in execute methods.");
        }
    }
}
Also used : ExecutableTypeData(com.oracle.truffle.dsl.processor.model.ExecutableTypeData) NodeExecutionData(com.oracle.truffle.dsl.processor.model.NodeExecutionData) NodeChildData(com.oracle.truffle.dsl.processor.model.NodeChildData) ArrayList(java.util.ArrayList) ArrayCodeTypeMirror(com.oracle.truffle.dsl.processor.java.model.CodeTypeMirror.ArrayCodeTypeMirror) TypeMirror(javax.lang.model.type.TypeMirror) HashSet(java.util.HashSet)

Example 9 with NodeChildData

use of com.oracle.truffle.dsl.processor.model.NodeChildData in project graal by oracle.

the class FlatNodeGenFactory method parameterBoxingElimination.

/*
     * It duplicates a group into small subgroups of specializations that don't need boxing when
     * executing the children.
     */
private List<BoxingSplit> parameterBoxingElimination(SpecializationGroup group, int evaluatedcount) {
    if (!boxingEliminationEnabled) {
        return Collections.emptyList();
    }
    List<SpecializationData> allSpecializations = group.collectSpecializations();
    List<Set<TypeGuard>> signatures = new ArrayList<>();
    List<List<SpecializationData>> signatureSpecializations = new ArrayList<>();
    for (SpecializationData specialization : allSpecializations) {
        int index = -1;
        List<TypeGuard> guards = new ArrayList<>();
        for (Parameter p : specialization.getSignatureParameters()) {
            index++;
            if (!ElementUtils.isPrimitive(p.getType())) {
                continue;
            } else if (index < evaluatedcount) {
                continue;
            } else {
                NodeChildData child = p.getSpecification().getExecution().getChild();
                if (child != null && child.findExecutableType(p.getType()) == null) {
                    // type cannot be executed so it cannot be eliminated
                    continue;
                }
            }
            guards.add(new TypeGuard(p.getType(), index));
        }
        if (!guards.isEmpty()) {
            boolean directFound = false;
            for (int i = 0; i < signatures.size(); i++) {
                if (guards.containsAll(signatures.get(i))) {
                    if (signatures.get(i).containsAll(guards)) {
                        directFound = true;
                    }
                    signatureSpecializations.get(i).add(specialization);
                }
            }
            if (!directFound) {
                signatures.add(new LinkedHashSet<>(guards));
                List<SpecializationData> specializations = new ArrayList<>();
                specializations.add(specialization);
                signatureSpecializations.add(specializations);
            }
        }
    }
    List<BoxingSplit> groups = new ArrayList<>();
    for (int i = 0; i < signatureSpecializations.size(); i++) {
        List<SpecializationData> groupedSpecialization = signatureSpecializations.get(i);
        if (allSpecializations.size() == groupedSpecialization.size()) {
            // contains all specializations does not make sense to group
            continue;
        }
        Set<TypeGuard> signature = signatures.get(i);
        TypeMirror[] signatureMirrors = new TypeMirror[signature.size()];
        int index = 0;
        for (TypeGuard typeGuard : signature) {
            signatureMirrors[index] = typeGuard.getType();
            index++;
        }
        groups.add(new BoxingSplit(SpecializationGroup.create(groupedSpecialization), signatureMirrors));
    }
    Collections.sort(groups, new Comparator<BoxingSplit>() {

        public int compare(BoxingSplit o1, BoxingSplit o2) {
            return Integer.compare(o2.primitiveSignature.length, o1.primitiveSignature.length);
        }
    });
    return groups;
}
Also used : Set(java.util.Set) HashSet(java.util.HashSet) LinkedHashSet(java.util.LinkedHashSet) NodeChildData(com.oracle.truffle.dsl.processor.model.NodeChildData) SpecializationData(com.oracle.truffle.dsl.processor.model.SpecializationData) ArrayList(java.util.ArrayList) DeclaredCodeTypeMirror(com.oracle.truffle.dsl.processor.java.model.CodeTypeMirror.DeclaredCodeTypeMirror) ArrayCodeTypeMirror(com.oracle.truffle.dsl.processor.java.model.CodeTypeMirror.ArrayCodeTypeMirror) GeneratedTypeMirror(com.oracle.truffle.dsl.processor.java.model.GeneratedTypeMirror) TypeMirror(javax.lang.model.type.TypeMirror) Parameter(com.oracle.truffle.dsl.processor.model.Parameter) List(java.util.List) ArrayList(java.util.ArrayList) TypeGuard(com.oracle.truffle.dsl.processor.parser.SpecializationGroup.TypeGuard)

Example 10 with NodeChildData

use of com.oracle.truffle.dsl.processor.model.NodeChildData in project graal by oracle.

the class FlatNodeGenFactory method resolveTargetExecutable.

private ExecutableTypeData resolveTargetExecutable(NodeExecutionData execution, TypeMirror target) {
    NodeChildData child = execution.getChild();
    if (child == null) {
        return null;
    }
    ExecutableTypeData targetExecutable = child.findExecutableType(target);
    if (targetExecutable == null) {
        targetExecutable = child.findAnyGenericExecutableType(context);
    }
    return targetExecutable;
}
Also used : ExecutableTypeData(com.oracle.truffle.dsl.processor.model.ExecutableTypeData) NodeChildData(com.oracle.truffle.dsl.processor.model.NodeChildData)

Aggregations

NodeChildData (com.oracle.truffle.dsl.processor.model.NodeChildData)13 ArrayList (java.util.ArrayList)10 TypeMirror (javax.lang.model.type.TypeMirror)8 ArrayCodeTypeMirror (com.oracle.truffle.dsl.processor.java.model.CodeTypeMirror.ArrayCodeTypeMirror)7 CodeExecutableElement (com.oracle.truffle.dsl.processor.java.model.CodeExecutableElement)6 CodeVariableElement (com.oracle.truffle.dsl.processor.java.model.CodeVariableElement)6 NodeExecutionData (com.oracle.truffle.dsl.processor.model.NodeExecutionData)6 ExecutableElement (javax.lang.model.element.ExecutableElement)5 ExecutableTypeData (com.oracle.truffle.dsl.processor.model.ExecutableTypeData)4 HashSet (java.util.HashSet)4 NodeFieldData (com.oracle.truffle.dsl.processor.model.NodeFieldData)3 List (java.util.List)3 AnnotationMirror (javax.lang.model.element.AnnotationMirror)3 AnnotationValue (javax.lang.model.element.AnnotationValue)3 VariableElement (javax.lang.model.element.VariableElement)3 Child (com.oracle.truffle.api.nodes.Node.Child)2 CodeTree (com.oracle.truffle.dsl.processor.java.model.CodeTree)2 CodeTreeBuilder (com.oracle.truffle.dsl.processor.java.model.CodeTreeBuilder)2 DeclaredCodeTypeMirror (com.oracle.truffle.dsl.processor.java.model.CodeTypeMirror.DeclaredCodeTypeMirror)2 GeneratedTypeMirror (com.oracle.truffle.dsl.processor.java.model.GeneratedTypeMirror)2