http://git-wip-us.apache.org/repos/asf/hbase-site/blob/1241ee85/devapidocs/src-html/org/apache/hadoop/hbase/regionserver/StoreFile.Comparators.GetSeqId.html
----------------------------------------------------------------------
diff --git 
a/devapidocs/src-html/org/apache/hadoop/hbase/regionserver/StoreFile.Comparators.GetSeqId.html
 
b/devapidocs/src-html/org/apache/hadoop/hbase/regionserver/StoreFile.Comparators.GetSeqId.html
index b01aa5a..8090868 100644
--- 
a/devapidocs/src-html/org/apache/hadoop/hbase/regionserver/StoreFile.Comparators.GetSeqId.html
+++ 
b/devapidocs/src-html/org/apache/hadoop/hbase/regionserver/StoreFile.Comparators.GetSeqId.html
@@ -597,215 +597,221 @@
 <span class="sourceLineNo">589</span>    return reader;<a name="line.589"></a>
 <span class="sourceLineNo">590</span>  }<a name="line.590"></a>
 <span class="sourceLineNo">591</span><a name="line.591"></a>
-<span class="sourceLineNo">592</span>  public StoreFileScanner 
getStreamScanner(boolean canUseDropBehind, boolean cacheBlocks,<a 
name="line.592"></a>
-<span class="sourceLineNo">593</span>      boolean pread, boolean 
isCompaction, long readPt, long scannerOrder,<a name="line.593"></a>
-<span class="sourceLineNo">594</span>      boolean 
canOptimizeForNonNullColumn) throws IOException {<a name="line.594"></a>
-<span class="sourceLineNo">595</span>    return 
createStreamReader(canUseDropBehind).getStoreFileScanner(<a name="line.595"></a>
-<span class="sourceLineNo">596</span>      cacheBlocks, pread, isCompaction, 
readPt, scannerOrder, canOptimizeForNonNullColumn);<a name="line.596"></a>
-<span class="sourceLineNo">597</span>  }<a name="line.597"></a>
-<span class="sourceLineNo">598</span><a name="line.598"></a>
-<span class="sourceLineNo">599</span>  /**<a name="line.599"></a>
-<span class="sourceLineNo">600</span>   * @return Current reader.  Must call 
initReader first else returns null.<a name="line.600"></a>
-<span class="sourceLineNo">601</span>   * @see #initReader()<a 
name="line.601"></a>
-<span class="sourceLineNo">602</span>   */<a name="line.602"></a>
-<span class="sourceLineNo">603</span>  public StoreFileReader getReader() {<a 
name="line.603"></a>
-<span class="sourceLineNo">604</span>    return this.reader;<a 
name="line.604"></a>
-<span class="sourceLineNo">605</span>  }<a name="line.605"></a>
-<span class="sourceLineNo">606</span><a name="line.606"></a>
-<span class="sourceLineNo">607</span>  /**<a name="line.607"></a>
-<span class="sourceLineNo">608</span>   * @param evictOnClose whether to evict 
blocks belonging to this file<a name="line.608"></a>
-<span class="sourceLineNo">609</span>   * @throws IOException<a 
name="line.609"></a>
-<span class="sourceLineNo">610</span>   */<a name="line.610"></a>
-<span class="sourceLineNo">611</span>  public synchronized void 
closeReader(boolean evictOnClose)<a name="line.611"></a>
-<span class="sourceLineNo">612</span>      throws IOException {<a 
name="line.612"></a>
-<span class="sourceLineNo">613</span>    if (this.reader != null) {<a 
name="line.613"></a>
-<span class="sourceLineNo">614</span>      this.reader.close(evictOnClose);<a 
name="line.614"></a>
-<span class="sourceLineNo">615</span>      this.reader = null;<a 
name="line.615"></a>
-<span class="sourceLineNo">616</span>    }<a name="line.616"></a>
-<span class="sourceLineNo">617</span>  }<a name="line.617"></a>
-<span class="sourceLineNo">618</span><a name="line.618"></a>
-<span class="sourceLineNo">619</span>  /**<a name="line.619"></a>
-<span class="sourceLineNo">620</span>   * Marks the status of the file as 
compactedAway.<a name="line.620"></a>
-<span class="sourceLineNo">621</span>   */<a name="line.621"></a>
-<span class="sourceLineNo">622</span>  public void markCompactedAway() {<a 
name="line.622"></a>
-<span class="sourceLineNo">623</span>    this.compactedAway = true;<a 
name="line.623"></a>
-<span class="sourceLineNo">624</span>  }<a name="line.624"></a>
-<span class="sourceLineNo">625</span><a name="line.625"></a>
-<span class="sourceLineNo">626</span>  /**<a name="line.626"></a>
-<span class="sourceLineNo">627</span>   * Delete this file<a 
name="line.627"></a>
-<span class="sourceLineNo">628</span>   * @throws IOException<a 
name="line.628"></a>
-<span class="sourceLineNo">629</span>   */<a name="line.629"></a>
-<span class="sourceLineNo">630</span>  public void deleteReader() throws 
IOException {<a name="line.630"></a>
-<span class="sourceLineNo">631</span>    boolean evictOnClose =<a 
name="line.631"></a>
-<span class="sourceLineNo">632</span>        cacheConf != null? 
cacheConf.shouldEvictOnClose(): true;<a name="line.632"></a>
-<span class="sourceLineNo">633</span>    closeReader(evictOnClose);<a 
name="line.633"></a>
-<span class="sourceLineNo">634</span>    this.fs.delete(getPath(), true);<a 
name="line.634"></a>
-<span class="sourceLineNo">635</span>  }<a name="line.635"></a>
-<span class="sourceLineNo">636</span><a name="line.636"></a>
-<span class="sourceLineNo">637</span>  @Override<a name="line.637"></a>
-<span class="sourceLineNo">638</span>  public String toString() {<a 
name="line.638"></a>
-<span class="sourceLineNo">639</span>    return this.fileInfo.toString();<a 
name="line.639"></a>
-<span class="sourceLineNo">640</span>  }<a name="line.640"></a>
-<span class="sourceLineNo">641</span><a name="line.641"></a>
-<span class="sourceLineNo">642</span>  /**<a name="line.642"></a>
-<span class="sourceLineNo">643</span>   * @return a length description of this 
StoreFile, suitable for debug output<a name="line.643"></a>
-<span class="sourceLineNo">644</span>   */<a name="line.644"></a>
-<span class="sourceLineNo">645</span>  public String toStringDetailed() {<a 
name="line.645"></a>
-<span class="sourceLineNo">646</span>    StringBuilder sb = new 
StringBuilder();<a name="line.646"></a>
-<span class="sourceLineNo">647</span>    
sb.append(this.getPath().toString());<a name="line.647"></a>
-<span class="sourceLineNo">648</span>    sb.append(", 
isReference=").append(isReference());<a name="line.648"></a>
-<span class="sourceLineNo">649</span>    sb.append(", 
isBulkLoadResult=").append(isBulkLoadResult());<a name="line.649"></a>
-<span class="sourceLineNo">650</span>    if (isBulkLoadResult()) {<a 
name="line.650"></a>
-<span class="sourceLineNo">651</span>      sb.append(", 
bulkLoadTS=").append(getBulkLoadTimestamp());<a name="line.651"></a>
-<span class="sourceLineNo">652</span>    } else {<a name="line.652"></a>
-<span class="sourceLineNo">653</span>      sb.append(", 
seqid=").append(getMaxSequenceId());<a name="line.653"></a>
-<span class="sourceLineNo">654</span>    }<a name="line.654"></a>
-<span class="sourceLineNo">655</span>    sb.append(", 
majorCompaction=").append(isMajorCompaction());<a name="line.655"></a>
-<span class="sourceLineNo">656</span><a name="line.656"></a>
-<span class="sourceLineNo">657</span>    return sb.toString();<a 
name="line.657"></a>
-<span class="sourceLineNo">658</span>  }<a name="line.658"></a>
-<span class="sourceLineNo">659</span><a name="line.659"></a>
-<span class="sourceLineNo">660</span>  /**<a name="line.660"></a>
-<span class="sourceLineNo">661</span>   * Gets whether to skip resetting the 
sequence id for cells.<a name="line.661"></a>
-<span class="sourceLineNo">662</span>   * @param skipResetSeqId The byte array 
of boolean.<a name="line.662"></a>
-<span class="sourceLineNo">663</span>   * @return Whether to skip resetting 
the sequence id.<a name="line.663"></a>
-<span class="sourceLineNo">664</span>   */<a name="line.664"></a>
-<span class="sourceLineNo">665</span>  private boolean isSkipResetSeqId(byte[] 
skipResetSeqId) {<a name="line.665"></a>
-<span class="sourceLineNo">666</span>    if (skipResetSeqId != null &amp;&amp; 
skipResetSeqId.length == 1) {<a name="line.666"></a>
-<span class="sourceLineNo">667</span>      return 
Bytes.toBoolean(skipResetSeqId);<a name="line.667"></a>
-<span class="sourceLineNo">668</span>    }<a name="line.668"></a>
-<span class="sourceLineNo">669</span>    return false;<a name="line.669"></a>
-<span class="sourceLineNo">670</span>  }<a name="line.670"></a>
-<span class="sourceLineNo">671</span><a name="line.671"></a>
-<span class="sourceLineNo">672</span>  /**<a name="line.672"></a>
-<span class="sourceLineNo">673</span>   * @param fs<a name="line.673"></a>
-<span class="sourceLineNo">674</span>   * @param dir Directory to create file 
in.<a name="line.674"></a>
-<span class="sourceLineNo">675</span>   * @return random filename inside 
passed &lt;code&gt;dir&lt;/code&gt;<a name="line.675"></a>
-<span class="sourceLineNo">676</span>   */<a name="line.676"></a>
-<span class="sourceLineNo">677</span>  public static Path getUniqueFile(final 
FileSystem fs, final Path dir)<a name="line.677"></a>
-<span class="sourceLineNo">678</span>      throws IOException {<a 
name="line.678"></a>
-<span class="sourceLineNo">679</span>    if 
(!fs.getFileStatus(dir).isDirectory()) {<a name="line.679"></a>
-<span class="sourceLineNo">680</span>      throw new IOException("Expecting " 
+ dir.toString() +<a name="line.680"></a>
-<span class="sourceLineNo">681</span>        " to be a directory");<a 
name="line.681"></a>
-<span class="sourceLineNo">682</span>    }<a name="line.682"></a>
-<span class="sourceLineNo">683</span>    return new Path(dir, 
UUID.randomUUID().toString().replaceAll("-", ""));<a name="line.683"></a>
-<span class="sourceLineNo">684</span>  }<a name="line.684"></a>
-<span class="sourceLineNo">685</span><a name="line.685"></a>
-<span class="sourceLineNo">686</span>  public Long getMinimumTimestamp() {<a 
name="line.686"></a>
-<span class="sourceLineNo">687</span>    return getReader().timeRange == null? 
null: getReader().timeRange.getMin();<a name="line.687"></a>
-<span class="sourceLineNo">688</span>  }<a name="line.688"></a>
-<span class="sourceLineNo">689</span><a name="line.689"></a>
-<span class="sourceLineNo">690</span>  public Long getMaximumTimestamp() {<a 
name="line.690"></a>
-<span class="sourceLineNo">691</span>    return getReader().timeRange == null? 
null: getReader().timeRange.getMax();<a name="line.691"></a>
-<span class="sourceLineNo">692</span>  }<a name="line.692"></a>
-<span class="sourceLineNo">693</span><a name="line.693"></a>
-<span class="sourceLineNo">694</span><a name="line.694"></a>
-<span class="sourceLineNo">695</span>  /**<a name="line.695"></a>
-<span class="sourceLineNo">696</span>   * Gets the approximate mid-point of 
this file that is optimal for use in splitting it.<a name="line.696"></a>
-<span class="sourceLineNo">697</span>   * @param comparator Comparator used to 
compare KVs.<a name="line.697"></a>
-<span class="sourceLineNo">698</span>   * @return The split point row, or null 
if splitting is not possible, or reader is null.<a name="line.698"></a>
-<span class="sourceLineNo">699</span>   */<a name="line.699"></a>
-<span class="sourceLineNo">700</span>  byte[] getFileSplitPoint(CellComparator 
comparator) throws IOException {<a name="line.700"></a>
-<span class="sourceLineNo">701</span>    if (this.reader == null) {<a 
name="line.701"></a>
-<span class="sourceLineNo">702</span>      LOG.warn("Storefile " + this + " 
Reader is null; cannot get split point");<a name="line.702"></a>
-<span class="sourceLineNo">703</span>      return null;<a name="line.703"></a>
-<span class="sourceLineNo">704</span>    }<a name="line.704"></a>
-<span class="sourceLineNo">705</span>    // Get first, last, and mid keys.  
Midkey is the key that starts block<a name="line.705"></a>
-<span class="sourceLineNo">706</span>    // in middle of hfile.  Has column 
and timestamp.  Need to return just<a name="line.706"></a>
-<span class="sourceLineNo">707</span>    // the row we want to split on as 
midkey.<a name="line.707"></a>
-<span class="sourceLineNo">708</span>    Cell midkey = this.reader.midkey();<a 
name="line.708"></a>
-<span class="sourceLineNo">709</span>    if (midkey != null) {<a 
name="line.709"></a>
-<span class="sourceLineNo">710</span>      Cell firstKey = 
this.reader.getFirstKey();<a name="line.710"></a>
-<span class="sourceLineNo">711</span>      Cell lastKey = 
this.reader.getLastKey();<a name="line.711"></a>
-<span class="sourceLineNo">712</span>      // if the midkey is the same as the 
first or last keys, we cannot (ever) split this region.<a name="line.712"></a>
-<span class="sourceLineNo">713</span>      if (comparator.compareRows(midkey, 
firstKey) == 0<a name="line.713"></a>
-<span class="sourceLineNo">714</span>          || 
comparator.compareRows(midkey, lastKey) == 0) {<a name="line.714"></a>
-<span class="sourceLineNo">715</span>        if (LOG.isDebugEnabled()) {<a 
name="line.715"></a>
-<span class="sourceLineNo">716</span>          LOG.debug("cannot split because 
midkey is the same as first or last row");<a name="line.716"></a>
-<span class="sourceLineNo">717</span>        }<a name="line.717"></a>
-<span class="sourceLineNo">718</span>        return null;<a 
name="line.718"></a>
-<span class="sourceLineNo">719</span>      }<a name="line.719"></a>
-<span class="sourceLineNo">720</span>      return CellUtil.cloneRow(midkey);<a 
name="line.720"></a>
-<span class="sourceLineNo">721</span>    }<a name="line.721"></a>
-<span class="sourceLineNo">722</span>    return null;<a name="line.722"></a>
-<span class="sourceLineNo">723</span>  }<a name="line.723"></a>
-<span class="sourceLineNo">724</span><a name="line.724"></a>
-<span class="sourceLineNo">725</span>  /**<a name="line.725"></a>
-<span class="sourceLineNo">726</span>   * Useful comparators for comparing 
StoreFiles.<a name="line.726"></a>
-<span class="sourceLineNo">727</span>   */<a name="line.727"></a>
-<span class="sourceLineNo">728</span>  public abstract static class 
Comparators {<a name="line.728"></a>
-<span class="sourceLineNo">729</span>    /**<a name="line.729"></a>
-<span class="sourceLineNo">730</span>     * Comparator that compares based on 
the Sequence Ids of the<a name="line.730"></a>
-<span class="sourceLineNo">731</span>     * the StoreFiles. Bulk loads that 
did not request a seq ID<a name="line.731"></a>
-<span class="sourceLineNo">732</span>     * are given a seq id of -1; thus, 
they are placed before all non-<a name="line.732"></a>
-<span class="sourceLineNo">733</span>     * bulk loads, and bulk loads with 
sequence Id. Among these files,<a name="line.733"></a>
-<span class="sourceLineNo">734</span>     * the size is used to determine the 
ordering, then bulkLoadTime.<a name="line.734"></a>
-<span class="sourceLineNo">735</span>     * If there are ties, the path name 
is used as a tie-breaker.<a name="line.735"></a>
-<span class="sourceLineNo">736</span>     */<a name="line.736"></a>
-<span class="sourceLineNo">737</span>    public static final 
Comparator&lt;StoreFile&gt; SEQ_ID =<a name="line.737"></a>
-<span class="sourceLineNo">738</span>      
Ordering.compound(ImmutableList.of(<a name="line.738"></a>
-<span class="sourceLineNo">739</span>          
Ordering.natural().onResultOf(new GetSeqId()),<a name="line.739"></a>
-<span class="sourceLineNo">740</span>          
Ordering.natural().onResultOf(new GetFileSize()).reverse(),<a 
name="line.740"></a>
-<span class="sourceLineNo">741</span>          
Ordering.natural().onResultOf(new GetBulkTime()),<a name="line.741"></a>
-<span class="sourceLineNo">742</span>          
Ordering.natural().onResultOf(new GetPathName())<a name="line.742"></a>
-<span class="sourceLineNo">743</span>      ));<a name="line.743"></a>
-<span class="sourceLineNo">744</span><a name="line.744"></a>
-<span class="sourceLineNo">745</span>    /**<a name="line.745"></a>
-<span class="sourceLineNo">746</span>     * Comparator for time-aware 
compaction. SeqId is still the first<a name="line.746"></a>
-<span class="sourceLineNo">747</span>     *   ordering criterion to maintain 
MVCC.<a name="line.747"></a>
-<span class="sourceLineNo">748</span>     */<a name="line.748"></a>
-<span class="sourceLineNo">749</span>    public static final 
Comparator&lt;StoreFile&gt; SEQ_ID_MAX_TIMESTAMP =<a name="line.749"></a>
-<span class="sourceLineNo">750</span>      
Ordering.compound(ImmutableList.of(<a name="line.750"></a>
-<span class="sourceLineNo">751</span>        Ordering.natural().onResultOf(new 
GetSeqId()),<a name="line.751"></a>
-<span class="sourceLineNo">752</span>        Ordering.natural().onResultOf(new 
GetMaxTimestamp()),<a name="line.752"></a>
-<span class="sourceLineNo">753</span>        Ordering.natural().onResultOf(new 
GetFileSize()).reverse(),<a name="line.753"></a>
-<span class="sourceLineNo">754</span>        Ordering.natural().onResultOf(new 
GetBulkTime()),<a name="line.754"></a>
-<span class="sourceLineNo">755</span>        Ordering.natural().onResultOf(new 
GetPathName())<a name="line.755"></a>
-<span class="sourceLineNo">756</span>      ));<a name="line.756"></a>
-<span class="sourceLineNo">757</span><a name="line.757"></a>
-<span class="sourceLineNo">758</span>    private static class GetSeqId 
implements Function&lt;StoreFile, Long&gt; {<a name="line.758"></a>
-<span class="sourceLineNo">759</span>      @Override<a name="line.759"></a>
-<span class="sourceLineNo">760</span>      public Long apply(StoreFile sf) {<a 
name="line.760"></a>
-<span class="sourceLineNo">761</span>        return sf.getMaxSequenceId();<a 
name="line.761"></a>
-<span class="sourceLineNo">762</span>      }<a name="line.762"></a>
-<span class="sourceLineNo">763</span>    }<a name="line.763"></a>
-<span class="sourceLineNo">764</span><a name="line.764"></a>
-<span class="sourceLineNo">765</span>    private static class GetFileSize 
implements Function&lt;StoreFile, Long&gt; {<a name="line.765"></a>
-<span class="sourceLineNo">766</span>      @Override<a name="line.766"></a>
-<span class="sourceLineNo">767</span>      public Long apply(StoreFile sf) {<a 
name="line.767"></a>
-<span class="sourceLineNo">768</span>        if (sf.getReader() != null) {<a 
name="line.768"></a>
-<span class="sourceLineNo">769</span>          return 
sf.getReader().length();<a name="line.769"></a>
-<span class="sourceLineNo">770</span>        } else {<a name="line.770"></a>
-<span class="sourceLineNo">771</span>          // the reader may be null for 
the compacted files and if the archiving<a name="line.771"></a>
-<span class="sourceLineNo">772</span>          // had failed.<a 
name="line.772"></a>
-<span class="sourceLineNo">773</span>          return -1L;<a 
name="line.773"></a>
-<span class="sourceLineNo">774</span>        }<a name="line.774"></a>
-<span class="sourceLineNo">775</span>      }<a name="line.775"></a>
-<span class="sourceLineNo">776</span>    }<a name="line.776"></a>
-<span class="sourceLineNo">777</span><a name="line.777"></a>
-<span class="sourceLineNo">778</span>    private static class GetBulkTime 
implements Function&lt;StoreFile, Long&gt; {<a name="line.778"></a>
-<span class="sourceLineNo">779</span>      @Override<a name="line.779"></a>
-<span class="sourceLineNo">780</span>      public Long apply(StoreFile sf) {<a 
name="line.780"></a>
-<span class="sourceLineNo">781</span>        if (!sf.isBulkLoadResult()) 
return Long.MAX_VALUE;<a name="line.781"></a>
-<span class="sourceLineNo">782</span>        return 
sf.getBulkLoadTimestamp();<a name="line.782"></a>
-<span class="sourceLineNo">783</span>      }<a name="line.783"></a>
-<span class="sourceLineNo">784</span>    }<a name="line.784"></a>
-<span class="sourceLineNo">785</span><a name="line.785"></a>
-<span class="sourceLineNo">786</span>    private static class GetPathName 
implements Function&lt;StoreFile, String&gt; {<a name="line.786"></a>
-<span class="sourceLineNo">787</span>      @Override<a name="line.787"></a>
-<span class="sourceLineNo">788</span>      public String apply(StoreFile sf) 
{<a name="line.788"></a>
-<span class="sourceLineNo">789</span>        return sf.getPath().getName();<a 
name="line.789"></a>
-<span class="sourceLineNo">790</span>      }<a name="line.790"></a>
-<span class="sourceLineNo">791</span>    }<a name="line.791"></a>
-<span class="sourceLineNo">792</span><a name="line.792"></a>
-<span class="sourceLineNo">793</span>    private static class GetMaxTimestamp 
implements Function&lt;StoreFile, Long&gt; {<a name="line.793"></a>
-<span class="sourceLineNo">794</span>      @Override<a name="line.794"></a>
-<span class="sourceLineNo">795</span>      public Long apply(StoreFile sf) {<a 
name="line.795"></a>
-<span class="sourceLineNo">796</span>        return sf.getMaximumTimestamp() 
== null? (Long)Long.MAX_VALUE : sf.getMaximumTimestamp();<a name="line.796"></a>
-<span class="sourceLineNo">797</span>      }<a name="line.797"></a>
-<span class="sourceLineNo">798</span>    }<a name="line.798"></a>
-<span class="sourceLineNo">799</span>  }<a name="line.799"></a>
-<span class="sourceLineNo">800</span>}<a name="line.800"></a>
+<span class="sourceLineNo">592</span>  public StoreFileScanner 
getPreadScanner(boolean cacheBlocks, long readPt, long scannerOrder,<a 
name="line.592"></a>
+<span class="sourceLineNo">593</span>      boolean 
canOptimizeForNonNullColumn) {<a name="line.593"></a>
+<span class="sourceLineNo">594</span>    return 
getReader().getStoreFileScanner(cacheBlocks, true, false, readPt, 
scannerOrder,<a name="line.594"></a>
+<span class="sourceLineNo">595</span>      canOptimizeForNonNullColumn);<a 
name="line.595"></a>
+<span class="sourceLineNo">596</span>  }<a name="line.596"></a>
+<span class="sourceLineNo">597</span><a name="line.597"></a>
+<span class="sourceLineNo">598</span>  public StoreFileScanner 
getStreamScanner(boolean canUseDropBehind, boolean cacheBlocks,<a 
name="line.598"></a>
+<span class="sourceLineNo">599</span>      boolean isCompaction, long readPt, 
long scannerOrder, boolean canOptimizeForNonNullColumn)<a name="line.599"></a>
+<span class="sourceLineNo">600</span>      throws IOException {<a 
name="line.600"></a>
+<span class="sourceLineNo">601</span>    return 
createStreamReader(canUseDropBehind).getStoreFileScanner(cacheBlocks, false,<a 
name="line.601"></a>
+<span class="sourceLineNo">602</span>      isCompaction, readPt, scannerOrder, 
canOptimizeForNonNullColumn);<a name="line.602"></a>
+<span class="sourceLineNo">603</span>  }<a name="line.603"></a>
+<span class="sourceLineNo">604</span><a name="line.604"></a>
+<span class="sourceLineNo">605</span>  /**<a name="line.605"></a>
+<span class="sourceLineNo">606</span>   * @return Current reader.  Must call 
initReader first else returns null.<a name="line.606"></a>
+<span class="sourceLineNo">607</span>   * @see #initReader()<a 
name="line.607"></a>
+<span class="sourceLineNo">608</span>   */<a name="line.608"></a>
+<span class="sourceLineNo">609</span>  public StoreFileReader getReader() {<a 
name="line.609"></a>
+<span class="sourceLineNo">610</span>    return this.reader;<a 
name="line.610"></a>
+<span class="sourceLineNo">611</span>  }<a name="line.611"></a>
+<span class="sourceLineNo">612</span><a name="line.612"></a>
+<span class="sourceLineNo">613</span>  /**<a name="line.613"></a>
+<span class="sourceLineNo">614</span>   * @param evictOnClose whether to evict 
blocks belonging to this file<a name="line.614"></a>
+<span class="sourceLineNo">615</span>   * @throws IOException<a 
name="line.615"></a>
+<span class="sourceLineNo">616</span>   */<a name="line.616"></a>
+<span class="sourceLineNo">617</span>  public synchronized void 
closeReader(boolean evictOnClose)<a name="line.617"></a>
+<span class="sourceLineNo">618</span>      throws IOException {<a 
name="line.618"></a>
+<span class="sourceLineNo">619</span>    if (this.reader != null) {<a 
name="line.619"></a>
+<span class="sourceLineNo">620</span>      this.reader.close(evictOnClose);<a 
name="line.620"></a>
+<span class="sourceLineNo">621</span>      this.reader = null;<a 
name="line.621"></a>
+<span class="sourceLineNo">622</span>    }<a name="line.622"></a>
+<span class="sourceLineNo">623</span>  }<a name="line.623"></a>
+<span class="sourceLineNo">624</span><a name="line.624"></a>
+<span class="sourceLineNo">625</span>  /**<a name="line.625"></a>
+<span class="sourceLineNo">626</span>   * Marks the status of the file as 
compactedAway.<a name="line.626"></a>
+<span class="sourceLineNo">627</span>   */<a name="line.627"></a>
+<span class="sourceLineNo">628</span>  public void markCompactedAway() {<a 
name="line.628"></a>
+<span class="sourceLineNo">629</span>    this.compactedAway = true;<a 
name="line.629"></a>
+<span class="sourceLineNo">630</span>  }<a name="line.630"></a>
+<span class="sourceLineNo">631</span><a name="line.631"></a>
+<span class="sourceLineNo">632</span>  /**<a name="line.632"></a>
+<span class="sourceLineNo">633</span>   * Delete this file<a 
name="line.633"></a>
+<span class="sourceLineNo">634</span>   * @throws IOException<a 
name="line.634"></a>
+<span class="sourceLineNo">635</span>   */<a name="line.635"></a>
+<span class="sourceLineNo">636</span>  public void deleteReader() throws 
IOException {<a name="line.636"></a>
+<span class="sourceLineNo">637</span>    boolean evictOnClose =<a 
name="line.637"></a>
+<span class="sourceLineNo">638</span>        cacheConf != null? 
cacheConf.shouldEvictOnClose(): true;<a name="line.638"></a>
+<span class="sourceLineNo">639</span>    closeReader(evictOnClose);<a 
name="line.639"></a>
+<span class="sourceLineNo">640</span>    this.fs.delete(getPath(), true);<a 
name="line.640"></a>
+<span class="sourceLineNo">641</span>  }<a name="line.641"></a>
+<span class="sourceLineNo">642</span><a name="line.642"></a>
+<span class="sourceLineNo">643</span>  @Override<a name="line.643"></a>
+<span class="sourceLineNo">644</span>  public String toString() {<a 
name="line.644"></a>
+<span class="sourceLineNo">645</span>    return this.fileInfo.toString();<a 
name="line.645"></a>
+<span class="sourceLineNo">646</span>  }<a name="line.646"></a>
+<span class="sourceLineNo">647</span><a name="line.647"></a>
+<span class="sourceLineNo">648</span>  /**<a name="line.648"></a>
+<span class="sourceLineNo">649</span>   * @return a length description of this 
StoreFile, suitable for debug output<a name="line.649"></a>
+<span class="sourceLineNo">650</span>   */<a name="line.650"></a>
+<span class="sourceLineNo">651</span>  public String toStringDetailed() {<a 
name="line.651"></a>
+<span class="sourceLineNo">652</span>    StringBuilder sb = new 
StringBuilder();<a name="line.652"></a>
+<span class="sourceLineNo">653</span>    
sb.append(this.getPath().toString());<a name="line.653"></a>
+<span class="sourceLineNo">654</span>    sb.append(", 
isReference=").append(isReference());<a name="line.654"></a>
+<span class="sourceLineNo">655</span>    sb.append(", 
isBulkLoadResult=").append(isBulkLoadResult());<a name="line.655"></a>
+<span class="sourceLineNo">656</span>    if (isBulkLoadResult()) {<a 
name="line.656"></a>
+<span class="sourceLineNo">657</span>      sb.append(", 
bulkLoadTS=").append(getBulkLoadTimestamp());<a name="line.657"></a>
+<span class="sourceLineNo">658</span>    } else {<a name="line.658"></a>
+<span class="sourceLineNo">659</span>      sb.append(", 
seqid=").append(getMaxSequenceId());<a name="line.659"></a>
+<span class="sourceLineNo">660</span>    }<a name="line.660"></a>
+<span class="sourceLineNo">661</span>    sb.append(", 
majorCompaction=").append(isMajorCompaction());<a name="line.661"></a>
+<span class="sourceLineNo">662</span><a name="line.662"></a>
+<span class="sourceLineNo">663</span>    return sb.toString();<a 
name="line.663"></a>
+<span class="sourceLineNo">664</span>  }<a name="line.664"></a>
+<span class="sourceLineNo">665</span><a name="line.665"></a>
+<span class="sourceLineNo">666</span>  /**<a name="line.666"></a>
+<span class="sourceLineNo">667</span>   * Gets whether to skip resetting the 
sequence id for cells.<a name="line.667"></a>
+<span class="sourceLineNo">668</span>   * @param skipResetSeqId The byte array 
of boolean.<a name="line.668"></a>
+<span class="sourceLineNo">669</span>   * @return Whether to skip resetting 
the sequence id.<a name="line.669"></a>
+<span class="sourceLineNo">670</span>   */<a name="line.670"></a>
+<span class="sourceLineNo">671</span>  private boolean isSkipResetSeqId(byte[] 
skipResetSeqId) {<a name="line.671"></a>
+<span class="sourceLineNo">672</span>    if (skipResetSeqId != null &amp;&amp; 
skipResetSeqId.length == 1) {<a name="line.672"></a>
+<span class="sourceLineNo">673</span>      return 
Bytes.toBoolean(skipResetSeqId);<a name="line.673"></a>
+<span class="sourceLineNo">674</span>    }<a name="line.674"></a>
+<span class="sourceLineNo">675</span>    return false;<a name="line.675"></a>
+<span class="sourceLineNo">676</span>  }<a name="line.676"></a>
+<span class="sourceLineNo">677</span><a name="line.677"></a>
+<span class="sourceLineNo">678</span>  /**<a name="line.678"></a>
+<span class="sourceLineNo">679</span>   * @param fs<a name="line.679"></a>
+<span class="sourceLineNo">680</span>   * @param dir Directory to create file 
in.<a name="line.680"></a>
+<span class="sourceLineNo">681</span>   * @return random filename inside 
passed &lt;code&gt;dir&lt;/code&gt;<a name="line.681"></a>
+<span class="sourceLineNo">682</span>   */<a name="line.682"></a>
+<span class="sourceLineNo">683</span>  public static Path getUniqueFile(final 
FileSystem fs, final Path dir)<a name="line.683"></a>
+<span class="sourceLineNo">684</span>      throws IOException {<a 
name="line.684"></a>
+<span class="sourceLineNo">685</span>    if 
(!fs.getFileStatus(dir).isDirectory()) {<a name="line.685"></a>
+<span class="sourceLineNo">686</span>      throw new IOException("Expecting " 
+ dir.toString() +<a name="line.686"></a>
+<span class="sourceLineNo">687</span>        " to be a directory");<a 
name="line.687"></a>
+<span class="sourceLineNo">688</span>    }<a name="line.688"></a>
+<span class="sourceLineNo">689</span>    return new Path(dir, 
UUID.randomUUID().toString().replaceAll("-", ""));<a name="line.689"></a>
+<span class="sourceLineNo">690</span>  }<a name="line.690"></a>
+<span class="sourceLineNo">691</span><a name="line.691"></a>
+<span class="sourceLineNo">692</span>  public Long getMinimumTimestamp() {<a 
name="line.692"></a>
+<span class="sourceLineNo">693</span>    return getReader().timeRange == null? 
null: getReader().timeRange.getMin();<a name="line.693"></a>
+<span class="sourceLineNo">694</span>  }<a name="line.694"></a>
+<span class="sourceLineNo">695</span><a name="line.695"></a>
+<span class="sourceLineNo">696</span>  public Long getMaximumTimestamp() {<a 
name="line.696"></a>
+<span class="sourceLineNo">697</span>    return getReader().timeRange == null? 
null: getReader().timeRange.getMax();<a name="line.697"></a>
+<span class="sourceLineNo">698</span>  }<a name="line.698"></a>
+<span class="sourceLineNo">699</span><a name="line.699"></a>
+<span class="sourceLineNo">700</span><a name="line.700"></a>
+<span class="sourceLineNo">701</span>  /**<a name="line.701"></a>
+<span class="sourceLineNo">702</span>   * Gets the approximate mid-point of 
this file that is optimal for use in splitting it.<a name="line.702"></a>
+<span class="sourceLineNo">703</span>   * @param comparator Comparator used to 
compare KVs.<a name="line.703"></a>
+<span class="sourceLineNo">704</span>   * @return The split point row, or null 
if splitting is not possible, or reader is null.<a name="line.704"></a>
+<span class="sourceLineNo">705</span>   */<a name="line.705"></a>
+<span class="sourceLineNo">706</span>  byte[] getFileSplitPoint(CellComparator 
comparator) throws IOException {<a name="line.706"></a>
+<span class="sourceLineNo">707</span>    if (this.reader == null) {<a 
name="line.707"></a>
+<span class="sourceLineNo">708</span>      LOG.warn("Storefile " + this + " 
Reader is null; cannot get split point");<a name="line.708"></a>
+<span class="sourceLineNo">709</span>      return null;<a name="line.709"></a>
+<span class="sourceLineNo">710</span>    }<a name="line.710"></a>
+<span class="sourceLineNo">711</span>    // Get first, last, and mid keys.  
Midkey is the key that starts block<a name="line.711"></a>
+<span class="sourceLineNo">712</span>    // in middle of hfile.  Has column 
and timestamp.  Need to return just<a name="line.712"></a>
+<span class="sourceLineNo">713</span>    // the row we want to split on as 
midkey.<a name="line.713"></a>
+<span class="sourceLineNo">714</span>    Cell midkey = this.reader.midkey();<a 
name="line.714"></a>
+<span class="sourceLineNo">715</span>    if (midkey != null) {<a 
name="line.715"></a>
+<span class="sourceLineNo">716</span>      Cell firstKey = 
this.reader.getFirstKey();<a name="line.716"></a>
+<span class="sourceLineNo">717</span>      Cell lastKey = 
this.reader.getLastKey();<a name="line.717"></a>
+<span class="sourceLineNo">718</span>      // if the midkey is the same as the 
first or last keys, we cannot (ever) split this region.<a name="line.718"></a>
+<span class="sourceLineNo">719</span>      if (comparator.compareRows(midkey, 
firstKey) == 0<a name="line.719"></a>
+<span class="sourceLineNo">720</span>          || 
comparator.compareRows(midkey, lastKey) == 0) {<a name="line.720"></a>
+<span class="sourceLineNo">721</span>        if (LOG.isDebugEnabled()) {<a 
name="line.721"></a>
+<span class="sourceLineNo">722</span>          LOG.debug("cannot split because 
midkey is the same as first or last row");<a name="line.722"></a>
+<span class="sourceLineNo">723</span>        }<a name="line.723"></a>
+<span class="sourceLineNo">724</span>        return null;<a 
name="line.724"></a>
+<span class="sourceLineNo">725</span>      }<a name="line.725"></a>
+<span class="sourceLineNo">726</span>      return CellUtil.cloneRow(midkey);<a 
name="line.726"></a>
+<span class="sourceLineNo">727</span>    }<a name="line.727"></a>
+<span class="sourceLineNo">728</span>    return null;<a name="line.728"></a>
+<span class="sourceLineNo">729</span>  }<a name="line.729"></a>
+<span class="sourceLineNo">730</span><a name="line.730"></a>
+<span class="sourceLineNo">731</span>  /**<a name="line.731"></a>
+<span class="sourceLineNo">732</span>   * Useful comparators for comparing 
StoreFiles.<a name="line.732"></a>
+<span class="sourceLineNo">733</span>   */<a name="line.733"></a>
+<span class="sourceLineNo">734</span>  public abstract static class 
Comparators {<a name="line.734"></a>
+<span class="sourceLineNo">735</span>    /**<a name="line.735"></a>
+<span class="sourceLineNo">736</span>     * Comparator that compares based on 
the Sequence Ids of the<a name="line.736"></a>
+<span class="sourceLineNo">737</span>     * the StoreFiles. Bulk loads that 
did not request a seq ID<a name="line.737"></a>
+<span class="sourceLineNo">738</span>     * are given a seq id of -1; thus, 
they are placed before all non-<a name="line.738"></a>
+<span class="sourceLineNo">739</span>     * bulk loads, and bulk loads with 
sequence Id. Among these files,<a name="line.739"></a>
+<span class="sourceLineNo">740</span>     * the size is used to determine the 
ordering, then bulkLoadTime.<a name="line.740"></a>
+<span class="sourceLineNo">741</span>     * If there are ties, the path name 
is used as a tie-breaker.<a name="line.741"></a>
+<span class="sourceLineNo">742</span>     */<a name="line.742"></a>
+<span class="sourceLineNo">743</span>    public static final 
Comparator&lt;StoreFile&gt; SEQ_ID =<a name="line.743"></a>
+<span class="sourceLineNo">744</span>      
Ordering.compound(ImmutableList.of(<a name="line.744"></a>
+<span class="sourceLineNo">745</span>          
Ordering.natural().onResultOf(new GetSeqId()),<a name="line.745"></a>
+<span class="sourceLineNo">746</span>          
Ordering.natural().onResultOf(new GetFileSize()).reverse(),<a 
name="line.746"></a>
+<span class="sourceLineNo">747</span>          
Ordering.natural().onResultOf(new GetBulkTime()),<a name="line.747"></a>
+<span class="sourceLineNo">748</span>          
Ordering.natural().onResultOf(new GetPathName())<a name="line.748"></a>
+<span class="sourceLineNo">749</span>      ));<a name="line.749"></a>
+<span class="sourceLineNo">750</span><a name="line.750"></a>
+<span class="sourceLineNo">751</span>    /**<a name="line.751"></a>
+<span class="sourceLineNo">752</span>     * Comparator for time-aware 
compaction. SeqId is still the first<a name="line.752"></a>
+<span class="sourceLineNo">753</span>     *   ordering criterion to maintain 
MVCC.<a name="line.753"></a>
+<span class="sourceLineNo">754</span>     */<a name="line.754"></a>
+<span class="sourceLineNo">755</span>    public static final 
Comparator&lt;StoreFile&gt; SEQ_ID_MAX_TIMESTAMP =<a name="line.755"></a>
+<span class="sourceLineNo">756</span>      
Ordering.compound(ImmutableList.of(<a name="line.756"></a>
+<span class="sourceLineNo">757</span>        Ordering.natural().onResultOf(new 
GetSeqId()),<a name="line.757"></a>
+<span class="sourceLineNo">758</span>        Ordering.natural().onResultOf(new 
GetMaxTimestamp()),<a name="line.758"></a>
+<span class="sourceLineNo">759</span>        Ordering.natural().onResultOf(new 
GetFileSize()).reverse(),<a name="line.759"></a>
+<span class="sourceLineNo">760</span>        Ordering.natural().onResultOf(new 
GetBulkTime()),<a name="line.760"></a>
+<span class="sourceLineNo">761</span>        Ordering.natural().onResultOf(new 
GetPathName())<a name="line.761"></a>
+<span class="sourceLineNo">762</span>      ));<a name="line.762"></a>
+<span class="sourceLineNo">763</span><a name="line.763"></a>
+<span class="sourceLineNo">764</span>    private static class GetSeqId 
implements Function&lt;StoreFile, Long&gt; {<a name="line.764"></a>
+<span class="sourceLineNo">765</span>      @Override<a name="line.765"></a>
+<span class="sourceLineNo">766</span>      public Long apply(StoreFile sf) {<a 
name="line.766"></a>
+<span class="sourceLineNo">767</span>        return sf.getMaxSequenceId();<a 
name="line.767"></a>
+<span class="sourceLineNo">768</span>      }<a name="line.768"></a>
+<span class="sourceLineNo">769</span>    }<a name="line.769"></a>
+<span class="sourceLineNo">770</span><a name="line.770"></a>
+<span class="sourceLineNo">771</span>    private static class GetFileSize 
implements Function&lt;StoreFile, Long&gt; {<a name="line.771"></a>
+<span class="sourceLineNo">772</span>      @Override<a name="line.772"></a>
+<span class="sourceLineNo">773</span>      public Long apply(StoreFile sf) {<a 
name="line.773"></a>
+<span class="sourceLineNo">774</span>        if (sf.getReader() != null) {<a 
name="line.774"></a>
+<span class="sourceLineNo">775</span>          return 
sf.getReader().length();<a name="line.775"></a>
+<span class="sourceLineNo">776</span>        } else {<a name="line.776"></a>
+<span class="sourceLineNo">777</span>          // the reader may be null for 
the compacted files and if the archiving<a name="line.777"></a>
+<span class="sourceLineNo">778</span>          // had failed.<a 
name="line.778"></a>
+<span class="sourceLineNo">779</span>          return -1L;<a 
name="line.779"></a>
+<span class="sourceLineNo">780</span>        }<a name="line.780"></a>
+<span class="sourceLineNo">781</span>      }<a name="line.781"></a>
+<span class="sourceLineNo">782</span>    }<a name="line.782"></a>
+<span class="sourceLineNo">783</span><a name="line.783"></a>
+<span class="sourceLineNo">784</span>    private static class GetBulkTime 
implements Function&lt;StoreFile, Long&gt; {<a name="line.784"></a>
+<span class="sourceLineNo">785</span>      @Override<a name="line.785"></a>
+<span class="sourceLineNo">786</span>      public Long apply(StoreFile sf) {<a 
name="line.786"></a>
+<span class="sourceLineNo">787</span>        if (!sf.isBulkLoadResult()) 
return Long.MAX_VALUE;<a name="line.787"></a>
+<span class="sourceLineNo">788</span>        return 
sf.getBulkLoadTimestamp();<a name="line.788"></a>
+<span class="sourceLineNo">789</span>      }<a name="line.789"></a>
+<span class="sourceLineNo">790</span>    }<a name="line.790"></a>
+<span class="sourceLineNo">791</span><a name="line.791"></a>
+<span class="sourceLineNo">792</span>    private static class GetPathName 
implements Function&lt;StoreFile, String&gt; {<a name="line.792"></a>
+<span class="sourceLineNo">793</span>      @Override<a name="line.793"></a>
+<span class="sourceLineNo">794</span>      public String apply(StoreFile sf) 
{<a name="line.794"></a>
+<span class="sourceLineNo">795</span>        return sf.getPath().getName();<a 
name="line.795"></a>
+<span class="sourceLineNo">796</span>      }<a name="line.796"></a>
+<span class="sourceLineNo">797</span>    }<a name="line.797"></a>
+<span class="sourceLineNo">798</span><a name="line.798"></a>
+<span class="sourceLineNo">799</span>    private static class GetMaxTimestamp 
implements Function&lt;StoreFile, Long&gt; {<a name="line.799"></a>
+<span class="sourceLineNo">800</span>      @Override<a name="line.800"></a>
+<span class="sourceLineNo">801</span>      public Long apply(StoreFile sf) {<a 
name="line.801"></a>
+<span class="sourceLineNo">802</span>        return sf.getMaximumTimestamp() 
== null? (Long)Long.MAX_VALUE : sf.getMaximumTimestamp();<a name="line.802"></a>
+<span class="sourceLineNo">803</span>      }<a name="line.803"></a>
+<span class="sourceLineNo">804</span>    }<a name="line.804"></a>
+<span class="sourceLineNo">805</span>  }<a name="line.805"></a>
+<span class="sourceLineNo">806</span>}<a name="line.806"></a>
 
 
 

http://git-wip-us.apache.org/repos/asf/hbase-site/blob/1241ee85/devapidocs/src-html/org/apache/hadoop/hbase/regionserver/StoreFile.Comparators.html
----------------------------------------------------------------------
diff --git 
a/devapidocs/src-html/org/apache/hadoop/hbase/regionserver/StoreFile.Comparators.html
 
b/devapidocs/src-html/org/apache/hadoop/hbase/regionserver/StoreFile.Comparators.html
index b01aa5a..8090868 100644
--- 
a/devapidocs/src-html/org/apache/hadoop/hbase/regionserver/StoreFile.Comparators.html
+++ 
b/devapidocs/src-html/org/apache/hadoop/hbase/regionserver/StoreFile.Comparators.html
@@ -597,215 +597,221 @@
 <span class="sourceLineNo">589</span>    return reader;<a name="line.589"></a>
 <span class="sourceLineNo">590</span>  }<a name="line.590"></a>
 <span class="sourceLineNo">591</span><a name="line.591"></a>
-<span class="sourceLineNo">592</span>  public StoreFileScanner 
getStreamScanner(boolean canUseDropBehind, boolean cacheBlocks,<a 
name="line.592"></a>
-<span class="sourceLineNo">593</span>      boolean pread, boolean 
isCompaction, long readPt, long scannerOrder,<a name="line.593"></a>
-<span class="sourceLineNo">594</span>      boolean 
canOptimizeForNonNullColumn) throws IOException {<a name="line.594"></a>
-<span class="sourceLineNo">595</span>    return 
createStreamReader(canUseDropBehind).getStoreFileScanner(<a name="line.595"></a>
-<span class="sourceLineNo">596</span>      cacheBlocks, pread, isCompaction, 
readPt, scannerOrder, canOptimizeForNonNullColumn);<a name="line.596"></a>
-<span class="sourceLineNo">597</span>  }<a name="line.597"></a>
-<span class="sourceLineNo">598</span><a name="line.598"></a>
-<span class="sourceLineNo">599</span>  /**<a name="line.599"></a>
-<span class="sourceLineNo">600</span>   * @return Current reader.  Must call 
initReader first else returns null.<a name="line.600"></a>
-<span class="sourceLineNo">601</span>   * @see #initReader()<a 
name="line.601"></a>
-<span class="sourceLineNo">602</span>   */<a name="line.602"></a>
-<span class="sourceLineNo">603</span>  public StoreFileReader getReader() {<a 
name="line.603"></a>
-<span class="sourceLineNo">604</span>    return this.reader;<a 
name="line.604"></a>
-<span class="sourceLineNo">605</span>  }<a name="line.605"></a>
-<span class="sourceLineNo">606</span><a name="line.606"></a>
-<span class="sourceLineNo">607</span>  /**<a name="line.607"></a>
-<span class="sourceLineNo">608</span>   * @param evictOnClose whether to evict 
blocks belonging to this file<a name="line.608"></a>
-<span class="sourceLineNo">609</span>   * @throws IOException<a 
name="line.609"></a>
-<span class="sourceLineNo">610</span>   */<a name="line.610"></a>
-<span class="sourceLineNo">611</span>  public synchronized void 
closeReader(boolean evictOnClose)<a name="line.611"></a>
-<span class="sourceLineNo">612</span>      throws IOException {<a 
name="line.612"></a>
-<span class="sourceLineNo">613</span>    if (this.reader != null) {<a 
name="line.613"></a>
-<span class="sourceLineNo">614</span>      this.reader.close(evictOnClose);<a 
name="line.614"></a>
-<span class="sourceLineNo">615</span>      this.reader = null;<a 
name="line.615"></a>
-<span class="sourceLineNo">616</span>    }<a name="line.616"></a>
-<span class="sourceLineNo">617</span>  }<a name="line.617"></a>
-<span class="sourceLineNo">618</span><a name="line.618"></a>
-<span class="sourceLineNo">619</span>  /**<a name="line.619"></a>
-<span class="sourceLineNo">620</span>   * Marks the status of the file as 
compactedAway.<a name="line.620"></a>
-<span class="sourceLineNo">621</span>   */<a name="line.621"></a>
-<span class="sourceLineNo">622</span>  public void markCompactedAway() {<a 
name="line.622"></a>
-<span class="sourceLineNo">623</span>    this.compactedAway = true;<a 
name="line.623"></a>
-<span class="sourceLineNo">624</span>  }<a name="line.624"></a>
-<span class="sourceLineNo">625</span><a name="line.625"></a>
-<span class="sourceLineNo">626</span>  /**<a name="line.626"></a>
-<span class="sourceLineNo">627</span>   * Delete this file<a 
name="line.627"></a>
-<span class="sourceLineNo">628</span>   * @throws IOException<a 
name="line.628"></a>
-<span class="sourceLineNo">629</span>   */<a name="line.629"></a>
-<span class="sourceLineNo">630</span>  public void deleteReader() throws 
IOException {<a name="line.630"></a>
-<span class="sourceLineNo">631</span>    boolean evictOnClose =<a 
name="line.631"></a>
-<span class="sourceLineNo">632</span>        cacheConf != null? 
cacheConf.shouldEvictOnClose(): true;<a name="line.632"></a>
-<span class="sourceLineNo">633</span>    closeReader(evictOnClose);<a 
name="line.633"></a>
-<span class="sourceLineNo">634</span>    this.fs.delete(getPath(), true);<a 
name="line.634"></a>
-<span class="sourceLineNo">635</span>  }<a name="line.635"></a>
-<span class="sourceLineNo">636</span><a name="line.636"></a>
-<span class="sourceLineNo">637</span>  @Override<a name="line.637"></a>
-<span class="sourceLineNo">638</span>  public String toString() {<a 
name="line.638"></a>
-<span class="sourceLineNo">639</span>    return this.fileInfo.toString();<a 
name="line.639"></a>
-<span class="sourceLineNo">640</span>  }<a name="line.640"></a>
-<span class="sourceLineNo">641</span><a name="line.641"></a>
-<span class="sourceLineNo">642</span>  /**<a name="line.642"></a>
-<span class="sourceLineNo">643</span>   * @return a length description of this 
StoreFile, suitable for debug output<a name="line.643"></a>
-<span class="sourceLineNo">644</span>   */<a name="line.644"></a>
-<span class="sourceLineNo">645</span>  public String toStringDetailed() {<a 
name="line.645"></a>
-<span class="sourceLineNo">646</span>    StringBuilder sb = new 
StringBuilder();<a name="line.646"></a>
-<span class="sourceLineNo">647</span>    
sb.append(this.getPath().toString());<a name="line.647"></a>
-<span class="sourceLineNo">648</span>    sb.append(", 
isReference=").append(isReference());<a name="line.648"></a>
-<span class="sourceLineNo">649</span>    sb.append(", 
isBulkLoadResult=").append(isBulkLoadResult());<a name="line.649"></a>
-<span class="sourceLineNo">650</span>    if (isBulkLoadResult()) {<a 
name="line.650"></a>
-<span class="sourceLineNo">651</span>      sb.append(", 
bulkLoadTS=").append(getBulkLoadTimestamp());<a name="line.651"></a>
-<span class="sourceLineNo">652</span>    } else {<a name="line.652"></a>
-<span class="sourceLineNo">653</span>      sb.append(", 
seqid=").append(getMaxSequenceId());<a name="line.653"></a>
-<span class="sourceLineNo">654</span>    }<a name="line.654"></a>
-<span class="sourceLineNo">655</span>    sb.append(", 
majorCompaction=").append(isMajorCompaction());<a name="line.655"></a>
-<span class="sourceLineNo">656</span><a name="line.656"></a>
-<span class="sourceLineNo">657</span>    return sb.toString();<a 
name="line.657"></a>
-<span class="sourceLineNo">658</span>  }<a name="line.658"></a>
-<span class="sourceLineNo">659</span><a name="line.659"></a>
-<span class="sourceLineNo">660</span>  /**<a name="line.660"></a>
-<span class="sourceLineNo">661</span>   * Gets whether to skip resetting the 
sequence id for cells.<a name="line.661"></a>
-<span class="sourceLineNo">662</span>   * @param skipResetSeqId The byte array 
of boolean.<a name="line.662"></a>
-<span class="sourceLineNo">663</span>   * @return Whether to skip resetting 
the sequence id.<a name="line.663"></a>
-<span class="sourceLineNo">664</span>   */<a name="line.664"></a>
-<span class="sourceLineNo">665</span>  private boolean isSkipResetSeqId(byte[] 
skipResetSeqId) {<a name="line.665"></a>
-<span class="sourceLineNo">666</span>    if (skipResetSeqId != null &amp;&amp; 
skipResetSeqId.length == 1) {<a name="line.666"></a>
-<span class="sourceLineNo">667</span>      return 
Bytes.toBoolean(skipResetSeqId);<a name="line.667"></a>
-<span class="sourceLineNo">668</span>    }<a name="line.668"></a>
-<span class="sourceLineNo">669</span>    return false;<a name="line.669"></a>
-<span class="sourceLineNo">670</span>  }<a name="line.670"></a>
-<span class="sourceLineNo">671</span><a name="line.671"></a>
-<span class="sourceLineNo">672</span>  /**<a name="line.672"></a>
-<span class="sourceLineNo">673</span>   * @param fs<a name="line.673"></a>
-<span class="sourceLineNo">674</span>   * @param dir Directory to create file 
in.<a name="line.674"></a>
-<span class="sourceLineNo">675</span>   * @return random filename inside 
passed &lt;code&gt;dir&lt;/code&gt;<a name="line.675"></a>
-<span class="sourceLineNo">676</span>   */<a name="line.676"></a>
-<span class="sourceLineNo">677</span>  public static Path getUniqueFile(final 
FileSystem fs, final Path dir)<a name="line.677"></a>
-<span class="sourceLineNo">678</span>      throws IOException {<a 
name="line.678"></a>
-<span class="sourceLineNo">679</span>    if 
(!fs.getFileStatus(dir).isDirectory()) {<a name="line.679"></a>
-<span class="sourceLineNo">680</span>      throw new IOException("Expecting " 
+ dir.toString() +<a name="line.680"></a>
-<span class="sourceLineNo">681</span>        " to be a directory");<a 
name="line.681"></a>
-<span class="sourceLineNo">682</span>    }<a name="line.682"></a>
-<span class="sourceLineNo">683</span>    return new Path(dir, 
UUID.randomUUID().toString().replaceAll("-", ""));<a name="line.683"></a>
-<span class="sourceLineNo">684</span>  }<a name="line.684"></a>
-<span class="sourceLineNo">685</span><a name="line.685"></a>
-<span class="sourceLineNo">686</span>  public Long getMinimumTimestamp() {<a 
name="line.686"></a>
-<span class="sourceLineNo">687</span>    return getReader().timeRange == null? 
null: getReader().timeRange.getMin();<a name="line.687"></a>
-<span class="sourceLineNo">688</span>  }<a name="line.688"></a>
-<span class="sourceLineNo">689</span><a name="line.689"></a>
-<span class="sourceLineNo">690</span>  public Long getMaximumTimestamp() {<a 
name="line.690"></a>
-<span class="sourceLineNo">691</span>    return getReader().timeRange == null? 
null: getReader().timeRange.getMax();<a name="line.691"></a>
-<span class="sourceLineNo">692</span>  }<a name="line.692"></a>
-<span class="sourceLineNo">693</span><a name="line.693"></a>
-<span class="sourceLineNo">694</span><a name="line.694"></a>
-<span class="sourceLineNo">695</span>  /**<a name="line.695"></a>
-<span class="sourceLineNo">696</span>   * Gets the approximate mid-point of 
this file that is optimal for use in splitting it.<a name="line.696"></a>
-<span class="sourceLineNo">697</span>   * @param comparator Comparator used to 
compare KVs.<a name="line.697"></a>
-<span class="sourceLineNo">698</span>   * @return The split point row, or null 
if splitting is not possible, or reader is null.<a name="line.698"></a>
-<span class="sourceLineNo">699</span>   */<a name="line.699"></a>
-<span class="sourceLineNo">700</span>  byte[] getFileSplitPoint(CellComparator 
comparator) throws IOException {<a name="line.700"></a>
-<span class="sourceLineNo">701</span>    if (this.reader == null) {<a 
name="line.701"></a>
-<span class="sourceLineNo">702</span>      LOG.warn("Storefile " + this + " 
Reader is null; cannot get split point");<a name="line.702"></a>
-<span class="sourceLineNo">703</span>      return null;<a name="line.703"></a>
-<span class="sourceLineNo">704</span>    }<a name="line.704"></a>
-<span class="sourceLineNo">705</span>    // Get first, last, and mid keys.  
Midkey is the key that starts block<a name="line.705"></a>
-<span class="sourceLineNo">706</span>    // in middle of hfile.  Has column 
and timestamp.  Need to return just<a name="line.706"></a>
-<span class="sourceLineNo">707</span>    // the row we want to split on as 
midkey.<a name="line.707"></a>
-<span class="sourceLineNo">708</span>    Cell midkey = this.reader.midkey();<a 
name="line.708"></a>
-<span class="sourceLineNo">709</span>    if (midkey != null) {<a 
name="line.709"></a>
-<span class="sourceLineNo">710</span>      Cell firstKey = 
this.reader.getFirstKey();<a name="line.710"></a>
-<span class="sourceLineNo">711</span>      Cell lastKey = 
this.reader.getLastKey();<a name="line.711"></a>
-<span class="sourceLineNo">712</span>      // if the midkey is the same as the 
first or last keys, we cannot (ever) split this region.<a name="line.712"></a>
-<span class="sourceLineNo">713</span>      if (comparator.compareRows(midkey, 
firstKey) == 0<a name="line.713"></a>
-<span class="sourceLineNo">714</span>          || 
comparator.compareRows(midkey, lastKey) == 0) {<a name="line.714"></a>
-<span class="sourceLineNo">715</span>        if (LOG.isDebugEnabled()) {<a 
name="line.715"></a>
-<span class="sourceLineNo">716</span>          LOG.debug("cannot split because 
midkey is the same as first or last row");<a name="line.716"></a>
-<span class="sourceLineNo">717</span>        }<a name="line.717"></a>
-<span class="sourceLineNo">718</span>        return null;<a 
name="line.718"></a>
-<span class="sourceLineNo">719</span>      }<a name="line.719"></a>
-<span class="sourceLineNo">720</span>      return CellUtil.cloneRow(midkey);<a 
name="line.720"></a>
-<span class="sourceLineNo">721</span>    }<a name="line.721"></a>
-<span class="sourceLineNo">722</span>    return null;<a name="line.722"></a>
-<span class="sourceLineNo">723</span>  }<a name="line.723"></a>
-<span class="sourceLineNo">724</span><a name="line.724"></a>
-<span class="sourceLineNo">725</span>  /**<a name="line.725"></a>
-<span class="sourceLineNo">726</span>   * Useful comparators for comparing 
StoreFiles.<a name="line.726"></a>
-<span class="sourceLineNo">727</span>   */<a name="line.727"></a>
-<span class="sourceLineNo">728</span>  public abstract static class 
Comparators {<a name="line.728"></a>
-<span class="sourceLineNo">729</span>    /**<a name="line.729"></a>
-<span class="sourceLineNo">730</span>     * Comparator that compares based on 
the Sequence Ids of the<a name="line.730"></a>
-<span class="sourceLineNo">731</span>     * the StoreFiles. Bulk loads that 
did not request a seq ID<a name="line.731"></a>
-<span class="sourceLineNo">732</span>     * are given a seq id of -1; thus, 
they are placed before all non-<a name="line.732"></a>
-<span class="sourceLineNo">733</span>     * bulk loads, and bulk loads with 
sequence Id. Among these files,<a name="line.733"></a>
-<span class="sourceLineNo">734</span>     * the size is used to determine the 
ordering, then bulkLoadTime.<a name="line.734"></a>
-<span class="sourceLineNo">735</span>     * If there are ties, the path name 
is used as a tie-breaker.<a name="line.735"></a>
-<span class="sourceLineNo">736</span>     */<a name="line.736"></a>
-<span class="sourceLineNo">737</span>    public static final 
Comparator&lt;StoreFile&gt; SEQ_ID =<a name="line.737"></a>
-<span class="sourceLineNo">738</span>      
Ordering.compound(ImmutableList.of(<a name="line.738"></a>
-<span class="sourceLineNo">739</span>          
Ordering.natural().onResultOf(new GetSeqId()),<a name="line.739"></a>
-<span class="sourceLineNo">740</span>          
Ordering.natural().onResultOf(new GetFileSize()).reverse(),<a 
name="line.740"></a>
-<span class="sourceLineNo">741</span>          
Ordering.natural().onResultOf(new GetBulkTime()),<a name="line.741"></a>
-<span class="sourceLineNo">742</span>          
Ordering.natural().onResultOf(new GetPathName())<a name="line.742"></a>
-<span class="sourceLineNo">743</span>      ));<a name="line.743"></a>
-<span class="sourceLineNo">744</span><a name="line.744"></a>
-<span class="sourceLineNo">745</span>    /**<a name="line.745"></a>
-<span class="sourceLineNo">746</span>     * Comparator for time-aware 
compaction. SeqId is still the first<a name="line.746"></a>
-<span class="sourceLineNo">747</span>     *   ordering criterion to maintain 
MVCC.<a name="line.747"></a>
-<span class="sourceLineNo">748</span>     */<a name="line.748"></a>
-<span class="sourceLineNo">749</span>    public static final 
Comparator&lt;StoreFile&gt; SEQ_ID_MAX_TIMESTAMP =<a name="line.749"></a>
-<span class="sourceLineNo">750</span>      
Ordering.compound(ImmutableList.of(<a name="line.750"></a>
-<span class="sourceLineNo">751</span>        Ordering.natural().onResultOf(new 
GetSeqId()),<a name="line.751"></a>
-<span class="sourceLineNo">752</span>        Ordering.natural().onResultOf(new 
GetMaxTimestamp()),<a name="line.752"></a>
-<span class="sourceLineNo">753</span>        Ordering.natural().onResultOf(new 
GetFileSize()).reverse(),<a name="line.753"></a>
-<span class="sourceLineNo">754</span>        Ordering.natural().onResultOf(new 
GetBulkTime()),<a name="line.754"></a>
-<span class="sourceLineNo">755</span>        Ordering.natural().onResultOf(new 
GetPathName())<a name="line.755"></a>
-<span class="sourceLineNo">756</span>      ));<a name="line.756"></a>
-<span class="sourceLineNo">757</span><a name="line.757"></a>
-<span class="sourceLineNo">758</span>    private static class GetSeqId 
implements Function&lt;StoreFile, Long&gt; {<a name="line.758"></a>
-<span class="sourceLineNo">759</span>      @Override<a name="line.759"></a>
-<span class="sourceLineNo">760</span>      public Long apply(StoreFile sf) {<a 
name="line.760"></a>
-<span class="sourceLineNo">761</span>        return sf.getMaxSequenceId();<a 
name="line.761"></a>
-<span class="sourceLineNo">762</span>      }<a name="line.762"></a>
-<span class="sourceLineNo">763</span>    }<a name="line.763"></a>
-<span class="sourceLineNo">764</span><a name="line.764"></a>
-<span class="sourceLineNo">765</span>    private static class GetFileSize 
implements Function&lt;StoreFile, Long&gt; {<a name="line.765"></a>
-<span class="sourceLineNo">766</span>      @Override<a name="line.766"></a>
-<span class="sourceLineNo">767</span>      public Long apply(StoreFile sf) {<a 
name="line.767"></a>
-<span class="sourceLineNo">768</span>        if (sf.getReader() != null) {<a 
name="line.768"></a>
-<span class="sourceLineNo">769</span>          return 
sf.getReader().length();<a name="line.769"></a>
-<span class="sourceLineNo">770</span>        } else {<a name="line.770"></a>
-<span class="sourceLineNo">771</span>          // the reader may be null for 
the compacted files and if the archiving<a name="line.771"></a>
-<span class="sourceLineNo">772</span>          // had failed.<a 
name="line.772"></a>
-<span class="sourceLineNo">773</span>          return -1L;<a 
name="line.773"></a>
-<span class="sourceLineNo">774</span>        }<a name="line.774"></a>
-<span class="sourceLineNo">775</span>      }<a name="line.775"></a>
-<span class="sourceLineNo">776</span>    }<a name="line.776"></a>
-<span class="sourceLineNo">777</span><a name="line.777"></a>
-<span class="sourceLineNo">778</span>    private static class GetBulkTime 
implements Function&lt;StoreFile, Long&gt; {<a name="line.778"></a>
-<span class="sourceLineNo">779</span>      @Override<a name="line.779"></a>
-<span class="sourceLineNo">780</span>      public Long apply(StoreFile sf) {<a 
name="line.780"></a>
-<span class="sourceLineNo">781</span>        if (!sf.isBulkLoadResult()) 
return Long.MAX_VALUE;<a name="line.781"></a>
-<span class="sourceLineNo">782</span>        return 
sf.getBulkLoadTimestamp();<a name="line.782"></a>
-<span class="sourceLineNo">783</span>      }<a name="line.783"></a>
-<span class="sourceLineNo">784</span>    }<a name="line.784"></a>
-<span class="sourceLineNo">785</span><a name="line.785"></a>
-<span class="sourceLineNo">786</span>    private static class GetPathName 
implements Function&lt;StoreFile, String&gt; {<a name="line.786"></a>
-<span class="sourceLineNo">787</span>      @Override<a name="line.787"></a>
-<span class="sourceLineNo">788</span>      public String apply(StoreFile sf) 
{<a name="line.788"></a>
-<span class="sourceLineNo">789</span>        return sf.getPath().getName();<a 
name="line.789"></a>
-<span class="sourceLineNo">790</span>      }<a name="line.790"></a>
-<span class="sourceLineNo">791</span>    }<a name="line.791"></a>
-<span class="sourceLineNo">792</span><a name="line.792"></a>
-<span class="sourceLineNo">793</span>    private static class GetMaxTimestamp 
implements Function&lt;StoreFile, Long&gt; {<a name="line.793"></a>
-<span class="sourceLineNo">794</span>      @Override<a name="line.794"></a>
-<span class="sourceLineNo">795</span>      public Long apply(StoreFile sf) {<a 
name="line.795"></a>
-<span class="sourceLineNo">796</span>        return sf.getMaximumTimestamp() 
== null? (Long)Long.MAX_VALUE : sf.getMaximumTimestamp();<a name="line.796"></a>
-<span class="sourceLineNo">797</span>      }<a name="line.797"></a>
-<span class="sourceLineNo">798</span>    }<a name="line.798"></a>
-<span class="sourceLineNo">799</span>  }<a name="line.799"></a>
-<span class="sourceLineNo">800</span>}<a name="line.800"></a>
+<span class="sourceLineNo">592</span>  public StoreFileScanner 
getPreadScanner(boolean cacheBlocks, long readPt, long scannerOrder,<a 
name="line.592"></a>
+<span class="sourceLineNo">593</span>      boolean 
canOptimizeForNonNullColumn) {<a name="line.593"></a>
+<span class="sourceLineNo">594</span>    return 
getReader().getStoreFileScanner(cacheBlocks, true, false, readPt, 
scannerOrder,<a name="line.594"></a>
+<span class="sourceLineNo">595</span>      canOptimizeForNonNullColumn);<a 
name="line.595"></a>
+<span class="sourceLineNo">596</span>  }<a name="line.596"></a>
+<span class="sourceLineNo">597</span><a name="line.597"></a>
+<span class="sourceLineNo">598</span>  public StoreFileScanner 
getStreamScanner(boolean canUseDropBehind, boolean cacheBlocks,<a 
name="line.598"></a>
+<span class="sourceLineNo">599</span>      boolean isCompaction, long readPt, 
long scannerOrder, boolean canOptimizeForNonNullColumn)<a name="line.599"></a>
+<span class="sourceLineNo">600</span>      throws IOException {<a 
name="line.600"></a>
+<span class="sourceLineNo">601</span>    return 
createStreamReader(canUseDropBehind).getStoreFileScanner(cacheBlocks, false,<a 
name="line.601"></a>
+<span class="sourceLineNo">602</span>      isCompaction, readPt, scannerOrder, 
canOptimizeForNonNullColumn);<a name="line.602"></a>
+<span class="sourceLineNo">603</span>  }<a name="line.603"></a>
+<span class="sourceLineNo">604</span><a name="line.604"></a>
+<span class="sourceLineNo">605</span>  /**<a name="line.605"></a>
+<span class="sourceLineNo">606</span>   * @return Current reader.  Must call 
initReader first else returns null.<a name="line.606"></a>
+<span class="sourceLineNo">607</span>   * @see #initReader()<a 
name="line.607"></a>
+<span class="sourceLineNo">608</span>   */<a name="line.608"></a>
+<span class="sourceLineNo">609</span>  public StoreFileReader getReader() {<a 
name="line.609"></a>
+<span class="sourceLineNo">610</span>    return this.reader;<a 
name="line.610"></a>
+<span class="sourceLineNo">611</span>  }<a name="line.611"></a>
+<span class="sourceLineNo">612</span><a name="line.612"></a>
+<span class="sourceLineNo">613</span>  /**<a name="line.613"></a>
+<span class="sourceLineNo">614</span>   * @param evictOnClose whether to evict 
blocks belonging to this file<a name="line.614"></a>
+<span class="sourceLineNo">615</span>   * @throws IOException<a 
name="line.615"></a>
+<span class="sourceLineNo">616</span>   */<a name="line.616"></a>
+<span class="sourceLineNo">617</span>  public synchronized void 
closeReader(boolean evictOnClose)<a name="line.617"></a>
+<span class="sourceLineNo">618</span>      throws IOException {<a 
name="line.618"></a>
+<span class="sourceLineNo">619</span>    if (this.reader != null) {<a 
name="line.619"></a>
+<span class="sourceLineNo">620</span>      this.reader.close(evictOnClose);<a 
name="line.620"></a>
+<span class="sourceLineNo">621</span>      this.reader = null;<a 
name="line.621"></a>
+<span class="sourceLineNo">622</span>    }<a name="line.622"></a>
+<span class="sourceLineNo">623</span>  }<a name="line.623"></a>
+<span class="sourceLineNo">624</span><a name="line.624"></a>
+<span class="sourceLineNo">625</span>  /**<a name="line.625"></a>
+<span class="sourceLineNo">626</span>   * Marks the status of the file as 
compactedAway.<a name="line.626"></a>
+<span class="sourceLineNo">627</span>   */<a name="line.627"></a>
+<span class="sourceLineNo">628</span>  public void markCompactedAway() {<a 
name="line.628"></a>
+<span class="sourceLineNo">629</span>    this.compactedAway = true;<a 
name="line.629"></a>
+<span class="sourceLineNo">630</span>  }<a name="line.630"></a>
+<span class="sourceLineNo">631</span><a name="line.631"></a>
+<span class="sourceLineNo">632</span>  /**<a name="line.632"></a>
+<span class="sourceLineNo">633</span>   * Delete this file<a 
name="line.633"></a>
+<span class="sourceLineNo">634</span>   * @throws IOException<a 
name="line.634"></a>
+<span class="sourceLineNo">635</span>   */<a name="line.635"></a>
+<span class="sourceLineNo">636</span>  public void deleteReader() throws 
IOException {<a name="line.636"></a>
+<span class="sourceLineNo">637</span>    boolean evictOnClose =<a 
name="line.637"></a>
+<span class="sourceLineNo">638</span>        cacheConf != null? 
cacheConf.shouldEvictOnClose(): true;<a name="line.638"></a>
+<span class="sourceLineNo">639</span>    closeReader(evictOnClose);<a 
name="line.639"></a>
+<span class="sourceLineNo">640</span>    this.fs.delete(getPath(), true);<a 
name="line.640"></a>
+<span class="sourceLineNo">641</span>  }<a name="line.641"></a>
+<span class="sourceLineNo">642</span><a name="line.642"></a>
+<span class="sourceLineNo">643</span>  @Override<a name="line.643"></a>
+<span class="sourceLineNo">644</span>  public String toString() {<a 
name="line.644"></a>
+<span class="sourceLineNo">645</span>    return this.fileInfo.toString();<a 
name="line.645"></a>
+<span class="sourceLineNo">646</span>  }<a name="line.646"></a>
+<span class="sourceLineNo">647</span><a name="line.647"></a>
+<span class="sourceLineNo">648</span>  /**<a name="line.648"></a>
+<span class="sourceLineNo">649</span>   * @return a length description of this 
StoreFile, suitable for debug output<a name="line.649"></a>
+<span class="sourceLineNo">650</span>   */<a name="line.650"></a>
+<span class="sourceLineNo">651</span>  public String toStringDetailed() {<a 
name="line.651"></a>
+<span class="sourceLineNo">652</span>    StringBuilder sb = new 
StringBuilder();<a name="line.652"></a>
+<span class="sourceLineNo">653</span>    
sb.append(this.getPath().toString());<a name="line.653"></a>
+<span class="sourceLineNo">654</span>    sb.append(", 
isReference=").append(isReference());<a name="line.654"></a>
+<span class="sourceLineNo">655</span>    sb.append(", 
isBulkLoadResult=").append(isBulkLoadResult());<a name="line.655"></a>
+<span class="sourceLineNo">656</span>    if (isBulkLoadResult()) {<a 
name="line.656"></a>
+<span class="sourceLineNo">657</span>      sb.append(", 
bulkLoadTS=").append(getBulkLoadTimestamp());<a name="line.657"></a>
+<span class="sourceLineNo">658</span>    } else {<a name="line.658"></a>
+<span class="sourceLineNo">659</span>      sb.append(", 
seqid=").append(getMaxSequenceId());<a name="line.659"></a>
+<span class="sourceLineNo">660</span>    }<a name="line.660"></a>
+<span class="sourceLineNo">661</span>    sb.append(", 
majorCompaction=").append(isMajorCompaction());<a name="line.661"></a>
+<span class="sourceLineNo">662</span><a name="line.662"></a>
+<span class="sourceLineNo">663</span>    return sb.toString();<a 
name="line.663"></a>
+<span class="sourceLineNo">664</span>  }<a name="line.664"></a>
+<span class="sourceLineNo">665</span><a name="line.665"></a>
+<span class="sourceLineNo">666</span>  /**<a name="line.666"></a>
+<span class="sourceLineNo">667</span>   * Gets whether to skip resetting the 
sequence id for cells.<a name="line.667"></a>
+<span class="sourceLineNo">668</span>   * @param skipResetSeqId The byte array 
of boolean.<a name="line.668"></a>
+<span class="sourceLineNo">669</span>   * @return Whether to skip resetting 
the sequence id.<a name="line.669"></a>
+<span class="sourceLineNo">670</span>   */<a name="line.670"></a>
+<span class="sourceLineNo">671</span>  private boolean isSkipResetSeqId(byte[] 
skipResetSeqId) {<a name="line.671"></a>
+<span class="sourceLineNo">672</span>    if (skipResetSeqId != null &amp;&amp; 
skipResetSeqId.length == 1) {<a name="line.672"></a>
+<span class="sourceLineNo">673</span>      return 
Bytes.toBoolean(skipResetSeqId);<a name="line.673"></a>
+<span class="sourceLineNo">674</span>    }<a name="line.674"></a>
+<span class="sourceLineNo">675</span>    return false;<a name="line.675"></a>
+<span class="sourceLineNo">676</span>  }<a name="line.676"></a>
+<span class="sourceLineNo">677</span><a name="line.677"></a>
+<span class="sourceLineNo">678</span>  /**<a name="line.678"></a>
+<span class="sourceLineNo">679</span>   * @param fs<a name="line.679"></a>
+<span class="sourceLineNo">680</span>   * @param dir Directory to create file 
in.<a name="line.680"></a>
+<span class="sourceLineNo">681</span>   * @return random filename inside 
passed &lt;code&gt;dir&lt;/code&gt;<a name="line.681"></a>
+<span class="sourceLineNo">682</span>   */<a name="line.682"></a>
+<span class="sourceLineNo">683</span>  public static Path getUniqueFile(final 
FileSystem fs, final Path dir)<a name="line.683"></a>
+<span class="sourceLineNo">684</span>      throws IOException {<a 
name="line.684"></a>
+<span class="sourceLineNo">685</span>    if 
(!fs.getFileStatus(dir).isDirectory()) {<a name="line.685"></a>
+<span class="sourceLineNo">686</span>      throw new IOException("Expecting " 
+ dir.toString() +<a name="line.686"></a>
+<span class="sourceLineNo">687</span>        " to be a directory");<a 
name="line.687"></a>
+<span class="sourceLineNo">688</span>    }<a name="line.688"></a>
+<span class="sourceLineNo">689</span>    return new Path(dir, 
UUID.randomUUID().toString().replaceAll("-", ""));<a name="line.689"></a>
+<span class="sourceLineNo">690</span>  }<a name="line.690"></a>
+<span class="sourceLineNo">691</span><a name="line.691"></a>
+<span class="sourceLineNo">692</span>  public Long getMinimumTimestamp() {<a 
name="line.692"></a>
+<span class="sourceLineNo">693</span>    return getReader().timeRange == null? 
null: getReader().timeRange.getMin();<a name="line.693"></a>
+<span class="sourceLineNo">694</span>  }<a name="line.694"></a>
+<span class="sourceLineNo">695</span><a name="line.695"></a>
+<span class="sourceLineNo">696</span>  public Long getMaximumTimestamp() {<a 
name="line.696"></a>
+<span class="sourceLineNo">697</span>    return getReader().timeRange == null? 
null: getReader().timeRange.getMax();<a name="line.697"></a>
+<span class="sourceLineNo">698</span>  }<a name="line.698"></a>
+<span class="sourceLineNo">699</span><a name="line.699"></a>
+<span class="sourceLineNo">700</span><a name="line.700"></a>
+<span class="sourceLineNo">701</span>  /**<a name="line.701"></a>
+<span class="sourceLineNo">702</span>   * Gets the approximate mid-point of 
this file that is optimal for use in splitting it.<a name="line.702"></a>
+<span class="sourceLineNo">703</span>   * @param comparator Comparator used to 
compare KVs.<a name="line.703"></a>
+<span class="sourceLineNo">704</span>   * @return The split point row, or null 
if splitting is not possible, or reader is null.<a name="line.704"></a>
+<span class="sourceLineNo">705</span>   */<a name="line.705"></a>
+<span class="sourceLineNo">706</span>  byte[] getFileSplitPoint(CellComparator 
comparator) throws IOException {<a name="line.706"></a>
+<span class="sourceLineNo">707</span>    if (this.reader == null) {<a 
name="line.707"></a>
+<span class="sourceLineNo">708</span>      LOG.warn("Storefile " + this + " 
Reader is null; cannot get split point");<a name="line.708"></a>
+<span class="sourceLineNo">709</span>      return null;<a name="line.709"></a>
+<span class="sourceLineNo">710</span>    }<a name="line.710"></a>
+<span class="sourceLineNo">711</span>    // Get first, last, and mid keys.  
Midkey is the key that starts block<a name="line.711"></a>
+<span class="sourceLineNo">712</span>    // in middle of hfile.  Has column 
and timestamp.  Need to return just<a name="line.712"></a>
+<span class="sourceLineNo">713</span>    // the row we want to split on as 
midkey.<a name="line.713"></a>
+<span class="sourceLineNo">714</span>    Cell midkey = this.reader.midkey();<a 
name="line.714"></a>
+<span class="sourceLineNo">715</span>    if (midkey != null) {<a 
name="line.715"></a>
+<span class="sourceLineNo">716</span>      Cell firstKey = 
this.reader.getFirstKey();<a name="line.716"></a>
+<span class="sourceLineNo">717</span>      Cell lastKey = 
this.reader.getLastKey();<a name="line.717"></a>
+<span class="sourceLineNo">718</span>      // if the midkey is the same as the 
first or last keys, we cannot (ever) split this region.<a name="line.718"></a>
+<span class="sourceLineNo">719</span>      if (comparator.compareRows(midkey, 
firstKey) == 0<a name="line.719"></a>
+<span class="sourceLineNo">720</span>          || 
comparator.compareRows(midkey, lastKey) == 0) {<a name="line.720"></a>
+<span class="sourceLineNo">721</span>        if (LOG.isDebugEnabled()) {<a 
name="line.721"></a>
+<span class="sourceLineNo">722</span>          LOG.debug("cannot split because 
midkey is the same as first or last row");<a name="line.722"></a>
+<span class="sourceLineNo">723</span>        }<a name="line.723"></a>
+<span class="sourceLineNo">724</span>        return null;<a 
name="line.724"></a>
+<span class="sourceLineNo">725</span>      }<a name="line.725"></a>
+<span class="sourceLineNo">726</span>      return CellUtil.cloneRow(midkey);<a 
name="line.726"></a>
+<span class="sourceLineNo">727</span>    }<a name="line.727"></a>
+<span class="sourceLineNo">728</span>    return null;<a name="line.728"></a>
+<span class="sourceLineNo">729</span>  }<a name="line.729"></a>
+<span class="sourceLineNo">730</span><a name="line.730"></a>
+<span class="sourceLineNo">731</span>  /**<a name="line.731"></a>
+<span class="sourceLineNo">732</span>   * Useful comparators for comparing 
StoreFiles.<a name="line.732"></a>
+<span class="sourceLineNo">733</span>   */<a name="line.733"></a>
+<span class="sourceLineNo">734</span>  public abstract static class 
Comparators {<a name="line.734"></a>
+<span class="sourceLineNo">735</span>    /**<a name="line.735"></a>
+<span class="sourceLineNo">736</span>     * Comparator that compares based on 
the Sequence Ids of the<a name="line.736"></a>
+<span class="sourceLineNo">737</span>     * the StoreFiles. Bulk loads that 
did not request a seq ID<a name="line.737"></a>
+<span class="sourceLineNo">738</span>     * are given a seq id of -1; thus, 
they are placed before all non-<a name="line.738"></a>
+<span class="sourceLineNo">739</span>     * bulk loads, and bulk loads with 
sequence Id. Among these files,<a name="line.739"></a>
+<span class="sourceLineNo">740</span>     * the size is used to determine the 
ordering, then bulkLoadTime.<a name="line.740"></a>
+<span class="sourceLineNo">741</span>     * If there are ties, the path name 
is used as a tie-breaker.<a name="line.741"></a>
+<span class="sourceLineNo">742</span>     */<a name="line.742"></a>
+<span class="sourceLineNo">743</span>    public static final 
Comparator&lt;StoreFile&gt; SEQ_ID =<a name="line.743"></a>
+<span class="sourceLineNo">744</span>      
Ordering.compound(ImmutableList.of(<a name="line.744"></a>
+<span class="sourceLineNo">745</span>          
Ordering.natural().onResultOf(new GetSeqId()),<a name="line.745"></a>
+<span class="sourceLineNo">746</span>          
Ordering.natural().onResultOf(new GetFileSize()).reverse(),<a 
name="line.746"></a>
+<span class="sourceLineNo">747</span>          
Ordering.natural().onResultOf(new GetBulkTime()),<a name="line.747"></a>
+<span class="sourceLineNo">748</span>          
Ordering.natural().onResultOf(new GetPathName())<a name="line.748"></a>
+<span class="sourceLineNo">749</span>      ));<a name="line.749"></a>
+<span class="sourceLineNo">750</span><a name="line.750"></a>
+<span class="sourceLineNo">751</span>    /**<a name="line.751"></a>
+<span class="sourceLineNo">752</span>     * Comparator for time-aware 
compaction. SeqId is still the first<a name="line.752"></a>
+<span class="sourceLineNo">753</span>     *   ordering criterion to maintain 
MVCC.<a name="line.753"></a>
+<span class="sourceLineNo">754</span>     */<a name="line.754"></a>
+<span class="sourceLineNo">755</span>    public static final 
Comparator&lt;StoreFile&gt; SEQ_ID_MAX_TIMESTAMP =<a name="line.755"></a>
+<span class="sourceLineNo">756</span>      
Ordering.compound(ImmutableList.of(<a name="line.756"></a>
+<span class="sourceLineNo">757</span>        Ordering.natural().onResultOf(new 
GetSeqId()),<a name="line.757"></a>
+<span class="sourceLineNo">758</span>        Ordering.natural().onResultOf(new 
GetMaxTimestamp()),<a name="line.758"></a>
+<span class="sourceLineNo">759</span>        Ordering.natural().onResultOf(new 
GetFileSize()).reverse(),<a name="line.759"></a>
+<span class="sourceLineNo">760</span>        Ordering.natural().onResultOf(new 
GetBulkTime()),<a name="line.760"></a>
+<span class="sourceLineNo">761</span>        Ordering.natural().onResultOf(new 
GetPathName())<a name="line.761"></a>
+<span class="sourceLineNo">762</span>      ));<a name="line.762"></a>
+<span class="sourceLineNo">763</span><a name="line.763"></a>
+<span class="sourceLineNo">764</span>    private static class GetSeqId 
implements Function&lt;StoreFile, Long&gt; {<a name="line.764"></a>
+<span class="sourceLineNo">765</span>      @Override<a name="line.765"></a>
+<span class="sourceLineNo">766</span>      public Long apply(StoreFile sf) {<a 
name="line.766"></a>
+<span class="sourceLineNo">767</span>        return sf.getMaxSequenceId();<a 
name="line.767"></a>
+<span class="sourceLineNo">768</span>      }<a name="line.768"></a>
+<span class="sourceLineNo">769</span>    }<a name="line.769"></a>
+<span class="sourceLineNo">770</span><a name="line.770"></a>
+<span class="sourceLineNo">771</span>    private static class GetFileSize 
implements Function&lt;StoreFile, Long&gt; {<a name="line.771"></a>
+<span class="sourceLineNo">772</span>      @Override<a name="line.772"></a>
+<span class="sourceLineNo">773</span>      public Long apply(StoreFile sf) {<a 
name="line.773"></a>
+<span class="sourceLineNo">774</span>        if (sf.getReader() != null) {<a 
name="line.774"></a>
+<span class="sourceLineNo">775</span>          return 
sf.getReader().length();<a name="line.775"></a>
+<span class="sourceLineNo">776</span>        } else {<a name="line.776"></a>
+<span class="sourceLineNo">777</span>          // the reader may be null for 
the compacted files and if the archiving<a name="line.777"></a>
+<span class="sourceLineNo">778</span>          // had failed.<a 
name="line.778"></a>
+<span class="sourceLineNo">779</span>          return -1L;<a 
name="line.779"></a>
+<span class="sourceLineNo">780</span>        }<a name="line.780"></a>
+<span class="sourceLineNo">781</span>      }<a name="line.781"></a>
+<span class="sourceLineNo">782</span>    }<a name="line.782"></a>
+<span class="sourceLineNo">783</span><a name="line.783"></a>
+<span class="sourceLineNo">784</span>    private static class GetBulkTime 
implements Function&lt;StoreFile, Long&gt; {<a name="line.784"></a>
+<span class="sourceLineNo">785</span>      @Override<a name="line.785"></a>
+<span class="sourceLineNo">786</span>      public Long apply(StoreFile sf) {<a 
name="line.786"></a>
+<span class="sourceLineNo">787</span>        if (!sf.isBulkLoadResult()) 
return Long.MAX_VALUE;<a name="line.787"></a>
+<span class="sourceLineNo">788</span>        return 
sf.getBulkLoadTimestamp();<a name="line.788"></a>
+<span class="sourceLineNo">789</span>      }<a name="line.789"></a>
+<span class="sourceLineNo">790</span>    }<a name="line.790"></a>
+<span class="sourceLineNo">791</span><a name="line.791"></a>
+<span class="sourceLineNo">792</span>    private static class GetPathName 
implements Function&lt;StoreFile, String&gt; {<a name="line.792"></a>
+<span class="sourceLineNo">793</span>      @Override<a name="line.793"></a>
+<span class="sourceLineNo">794</span>      public String apply(StoreFile sf) 
{<a name="line.794"></a>
+<span class="sourceLineNo">795</span>        return sf.getPath().getName();<a 
name="line.795"></a>
+<span class="sourceLineNo">796</span>      }<a name="line.796"></a>
+<span class="sourceLineNo">797</span>    }<a name="line.797"></a>
+<span class="sourceLineNo">798</span><a name="line.798"></a>
+<span class="sourceLineNo">799</span>    private static class GetMaxTimestamp 
implements Function&lt;StoreFile, Long&gt; {<a name="line.799"></a>
+<span class="sourceLineNo">800</span>      @Override<a name="line.800"></a>
+<span class="sourceLineNo">801</span>      public Long apply(StoreFile sf) {<a 
name="line.801"></a>
+<span class="sourceLineNo">802</span>        return sf.getMaximumTimestamp() 
== null? (Long)Long.MAX_VALUE : sf.getMaximumTimestamp();<a name="line.802"></a>
+<span class="sourceLineNo">803</span>      }<a name="line.803"></a>
+<span class="sourceLineNo">804</span>    }<a name="line.804"></a>
+<span class="sourceLineNo">805</span>  }<a name="line.805"></a>
+<span class="sourceLineNo">806</span>}<a name="line.806"></a>
 
 
 

Reply via email to