Formatted with Google Java Style

This commit is contained in:
armin 2018-04-28 16:10:13 +02:00
parent 1e2b04a75c
commit 7c283aa827
21 changed files with 872 additions and 816 deletions

View file

@ -0,0 +1,3 @@
@
src/bfclient.cpp,4/6/4680e865da2ad46d274693738207d7b9d80f04ae

View file

@ -0,0 +1,3 @@
m squid:S1118":Add a private constructor to hide the implicit public one.(ôÒÿùüÿÿÿÿHÓ•RMAJORZ
CODE_SMELL

View file

@ -0,0 +1,23 @@
Œ
squid:S135œ"YReduce the total number of break and continue statements in this loop to use at most one.(ÊÑ€ÄûÿÿÿÿHÈ•RMINORZ
CODE_SMELL
Œ
squid:S135Ä"YReduce the total number of break and continue statements in this loop to use at most one.(ÊÑ€ÄûÿÿÿÿHÉ•RMINORZ
CODE_SMELL
ˆ squid:S14885"ZImmediately return this expression instead of assigning it to the temporary variable "kr".(·“žÉHÊ•RMINORZ
CODE_SMELL
wsquid:HiddenFieldChecké"8Rename "root" which hides the field declared at line 20.(Ë·Þ÷ÿÿÿÿÿHË•RMAJORZ
CODE_SMELL
 squid:S3776<18>"RRefactor this method to reduce its Cognitive Complexity from 21 to the 15 allowed.(¨îïƒHÌ•RCRITICALZ
CODE_SMELL
 squid:S1149Q"_Replace the synchronized class "StringBuffer" by an unsynchronized one such as "StringBuilder".(¨âà<C3A2>øÿÿÿÿHÍ•RMAJORZ
CODE_SMELL
S squid:S3457#"%String contains no format specifiers.(Ï·Ž®HΕRMAJORZ
CODE_SMELL
S squid:S3457'"%String contains no format specifiers.(<28>¹ÓáHÏ•RMAJORZ
CODE_SMELL
Y squid:S3457ê"%String contains no format specifiers.(óŠ¡ËþÿÿÿÿHЕRMAJORZ
CODE_SMELL
T squid:S3457ì"%String contains no format specifiers.(ÐÒ̉HÑ•RMAJORZ
CODE_SMELL

View file

@ -0,0 +1,3 @@
Œsquid:UselessImportCheck "QRemove this unused import 'org.btcollider.cnc.keysrv.impl.keytree.KeyTreeServer'.(‹Ö†’H¶•RMINORZ
CODE_SMELL

View file

@ -0,0 +1,8 @@
j"squid:SwitchLastCaseIsDefaultChecky""Add a default case to this switch.(¬ý<C2AC>½HÝ•RCRITICALZ
CODE_SMELL
X squid:S3457."%String contains no format specifiers.(’†þ‡ùÿÿÿÿHß•RMAJORZ
CODE_SMELL
o squid:S2259y"AA "NullPointerException" could be thrown; "suc" is nullable here.(¬ý<C2AC>½8¤ðä°,Hà•RMAJORZBUG
y squid:S1301y"KReplace this "switch" statement by "if" statements to increase readability.(¬ý<C2AC>½HÞ•RMINORZ
CODE_SMELL

View file

@ -0,0 +1,13 @@
g
7src/main/java/org/btcollider/cnc/comm/ClientWorker.java,f/b/fb0de740b71d2edb598c4f3deb39da1c59c1ec4f
Y
)src/main/java/org/btcollider/cnc/CnC.java,e/c/ecc7f16c71ca2f68bf6a65ea47837815c0ff6322
w
Gsrc/main/java/org/btcollider/cnc/keysrv/impl/keytree/KeyTreeServer.java,7/c/7c3c3c10537a28026398df21221528f81672fc33
f
6src/main/java/org/btcollider/cnc/keysrv/KSFactory.java,1/3/136c36f2bf1690ff10397e07c3d82baa9b298770
q
Asrc/main/java/org/btcollider/cnc/keysrv/impl/keytree/KeyTree.java,b/a/ba1dbf788a980366658d348281a337f09d5317fc
~
Nsrc/main/java/org/btcollider/cnc/keysrv/impl/multistage/MultiStagedServer.java,3/8/3893e371f649cb23d5f6428b3ca5eeae3bd4979f

