blob: f549926f218739cee5410489121a90a3ffa1b035 [file] [log] [blame]
/*
* Copyright 2014 Google Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except
* in compliance with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software distributed under the License
* is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
* or implied. See the License for the specific language governing permissions and limitations under
* the License.
*/
package com.google.gwt.core.ext.linker.impl;
import com.google.gwt.core.ext.linker.StatementRanges;
import com.google.gwt.thirdparty.guava.common.collect.Lists;
import java.util.List;
/**
* An efficient StatementRanges extractor.
* <p>
* Efficient extraction comes with the restriction that extracted ranges must be consecutive to
* avoid having the seek within the subject StatementRanges instance.
*/
public class StatementRangesExtractor {
private int lastRangeEndPosition;
private int statementRangeIndex;
private final StatementRanges statementRanges;
public StatementRangesExtractor(StatementRanges statementRanges) {
this.statementRanges = statementRanges;
}
public StatementRanges extract(int rangeStartPosition, int rangeEndPosition) {
assert statementRangeIndex
< statementRanges.numStatements() : "Ranges can't be extracted past the end.";
skipTo(rangeStartPosition);
lastRangeEndPosition = rangeEndPosition;
List<Integer> statementStartPositions = Lists.newArrayList();
List<Integer> statementEndPositions = Lists.newArrayList();
do {
int statementStartPosition = statementRanges.start(statementRangeIndex);
if (statementStartPosition < rangeStartPosition
|| statementStartPosition >= rangeEndPosition) {
break;
}
int statementEndPosition = statementRanges.end(statementRangeIndex);
if (statementEndPosition <= rangeStartPosition || statementEndPosition > rangeEndPosition) {
break;
}
statementStartPositions.add(statementStartPosition);
statementEndPositions.add(statementEndPosition);
} while (++statementRangeIndex < statementRanges.numStatements());
return new StandardStatementRanges(statementStartPositions, statementEndPositions);
}
private void skipTo(int rangeEndPosition) {
assert statementRangeIndex <= statementRanges.numStatements() : "You can't skip past the end.";
assert lastRangeEndPosition <= rangeEndPosition : "You can only skip forward.";
do {
int statementStartPosition = statementRanges.start(statementRangeIndex);
if (statementStartPosition >= rangeEndPosition) {
break;
}
int statementEndPosition = statementRanges.end(statementRangeIndex);
if (statementEndPosition > rangeEndPosition) {
break;
}
} while (++statementRangeIndex < statementRanges.numStatements());
}
}