mirror of
https://github.com/mimblewimble/grin.git
synced 2025-01-21 03:21:08 +03:00
[T4] Rename all shiftsize / cuckoo_size to edge_bits and change value for T4 (#1752)
* replace all size_shift / cuckoo_size by edge_bits and change some constants for T4 * replace remaining occurrences of sizeshift
This commit is contained in:
parent
a41022f1e3
commit
34646ddf51
22 changed files with 136 additions and 137 deletions
|
@ -502,7 +502,7 @@ pub struct BlockHeaderPrintable {
|
|||
/// Nonce increment used to mine this block.
|
||||
pub nonce: u64,
|
||||
/// Size of the cuckoo graph
|
||||
pub cuckoo_size: u8,
|
||||
pub edge_bits: u8,
|
||||
pub cuckoo_solution: Vec<u64>,
|
||||
/// Total accumulated difficulty since genesis block
|
||||
pub total_difficulty: u64,
|
||||
|
@ -522,7 +522,7 @@ impl BlockHeaderPrintable {
|
|||
range_proof_root: util::to_hex(h.range_proof_root.to_vec()),
|
||||
kernel_root: util::to_hex(h.kernel_root.to_vec()),
|
||||
nonce: h.pow.nonce,
|
||||
cuckoo_size: h.pow.cuckoo_sizeshift(),
|
||||
edge_bits: h.pow.edge_bits(),
|
||||
cuckoo_solution: h.pow.proof.nonces.clone(),
|
||||
total_difficulty: h.pow.total_difficulty.to_num(),
|
||||
total_kernel_offset: h.total_kernel_offset.to_hex(),
|
||||
|
|
|
@ -45,9 +45,9 @@ pub enum ErrorKind {
|
|||
/// Addition of difficulties on all previous block is wrong
|
||||
#[fail(display = "Addition of difficulties on all previous blocks is wrong")]
|
||||
WrongTotalDifficulty,
|
||||
/// Block header sizeshift is incorrect
|
||||
#[fail(display = "Cuckoo size shift is invalid")]
|
||||
InvalidSizeshift,
|
||||
/// Block header edge_bits is lower than our min
|
||||
#[fail(display = "Cuckoo Size too small")]
|
||||
LowEdgebits,
|
||||
/// Scaling factor between primary and secondary PoW is invalid
|
||||
#[fail(display = "Wrong scaling factor")]
|
||||
InvalidScaling,
|
||||
|
|
|
@ -371,13 +371,13 @@ fn validate_header(header: &BlockHeader, ctx: &mut BlockContext) -> Result<(), E
|
|||
|
||||
if !ctx.opts.contains(Options::SKIP_POW) {
|
||||
if !header.pow.is_primary() && !header.pow.is_secondary() {
|
||||
return Err(ErrorKind::InvalidSizeshift.into());
|
||||
return Err(ErrorKind::LowEdgebits.into());
|
||||
}
|
||||
let shift = header.pow.cuckoo_sizeshift();
|
||||
if !(ctx.pow_verifier)(header, shift).is_ok() {
|
||||
let edge_bits = header.pow.edge_bits();
|
||||
if !(ctx.pow_verifier)(header, edge_bits).is_ok() {
|
||||
error!(
|
||||
LOGGER,
|
||||
"pipe: error validating header with cuckoo shift size {}", shift
|
||||
"pipe: error validating header with cuckoo edge_bits {}", edge_bits
|
||||
);
|
||||
return Err(ErrorKind::InvalidPow.into());
|
||||
}
|
||||
|
|
|
@ -97,7 +97,7 @@ fn data_files() {
|
|||
&mut b.header,
|
||||
next_header_info.difficulty,
|
||||
global::proofsize(),
|
||||
global::min_sizeshift(),
|
||||
global::min_edge_bits(),
|
||||
).unwrap();
|
||||
|
||||
let _bhash = b.hash();
|
||||
|
|
|
@ -75,19 +75,19 @@ fn mine_empty_chain() {
|
|||
|
||||
chain.set_txhashset_roots(&mut b, false).unwrap();
|
||||
|
||||
let sizeshift = if n == 2 {
|
||||
global::min_sizeshift() + 1
|
||||
let edge_bits = if n == 2 {
|
||||
global::min_edge_bits() + 1
|
||||
} else {
|
||||
global::min_sizeshift()
|
||||
global::min_edge_bits()
|
||||
};
|
||||
b.header.pow.proof.cuckoo_sizeshift = sizeshift;
|
||||
b.header.pow.proof.edge_bits = edge_bits;
|
||||
pow::pow_size(
|
||||
&mut b.header,
|
||||
next_header_info.difficulty,
|
||||
global::proofsize(),
|
||||
sizeshift,
|
||||
edge_bits,
|
||||
).unwrap();
|
||||
b.header.pow.proof.cuckoo_sizeshift = sizeshift;
|
||||
b.header.pow.proof.edge_bits = edge_bits;
|
||||
|
||||
let bhash = b.hash();
|
||||
chain.process_block(b, chain::Options::MINE).unwrap();
|
||||
|
@ -399,19 +399,19 @@ fn output_header_mappings() {
|
|||
|
||||
chain.set_txhashset_roots(&mut b, false).unwrap();
|
||||
|
||||
let sizeshift = if n == 2 {
|
||||
global::min_sizeshift() + 1
|
||||
let edge_bits = if n == 2 {
|
||||
global::min_edge_bits() + 1
|
||||
} else {
|
||||
global::min_sizeshift()
|
||||
global::min_edge_bits()
|
||||
};
|
||||
b.header.pow.proof.cuckoo_sizeshift = sizeshift;
|
||||
b.header.pow.proof.edge_bits = edge_bits;
|
||||
pow::pow_size(
|
||||
&mut b.header,
|
||||
next_header_info.difficulty,
|
||||
global::proofsize(),
|
||||
sizeshift,
|
||||
edge_bits,
|
||||
).unwrap();
|
||||
b.header.pow.proof.cuckoo_sizeshift = sizeshift;
|
||||
b.header.pow.proof.edge_bits = edge_bits;
|
||||
|
||||
chain.process_block(b, chain::Options::MINE).unwrap();
|
||||
|
||||
|
|
|
@ -80,7 +80,7 @@ fn test_coinbase_maturity() {
|
|||
&mut block.header,
|
||||
next_header_info.difficulty,
|
||||
global::proofsize(),
|
||||
global::min_sizeshift(),
|
||||
global::min_edge_bits(),
|
||||
).unwrap();
|
||||
|
||||
assert_eq!(block.outputs().len(), 1);
|
||||
|
@ -137,7 +137,7 @@ fn test_coinbase_maturity() {
|
|||
&mut block.header,
|
||||
next_header_info.difficulty,
|
||||
global::proofsize(),
|
||||
global::min_sizeshift(),
|
||||
global::min_edge_bits(),
|
||||
).unwrap();
|
||||
|
||||
// mine enough blocks to increase the height sufficiently for
|
||||
|
@ -160,7 +160,7 @@ fn test_coinbase_maturity() {
|
|||
&mut block.header,
|
||||
next_header_info.difficulty,
|
||||
global::proofsize(),
|
||||
global::min_sizeshift(),
|
||||
global::min_edge_bits(),
|
||||
).unwrap();
|
||||
|
||||
chain.process_block(block, chain::Options::MINE).unwrap();
|
||||
|
@ -187,7 +187,7 @@ fn test_coinbase_maturity() {
|
|||
&mut block.header,
|
||||
next_header_info.difficulty,
|
||||
global::proofsize(),
|
||||
global::min_sizeshift(),
|
||||
global::min_edge_bits(),
|
||||
).unwrap();
|
||||
|
||||
let result = chain.process_block(block, chain::Options::MINE);
|
||||
|
|
|
@ -62,19 +62,20 @@ pub fn secondary_pow_ratio(height: u64) -> u64 {
|
|||
/// Cuckoo-cycle proof size (cycle length)
|
||||
pub const PROOFSIZE: usize = 42;
|
||||
|
||||
/// Default Cuckoo Cycle size shift used for mining and validating.
|
||||
pub const DEFAULT_MIN_SIZESHIFT: u8 = 30;
|
||||
/// Default Cuckoo Cycle edge_bits, used for mining and validating.
|
||||
pub const DEFAULT_MIN_EDGE_BITS: u8 = 30;
|
||||
|
||||
/// Secondary proof-of-work size shift, meant to be ASIC resistant.
|
||||
pub const SECOND_POW_SIZESHIFT: u8 = 29;
|
||||
/// Secondary proof-of-work edge_bits, meant to be ASIC resistant.
|
||||
pub const SECOND_POW_EDGE_BITS: u8 = 29;
|
||||
|
||||
/// Original reference sizeshift to compute difficulty factors for higher
|
||||
/// Original reference edge_bits to compute difficulty factors for higher
|
||||
/// Cuckoo graph sizes, changing this would hard fork
|
||||
pub const REFERENCE_SIZESHIFT: u8 = 30;
|
||||
pub const BASE_EDGE_BITS: u8 = 24;
|
||||
|
||||
/// Default Cuckoo Cycle easiness, high enough to have good likeliness to find
|
||||
/// a solution.
|
||||
pub const EASINESS: u32 = 50;
|
||||
/// maximum scaling factor for secondary pow, enforced in diff retargetting
|
||||
/// increasing scaling factor increases frequency of secondary blocks
|
||||
/// ONLY IN TESTNET4 LIMITED TO ABOUT 8 TIMES THE NATURAL SCALE
|
||||
pub const MAX_SECOND_POW_SCALE: u64 = 8 << 11;
|
||||
|
||||
/// Default number of blocks in the past when cross-block cut-through will start
|
||||
/// happening. Needs to be long enough to not overlap with a long reorg.
|
||||
|
|
|
@ -158,11 +158,11 @@ fn fixed_size_of_serialized_header(_version: u16) -> usize {
|
|||
}
|
||||
|
||||
/// Serialized size of a BlockHeader
|
||||
pub fn serialized_size_of_header(version: u16, cuckoo_sizeshift: u8) -> usize {
|
||||
pub fn serialized_size_of_header(version: u16, edge_bits: u8) -> usize {
|
||||
let mut size = fixed_size_of_serialized_header(version);
|
||||
|
||||
size += mem::size_of::<u8>(); // pow.cuckoo_sizeshift
|
||||
let nonce_bits = cuckoo_sizeshift as usize - 1;
|
||||
size += mem::size_of::<u8>(); // pow.edge_bits
|
||||
let nonce_bits = edge_bits as usize;
|
||||
let bitvec_len = global::proofsize() * nonce_bits;
|
||||
size += bitvec_len / 8; // pow.nonces
|
||||
if bitvec_len % 8 != 0 {
|
||||
|
@ -306,8 +306,8 @@ impl BlockHeader {
|
|||
pub fn serialized_size(&self) -> usize {
|
||||
let mut size = fixed_size_of_serialized_header(self.version);
|
||||
|
||||
size += mem::size_of::<u8>(); // pow.cuckoo_sizeshift
|
||||
let nonce_bits = self.pow.cuckoo_sizeshift() as usize - 1;
|
||||
size += mem::size_of::<u8>(); // pow.edge_bits
|
||||
let nonce_bits = self.pow.edge_bits() as usize;
|
||||
let bitvec_len = global::proofsize() * nonce_bits;
|
||||
size += bitvec_len / 8; // pow.nonces
|
||||
if bitvec_len % 8 != 0 {
|
||||
|
|
|
@ -18,12 +18,11 @@
|
|||
|
||||
use consensus::HeaderInfo;
|
||||
use consensus::{
|
||||
BLOCK_TIME_SEC, COINBASE_MATURITY, CUT_THROUGH_HORIZON, DEFAULT_MIN_SIZESHIFT,
|
||||
BLOCK_TIME_SEC, COINBASE_MATURITY, CUT_THROUGH_HORIZON, DEFAULT_MIN_EDGE_BITS,
|
||||
DIFFICULTY_ADJUST_WINDOW, INITIAL_DIFFICULTY, MEDIAN_TIME_WINDOW, PROOFSIZE,
|
||||
REFERENCE_SIZESHIFT,
|
||||
BASE_EDGE_BITS,
|
||||
};
|
||||
use pow::{self, CuckatooContext, EdgeType, PoWContext};
|
||||
|
||||
/// An enum collecting sets of parameters used throughout the
|
||||
/// code wherever mining is needed. This should allow for
|
||||
/// different sets of parameters for different purposes,
|
||||
|
@ -33,14 +32,14 @@ use std::sync::RwLock;
|
|||
/// Define these here, as they should be developer-set, not really tweakable
|
||||
/// by users
|
||||
|
||||
/// Automated testing sizeshift
|
||||
pub const AUTOMATED_TESTING_MIN_SIZESHIFT: u8 = 10;
|
||||
/// Automated testing edge_bits
|
||||
pub const AUTOMATED_TESTING_MIN_EDGE_BITS: u8 = 9;
|
||||
|
||||
/// Automated testing proof size
|
||||
pub const AUTOMATED_TESTING_PROOF_SIZE: usize = 4;
|
||||
|
||||
/// User testing sizeshift
|
||||
pub const USER_TESTING_MIN_SIZESHIFT: u8 = 19;
|
||||
/// User testing edge_bits
|
||||
pub const USER_TESTING_MIN_EDGE_BITS: u8 = 15;
|
||||
|
||||
/// User testing proof size
|
||||
pub const USER_TESTING_PROOF_SIZE: usize = 42;
|
||||
|
@ -147,27 +146,27 @@ pub fn pow_type() -> PoWContextTypes {
|
|||
PoWContextTypes::Cuckatoo
|
||||
}
|
||||
|
||||
/// The minimum acceptable sizeshift
|
||||
pub fn min_sizeshift() -> u8 {
|
||||
/// The minimum acceptable edge_bits
|
||||
pub fn min_edge_bits() -> u8 {
|
||||
let param_ref = CHAIN_TYPE.read().unwrap();
|
||||
match *param_ref {
|
||||
ChainTypes::AutomatedTesting => AUTOMATED_TESTING_MIN_SIZESHIFT,
|
||||
ChainTypes::UserTesting => USER_TESTING_MIN_SIZESHIFT,
|
||||
ChainTypes::Testnet1 => USER_TESTING_MIN_SIZESHIFT,
|
||||
_ => DEFAULT_MIN_SIZESHIFT,
|
||||
ChainTypes::AutomatedTesting => AUTOMATED_TESTING_MIN_EDGE_BITS,
|
||||
ChainTypes::UserTesting => USER_TESTING_MIN_EDGE_BITS,
|
||||
ChainTypes::Testnet1 => USER_TESTING_MIN_EDGE_BITS,
|
||||
_ => DEFAULT_MIN_EDGE_BITS,
|
||||
}
|
||||
}
|
||||
|
||||
/// Reference sizeshift used to compute factor on higher Cuckoo graph sizes,
|
||||
/// while the min_sizeshift can be changed on a soft fork, changing
|
||||
/// ref_sizeshift is a hard fork.
|
||||
pub fn ref_sizeshift() -> u8 {
|
||||
/// Reference edge_bits used to compute factor on higher Cuck(at)oo graph sizes,
|
||||
/// while the min_edge_bits can be changed on a soft fork, changing
|
||||
/// base_edge_bits is a hard fork.
|
||||
pub fn base_edge_bits() -> u8 {
|
||||
let param_ref = CHAIN_TYPE.read().unwrap();
|
||||
match *param_ref {
|
||||
ChainTypes::AutomatedTesting => AUTOMATED_TESTING_MIN_SIZESHIFT,
|
||||
ChainTypes::UserTesting => USER_TESTING_MIN_SIZESHIFT,
|
||||
ChainTypes::Testnet1 => USER_TESTING_MIN_SIZESHIFT,
|
||||
_ => REFERENCE_SIZESHIFT,
|
||||
ChainTypes::AutomatedTesting => AUTOMATED_TESTING_MIN_EDGE_BITS,
|
||||
ChainTypes::UserTesting => USER_TESTING_MIN_EDGE_BITS,
|
||||
ChainTypes::Testnet1 => USER_TESTING_MIN_EDGE_BITS,
|
||||
_ => BASE_EDGE_BITS,
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -250,9 +249,9 @@ pub fn get_genesis_nonce() -> u64 {
|
|||
match *param_ref {
|
||||
// won't make a difference
|
||||
ChainTypes::AutomatedTesting => 0,
|
||||
// Magic nonce for current genesis block at cuckoo16
|
||||
// Magic nonce for current genesis block at cuckatoo15
|
||||
ChainTypes::UserTesting => 27944,
|
||||
// Magic nonce for genesis block for testnet2 (cuckoo30)
|
||||
// Magic nonce for genesis block for testnet2 (cuckatoo29)
|
||||
_ => panic!("Pre-set"),
|
||||
}
|
||||
}
|
||||
|
|
|
@ -130,7 +130,7 @@ macro_rules! to_edge {
|
|||
}
|
||||
|
||||
/// Utility struct to calculate commonly used Cuckoo parameters calculated
|
||||
/// from header, nonce, sizeshift, etc.
|
||||
/// from header, nonce, edge_bits, etc.
|
||||
pub struct CuckooParams<T>
|
||||
where
|
||||
T: EdgeType,
|
||||
|
|
|
@ -246,7 +246,7 @@ where
|
|||
match sol {
|
||||
Ok(s) => {
|
||||
let mut proof = Proof::new(map_vec!(s.to_vec(), |&n| n.to_u64().unwrap_or(0)));
|
||||
proof.cuckoo_sizeshift = self.params.edge_bits;
|
||||
proof.edge_bits = self.params.edge_bits;
|
||||
return Ok(vec![proof]);
|
||||
}
|
||||
Err(e) => match e.kind() {
|
||||
|
@ -398,21 +398,21 @@ mod test {
|
|||
cuckoo_ctx.set_header_nonce(header.clone(), Some(39), true)?;
|
||||
let res = cuckoo_ctx.find_cycles()?;
|
||||
let mut proof = Proof::new(V1.to_vec());
|
||||
proof.cuckoo_sizeshift = 20;
|
||||
proof.edge_bits = 20;
|
||||
assert_eq!(proof, res[0]);
|
||||
|
||||
let mut cuckoo_ctx = CuckooContext::<T>::new(20, 42, 10)?;
|
||||
cuckoo_ctx.set_header_nonce(header.clone(), Some(56), true)?;
|
||||
let res = cuckoo_ctx.find_cycles()?;
|
||||
let mut proof = Proof::new(V2.to_vec());
|
||||
proof.cuckoo_sizeshift = 20;
|
||||
proof.edge_bits = 20;
|
||||
assert_eq!(proof, res[0]);
|
||||
|
||||
//re-use context
|
||||
cuckoo_ctx.set_header_nonce(header, Some(66), true)?;
|
||||
let res = cuckoo_ctx.find_cycles()?;
|
||||
let mut proof = Proof::new(V3.to_vec());
|
||||
proof.cuckoo_sizeshift = 20;
|
||||
proof.edge_bits = 20;
|
||||
assert_eq!(proof, res[0]);
|
||||
Ok(())
|
||||
}
|
||||
|
|
|
@ -79,7 +79,7 @@ pub fn mine_genesis_block() -> Result<Block, Error> {
|
|||
// total_difficulty on the genesis header *is* the difficulty of that block
|
||||
let genesis_difficulty = gen.header.pow.total_difficulty.clone();
|
||||
|
||||
let sz = global::min_sizeshift();
|
||||
let sz = global::min_edge_bits();
|
||||
let proof_size = global::proofsize();
|
||||
|
||||
pow_size(&mut gen.header, genesis_difficulty, proof_size, sz)?;
|
||||
|
@ -143,10 +143,10 @@ mod test {
|
|||
&mut b.header,
|
||||
Difficulty::one(),
|
||||
global::proofsize(),
|
||||
global::min_sizeshift(),
|
||||
global::min_edge_bits(),
|
||||
).unwrap();
|
||||
assert!(b.header.pow.nonce != 310);
|
||||
assert!(b.header.pow.to_difficulty() >= Difficulty::one());
|
||||
assert!(verify_size(&b.header, global::min_sizeshift()).is_ok());
|
||||
assert!(verify_size(&b.header, global::min_edge_bits()).is_ok());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -21,7 +21,7 @@ use std::{fmt, iter};
|
|||
use rand::{thread_rng, Rng};
|
||||
use serde::{de, Deserialize, Deserializer, Serialize, Serializer};
|
||||
|
||||
use consensus::SECOND_POW_SIZESHIFT;
|
||||
use consensus::SECOND_POW_EDGE_BITS;
|
||||
use core::hash::Hashed;
|
||||
use global;
|
||||
use ser::{self, Readable, Reader, Writeable, Writer};
|
||||
|
@ -80,16 +80,20 @@ impl Difficulty {
|
|||
Difficulty { num: max(num, 1) }
|
||||
}
|
||||
|
||||
/// Compute difficulty scaling factor for graph defined by 2 * 2^edge_bits * edge_bits bits
|
||||
pub fn scale(edge_bits: u8) -> u64 {
|
||||
(2 << (edge_bits - global::base_edge_bits()) as u64) * (edge_bits as u64)
|
||||
}
|
||||
|
||||
/// Computes the difficulty from a hash. Divides the maximum target by the
|
||||
/// provided hash and applies the Cuckoo sizeshift adjustment factor (see
|
||||
/// provided hash and applies the Cuck(at)oo size adjustment factor (see
|
||||
/// https://lists.launchpad.net/mimblewimble/msg00494.html).
|
||||
fn from_proof_adjusted(proof: &Proof) -> Difficulty {
|
||||
// Adjust the difficulty based on a 2^(N-M)*(N-1) factor, with M being
|
||||
// the minimum sizeshift and N the provided sizeshift
|
||||
let shift = proof.cuckoo_sizeshift;
|
||||
let adjust_factor = (1 << (shift - global::ref_sizeshift()) as u64) * (shift as u64 - 1);
|
||||
// the minimum edge_bits and N the provided edge_bits
|
||||
let edge_bits = proof.edge_bits;
|
||||
|
||||
Difficulty::from_num(proof.raw_difficulty() * adjust_factor)
|
||||
Difficulty::from_num(proof.raw_difficulty() * Difficulty::scale(edge_bits))
|
||||
}
|
||||
|
||||
/// Same as `from_proof_adjusted` but instead of an adjustment based on
|
||||
|
@ -277,38 +281,38 @@ impl ProofOfWork {
|
|||
pub fn to_difficulty(&self) -> Difficulty {
|
||||
// 2 proof of works, Cuckoo29 (for now) and Cuckoo30+, which are scaled
|
||||
// differently (scaling not controlled for now)
|
||||
if self.proof.cuckoo_sizeshift == SECOND_POW_SIZESHIFT {
|
||||
if self.proof.edge_bits == SECOND_POW_EDGE_BITS {
|
||||
Difficulty::from_proof_scaled(&self.proof, self.scaling_difficulty)
|
||||
} else {
|
||||
Difficulty::from_proof_adjusted(&self.proof)
|
||||
}
|
||||
}
|
||||
|
||||
/// The shift used for the cuckoo cycle size on this proof
|
||||
pub fn cuckoo_sizeshift(&self) -> u8 {
|
||||
self.proof.cuckoo_sizeshift
|
||||
/// The edge_bits used for the cuckoo cycle size on this proof
|
||||
pub fn edge_bits(&self) -> u8 {
|
||||
self.proof.edge_bits
|
||||
}
|
||||
|
||||
/// Whether this proof of work is for the primary algorithm (as opposed
|
||||
/// to secondary). Only depends on the size shift at this time.
|
||||
/// to secondary). Only depends on the edge_bits at this time.
|
||||
pub fn is_primary(&self) -> bool {
|
||||
// 2 conditions are redundant right now but not necessarily in
|
||||
// the future
|
||||
self.proof.cuckoo_sizeshift != SECOND_POW_SIZESHIFT
|
||||
&& self.proof.cuckoo_sizeshift >= global::min_sizeshift()
|
||||
self.proof.edge_bits != SECOND_POW_EDGE_BITS
|
||||
&& self.proof.edge_bits >= global::min_edge_bits()
|
||||
}
|
||||
|
||||
/// Whether this proof of work is for the secondary algorithm (as opposed
|
||||
/// to primary). Only depends on the size shift at this time.
|
||||
/// to primary). Only depends on the edge_bits at this time.
|
||||
pub fn is_secondary(&self) -> bool {
|
||||
self.proof.cuckoo_sizeshift == SECOND_POW_SIZESHIFT
|
||||
self.proof.edge_bits == SECOND_POW_EDGE_BITS
|
||||
}
|
||||
}
|
||||
|
||||
/// A Cuckoo Cycle proof of work, consisting of the shift to get the graph
|
||||
/// size (i.e. 31 for Cuckoo31 with a 2^31 or 1<<31 graph size) and the nonces
|
||||
/// of the graph solution. While being expressed as u64 for simplicity, each
|
||||
/// nonce is strictly less than half the cycle size (i.e. <2^30 for Cuckoo 31).
|
||||
/// A Cuck(at)oo Cycle proof of work, consisting of the edge_bits to get the graph
|
||||
/// size (i.e. the 2-log of the number of edges) and the nonces
|
||||
/// of the graph solution. While being expressed as u64 for simplicity,
|
||||
/// nonces a.k.a. edge indices range from 0 to (1 << edge_bits) - 1
|
||||
///
|
||||
/// The hash of the `Proof` is the hash of its packed nonces when serializing
|
||||
/// them at their exact bit size. The resulting bit sequence is padded to be
|
||||
|
@ -317,14 +321,14 @@ impl ProofOfWork {
|
|||
#[derive(Clone, PartialOrd, PartialEq)]
|
||||
pub struct Proof {
|
||||
/// Power of 2 used for the size of the cuckoo graph
|
||||
pub cuckoo_sizeshift: u8,
|
||||
pub edge_bits: u8,
|
||||
/// The nonces
|
||||
pub nonces: Vec<u64>,
|
||||
}
|
||||
|
||||
impl fmt::Debug for Proof {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
write!(f, "Cuckoo{}(", self.cuckoo_sizeshift)?;
|
||||
write!(f, "Cuckoo{}(", self.edge_bits)?;
|
||||
for (i, val) in self.nonces[..].iter().enumerate() {
|
||||
write!(f, "{:x}", val)?;
|
||||
if i < self.nonces.len() - 1 {
|
||||
|
@ -338,11 +342,11 @@ impl fmt::Debug for Proof {
|
|||
impl Eq for Proof {}
|
||||
|
||||
impl Proof {
|
||||
/// Builds a proof with provided nonces at default sizeshift
|
||||
/// Builds a proof with provided nonces at default edge_bits
|
||||
pub fn new(mut in_nonces: Vec<u64>) -> Proof {
|
||||
in_nonces.sort();
|
||||
Proof {
|
||||
cuckoo_sizeshift: global::min_sizeshift(),
|
||||
edge_bits: global::min_edge_bits(),
|
||||
nonces: in_nonces,
|
||||
}
|
||||
}
|
||||
|
@ -350,7 +354,7 @@ impl Proof {
|
|||
/// Builds a proof with all bytes zeroed out
|
||||
pub fn zero(proof_size: usize) -> Proof {
|
||||
Proof {
|
||||
cuckoo_sizeshift: global::min_sizeshift(),
|
||||
edge_bits: global::min_edge_bits(),
|
||||
nonces: vec![0; proof_size],
|
||||
}
|
||||
}
|
||||
|
@ -359,17 +363,17 @@ impl Proof {
|
|||
/// needed so that tests that ignore POW
|
||||
/// don't fail due to duplicate hashes
|
||||
pub fn random(proof_size: usize) -> Proof {
|
||||
let sizeshift = global::min_sizeshift();
|
||||
let nonce_mask = (1 << (sizeshift - 1)) - 1;
|
||||
let edge_bits = global::min_edge_bits();
|
||||
let nonce_mask = (1 << edge_bits) - 1;
|
||||
let mut rng = thread_rng();
|
||||
// force the random num to be within sizeshift bits
|
||||
// force the random num to be within edge_bits bits
|
||||
let mut v: Vec<u64> = iter::repeat(())
|
||||
.map(|()| (rng.gen::<u32>() & nonce_mask) as u64)
|
||||
.take(proof_size)
|
||||
.collect();
|
||||
v.sort();
|
||||
Proof {
|
||||
cuckoo_sizeshift: global::min_sizeshift(),
|
||||
edge_bits: global::min_edge_bits(),
|
||||
nonces: v,
|
||||
}
|
||||
}
|
||||
|
@ -387,16 +391,13 @@ impl Proof {
|
|||
|
||||
impl Readable for Proof {
|
||||
fn read(reader: &mut Reader) -> Result<Proof, ser::Error> {
|
||||
let cuckoo_sizeshift = reader.read_u8()?;
|
||||
if cuckoo_sizeshift == 0 || cuckoo_sizeshift > 64 {
|
||||
let edge_bits = reader.read_u8()?;
|
||||
if edge_bits == 0 || edge_bits > 64 {
|
||||
return Err(ser::Error::CorruptedData);
|
||||
}
|
||||
|
||||
let mut nonces = Vec::with_capacity(global::proofsize());
|
||||
let mut nonce_bits = cuckoo_sizeshift as usize;
|
||||
if global::pow_type() == global::PoWContextTypes::Cuckoo {
|
||||
nonce_bits -= 1;
|
||||
}
|
||||
let nonce_bits = edge_bits as usize;
|
||||
let bytes_len = BitVec::bytes_len(nonce_bits * global::proofsize());
|
||||
let bits = reader.read_fixed_bytes(bytes_len)?;
|
||||
let bitvec = BitVec { bits };
|
||||
|
@ -410,7 +411,7 @@ impl Readable for Proof {
|
|||
nonces.push(nonce);
|
||||
}
|
||||
Ok(Proof {
|
||||
cuckoo_sizeshift,
|
||||
edge_bits,
|
||||
nonces,
|
||||
})
|
||||
}
|
||||
|
@ -419,13 +420,9 @@ impl Readable for Proof {
|
|||
impl Writeable for Proof {
|
||||
fn write<W: Writer>(&self, writer: &mut W) -> Result<(), ser::Error> {
|
||||
if writer.serialization_mode() != ser::SerializationMode::Hash {
|
||||
writer.write_u8(self.cuckoo_sizeshift)?;
|
||||
}
|
||||
|
||||
let mut nonce_bits = self.cuckoo_sizeshift as usize;
|
||||
if global::pow_type() == global::PoWContextTypes::Cuckoo {
|
||||
nonce_bits -= 1;
|
||||
writer.write_u8(self.edge_bits)?;
|
||||
}
|
||||
let nonce_bits = self.edge_bits as usize;
|
||||
let mut bitvec = BitVec::new(nonce_bits * global::proofsize());
|
||||
for (n, nonce) in self.nonces.iter().enumerate() {
|
||||
for bit in 0..nonce_bits {
|
||||
|
|
|
@ -78,7 +78,7 @@ Optionally return results as "compact blocks" by passing `?compact` query.
|
|||
| - range_proof_root | string | Merklish root of all range proofs in the TxHashSet |
|
||||
| - kernel_root | string | Merklish root of all transaction kernels in the TxHashSet |
|
||||
| - nonce | number | Nonce increment used to mine this block |
|
||||
| - cuckoo_size | number | Size of the cuckoo graph |
|
||||
| - edge_bits | number | Size of the cuckoo graph (2_log of number of edges) |
|
||||
| - cuckoo_solution | []number | The Cuckoo solution for this block |
|
||||
| - total_difficulty | number | Total accumulated difficulty since genesis block |
|
||||
| - total_kernel_offset | string | Total kernel offset since genesis block |
|
||||
|
@ -163,7 +163,7 @@ Returns data about a block headers given either a hash or height or an output co
|
|||
| - range_proof_root | string | Merklish root of all range proofs in the TxHashSet |
|
||||
| - kernel_root | string | Merklish root of all transaction kernels in the TxHashSet |
|
||||
| - nonce | number | Nonce increment used to mine this block |
|
||||
| - cuckoo_size | number | Size of the cuckoo graph |
|
||||
| - edge_bits | number | Size of the cuckoo graph (2_log of number of edges) |
|
||||
| - cuckoo_solution | []number | The Cuckoo solution for this block |
|
||||
| - total_difficulty | number | Total accumulated difficulty since genesis block |
|
||||
| - total_kernel_offset | string | Total kernel offset since genesis block |
|
||||
|
@ -1146,4 +1146,4 @@ Retrieves information about a specific peer.
|
|||
console.log(r);
|
||||
}
|
||||
});
|
||||
```
|
||||
```
|
||||
|
|
|
@ -335,9 +335,9 @@ fn headers_header_size(conn: &mut TcpStream, msg_len: u64) -> Result<u64, Error>
|
|||
}
|
||||
let average_header_size = (msg_len - 2) / total_headers;
|
||||
|
||||
// support size of Cuckoo: from Cuckoo 30 to Cuckoo 36, with version 2
|
||||
// support size of Cuck(at)oo: from Cuck(at)oo 29 to Cuck(at)oo 35, with version 2
|
||||
// having slightly larger headers
|
||||
let min_size = core::serialized_size_of_header(1, global::min_sizeshift());
|
||||
let min_size = core::serialized_size_of_header(1, global::min_edge_bits());
|
||||
let max_size = min_size + 6;
|
||||
if average_header_size < min_size as u64 || average_header_size > max_size as u64 {
|
||||
debug!(
|
||||
|
|
|
@ -19,6 +19,8 @@ use std::sync::atomic::AtomicBool;
|
|||
use std::sync::{Arc, RwLock};
|
||||
use std::time::SystemTime;
|
||||
|
||||
use core::pow::Difficulty;
|
||||
|
||||
use chrono::prelude::*;
|
||||
|
||||
use chain;
|
||||
|
@ -98,7 +100,7 @@ pub struct StratumStats {
|
|||
/// current network difficulty we're working on
|
||||
pub network_difficulty: u64,
|
||||
/// cuckoo size used for mining
|
||||
pub cuckoo_size: u16,
|
||||
pub edge_bits: u16,
|
||||
/// Individual worker status
|
||||
pub worker_stats: Vec<WorkerStats>,
|
||||
}
|
||||
|
@ -153,7 +155,7 @@ pub struct PeerStats {
|
|||
impl StratumStats {
|
||||
/// Calculate network hashrate
|
||||
pub fn network_hashrate(&self) -> f64 {
|
||||
42.0 * (self.network_difficulty as f64 / (self.cuckoo_size - 1) as f64) / 60.0
|
||||
42.0 * (self.network_difficulty as f64 / Difficulty::scale(self.edge_bits as u8) as f64) / 60.0
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -207,7 +209,7 @@ impl Default for StratumStats {
|
|||
num_workers: 0,
|
||||
block_height: 0,
|
||||
network_difficulty: 1000,
|
||||
cuckoo_size: 30,
|
||||
edge_bits: 29,
|
||||
worker_stats: Vec::new(),
|
||||
}
|
||||
}
|
||||
|
|
|
@ -313,7 +313,7 @@ impl Server {
|
|||
|
||||
/// Start a minimal "stratum" mining service on a separate thread
|
||||
pub fn start_stratum_server(&self, config: StratumServerConfig) {
|
||||
let cuckoo_size = global::min_sizeshift();
|
||||
let edge_bits = global::min_edge_bits();
|
||||
let proof_size = global::proofsize();
|
||||
let sync_state = self.sync_state.clone();
|
||||
|
||||
|
@ -327,7 +327,7 @@ impl Server {
|
|||
let _ = thread::Builder::new()
|
||||
.name("stratum_server".to_string())
|
||||
.spawn(move || {
|
||||
stratum_server.run_loop(stratum_stats, cuckoo_size as u32, proof_size, sync_state);
|
||||
stratum_server.run_loop(stratum_stats, edge_bits as u32, proof_size, sync_state);
|
||||
});
|
||||
}
|
||||
|
||||
|
|
|
@ -75,7 +75,7 @@ struct SubmitParams {
|
|||
height: u64,
|
||||
job_id: u64,
|
||||
nonce: u64,
|
||||
cuckoo_size: u32,
|
||||
edge_bits: u32,
|
||||
pow: Vec<u64>,
|
||||
}
|
||||
|
||||
|
@ -481,7 +481,7 @@ impl StratumServer {
|
|||
}
|
||||
let mut b: Block = b.unwrap().clone();
|
||||
// Reconstruct the block header with this nonce and pow added
|
||||
b.header.pow.proof.cuckoo_sizeshift = params.cuckoo_size as u8;
|
||||
b.header.pow.proof.edge_bits = params.edge_bits as u8;
|
||||
b.header.pow.nonce = params.nonce;
|
||||
b.header.pow.proof.nonces = params.pow;
|
||||
// Get share difficulty
|
||||
|
@ -532,7 +532,7 @@ impl StratumServer {
|
|||
);
|
||||
} else {
|
||||
// Do some validation but dont submit
|
||||
if !pow::verify_size(&b.header, b.header.pow.proof.cuckoo_sizeshift).is_ok() {
|
||||
if !pow::verify_size(&b.header, b.header.pow.proof.edge_bits).is_ok() {
|
||||
// Return error status
|
||||
error!(
|
||||
LOGGER,
|
||||
|
@ -653,15 +653,15 @@ impl StratumServer {
|
|||
pub fn run_loop(
|
||||
&mut self,
|
||||
stratum_stats: Arc<RwLock<StratumStats>>,
|
||||
cuckoo_size: u32,
|
||||
edge_bits: u32,
|
||||
proof_size: usize,
|
||||
sync_state: Arc<SyncState>,
|
||||
) {
|
||||
info!(
|
||||
LOGGER,
|
||||
"(Server ID: {}) Starting stratum server with cuckoo_size = {}, proof_size = {}",
|
||||
"(Server ID: {}) Starting stratum server with edge_bits = {}, proof_size = {}",
|
||||
self.id,
|
||||
cuckoo_size,
|
||||
edge_bits,
|
||||
proof_size
|
||||
);
|
||||
|
||||
|
@ -693,7 +693,7 @@ impl StratumServer {
|
|||
{
|
||||
let mut stratum_stats = stratum_stats.write().unwrap();
|
||||
stratum_stats.is_running = true;
|
||||
stratum_stats.cuckoo_size = cuckoo_size as u16;
|
||||
stratum_stats.edge_bits = edge_bits as u16;
|
||||
}
|
||||
|
||||
warn!(
|
||||
|
|
|
@ -87,7 +87,7 @@ impl Miner {
|
|||
LOGGER,
|
||||
"(Server ID: {}) Mining Cuckoo{} for max {}s on {} @ {} [{}].",
|
||||
self.debug_output_id,
|
||||
global::min_sizeshift(),
|
||||
global::min_edge_bits(),
|
||||
attempt_time_per_block,
|
||||
b.header.total_difficulty(),
|
||||
b.header.height,
|
||||
|
@ -97,7 +97,7 @@ impl Miner {
|
|||
|
||||
while head.hash() == *latest_hash && Utc::now().timestamp() < deadline {
|
||||
let mut ctx =
|
||||
global::create_pow_context::<u32>(global::min_sizeshift(), global::proofsize(), 10)
|
||||
global::create_pow_context::<u32>(global::min_edge_bits(), global::proofsize(), 10)
|
||||
.unwrap();
|
||||
ctx.set_header_nonce(b.header.pre_pow(), None, true)
|
||||
.unwrap();
|
||||
|
|
|
@ -217,7 +217,7 @@ impl TUIStatusListener for TUIMiningView {
|
|||
)
|
||||
.child(
|
||||
LinearLayout::new(Orientation::Horizontal)
|
||||
.child(TextView::new(" ").with_id("stratum_cuckoo_size_status")),
|
||||
.child(TextView::new(" ").with_id("stratum_edge_bits_status")),
|
||||
);
|
||||
|
||||
let mining_device_view = LinearLayout::new(Orientation::Vertical)
|
||||
|
@ -320,7 +320,7 @@ impl TUIStatusListener for TUIMiningView {
|
|||
let stratum_block_height = format!("Solving Block Height: {}", stratum_stats.block_height);
|
||||
let stratum_network_difficulty =
|
||||
format!("Network Difficulty: {}", stratum_stats.network_difficulty);
|
||||
let stratum_cuckoo_size = format!("Cuckoo Size: {}", stratum_stats.cuckoo_size);
|
||||
let stratum_edge_bits = format!("Cuckoo Size: {}", stratum_stats.edge_bits);
|
||||
|
||||
c.call_on_id("stratum_config_status", |t: &mut TextView| {
|
||||
t.set_content(stratum_enabled);
|
||||
|
@ -340,8 +340,8 @@ impl TUIStatusListener for TUIMiningView {
|
|||
c.call_on_id("stratum_network_hashrate", |t: &mut TextView| {
|
||||
t.set_content(stratum_network_hashrate);
|
||||
});
|
||||
c.call_on_id("stratum_cuckoo_size_status", |t: &mut TextView| {
|
||||
t.set_content(stratum_cuckoo_size);
|
||||
c.call_on_id("stratum_edge_bits_status", |t: &mut TextView| {
|
||||
t.set_content(stratum_edge_bits);
|
||||
});
|
||||
let _ = c.call_on_id(
|
||||
TABLE_MINING_STATUS,
|
||||
|
|
|
@ -201,7 +201,7 @@ impl TUIStatusListener for TUIStatusView {
|
|||
),
|
||||
format!(
|
||||
"Cuckoo {} - Network Difficulty {}",
|
||||
stats.mining_stats.cuckoo_size,
|
||||
stats.mining_stats.edge_bits,
|
||||
stats.mining_stats.network_difficulty.to_string()
|
||||
),
|
||||
)
|
||||
|
|
|
@ -103,7 +103,7 @@ pub fn add_block_with_reward(chain: &Chain, txs: Vec<&Transaction>, reward: CbDa
|
|||
&mut b.header,
|
||||
next_header_info.difficulty,
|
||||
global::proofsize(),
|
||||
global::min_sizeshift(),
|
||||
global::min_edge_bits(),
|
||||
).unwrap();
|
||||
chain.process_block(b, chain::Options::MINE).unwrap();
|
||||
chain.validate(false).unwrap();
|
||||
|
|
Loading…
Reference in a new issue