View file

@ -1,12 +1,10 @@
package org.btcollider.cnc; package org.btcollider.cnc;
import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeUnit;
import org.btcollider.cnc.comm.CommException; import org.btcollider.cnc.comm.CommException;
import org.btcollider.cnc.comm.CommServer; import org.btcollider.cnc.comm.CommServer;
import org.btcollider.cnc.keysrv.KSFactory; import org.btcollider.cnc.keysrv.KSFactory;
import org.btcollider.cnc.keysrv.KeyServer; import org.btcollider.cnc.keysrv.KeyServer;
import org.btcollider.cnc.keysrv.impl.keytree.KeyTreeServer;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;

View file

@ -8,7 +8,6 @@ import java.io.InputStreamReader;
import java.io.OutputStreamWriter; import java.io.OutputStreamWriter;
import java.io.PrintWriter; import java.io.PrintWriter;
import java.net.Socket; import java.net.Socket;
import org.btcollider.cnc.dto.KeyRange; import org.btcollider.cnc.dto.KeyRange;
import org.btcollider.cnc.keysrv.KeyServer; import org.btcollider.cnc.keysrv.KeyServer;
import org.slf4j.Logger; import org.slf4j.Logger;
@ -92,9 +91,9 @@ public class ClientWorker implements Runnable {
if (kr == null) { if (kr == null) {
out.println("NIL"); out.println("NIL");
log.debug("Stop work sent to {}", clientSocket.getInetAddress()); log.debug("Stop work sent to {}", clientSocket.getInetAddress());
} } else {
else { String work = Long.toHexString(kr.getStart()) + " " + Long.toHexString(kr.getEnd()) + " "
String work = Long.toHexString(kr.getStart()) + " " + Long.toHexString(kr.getEnd()) + " " + kr.getTotal(); + kr.getTotal();
out.println(work); out.println(work);
log.debug("Work <{}> sent to {}", work, clientSocket.getInetAddress()); log.debug("Work <{}> sent to {}", work, clientSocket.getInetAddress());
} }
@ -114,6 +113,12 @@ public class ClientWorker implements Runnable {
out.println("ACK"); out.println("ACK");
String suc = in.readLine(); String suc = in.readLine();
if (suc == null) {
log.warn("Result retrieved from {} for {} but couldn't read success status",
clientSocket.getRemoteSocketAddress(), kr);
return;
}
switch (suc) { switch (suc) {
case "NIL": case "NIL":
log.debug("Keyrange {} unsuccessful", kr); log.debug("Keyrange {} unsuccessful", kr);
@ -126,6 +131,8 @@ public class ClientWorker implements Runnable {
writeKey(suc); writeKey(suc);
out.println("ACK"); out.println("ACK");
break; break;
default:
assert (false);
} }
} catch (IOException e) { } catch (IOException e) {
@ -134,9 +141,9 @@ public class ClientWorker implements Runnable {
} }
private void writeKey(String key) { private void writeKey(String key) {
try(BufferedWriter writer = new BufferedWriter(new FileWriter("/home/armin/Desktop/cwkey"))){ try (BufferedWriter writer = new BufferedWriter(new FileWriter("/home/armin/Desktop/cwkey"))) {
writer.write(key); writer.write(key);
}catch(IOException e) { } catch (IOException e) {
log.error("Couldn't write key {} to keyfile", key, e); log.error("Couldn't write key {} to keyfile", key, e);
} }
} }

View file

@ -21,8 +21,7 @@ public class CommException extends Exception {
super(cause); super(cause);
} }
protected CommException(String message, Throwable cause, protected CommException(String message, Throwable cause, boolean enableSuppression,
boolean enableSuppression,
boolean writableStackTrace) { boolean writableStackTrace) {
super(message, cause, enableSuppression, writableStackTrace); super(message, cause, enableSuppression, writableStackTrace);
} }

View file

@ -6,7 +6,6 @@ import java.net.Socket;
import java.util.concurrent.ExecutorService; import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors; import java.util.concurrent.Executors;
import org.btcollider.cnc.keysrv.KeyServer; import org.btcollider.cnc.keysrv.KeyServer;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
@ -23,7 +22,7 @@ public class CommServer {
} }
public void listen() throws CommException { public void listen() throws CommException {
if(serverSocket == null || serverSocket.isClosed()) { if (serverSocket == null || serverSocket.isClosed()) {
openSocket(); openSocket();
} }

View file

@ -1,7 +1,6 @@
package org.btcollider.cnc.dto; package org.btcollider.cnc.dto;
import java.util.BitSet; import java.util.BitSet;
import org.btcollider.cnc.CnC; import org.btcollider.cnc.CnC;
public class KeyRange { public class KeyRange {
@ -37,7 +36,7 @@ public class KeyRange {
@Override @Override
public String toString() { public String toString() {
return "KeyRange [start=" + start + ", end=" + end + ", total=" + getTotal() +"]"; return "KeyRange [start=" + start + ", end=" + end + ", total=" + getTotal() + "]";
} }
@Override @Override

View file

@ -1,7 +1,6 @@
package org.btcollider.cnc.keysrv; package org.btcollider.cnc.keysrv;
import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeUnit;
import org.btcollider.cnc.keysrv.impl.keytree.KeyTreeServer; import org.btcollider.cnc.keysrv.impl.keytree.KeyTreeServer;
import org.btcollider.cnc.keysrv.impl.multistage.MultiStagedServer; import org.btcollider.cnc.keysrv.impl.multistage.MultiStagedServer;
@ -15,16 +14,18 @@ public class KSFactory {
return build(index, depth, maxWorkSpan, timeUnit, 0); return build(index, depth, maxWorkSpan, timeUnit, 0);
} }
public static KeyServer build(int index, int depth, long maxWorkSpan, TimeUnit timeUnit, float pruneFraction) { public static KeyServer build(int index, int depth, long maxWorkSpan, TimeUnit timeUnit,
float pruneFraction) {
assert (pruneFraction >= 0.0 && pruneFraction <= 1.0); assert (pruneFraction >= 0.0 && pruneFraction <= 1.0);
long maxKey = ((long) 1 << index) | (( (long) 1 << index) - 1); long maxKey = ((long) 1 << index) | (((long) 1 << index) - 1);
long pruneKey = (long) Math.floor(maxKey * pruneFraction); long pruneKey = (long) Math.floor(maxKey * pruneFraction);
return build(index, depth, maxWorkSpan, timeUnit, pruneKey); return build(index, depth, maxWorkSpan, timeUnit, pruneKey);
} }
public static KeyServer build(int index, int depth, long maxWorkSpan, TimeUnit timeUnit, long pruneKey) { public static KeyServer build(int index, int depth, long maxWorkSpan, TimeUnit timeUnit,
long pruneKey) {
if (depth == 25) { if (depth == 25) {
return new KeyTreeServer(index, depth, timeUnit.toMillis(maxWorkSpan), pruneKey); return new KeyTreeServer(index, depth, timeUnit.toMillis(maxWorkSpan), pruneKey);
} else { } else {

View file

@ -4,8 +4,7 @@ import org.btcollider.cnc.dto.KeyRange;
public interface KeyServer { public interface KeyServer {
/** /**
* Gets a free (= not setInWork and not setSearched) * Gets a free (= not setInWork and not setSearched) KeyRange from the pool of possible key ranges
* KeyRange from the pool of possible key ranges
* *
* @return A free KeyRange or null if none such exists * @return A free KeyRange or null if none such exists
*/ */
@ -14,20 +13,17 @@ public interface KeyServer {
/** /**
* Sets a KeyRange as being currently worked on. * Sets a KeyRange as being currently worked on.
* *
* As long as a KeyRange is not setSearched, there * As long as a KeyRange is not setSearched, there is no guarantee that an inWork KeyRange will be
* is no guarantee that an inWork KeyRange will be finished * finished in any specific time frame. The KeyServer has to clean up dangling inWorks in good
* in any specific time frame. * faith. Unexpected setSearched of already cleaned-up inWorks must not be of any harm.
* The KeyServer has to clean up dangling inWorks in good
* faith. Unexpected setSearched of already cleaned-up inWorks
* must not be of any harm.
* *
* @param keyRange The KeyRange to be set as being worked on, not null * @param keyRange The KeyRange to be set as being worked on, not null
*/ */
void setInWork(KeyRange keyRange); void setInWork(KeyRange keyRange);
/** /**
* Sets a KeyRange as being searched, finalizing this range * Sets a KeyRange as being searched, finalizing this range A searched KeyRange need not be
* A searched KeyRange need not be processed any more * processed any more
* *
* @param keyRange The KeyRange to be set as searched, not null * @param keyRange The KeyRange to be set as searched, not null
*/ */

View file

@ -20,20 +20,22 @@ public class KTConcierge implements Runnable {
} }
private void recCheckInWork(KeyTree node) { private void recCheckInWork(KeyTree node) {
if (node == null) return; if (node == null)
return;
if (node.inWork()) { if (node.inWork()) {
long inWorkSpan = System.currentTimeMillis() - node.inWorkSince(); long inWorkSpan = System.currentTimeMillis() - node.inWorkSince();
if (inWorkSpan >= maxWorkSpan) { if (inWorkSpan >= maxWorkSpan) {
if (node.isLeaf()) { if (node.isLeaf()) {
StringBuilder key = new StringBuilder(); StringBuilder key = new StringBuilder();
key.append(node.getValue() ? "1": "0"); key.append(node.getValue() ? "1" : "0");
KeyTree parent = node.getParent(); KeyTree parent = node.getParent();
while (parent != null) { while (parent != null) {
key.insert(0, parent.getValue() ? "1": "0"); key.insert(0, parent.getValue() ? "1" : "0");
parent = parent.getParent(); parent = parent.getParent();
} }
log.debug("{}: Retracting Work for key {}, inWorkSince: {}", System.currentTimeMillis(), key, node.inWorkSince()); log.debug("{}: Retracting Work for key {}, inWorkSince: {}", System.currentTimeMillis(),
key, node.inWorkSince());
} }
node.clearInWork(); node.clearInWork();
} }

View file

@ -7,7 +7,6 @@ import java.util.Random;
import java.util.concurrent.Executors; import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService; import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeUnit;
import org.btcollider.cnc.CnC; import org.btcollider.cnc.CnC;
import org.btcollider.cnc.dto.KeyRange; import org.btcollider.cnc.dto.KeyRange;
import org.btcollider.cnc.keysrv.KeyServer; import org.btcollider.cnc.keysrv.KeyServer;
@ -29,7 +28,8 @@ public class KeyTreeServer implements KeyServer {
this.index = index; this.index = index;
this.root = generateKeyTree(depth); this.root = generateKeyTree(depth);
if (pruneKey > 0) prune(pruneKey); if (pruneKey > 0)
prune(pruneKey);
if (maxWorkSpan > 0) { if (maxWorkSpan > 0) {
log.info("Starting KeyTree concierge"); log.info("Starting KeyTree concierge");
@ -40,6 +40,7 @@ public class KeyTreeServer implements KeyServer {
} }
} }
@Override
public KeyRange getRange() { public KeyRange getRange() {
BitSet keyStart = new BitSet(CnC.MAX_BITS); BitSet keyStart = new BitSet(CnC.MAX_BITS);
@ -61,20 +62,22 @@ public class KeyTreeServer implements KeyServer {
long step = (long) Math.pow(2, ((index + 1) - depth)); long step = (long) Math.pow(2, ((index + 1) - depth));
for (long i = from; i < to; i += step) { for (long i = from; i < to; i += step) {
BitSet searchedKey = BitSet.valueOf(new long[] { i }); BitSet searchedKey = BitSet.valueOf(new long[] {i});
markSearched(searchedKey); markSearched(searchedKey);
} }
} }
@Override
public void setSearched(KeyRange keyRange) { public void setSearched(KeyRange keyRange) {
markSearched(BitSet.valueOf(new long[] { keyRange.getStart() })); markSearched(BitSet.valueOf(new long[] {keyRange.getStart()}));
} }
@Override
public void setInWork(KeyRange keyRange) { public void setInWork(KeyRange keyRange) {
if (keyRange == null) if (keyRange == null)
return; return;
markInWork(BitSet.valueOf(new long[] { keyRange.getStart() })); markInWork(BitSet.valueOf(new long[] {keyRange.getStart()}));
} }
public String printDot() { public String printDot() {
@ -118,13 +121,11 @@ public class KeyTreeServer implements KeyServer {
/** /**
* Prunes every branch strictly smaller than pruneKey * Prunes every branch strictly smaller than pruneKey
* *
* @param prune * @param prune The smallest valid key in the keyspace Must be at least as large as the smallest
* The smallest valid key in the keyspace Must be at least as large * key in the tree Must be at most as large as the largest key in the tree
* as the smallest key in the tree Must be at most as large as the
* largest key in the tree
*/ */
private void prune(Long pruneKey) { private void prune(Long pruneKey) {
BitSet pkBS = BitSet.valueOf(new long[] { pruneKey }); BitSet pkBS = BitSet.valueOf(new long[] {pruneKey});
int curIdx = pkBS.length() - 1; int curIdx = pkBS.length() - 1;
assert (curIdx == this.index); // at least the smallest, at most the largest key in the tree assert (curIdx == this.index); // at least the smallest, at most the largest key in the tree
// -> pos of highest bits is equal // -> pos of highest bits is equal
@ -133,10 +134,12 @@ public class KeyTreeServer implements KeyServer {
} }
private void recPrune(BitSet pruneKey, KeyTree node, int curIdx) { private void recPrune(BitSet pruneKey, KeyTree node, int curIdx) {
if (node.getValue() && !pruneKey.get(curIdx)) { // node[ix] = 0 and pruneK[ix] = 1 -> path smaller if (node.getValue() && !pruneKey.get(curIdx)) { // node[ix] = 0 and pruneK[ix] = 1 -> path
// smaller
node.setSearched(true); node.setSearched(true);
return; return;
} else if (!node.getValue() && pruneKey.get(curIdx)) { // node[ix] = 1 and pruneK[ix] = 0 -> path } else if (!node.getValue() && pruneKey.get(curIdx)) { // node[ix] = 1 and pruneK[ix] = 0 ->
// path
return; return;
} }
@ -145,8 +148,8 @@ public class KeyTreeServer implements KeyServer {
return; return;
} }
recPrune(pruneKey, node.getLeft(), curIdx-1); recPrune(pruneKey, node.getLeft(), curIdx - 1);
recPrune(pruneKey, node.getRight(), curIdx-1); recPrune(pruneKey, node.getRight(), curIdx - 1);
} }
private void markInWork(BitSet key) { private void markInWork(BitSet key) {

View file

@ -2,18 +2,16 @@ package org.btcollider.cnc.keysrv.impl.multistage;
import java.util.HashMap; import java.util.HashMap;
import java.util.Map.Entry; import java.util.Map.Entry;
import org.btcollider.cnc.dto.KeyRange; import org.btcollider.cnc.dto.KeyRange;
/** /**
* The MultiStagedServer may switch partitions while there are still KeyRanges * The MultiStagedServer may switch partitions while there are still KeyRanges from the old
* from the old partition that are currently worked on. * partition that are currently worked on.
* *
* This buffer stores the state of unfinished KeyRanges from old partitions in * This buffer stores the state of unfinished KeyRanges from old partitions in order to handle them
* order to handle them correctly. * correctly.
* *
* Aborted KeyRanges from this Buffer should be always preferred to getting new * Aborted KeyRanges from this Buffer should be always preferred to getting new ranges.
* ranges.
* *
* @author armin * @author armin
*/ */
@ -38,8 +36,8 @@ public class KeyRangeBuffer {
long curTime = System.currentTimeMillis(); long curTime = System.currentTimeMillis();
KeyRange retracedRange = null; KeyRange retracedRange = null;
for (Entry<KeyRange, Long> kr: keyRanges.entrySet()) { for (Entry<KeyRange, Long> kr : keyRanges.entrySet()) {
if ( (curTime - kr.getValue()) >= maxWorkSpan ) { if ((curTime - kr.getValue()) >= maxWorkSpan) {
retracedRange = kr.getKey(); retracedRange = kr.getKey();
break; break;
} }

View file

@ -7,8 +7,8 @@ import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
/** /**
* Not entirely random KeyServer that handles very large trees in multiple stages * Not entirely random KeyServer that handles very large trees in multiple stages to reduce memory
* to reduce memory and processing time consumption * and processing time consumption
* *
* @author armin * @author armin
* *
@ -39,19 +39,20 @@ public class MultiStagedServer implements KeyServer {
// This represents the actual work-horse KeyTreeServer for the current partition with // This represents the actual work-horse KeyTreeServer for the current partition with
// enabled KTConcierge service. // enabled KTConcierge service.
// Needs subindex+1 because starting bit always set to 1 // Needs subindex+1 because starting bit always set to 1
long subPrune = ((long) 1 << subIndex+1) | ( (((long) 1 << subIndex+1) - 1) & pruneKey ); long subPrune = ((long) 1 << subIndex + 1) | ((((long) 1 << subIndex + 1) - 1) & pruneKey);
this.secKTS = new KeyTreeServer(subIndex+1, remainingDepth, maxWorkSpan, subPrune); this.secKTS = new KeyTreeServer(subIndex + 1, remainingDepth, maxWorkSpan, subPrune);
this.keyRangeBuffer = new KeyRangeBuffer(maxWorkSpan); this.keyRangeBuffer = new KeyRangeBuffer(maxWorkSpan);
} }
@Override @Override
public KeyRange getRange() { public KeyRange getRange() {
if (partition == null) return null; // We are finished searching the whole space if (partition == null)
return null; // We are finished searching the whole space
KeyRange kr = null; KeyRange kr = null;
if ( (kr = keyRangeBuffer.getRange()) == null) { // Get retracted KR from buffer if one exists if ((kr = keyRangeBuffer.getRange()) == null) { // Get retracted KR from buffer if one exists
kr = secKTS.getRange(); // else: get a random range from the subspace kr = secKTS.getRange(); // else: get a random range from the subspace
} }
@ -59,12 +60,12 @@ public class MultiStagedServer implements KeyServer {
log.info("Subrange {} finished. Opening new partition.", partition); log.info("Subrange {} finished. Opening new partition.", partition);
primKTS.setSearched(partition); primKTS.setSearched(partition);
partition = primKTS.getRange(); partition = primKTS.getRange();
secKTS = new KeyTreeServer(subIndex+1, remainingDepth, maxWorkSpan, 0); secKTS = new KeyTreeServer(subIndex + 1, remainingDepth, maxWorkSpan, 0);
return getRange(); return getRange();
} }
// strip out starting bit of subrange // strip out starting bit of subrange
long krStart = kr.getStart() & ~(1 << subIndex+1); long krStart = kr.getStart() & ~(1 << subIndex + 1);
// extract set tail bits // extract set tail bits
long krEnd = kr.getStart() ^ kr.getEnd(); long krEnd = kr.getStart() ^ kr.getEnd();
@ -80,9 +81,9 @@ public class MultiStagedServer implements KeyServer {
keyRangeBuffer.setInWork(keyRange); keyRangeBuffer.setInWork(keyRange);
// strip out partition bits -> get subspace KeyRange only // strip out partition bits -> get subspace KeyRange only
long mask = (long) Math.pow(2, (subIndex+1)) - 1; long mask = (long) Math.pow(2, (subIndex + 1)) - 1;
// add leading bit // add leading bit
long lb = (long) Math.pow(2, (subIndex+1)); long lb = (long) Math.pow(2, (subIndex + 1));
KeyRange secKR = new KeyRange(keyRange.getStart() & mask | lb, keyRange.getEnd() & mask | lb); KeyRange secKR = new KeyRange(keyRange.getStart() & mask | lb, keyRange.getEnd() & mask | lb);
secKTS.setInWork(secKR); secKTS.setInWork(secKR);
@ -93,9 +94,9 @@ public class MultiStagedServer implements KeyServer {
keyRangeBuffer.setSearched(keyRange); keyRangeBuffer.setSearched(keyRange);
// strip out partition bits -> get subspace KeyRange only // strip out partition bits -> get subspace KeyRange only
long mask = (long) Math.pow(2, (subIndex+1)) - 1; long mask = (long) Math.pow(2, (subIndex + 1)) - 1;
// add leading bit // add leading bit
long lb = (long) Math.pow(2, (subIndex+1)); long lb = (long) Math.pow(2, (subIndex + 1));
KeyRange secKR = new KeyRange(keyRange.getStart() & mask | lb, keyRange.getEnd() & mask | lb); KeyRange secKR = new KeyRange(keyRange.getStart() & mask | lb, keyRange.getEnd() & mask | lb);
secKTS.setSearched(secKR); secKTS.setSearched(secKR);