import Logger from '../logger';
import * as Shardus from '../shardus/shardus-types';
import { StateManager, P2P } from '@shardeum-foundation/lib-types';
import log4js from 'log4js';
import { Ordering } from '../utils';
type ShardGlobals = StateManager.shardFunctionTypes.ShardGlobals;
type ShardInfo = StateManager.shardFunctionTypes.ShardInfo;
type NodeShardData = StateManager.shardFunctionTypes.NodeShardData;
type NodeShardDataMap = StateManager.shardFunctionTypes.NodeShardDataMap;
type PartitionShardDataMap = StateManager.shardFunctionTypes.ParititionShardDataMap;
type WrappablePartitionRange = StateManager.shardFunctionTypes.WrappableParitionRange;
type HomeNodeSummary = StateManager.shardFunctionTypes.HomeNodeSummary;
type AddressRange = StateManager.shardFunctionTypes.AddressRange;
declare class ShardFunctions {
    static logger: Logger;
    static mainLogger: log4js.Logger;
    static fatalLogger: log4js.Logger;
    /**
     * calculateShardGlobals
     * @param {number} numNodes
     * @param {number} nodesPerConsenusGroup
     */
    static calculateShardGlobals(numNodes: number, nodesPerConsenusGroup: number, nodesPerEdge: number): ShardGlobals;
    static leadZeros8(input: string): string;
    static calculateShardValues(shardGlobals: ShardGlobals, address: string): ShardInfo;
    /**
     * calculateStoredPartitions2
     * gets the WrappablePartitionRange for a node's stored partitions
     * this uses nodesPerConsenusGroup as the radius to include, so we will end up with 1 + 2*nodesPerConsenusGroup stored partitions
     * @param shardGlobals
     * @param homePartition
     */
    static calculateStoredPartitions2(shardGlobals: ShardGlobals, homePartition: number): WrappablePartitionRange;
    static calculateConsensusPartitions(shardGlobals: ShardGlobals, homePartition: number): WrappablePartitionRange;
    /**
     * calculateParitionRange
     * give a center partition and the radius to calculate a WrappablePartitionRange
     * @param shardGlobals
     * @param homePartition
     * @param partitionRadius
     */
    static calculateParitionRange(shardGlobals: ShardGlobals, homePartition: number, partitionRadius: number): WrappablePartitionRange;
    /**
     * calculatePartitionRangeInternal
     * additional calculations required to fill out a WrappablePartitionRange and make sure the wrapping is correct
     * @param {ShardGlobals} shardGlobals
     * @param {WrappablePartitionRange} wrappablePartitionRange
     */
    static calculatePartitionRangeInternal(shardGlobals: ShardGlobals, wrappablePartitionRange: WrappablePartitionRange, partitionRadius: number): void;
    static testAddressInRange(address: string, wrappableParitionRange: WrappablePartitionRange): boolean;
    static testAddressNumberInRange(address: number, wrappableParitionRange: WrappablePartitionRange): boolean;
    static testInRange(partition: number, wrappableParitionRange: WrappablePartitionRange): boolean;
    static getPartitionsCovered(wrappableParitionRange: WrappablePartitionRange): number;
    static computePartitionShardDataMap(shardGlobals: ShardGlobals, partitionShardDataMap: PartitionShardDataMap, partitionStart: number, partitionsToScan: number): void;
    static computeNodePartitionDataMap(shardGlobals: ShardGlobals, nodeShardDataMap: NodeShardDataMap, nodesToGenerate: P2P.NodeListTypes.Node[], //Shardus.Node[],
    partitionShardDataMap: PartitionShardDataMap, activeNodes: Shardus.Node[], extendedData: boolean, isActiveNodeList?: boolean): void;
    static computeNodePartitionData(shardGlobals: ShardGlobals, node: Shardus.Node, nodeShardDataMap: NodeShardDataMap, partitionShardDataMap: PartitionShardDataMap, activeNodes: Shardus.Node[], extendedData?: boolean, thisNodeIndex?: number): NodeShardData;
    /**
     * @param {ShardGlobals} shardGlobals
     * @param {Map<string, NodeShardData>} nodeShardDataMap
     * @param {Map<number, ShardInfo>} partitionShardDataMap
     * @param {NodeShardData} nodeShardData
     * @param {Node[]} activeNodes
     */
    static computeExtendedNodePartitionData(shardGlobals: ShardGlobals, nodeShardDataMap: NodeShardDataMap, partitionShardDataMap: PartitionShardDataMap, nodeShardData: NodeShardData, activeNodes: Shardus.Node[]): void;
    static nodeSortAsc(a: Shardus.Node, b: Shardus.Node): Ordering;
    /**
     * getConsenusPartitions
     * @param {ShardGlobals} shardGlobals
     * @param {NodeShardData} nodeShardData the node we want to get a list of consensus partions from
     * @returns {number[]} a list of partitions
     */
    static getConsenusPartitionList(shardGlobals: ShardGlobals, nodeShardData: NodeShardData): number[];
    /**
     * getStoredPartitions
     * @param {ShardGlobals} shardGlobals
     * @param {NodeShardData} nodeShardData the node we want to get a list of consensus partions from
     * @returns {number[]} a list of partitions
     */
    static getStoredPartitionList(shardGlobals: ShardGlobals, nodeShardData: NodeShardData): number[];
    static setOverlap(aStart: number, aEnd: number, bStart: number, bEnd: number): boolean;
    static setEpanded(aStart: number, aEnd: number, bStart: number, bEnd: number): boolean;
    static setEpandedLeft(aStart: number, aEnd: number, bStart: number, bEnd: number): boolean;
    static setEpandedRight(aStart: number, aEnd: number, bStart: number, bEnd: number): boolean;
    static setShrink(aStart: number, aEnd: number, bStart: number, bEnd: number): boolean;
    static computeCoverageChanges(oldShardDataNodeShardData: NodeShardData, newSharddataNodeShardData: NodeShardData): {
        start: number;
        end: number;
    }[];
    static getHomeNodeSummaryObject(nodeShardData: NodeShardData): HomeNodeSummary;
    static getNodeRelation(nodeShardData: NodeShardData, nodeId: string): string;
    static getPartitionRangeFromRadix(shardGlobals: ShardGlobals, radix: string): {
        low: number;
        high: number;
    };
    static addressToPartition(shardGlobals: ShardGlobals, address: string): {
        homePartition: number;
        addressNum: number;
    };
    static addressNumberToPartition(shardGlobals: ShardGlobals, addressNum: number): number;
    static findHomeNode(shardGlobals: ShardGlobals, address: string, partitionShardDataMap: Map<number, ShardInfo>): NodeShardData | null;
    static circularDistance(a: number, b: number, max: number): number;
    /**
     * Merges two node lists
     * could make a faster version for sorted lists.. but not worth the complexity unless it shows up on a benchmark
     * @param {Shardus.Node[]} listA
     * @param {Shardus.Node[]} listB
     * @returns {array} result [results, extras]  TODO, convert the array response to a type object that has results and extras
     */
    static mergeNodeLists(listA: Shardus.Node[], listB: Shardus.Node[]): Shardus.Node[][];
    /**
     * @param {Shardus.Node[]} listA
     * @param {Shardus.Node[]} listB
     * @returns {Shardus.Node[]} results list
     */
    static subtractNodeLists(listA: Shardus.Node[], listB: Shardus.Node[]): Shardus.Node[];
    static partitionToAddressRange2(shardGlobals: ShardGlobals, partition: number, partitionMax?: number): AddressRange;
    /**
     * NOTE this is a raw answer.  edge cases with consensus node coverage can increase the results of our raw answer that is given here
     * @param {ShardGlobals} shardGlobals
     * @param {Map<string, NodeShardData>} nodeShardDataMap
     * @param {number} partition
     * @param {string[]} exclude
     * @param {Node[]} activeNodes
     */
    static getNodesThatCoverPartitionRaw(shardGlobals: ShardGlobals, nodeShardDataMap: Map<string, NodeShardData>, partition: number, exclude: string[], activeNodes: Shardus.Node[]): Shardus.Node[];
    static getCombinedNodeLists(shardGlobals: ShardGlobals, thisNode: NodeShardData, nodeShardDataMap: NodeShardDataMap, activeNodes: Shardus.Node[]): Record<string, P2P.NodeListTypes.Node[]>;
    /**
     * NOTE this is a raw answer.  edge cases with consensus node coverage can increase the results of our raw answer that is given here
     * @param {ShardGlobals} shardGlobals
     * @param {Map<string, NodeShardData>} nodeShardDataMap
     * @param {number} partition
     * @param {string[]} exclude
     * @param {Node[]} activeNodes
     */
    static getNodesThatCoverHomePartition(shardGlobals: ShardGlobals, thisNode: NodeShardData, nodeShardDataMap: Map<string, NodeShardData>, activeNodes: Shardus.Node[]): Shardus.Node[];
    static getEdgeNodes(shardGlobals: ShardGlobals, thisNode: NodeShardData, nodeShardDataMap: Map<string, NodeShardData>, activeNodes: Shardus.Node[]): Shardus.Node[];
    /**
     * getNeigborNodesInRange
     * get nodes in count range to either side of our node
     * position should be the position of the home node
     * @param {number} position
     * @param {number} radius
     * @param {string[]} exclude
     * @param {P2P.NodeListTypes.Node[]} allNodes
     */
    static getNeigborNodesInRange(position: number, radius: number, exclude: string[], allNodes: P2P.NodeListTypes.Node[]): Shardus.Node[];
    /**
     * getNodesByProximity This builds a sorted list of nodes based on how close they are to a given address
     * @param {ShardGlobals} shardGlobals
     * @param {Shardus.Node[]} activeNodes
     * @param {number} position
     * @param {string} excludeID
     * @param {number} [count]
     * @param {boolean} [centeredScan]
     */
    static getNodesByProximity(shardGlobals: ShardGlobals, activeNodes: Shardus.Node[], position: number, excludeID: string, count?: number, centeredScan?: boolean): Shardus.Node[];
    /**
     * findCenterAddressPair
     * @param {string} lowAddress
     * @param {string} highAddress
     * TSConversion  fix up any[] with a wrapped object.
     */
    static findCenterAddressPair(lowAddress: string, highAddress: string): string[];
    /**
     * This will find two address that are close to what we want
     * @param {string} address
     * @returns {{address1:string; address2:string}}
     * WARNING this only works input ends in all Fs after first byte.
     *
     */
    static getNextAdjacentAddresses(address: string): {
        address1: string;
        address2: string;
    };
    static getCenterHomeNode(shardGlobals: ShardGlobals, partitionShardDataMap: PartitionShardDataMap, lowAddress: string, highAddress: string): NodeShardData | null;
    /**
     * debug wrapper with exception handling for fastStableCorrespondingIndicies:
     * @param {number} fromListSize
     * @param {number} toListSize
     * @param {number} fromListIndex
     */
    static debugFastStableCorrespondingIndicies(fromListSize: number, toListSize: number, fromListIndex: number): number[];
    /**
     * Takes a list size of a from array and a list size of a to array.
     * uses the passed in index into list one to determine a list of indicies
     * that the from node would need to send a corresponding message to.
     * @param {number} fromListSize
     * @param {number} toListSize
     * @param {number} fromListIndex
     */
    static fastStableCorrespondingIndicies(fromListSize: number, toListSize: number, fromListIndex: number): number[];
    /**
     * partitionInWrappingRange
     * test if partition i is in the range of min and max P
     * This function understands wrapping, so that the min boundary can be
     * a higher number than the max boundary that wraps around back to 0
     * @param {number} i
     * @param {number} minP
     * @param {number} maxP
     */
    static partitionInWrappingRange(i: number, minP: number, maxP: number): boolean;
    private static modulo;
}
export default ShardFunctions;
export declare function addressToPartition(shardGlobals: ShardGlobals, address: string): {
    homePartition: number;
    addressNum: number;
};
export declare function partitionInWrappingRange(i: number, minP: number, maxP: number): boolean;
export declare function findHomeNode(shardGlobals: ShardGlobals, address: string, partitionShardDataMap: Map<number, ShardInfo>): NodeShardData | null;
