Coverage Summary for Class: DistanceCalculator (co.rsk.net.discovery.table)

Class Class, % Method, % Line, %
DistanceCalculator 0% (0/1) 0% (0/4) 0% (0/21)


1 /* 2  * This file is part of RskJ 3  * Copyright (C) 2017 RSK Labs Ltd. 4  * 5  * This program is free software: you can redistribute it and/or modify 6  * it under the terms of the GNU Lesser General Public License as published by 7  * the Free Software Foundation, either version 3 of the License, or 8  * (at your option) any later version. 9  * 10  * This program is distributed in the hope that it will be useful, 11  * but WITHOUT ANY WARRANTY; without even the implied warranty of 12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13  * GNU Lesser General Public License for more details. 14  * 15  * You should have received a copy of the GNU Lesser General Public License 16  * along with this program. If not, see <http://www.gnu.org/licenses/>. 17  */ 18  19 package co.rsk.net.discovery.table; 20  21 import co.rsk.net.NodeID; 22 import org.ethereum.crypto.HashUtil; 23  24 /** 25  * Calculates the distance between 2 nodes 26  */ 27 public class DistanceCalculator { 28  private final int maxDistance; 29  30  public DistanceCalculator(int maxDistance) { 31  this.maxDistance = maxDistance; 32  } 33  34  /** 35  * The distance is calculated as the Most Significant Bit (MSB) position 36  * of the XOR between the keccak256(keccak256(nodeId)) of the 2 nodes 37  * @param node1 id 38  * @param node2 id 39  * @return The distance between 2 nodes 40  */ 41  public int calculateDistance(NodeID node1, NodeID node2) { 42  byte[] nodeId1 = HashUtil.keccak256(HashUtil.keccak256(node1.getID())); 43  byte[] nodeId2 = HashUtil.keccak256(HashUtil.keccak256(node2.getID())); 44  byte[] result = new byte[nodeId1.length]; 45  46  for (int i = 0; i < result.length; i++) { 47  result[i] = (byte) (((int) nodeId1[i]) ^ ((int) nodeId2[i])); 48  } 49  50  return msbPosition(result); 51  } 52  53  /** 54  * 55  * @param result 56  * @return The MSB position of the XOR result. 57  */ 58  private int msbPosition(byte[] result) { 59  int distance = this.maxDistance; 60  61  for (byte b : result) { 62  if (b == 0) { 63  distance -= 8; 64  } else { 65  distance -= positionsToMove(b); 66  return distance; 67  } 68  } 69  70  return distance; 71  } 72  73  private int positionsToMove(byte b) { 74  int count = 0; 75  76  for (int i = 7; i >= 0; i--) { 77  if (((b & 0xff)& (1 << i)) == 0) { 78  count++; 79  } else { 80  return count; 81  } 82  } 83  84  return count; 85  } 86 }