Search in sources :

Example 6 with SyntheticCompositeNode

use of org.eclipse.xtext.nodemodel.impl.SyntheticCompositeNode in project n4js by eclipse.

the class AbstractSmokeTester method skipNodesInBetween.

private void skipNodesInBetween(CharSequence input) throws Exception {
    String string = input.toString();
    Script script = completeScript(string);
    if (script != null) {
        XtextResource resource = (XtextResource) script.eResource();
        ICompositeNode rootNode = resource.getParseResult().getRootNode();
        ReplaceRegion region = null;
        for (INode node : rootNode.getAsTreeIterable()) {
            if (node instanceof ICompositeNode && !(node instanceof SyntheticCompositeNode)) {
                ICompositeNode casted = (ICompositeNode) node;
                int offset = node.getTotalOffset();
                int length = node.getTotalLength();
                if (length != 0) {
                    if (casted.getFirstChild().equals(casted.getLastChild())) {
                        if (region == null || region.getOffset() != offset || region.getLength() != length) {
                            region = new ReplaceRegion(offset, length, "");
                            StringBuilder builder = new StringBuilder(rootNode.getText());
                            region.applyTo(builder);
                            processFile(builder.toString());
                        }
                    }
                }
            }
        }
    }
}
Also used : Script(org.eclipse.n4js.n4JS.Script) SyntheticCompositeNode(org.eclipse.xtext.nodemodel.impl.SyntheticCompositeNode) INode(org.eclipse.xtext.nodemodel.INode) ReplaceRegion(org.eclipse.xtext.util.ReplaceRegion) ICompositeNode(org.eclipse.xtext.nodemodel.ICompositeNode) XtextResource(org.eclipse.xtext.resource.XtextResource)

Example 7 with SyntheticCompositeNode

use of org.eclipse.xtext.nodemodel.impl.SyntheticCompositeNode in project xtext-core by eclipse.

the class PartialParsingHelper method isInvalidRootNode.

protected boolean isInvalidRootNode(ICompositeNode rootNode, ICompositeNode candidate) {
    int endOffset = candidate.getTotalEndOffset();
    if (candidate instanceof SyntheticCompositeNode)
        return true;
    if (candidate.getGrammarElement() instanceof RuleCall) {
        AbstractRule rule = ((RuleCall) candidate.getGrammarElement()).getRule();
        if (!(rule instanceof ParserRule))
            return true;
        ParserRule casted = (ParserRule) rule;
        if (GrammarUtil.isDatatypeRule(casted) || casted.isFragment() || !casted.getParameters().isEmpty()) {
            return true;
        }
        if (isInvalidDueToPredicates((AbstractElement) candidate.getGrammarElement()))
            return true;
    }
    if (candidate.getGrammarElement() instanceof Action) {
        return true;
    }
    if (endOffset == rootNode.getTotalEndOffset()) {
        INode lastChild = getLastChild(candidate);
        if (lastChild instanceof ICompositeNode) {
            INode lastLeaf = getLastLeaf(candidate);
            if (isInvalidLastChildNode(candidate, lastLeaf)) {
                return true;
            }
        }
        if (isInvalidLastChildNode(candidate, lastChild)) {
            return true;
        }
    }
    return false;
}
Also used : SyntheticCompositeNode(org.eclipse.xtext.nodemodel.impl.SyntheticCompositeNode) ParserRule(org.eclipse.xtext.ParserRule) Action(org.eclipse.xtext.Action) INode(org.eclipse.xtext.nodemodel.INode) ICompositeNode(org.eclipse.xtext.nodemodel.ICompositeNode) AbstractRule(org.eclipse.xtext.AbstractRule) RuleCall(org.eclipse.xtext.RuleCall)

Example 8 with SyntheticCompositeNode

use of org.eclipse.xtext.nodemodel.impl.SyntheticCompositeNode in project xtext-core by eclipse.

the class PartialParsingHelper method reparse.

