-
Notifications
You must be signed in to change notification settings - Fork 100
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add VRF nonce to the consensus. #590
Conversation
src/DBFTPlugin/ConsensusService.cs
Outdated
|
||
if (nonce == null) | ||
{ | ||
Log($"Random number verification failed: {message.VRFProof}", LogLevel.Warning); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I prefer throw an error in random method instead of break the consensus
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
And maybe ask ChangeView.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
And maybe ask ChangeView.
I just follow the way how you process other check failures. If you think ChangeView is better, I can add it here.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I prefer throw an error in random method instead of break the consensus
Updated by adding exception
src/DBFTPlugin/ConsensusContext.cs
Outdated
private Tuple<byte[], uint> GetNonce(byte[] prikey) | ||
{ | ||
byte[] aplha; | ||
if (Block.Index > 1000) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe the % with 1000?
src/DBFTPlugin/ConsensusService.cs
Outdated
try | ||
{ | ||
if (message.BlockIndex > 1000) | ||
// To prevent the primary uses the same block hash in Height (1000, 2000) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I did not understand this comment.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I want to use the 1000th ahead block hash as the current VRF input to generate the random number. However, if the block index is less than 1000, there will be out of index error. So I have to make the first 1000 block to use the prevHash as VRF input. The problem here is, if the first 1000 block uses prevHash, and Block of 1000 - 2000 use the hash of 1000th ahead block, it is possible that the same primary use the same block hash to generate random numbers, which means there might have a same random number, one among (0..1000), another among (1000, 2000).
Co-authored-by: Shargon <shargon@gmail.com>
src/DBFTPlugin/ConsensusService.cs
Outdated
byte[] nonce; | ||
try | ||
{ | ||
nonce = VRF.Verify(context.Validators[message.ValidatorIndex], message.VRFProof, message.PrevHash); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We should add the current merkletree in data
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If we add the current Merkle tree in the data
, the result would be mutable for the primary cause he can decide the Merkle tree.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
he can decide the Merkle tree.
But not the PrevHash
, it makes the things more complicated
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Using the block hash is a normal and the most easy way to get a well known input. Currently, almost all projects that use VRF take block hash as input, either prehash or previous n blocks. But if u have a better input source, definitely it is a good thing.
src/DBFTPlugin/VRF.cs
Outdated
var kBytes = k.ToByteArray(true, true); | ||
|
||
// Step 6: c = ECVRF_hash_points(H, Gamma, k*B, k*H) | ||
var u_point = DerivePubkeyPoint(k.ToByteArray(true, true)); | ||
var v_point = h_point * kBytes; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fixed the error, the issue is neo added extra
length
check to theprikey
@nicolegys
We should append leading zeros to kBytes
after var kBytes = k.ToByteArray(true, true)
in Prove
method, because the operator *
requires the second param to be 32 bits.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@Liaojinghui I think you've forgotten this issue 0.0
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@Liaojinghui I think you've forgotten this issue 0.0
My fault TT
Fixed, I changed the index of |
I used the newest code, and the issue still existed. TwT |
if the block has no transaction, no need to verify the nonce_tx.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No nonce_tx now.
src/DBFTPlugin/ConsensusContext.cs
Outdated
@@ -342,7 +354,8 @@ internal void EnsureMaxBlockLimitation(IEnumerable<Transaction> txs) | |||
uint maxTransactionsPerBlock = neoSystem.Settings.MaxTransactionsPerBlock; | |||
|
|||
// Limit Speaker proposal to the limit `MaxTransactionsPerBlock` or all available transactions of the mempool | |||
txs = txs.Take((int)maxTransactionsPerBlock); | |||
txs = txs.Take((int)maxTransactionsPerBlock - 1); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
txs = txs.Take((int)maxTransactionsPerBlock - 1); | |
txs = txs.Take((int)maxTransactionsPerBlock); |
Could you please also update |
src/RpcClient/Utility.cs
Outdated
@@ -142,7 +142,7 @@ public static Header HeaderFromJson(JObject json, ProtocolSettings protocolSetti | |||
PrevHash = UInt256.Parse(json["previousblockhash"].AsString()), | |||
MerkleRoot = UInt256.Parse(json["merkleroot"].AsString()), | |||
Timestamp = (ulong)json["time"].AsNumber(), | |||
Nonce = (ulong)json["nonce"].AsNumber(), | |||
Nonce = UInt64.Parse(json["nonce"].AsString()), |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think you should useUInt64.Parse(json["nonce"].AsString(), NumberStyles.AllowHexSpecifier)
to convert a hex string to uint64.
…i/neo-modules * 'master' of https://github.com/Liaojinghui/neo-modules: fix hex_str to uint64 * 'master' of https://github.com/Liaojinghui/neo-modules: fix hex_str to uint64
This pull request adds VRF support to the dBFT consensus.
Proof of the VRF only exists in the PrepareRequest message.