List<IElementType> (@NotNull CharSequence text, int offset) { int startOffset = 0; int data = 0; boolean isDataSet = false; int oldStartIndex = 0; int startIndex = 0; if (offset > 0 && mySegments.getSegmentCount() > 0) { int segmentIndex = mySegments.findSegmentIndex(offset - 1) - 2; oldStartIndex = Math.max(0, segmentIndex); startIndex = oldStartIndex; do { data = mySegments.getSegmentData(startIndex); isDataSet = true; if (isInitialState(data) || startIndex == 0) break; startIndex--; } while (true); startOffset = mySegments.getSegmentStart(startIndex); } int state; if (myLexer instanceof RestartableLexer) { if (isDataSet) { state = mySegments.unpackStateFromData(data); } else { state = ((RestartableLexer)myLexer).getStartState(); } } else { state = myInitialState; } if (offset == 0 && myLexer instanceof RestartableLexer) { myLexer.start(text, startOffset, text.length(), ((RestartableLexer)myLexer).getStartState()); } else { if (myLexer instanceof RestartableLexer) { ((RestartableLexer)myLexer).start(text, startOffset, text.length(), state, createTokenIterator(startIndex)); } else { myLexer.start(text, startOffset, text.length(), state); } } Lexer lexerWrapper = new ValidatingLexerWrapper(myLexer); while (lexerWrapper.getTokenType() != null) { if (startIndex >= oldStartIndex) break; int tokenStart = lexerWrapper.getTokenStart(); int lexerState = lexerWrapper.getState(); int tokenEnd = lexerWrapper.getTokenEnd(); data = mySegments.packData(lexerWrapper.getTokenType(), lexerState, canRestart(lexerState)); if (mySegments.getSegmentStart(startIndex) != tokenStart || mySegments.getSegmentEnd(startIndex) != tokenEnd || mySegments.getSegmentData(startIndex) != data) { break; } startIndex++; lexerWrapper.advance(); } IElementType tokenType1 = null; IElementType tokenType2 = null; while (lexerWrapper.getTokenType() != null) { int lexerState = lexerWrapper.getState(); data = mySegments.packData(lexerWrapper.getTokenType(), lexerState, canRestart(lexerState)); if (tokenType1 == null && lexerWrapper.getTokenEnd() >= offset) { tokenType1 = mySegments.unpackTokenFromData(data); } if (lexerWrapper.getTokenEnd() >= offset + 1) { tokenType2 = mySegments.unpackTokenFromData(data); break; } lexerWrapper.advance(); } return Arrays.asList(tokenType1, tokenType2); }