@Override
@SuppressWarnings({ "unchecked", "rawtypes" })
public IParseResult reparse(IParser parser, IParseResult previousParseResult, ReplaceRegion changedRegion) {
    if (parser == null)
        throw new NullPointerException("parser may not be null");
    if (previousParseResult == null) {
        throw new NullPointerException("previousParseResult and previousParseResult.rootNode may not be null");
    }
    ICompositeNode oldRootNode = previousParseResult.getRootNode();
    if (changedRegion.getEndOffset() > oldRootNode.getTotalLength()) {
        log.error("Invalid " + changedRegion + " originalLength=" + oldRootNode.getTotalLength());
        return fullyReparse(parser, previousParseResult, changedRegion);
    }
    if (changedRegion.getOffset() >= oldRootNode.getTotalLength() && changedRegion.getText().trim().length() == 0) {
        return fullyReparse(parser, previousParseResult, changedRegion);
    }
    ReplaceRegion replaceRegion;
    if (tokenRegionProvider != null) {
        replaceRegion = tokenRegionProvider.getTokenReplaceRegion(insertChangeIntoReplaceRegion(oldRootNode, changedRegion), changedRegion);
    } else {
        replaceRegion = changedRegion;
    }
    if (isNullEdit(oldRootNode, replaceRegion)) {
        return previousParseResult;
    }
    PartialParsingPointers parsingPointers = calculatePartialParsingPointers(previousParseResult, replaceRegion.getOffset(), replaceRegion.getLength());
    List<ICompositeNode> validReplaceRootNodes = parsingPointers.getValidReplaceRootNodes();
    ICompositeNode oldCompositeNode = null;
    String reparseRegion = "";
    for (int i = validReplaceRootNodes.size() - 1; i >= 0; --i) {
        oldCompositeNode = validReplaceRootNodes.get(i);
        if (!(oldCompositeNode instanceof SyntheticCompositeNode) && !isRangePartOfExceedingLookAhead((CompositeNode) oldCompositeNode, replaceRegion)) {
            boolean replaceAtEnd = oldCompositeNode.getTotalEndOffset() == replaceRegion.getEndOffset();
            reparseRegion = insertChangeIntoReplaceRegion(oldCompositeNode, replaceRegion);
            if (!"".equals(reparseRegion)) {
                if (!replaceAtEnd || !Character.isWhitespace(reparseRegion.charAt(reparseRegion.length() - 1))) {
                    if (log.isDebugEnabled()) {
                        log.debug("replace region: [" + oldCompositeNode.getTotalOffset() + " / length: " + oldCompositeNode.getTotalLength() + " of [" + oldRootNode.getTotalOffset() + " / lenght: " + oldRootNode.getTotalLength() + "]");
                    }
                    break;
                }
            }
        }
    }
    if (oldCompositeNode == null || reparseRegion.equals("") || oldCompositeNode == oldRootNode) {
        return fullyReparse(parser, previousParseResult, replaceRegion);
    }
    EObject entryRuleOrRuleCall = parsingPointers.findEntryRuleOrRuleCall(oldCompositeNode);
    IParseResult newParseResult = null;
    try {
        if (entryRuleOrRuleCall instanceof RuleCall)
            newParseResult = parser.parse((RuleCall) entryRuleOrRuleCall, new StringReader(reparseRegion), oldCompositeNode.getLookAhead());
        else
            newParseResult = parser.parse((ParserRule) entryRuleOrRuleCall, new StringReader(reparseRegion));
    } catch (ParseException exc) {
    }
    if (newParseResult == null || newParseResult.hasSyntaxErrors()) {
        // on error fully reparse
        return fullyReparse(parser, previousParseResult, replaceRegion);
    }
    if (oldRootNode.equals(oldCompositeNode)) {
        unloadSemanticObject(previousParseResult.getRootASTElement());
        return newParseResult;
    }
    EObject oldSemanticParentElement = oldCompositeNode.getParent().getSemanticElement();
    EObject oldSemanticElement = null;
    if (oldCompositeNode.hasDirectSemanticElement()) {
        oldSemanticElement = oldCompositeNode.getSemanticElement();
    } else {
        List<ICompositeNode> nodesEnclosingRegion = parsingPointers.getNodesEnclosingRegion();
        for (int i = nodesEnclosingRegion.size() - 1; i >= 0; --i) {
            ICompositeNode enclosingNode = nodesEnclosingRegion.get(i);
            if (enclosingNode == oldCompositeNode) {
                break;
            }
            if (enclosingNode.hasDirectSemanticElement())
                oldSemanticElement = enclosingNode.getSemanticElement();
        }
        if (oldSemanticElement == null)
            return fullyReparse(parser, previousParseResult, replaceRegion);
    }
    if (oldSemanticElement == oldSemanticParentElement) {
        throw new IllegalStateException("oldParent == oldElement");
    }
    if (oldSemanticParentElement != null) {
        EStructuralFeature feature = oldSemanticElement.eContainingFeature();
        if (feature == null)
            return fullyReparse(parser, previousParseResult, replaceRegion);
        oldSemanticParentElement = oldSemanticElement.eContainer();
        if (feature.isMany()) {
            List featureValueList = (List) oldSemanticParentElement.eGet(feature);
            int index = featureValueList.indexOf(oldSemanticElement);
            unloadSemanticObject(oldSemanticElement);
            EObject newSemanticObject = newParseResult.getRootASTElement();
            if (newSemanticObject != null) {
                featureValueList.set(index, newParseResult.getRootASTElement());
            } else {
                featureValueList.remove(index);
            }
        } else {
            unloadSemanticObject(oldSemanticElement);
            oldSemanticParentElement.eSet(feature, newParseResult.getRootASTElement());
        }
        ((ParseResult) newParseResult).setRootASTElement(previousParseResult.getRootASTElement());
    } else {
        unloadSemanticObject(oldSemanticElement);
    }
    if (oldCompositeNode != oldRootNode) {
        nodeModelBuilder.replaceAndTransferLookAhead(oldCompositeNode, newParseResult.getRootNode());
        ((ParseResult) newParseResult).setRootNode(oldRootNode);
        StringBuilder builder = new StringBuilder(oldRootNode.getText());
        replaceRegion.applyTo(builder);
        nodeModelBuilder.setCompleteContent(oldRootNode, builder.toString());
    }
    return newParseResult;
}
Also used : SyntheticCompositeNode(org.eclipse.xtext.nodemodel.impl.SyntheticCompositeNode) ParseResult(org.eclipse.xtext.parser.ParseResult) IParseResult(org.eclipse.xtext.parser.IParseResult) EStructuralFeature(org.eclipse.emf.ecore.EStructuralFeature) RuleCall(org.eclipse.xtext.RuleCall) ReplaceRegion(org.eclipse.xtext.util.ReplaceRegion) EObject(org.eclipse.emf.ecore.EObject) StringReader(java.io.StringReader) ICompositeNode(org.eclipse.xtext.nodemodel.ICompositeNode) ArrayList(java.util.ArrayList) List(java.util.List) IParseResult(org.eclipse.xtext.parser.IParseResult) ParseException(org.eclipse.xtext.parser.ParseException)

