Program: 94508
Project: 94508
Buggy source:
/** 
 * Performs cropping of input splits to the bounds specified in the ifContext. This logic is common to all pyramid input formats, regardless of the data provider, so there should be no need to override it in sub-classes.
 * @param ifContext
 * @param splits
 * @param zoomLevel
 * @param tileSize
 * @return
 */
List<TiledInputSplit> filterInputSplits(final TiledInputFormatContext ifContext,final List<TiledInputSplit> splits,final int zoomLevel,final int tileSize){
  if (splits.size() == 0 || ifContext.getBounds() == null) {
    return splits;
  }
  List<TiledInputSplit> result=new ArrayList<TiledInputSplit>();
  TMSUtils.TileBounds cropBounds=TMSUtils.boundsToTile(TMSUtils.Bounds.asTMSBounds(ifContext.getBounds()),ifContext.getZoomLevel(),tileSize);
  Collections.sort(splits,new Comparator<TiledInputSplit>(){
    @Override public int compare(    TiledInputSplit t1,    TiledInputSplit t2){
      if (t1.getStartTileId() < t2.getStartTileId())       return -1;
      return t1.getStartTileId() == t2.getStartTileId() ? 0 : 1;
    }
  }
);
  SplitIterator splitIter=new SplitIterator(splits,new RegionSplitVisitor(cropBounds));
  TiledInputSplit firstSplit=null;
  TiledInputSplit secondSplit=splitIter.next();
  long fromTileId=TMSUtils.tileid(cropBounds.w,cropBounds.s,ifContext.getZoomLevel());
  while (secondSplit != null) {
    long toTileId=secondSplit.getStartTileId() - 1;
    fillHoles(result,fromTileId,toTileId,ifContext.getZoomLevel(),ifContext.getTileSize(),cropBounds);
    result.add(secondSplit);
    firstSplit=secondSplit;
    secondSplit=splitIter.next();
    fromTileId=firstSplit.getEndTileId() + 1;
  }
  if (ifContext.getIncludeEmptyTiles()) {
    fillHoles(result,fromTileId,TMSUtils.tileid(cropBounds.e,cropBounds.n,zoomLevel),zoomLevel,tileSize,cropBounds);
  }
  return result;
}

Fixed version (ground truth):
/** 
 * Performs cropping of input splits to the bounds specified in the ifContext. This logic is common to all pyramid input formats, regardless of the data provider, so there should be no need to override it in sub-classes.
 * @param ifContext
 * @param splits
 * @param zoomLevel
 * @param tileSize
 * @return
 */
List<TiledInputSplit> filterInputSplits(final TiledInputFormatContext ifContext,final List<TiledInputSplit> splits,final int zoomLevel,final int tileSize){
  if (splits.size() == 0 || ifContext.getBounds() == null) {
    return splits;
  }
  List<TiledInputSplit> result=new ArrayList<TiledInputSplit>();
  TMSUtils.TileBounds cropBounds=TMSUtils.boundsToTile(TMSUtils.Bounds.asTMSBounds(ifContext.getBounds()),ifContext.getZoomLevel(),tileSize);
  Collections.sort(splits,new Comparator<TiledInputSplit>(){
    @Override public int compare(    TiledInputSplit t1,    TiledInputSplit t2){
      if (t1.getStartTileId() < t2.getStartTileId())       return -1;
      return t1.getStartTileId() == t2.getStartTileId() ? 0 : 1;
    }
  }
);
  SplitIterator splitIter=new SplitIterator(splits,new RegionSplitVisitor(cropBounds));
  TiledInputSplit firstSplit=null;
  TiledInputSplit secondSplit=splitIter.next();
  long fromTileId=TMSUtils.tileid(cropBounds.w,cropBounds.s,ifContext.getZoomLevel());
  while (secondSplit != null) {
    long toTileId=secondSplit.getStartTileId() - 1;
    if (ifContext.getIncludeEmptyTiles()) {
      fillHoles(result,fromTileId,toTileId,ifContext.getZoomLevel(),ifContext.getTileSize(),cropBounds);
    }
    result.add(secondSplit);
    firstSplit=secondSplit;
    secondSplit=splitIter.next();
    fromTileId=firstSplit.getEndTileId() + 1;
  }
  if (ifContext.getIncludeEmptyTiles()) {
    fillHoles(result,fromTileId,TMSUtils.tileid(cropBounds.e,cropBounds.n,zoomLevel),zoomLevel,tileSize,cropBounds);
  }
  return result;
}