Skip to content

Commit

Permalink
Renamed Sharding Table structs, added possibility to add Node to the …
Browse files Browse the repository at this point in the history
…Sharding Table using Binary Search for position search
  • Loading branch information
0xbraindevd committed Jan 24, 2024
1 parent dac7a27 commit 0aac2ab
Show file tree
Hide file tree
Showing 7 changed files with 125 additions and 94 deletions.
20 changes: 10 additions & 10 deletions contracts/v1/ShardingTable.sol
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import {ContractStatus} from "./abstract/ContractStatus.sol";
import {Initializable} from "./interface/Initializable.sol";
import {Named} from "./interface/Named.sol";
import {Versioned} from "./interface/Versioned.sol";
import {ShardingTableStructs} from "./structs/ShardingTableStructs.sol";
import {ShardingTableStructsV1} from "./structs/ShardingTableStructsV1.sol";
import {NULL} from "./constants/ShardingTableConstants.sol";

contract ShardingTable is Named, Versioned, ContractStatus, Initializable {
Expand Down Expand Up @@ -43,11 +43,11 @@ contract ShardingTable is Named, Versioned, ContractStatus, Initializable {
function getShardingTable(
uint72 startingIdentityId,
uint72 nodesNumber
) external view returns (ShardingTableStructs.NodeInfo[] memory) {
) external view returns (ShardingTableStructsV1.NodeInfo[] memory) {
return _getShardingTable(startingIdentityId, nodesNumber);
}

function getShardingTable() external view returns (ShardingTableStructs.NodeInfo[] memory) {
function getShardingTable() external view returns (ShardingTableStructsV1.NodeInfo[] memory) {
ShardingTableStorage sts = shardingTableStorage;
return _getShardingTable(sts.head(), sts.nodesCount());
}
Expand Down Expand Up @@ -106,7 +106,7 @@ contract ShardingTable is Named, Versioned, ContractStatus, Initializable {

ShardingTableStorage sts = shardingTableStorage;

ShardingTableStructs.Node memory nodeToRemove = sts.getNode(identityId);
ShardingTableStructsV1.Node memory nodeToRemove = sts.getNode(identityId);

uint72 head = sts.head();
uint72 tail = sts.tail();
Expand All @@ -133,24 +133,24 @@ contract ShardingTable is Named, Versioned, ContractStatus, Initializable {
function _getShardingTable(
uint72 startingIdentityId,
uint72 nodesNumber
) internal view virtual returns (ShardingTableStructs.NodeInfo[] memory) {
ShardingTableStructs.NodeInfo[] memory nodesPage;
) internal view virtual returns (ShardingTableStructsV1.NodeInfo[] memory) {
ShardingTableStructsV1.NodeInfo[] memory nodesPage;
ShardingTableStorage sts = shardingTableStorage;

if ((sts.nodesCount() == 0) || (nodesNumber == 0)) {
return nodesPage;
}

ShardingTableStructs.Node memory startingNode = sts.getNode(startingIdentityId);
ShardingTableStructsV1.Node memory startingNode = sts.getNode(startingIdentityId);

require((startingIdentityId == NULL) || (startingNode.identityId != NULL), "Wrong starting Identity ID");

nodesPage = new ShardingTableStructs.NodeInfo[](nodesNumber);
nodesPage = new ShardingTableStructsV1.NodeInfo[](nodesNumber);

ProfileStorage ps = profileStorage;
StakingStorage ss = stakingStorage;

nodesPage[0] = ShardingTableStructs.NodeInfo({
nodesPage[0] = ShardingTableStructsV1.NodeInfo({
nodeId: ps.getNodeId(startingIdentityId),
identityId: startingIdentityId,
ask: ps.getAsk(startingNode.identityId),
Expand All @@ -162,7 +162,7 @@ contract ShardingTable is Named, Versioned, ContractStatus, Initializable {
while ((i < nodesNumber) && (nextIdentityId != NULL)) {
nextIdentityId = sts.getNode(nextIdentityId).nextIdentityId;

nodesPage[i] = ShardingTableStructs.NodeInfo({
nodesPage[i] = ShardingTableStructsV1.NodeInfo({
nodeId: ps.getNodeId(nextIdentityId),
identityId: nextIdentityId,
ask: ps.getAsk(nextIdentityId),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

pragma solidity ^0.8.16;

library ShardingTableStructs {
library ShardingTableStructsV1 {
struct NodeInfo {
bytes nodeId;
uint72 identityId;
Expand Down
2 changes: 1 addition & 1 deletion contracts/v2/CommitManagerV1U1.sol
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ import {GeneralErrors} from "../v1/errors/GeneralErrors.sol";
import {ServiceAgreementErrorsV1} from "../v1/errors/ServiceAgreementErrorsV1.sol";
import {ServiceAgreementErrorsV2} from "./errors/ServiceAgreementErrorsV2.sol";
import {ServiceAgreementStructsV2} from "./structs/ServiceAgreementStructsV2.sol";
import {ShardingTableStructs} from "../v2/structs/ShardingTableStructs.sol";
import {ShardingTableStructsV2} from "../v2/structs/ShardingTableStructsV2.sol";
import {CommitManagerErrorsV2} from "./errors/CommitManagerErrorsV2.sol";

contract CommitManagerV2 is Named, Versioned, ContractStatus, Initializable {
Expand Down
141 changes: 90 additions & 51 deletions contracts/v2/ShardingTable.sol
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import {ContractStatus} from "../v1/abstract/ContractStatus.sol";
import {Initializable} from "../v1/interface/Initializable.sol";
import {Named} from "../v1/interface/Named.sol";
import {Versioned} from "../v1/interface/Versioned.sol";
import {ShardingTableStructs} from "./structs/ShardingTableStructs.sol";
import {ShardingTableStructsV2} from "./structs/ShardingTableStructsV2.sol";
import {ShardingTableErrors} from "./errors/ShardingTableErrors.sol";

import {NULL} from "../v1/constants/ShardingTableConstants.sol";
Expand Down Expand Up @@ -45,25 +45,90 @@ contract ShardingTableV2 is Named, Versioned, ContractStatus, Initializable {
function getShardingTable(
uint72 startingIdentityId,
uint72 nodesNumber
) external view returns (ShardingTableStructs.NodeInfo[] memory) {
) external view returns (ShardingTableStructsV2.NodeInfo[] memory) {
return _getShardingTable(startingIdentityId, nodesNumber);
}

function getShardingTable() external view returns (ShardingTableStructs.NodeInfo[] memory) {
function getShardingTable() external view returns (ShardingTableStructsV2.NodeInfo[] memory) {
ShardingTableStorageV2 sts = shardingTableStorage;
return _getShardingTable(sts.head(), sts.nodesCount());
}

function insertNode(uint72 identityId) external onlyContracts {
uint256 newNodeHashRingPosition = uint256(profileStorage.getNodeAddress(identityId, 1));
(uint72 prevIdentityId, uint72 nextIdentityId) = _binarySearchForPosition(newNodeHashRingPosition);

_insertNode(newNodeHashRingPosition, identityId, prevIdentityId, nextIdentityId);
}

function insertNode(uint72 identityId, uint72 prevIdentityId, uint72 nextIdentityId) external onlyContracts {
ProfileStorage ps = profileStorage;
_insertNode(uint256(profileStorage.getNodeAddress(identityId, 1)), identityId, prevIdentityId, nextIdentityId);
}

function removeNode(uint72 identityId) external onlyContracts {
ShardingTableStorageV2 sts = shardingTableStorage;

uint256 newNodeHashRingPosition = uint256(ps.getNodeAddress(identityId, 1));
ShardingTableStructsV2.Node memory nodeToRemove = sts.getNode(identityId);

require(newNodeHashRingPosition != 0, "Profile doesn't exist");
sts.link(nodeToRemove.prevIdentityId, nodeToRemove.nextIdentityId);

uint72 index = nodeToRemove.index;
uint72 nextIdentityId = nodeToRemove.nextIdentityId;
while (nextIdentityId != NULL) {
sts.decrementNodeIndex(nextIdentityId);
sts.setIdentityId(index, nextIdentityId);

unchecked {
index += 1;
}
nextIdentityId = sts.getNode(nextIdentityId).nextIdentityId;
}

sts.deleteNodeObject(identityId);
sts.decrementNodesCount();

emit NodeRemoved(identityId, profileStorage.getNodeId(identityId));
}

function _binarySearchForPosition(uint256 hashRingPosition) internal virtual returns (uint72, uint72) {
ShardingTableStorageV2 sts = shardingTableStorage;

ShardingTableStructs.Node memory prevNode = sts.getNode(prevIdentityId);
uint72 left = 0;
uint72 mid;
uint72 right = sts.nodesCount() - 1;

uint72 prevIdentityId;
uint72 nextIdentityId;
while (left <= right) {
mid = (left + right) / 2;
ShardingTableStructsV2.Node memory currentNode = sts.getNodeByIndex(mid);

if (currentNode.hashRingPosition < hashRingPosition) {
prevIdentityId = currentNode.identityId;
left = mid + 1;
} else if (currentNode.hashRingPosition > hashRingPosition) {
nextIdentityId = currentNode.identityId;
right = mid - 1;
} else {
prevIdentityId = currentNode.identityId;
nextIdentityId = currentNode.nextIdentityId;
break;
}
}

return (prevIdentityId, nextIdentityId);
}

function _insertNode(
uint256 newNodeHashRingPosition,
uint72 identityId,
uint72 prevIdentityId,
uint72 nextIdentityId
) internal virtual {
ShardingTableStorageV2 sts = shardingTableStorage;
ProfileStorage ps = profileStorage;

ShardingTableStructsV2.Node memory prevNode = sts.getNode(prevIdentityId);

if (prevNode.hashRingPosition > newNodeHashRingPosition) {
revert ShardingTableErrors.InvalidPreviousIdentityId(
Expand All @@ -74,7 +139,7 @@ contract ShardingTableV2 is Named, Versioned, ContractStatus, Initializable {
);
}

ShardingTableStructs.Node memory nextNode = sts.getNode(nextIdentityId);
ShardingTableStructsV2.Node memory nextNode = sts.getNode(nextIdentityId);

if (nextNode.identityId != NULL && nextNode.hashRingPosition < newNodeHashRingPosition) {
revert ShardingTableErrors.InvalidNextIdentityId(
Expand All @@ -95,13 +160,8 @@ contract ShardingTableV2 is Named, Versioned, ContractStatus, Initializable {
);
}

sts.createNodeObject(
uint256(ps.getNodeAddress(identityId, 1)),
nextNode.index,
identityId,
prevIdentityId,
nextIdentityId
);
sts.createNodeObject(newNodeHashRingPosition, identityId, prevIdentityId, nextIdentityId, nextNode.index);
sts.setIdentityId(nextNode.index, identityId);
sts.incrementNodesCount();

if (prevIdentityId == NULL) {
Expand All @@ -114,8 +174,14 @@ contract ShardingTableV2 is Named, Versioned, ContractStatus, Initializable {
sts.link(identityId, nextIdentityId);
}

uint72 index = nextNode.index + 1;
while (nextIdentityId != NULL) {
sts.incrementNodeIndex(nextIdentityId);
sts.setIdentityId(index, nextIdentityId);

unchecked {
index += 1;
}
nextIdentityId = sts.getNode(nextIdentityId).nextIdentityId;
}

Expand All @@ -127,66 +193,39 @@ contract ShardingTableV2 is Named, Versioned, ContractStatus, Initializable {
);
}

function removeNode(uint72 identityId) external onlyContracts {
ShardingTableStorageV2 sts = shardingTableStorage;

ShardingTableStructs.Node memory nodeToRemove = sts.getNode(identityId);

require(nodeToRemove.identityId != 0, "Profile doesn't exist");

sts.link(nodeToRemove.prevIdentityId, nodeToRemove.nextIdentityId);

uint72 nextIdentityId = nodeToRemove.nextIdentityId;
while (nextIdentityId != NULL) {
sts.decrementNodeIndex(nextIdentityId);
nextIdentityId = sts.getNode(nextIdentityId).nextIdentityId;
}

sts.deleteNodeObject(identityId);
sts.decrementNodesCount();

emit NodeRemoved(identityId, profileStorage.getNodeId(identityId));
}

function _getShardingTable(
uint72 startingIdentityId,
uint72 nodesNumber
) internal view virtual returns (ShardingTableStructs.NodeInfo[] memory) {
ShardingTableStructs.NodeInfo[] memory nodesPage;
) internal view virtual returns (ShardingTableStructsV2.NodeInfo[] memory) {
ShardingTableStructsV2.NodeInfo[] memory nodesPage;
ShardingTableStorageV2 sts = shardingTableStorage;

if ((sts.nodesCount() == 0) || (nodesNumber == 0)) {
return nodesPage;
}

ShardingTableStructs.Node memory startingNode = sts.getNode(startingIdentityId);
ShardingTableStructsV2.Node memory startingNode = sts.getNode(startingIdentityId);

require((startingIdentityId == NULL) || (startingNode.identityId != NULL), "Wrong starting Identity ID");

nodesPage = new ShardingTableStructs.NodeInfo[](nodesNumber);
nodesPage = new ShardingTableStructsV2.NodeInfo[](nodesNumber);

ProfileStorage ps = profileStorage;
StakingStorage ss = stakingStorage;

nodesPage[0] = ShardingTableStructs.NodeInfo({
nodeId: ps.getNodeId(startingIdentityId),
identityId: startingIdentityId,
ask: ps.getAsk(startingNode.identityId),
stake: ss.totalStakes(startingNode.identityId)
});

uint72 nextIdentityId = startingIdentityId;
uint72 i = 1;
uint72 i;
while ((i < nodesNumber) && (nextIdentityId != NULL)) {
nextIdentityId = sts.getNode(nextIdentityId).nextIdentityId;

nodesPage[i] = ShardingTableStructs.NodeInfo({
nodesPage[i] = ShardingTableStructsV2.NodeInfo({
hashRingPosition: uint256(ps.getNodeAddress(nextIdentityId, 1)),
nodeId: ps.getNodeId(nextIdentityId),
identityId: nextIdentityId,
ask: ps.getAsk(nextIdentityId),
stake: ss.totalStakes(nextIdentityId)
});

nextIdentityId = sts.getNode(nextIdentityId).nextIdentityId;

unchecked {
i += 1;
}
Expand Down
23 changes: 0 additions & 23 deletions contracts/v2/scoring/LinearSum.sol
Original file line number Diff line number Diff line change
Expand Up @@ -70,29 +70,6 @@ contract LinearSum is IScoreFunction, Indexable, Named, HubDependent, Initializa
return uint256(nodeIdHash ^ keywordHash);
}

function calculateClockwiseProximityOnHashRing(
uint8 hashFunctionId,
bytes calldata nodeId,
bytes calldata keyword
) external view returns (uint256) {
HashingProxy hp = hashingProxy;
bytes32 nodeIdHash = hp.callHashFunction(hashFunctionId, nodeId);
bytes32 keywordHash = hp.callHashFunction(hashFunctionId, keyword);

uint256 peerPositionOnHashRing = uint256(nodeIdHash);
uint256 keyPositionOnHashRing = uint256(keywordHash);

uint256 clockwiseDistance;
if (peerPositionOnHashRing > keyPositionOnHashRing) {
uint256 distanceToEnd = HASH_RING_SIZE - peerPositionOnHashRing;
clockwiseDistance = distanceToEnd + keyPositionOnHashRing;
} else {
clockwiseDistance = keyPositionOnHashRing - peerPositionOnHashRing;
}

return clockwiseDistance;
}

function calculateBidirectionalProximityOnHashRing(
uint8 hashFunctionId,
bytes calldata peerHash,
Expand Down
Loading

0 comments on commit 0aac2ab

Please sign in to comment.