Aggregations

SyntheticCompositeNode (org.eclipse.xtext.nodemodel.impl.SyntheticCompositeNode)8 ICompositeNode (org.eclipse.xtext.nodemodel.ICompositeNode)6 EObject (org.eclipse.emf.ecore.EObject)4 INode (org.eclipse.xtext.nodemodel.INode)4 ReplaceRegion (org.eclipse.xtext.util.ReplaceRegion)4 RuleCall (org.eclipse.xtext.RuleCall)3 Test (org.junit.Test)3 StringReader (java.io.StringReader)2 ArrayList (java.util.ArrayList)2 List (java.util.List)2 EStructuralFeature (org.eclipse.emf.ecore.EStructuralFeature)2 ParserRule (org.eclipse.xtext.ParserRule)2 IParseResult (org.eclipse.xtext.parser.IParseResult)2 ParseException (org.eclipse.xtext.parser.ParseException)2 ParseResult (org.eclipse.xtext.parser.ParseResult)2 XtextResource (org.eclipse.xtext.resource.XtextResource)2 Script (org.eclipse.n4js.n4JS.Script)1 AbstractRule (org.eclipse.xtext.AbstractRule)1 Action (org.eclipse.xtext.Action)1 Grammar (org.eclipse.xtext.Grammar)1