Skip to content

Commit

Permalink
Merge remote-tracking branch 'origin/v0.7-dev' into TD-30-dedicated-s…
Browse files Browse the repository at this point in the history
…lots
  • Loading branch information
lklimek committed Nov 22, 2021
2 parents af73135 + b1b6d2a commit 706c079
Show file tree
Hide file tree
Showing 8 changed files with 173 additions and 12 deletions.
6 changes: 3 additions & 3 deletions .github/workflows/coverage.yml
Original file line number Diff line number Diff line change
Expand Up @@ -86,7 +86,7 @@ jobs:
with:
go-version: "^1.15.4"
- uses: actions/checkout@v2
- uses: technote-space/[email protected].1
- uses: technote-space/[email protected].2
with:
PATTERNS: |
**/**.go
Expand Down Expand Up @@ -118,7 +118,7 @@ jobs:
with:
go-version: "^1.15.4"
- uses: actions/checkout@v2
- uses: technote-space/[email protected].1
- uses: technote-space/[email protected].2
with:
PATTERNS: |
**/**.go
Expand Down Expand Up @@ -156,7 +156,7 @@ jobs:
run: |
echo "::set-output name=hash::$(git --git-dir=third_party/bls-signatures/src/.git rev-parse HEAD)"
shell: bash
- uses: technote-space/[email protected].1
- uses: technote-space/[email protected].2
with:
PATTERNS: |
**/**.go
Expand Down
4 changes: 2 additions & 2 deletions .github/workflows/e2e.yml
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,7 @@ jobs:
run: |
echo "::set-output name=hash::$(git --git-dir=third_party/bls-signatures/src/.git rev-parse HEAD)"
shell: bash
- uses: technote-space/[email protected].1
- uses: technote-space/[email protected].2
with:
PATTERNS: |
**/**.go
Expand Down Expand Up @@ -111,7 +111,7 @@ jobs:
run: |
echo "::set-output name=hash::$(git --git-dir=third_party/bls-signatures/src/.git rev-parse HEAD)"
shell: bash
- uses: technote-space/[email protected].1
- uses: technote-space/[email protected].2
with:
PATTERNS: |
**/**.go
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/lint.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ jobs:
run: |
echo "::set-output name=hash::$(git --git-dir=third_party/bls-signatures/src/.git rev-parse HEAD)"
shell: bash
- uses: technote-space/[email protected].1
- uses: technote-space/[email protected].2
with:
PATTERNS: |
**/**.go
Expand Down
8 changes: 4 additions & 4 deletions .github/workflows/tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,7 @@ jobs:
with:
go-version: "^1.15.5"
- uses: actions/checkout@v2
- uses: technote-space/[email protected].1
- uses: technote-space/[email protected].2
with:
PATTERNS: |
**/**.go
Expand Down Expand Up @@ -95,7 +95,7 @@ jobs:
with:
go-version: "^1.15.5"
- uses: actions/checkout@v2
- uses: technote-space/[email protected].1
- uses: technote-space/[email protected].2
with:
PATTERNS: |
**/**.go
Expand Down Expand Up @@ -135,7 +135,7 @@ jobs:
with:
go-version: "^1.15.5"
- uses: actions/checkout@v2
- uses: technote-space/[email protected].1
- uses: technote-space/[email protected].2
with:
PATTERNS: |
**/**.go
Expand Down Expand Up @@ -166,7 +166,7 @@ jobs:
with:
go-version: "^1.15.5"
- uses: actions/checkout@v2
- uses: technote-space/[email protected].1
- uses: technote-space/[email protected].2
with:
PATTERNS: |
**/**.go
Expand Down
18 changes: 18 additions & 0 deletions test/e2e/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,12 @@ Multiple testnets can be run with the `run-multiple.sh` script:
./run-multiple.sh networks/generated/gen-group3-*.toml
```

In order to generate network configurations with settings for dash, you have to override a default preset with `dash`.

```sh
./build/generator -d networks/generated/ -p dash
```

## Test Stages

The test runner has the following stages, which can also be executed explicitly by running `./build/runner -f <manifest> <stage>`:
Expand Down Expand Up @@ -82,6 +88,18 @@ func init() {
}
```

### Full-node keys

Since Full nodes do not participate in the consensus process, then keeping validators' public keys also is not required.
By default, public keys are reset during network generation. However, if you need to keep its, then use this env
parameter `FULLNODE_PUBKEY_KEEP=true`.

For instance:

```sh
FULLNODE_PUBKEY_KEEP=true make runner/dashcore
```

### Speed up running e2e tests

Running the e2e tests using `make runner {network}` takes time because the
Expand Down
1 change: 1 addition & 0 deletions types/validator_set.go
Original file line number Diff line number Diff line change
Expand Up @@ -525,6 +525,7 @@ func (vals *ValidatorSet) QuorumVotingPower() int64 {
}

// QuorumVotingThresholdPower returns the threshold power of the voting power of the quorum if all the members existed.
// Voting is considered successful when voting power is at or above this threshold.
func (vals *ValidatorSet) QuorumVotingThresholdPower() int64 {
return int64(vals.QuorumTypeThresholdCount()) * DefaultDashVotingPower
}
Expand Down
3 changes: 2 additions & 1 deletion types/vote_set.go
Original file line number Diff line number Diff line change
Expand Up @@ -507,13 +507,14 @@ func (voteSet *VoteSet) IsCommit() bool {
return voteSet.maj23 != nil
}

// HasTwoThirdsAny returns true if we are above voting threshold, regardless of the block id voted
func (voteSet *VoteSet) HasTwoThirdsAny() bool {
if voteSet == nil {
return false
}
voteSet.mtx.Lock()
defer voteSet.mtx.Unlock()
return voteSet.sum > voteSet.valSet.TotalVotingPower()*2/3
return voteSet.sum >= voteSet.valSet.QuorumVotingThresholdPower()
}

func (voteSet *VoteSet) HasAll() bool {
Expand Down
143 changes: 142 additions & 1 deletion types/vote_set_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,16 @@ package types

import (
"bytes"
"math"
"sort"
"strconv"
"testing"

"github.com/dashevo/dashd-go/btcjson"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"

"github.com/tendermint/tendermint/crypto"
"github.com/tendermint/tendermint/crypto/bls12381"
tmrand "github.com/tendermint/tendermint/libs/rand"
tmproto "github.com/tendermint/tendermint/proto/tendermint/types"
)
Expand Down Expand Up @@ -519,6 +523,112 @@ func TestVoteSet_MakeCommit(t *testing.T) {
}
}

func TestVoteSet_LLMQType_50_60(t *testing.T) {
const (
height = int64(1)
round = int32(0)
)
testCases := []struct {
llmqType btcjson.LLMQType
numValidators int
threshold int
}{
{
llmqType: btcjson.LLMQType(0), // "tendermint" algorithm
numValidators: 40,
threshold: int(math.Floor(2.0/3.0*40)) + 1,
},
{
llmqType: btcjson.LLMQType_50_60,
numValidators: 35,
threshold: 30,
},
{
llmqType: btcjson.LLMQType(0),
numValidators: 50,
threshold: 34,
},
{
llmqType: btcjson.LLMQType_50_60,
numValidators: 50,
threshold: 30,
},
}

for ti, tt := range testCases {
name := strconv.Itoa(ti)
t.Run(name, func(t *testing.T) {
voteSet, valSet, privValidators := randVoteSetWithLLMQType(
height,
round,
tmproto.PrevoteType,
tt.numValidators,
RandStateID().WithHeight(height-1),
tt.llmqType,
tt.threshold,
)
assert.EqualValues(t, tt.threshold, valSet.QuorumTypeThresholdCount())
assert.GreaterOrEqual(t, len(privValidators), tt.threshold+3,
"need at least %d validators", tt.threshold+3)

blockHash := crypto.CRandBytes(32)
blockPartSetHeader := PartSetHeader{uint32(123), crypto.CRandBytes(32)}
votedBlock := BlockID{blockHash, blockPartSetHeader}

// below threshold
for i := 0; i < tt.threshold-1; i++ {
blockMaj, anyMaj := castVote(t, votedBlock, height, round, privValidators, int32(i), voteSet)
assert.False(t, blockMaj, "no block majority expected here: i=%d, threshold=%d", i, tt.threshold)
assert.False(t, anyMaj, "no 'any' majority expected here: i=%d, threshold=%d", i, tt.threshold)
}

// we add null vote
blockMaj, anyMaj := castVote(t, BlockID{}, height, round, privValidators, int32(tt.threshold), voteSet)
assert.False(t, blockMaj, "no block majority expected after nil vote")
assert.True(t, anyMaj, "'any' majority expected after nil vote at threshold")

// at threshold
blockMaj, anyMaj = castVote(t, votedBlock, height, round, privValidators, int32(tt.threshold+1), voteSet)
assert.True(t, blockMaj, "block majority expected")
assert.True(t, anyMaj, "'any' majority expected")

// above threshold
blockMaj, anyMaj = castVote(t, votedBlock, height, round, privValidators, int32(tt.threshold+2), voteSet)
assert.True(t, blockMaj, "block majority expected")
assert.True(t, anyMaj, "'any' majority expected")
})
}
}

func castVote(
t *testing.T,
blockID BlockID,
height int64,
round int32,
privValidators []PrivValidator,
validatorID int32,
voteSet *VoteSet,
) (twoThirdsMajority, hasTwoThirdsAny bool) {
voteProto := &Vote{
ValidatorProTxHash: nil, // NOTE: must fill in
ValidatorIndex: -1, // NOTE: must fill in
Height: height,
Round: round,
Type: tmproto.PrevoteType,
BlockID: blockID,
}
proTxHash, err := privValidators[validatorID].GetProTxHash()
require.NoError(t, err)
vote := withValidator(voteProto, proTxHash, validatorID)
signed, err := signAddVote(privValidators[validatorID], vote, voteSet)
require.True(t, signed)
require.NoError(t, err)

majorityBlock, twoThirdsMajority := voteSet.TwoThirdsMajority()
assert.EqualValues(t, twoThirdsMajority, !majorityBlock.IsZero())
return twoThirdsMajority, voteSet.HasTwoThirdsAny()
}

// NOTE: privValidators are in order
func randVoteSet(
height int64,
Expand All @@ -531,6 +641,37 @@ func randVoteSet(
return NewVoteSet("test_chain_id", height, round, signedMsgType, valSet, stateID), valSet, privValidators
}

func randVoteSetWithLLMQType(
height int64,
round int32,
signedMsgType tmproto.SignedMsgType,
numValidators int,
stateID StateID,
llmqType btcjson.LLMQType,
threshold int,
) (*VoteSet, *ValidatorSet, []PrivValidator) {
var (
valz = make([]*Validator, numValidators)
privValidators = make([]PrivValidator, numValidators)
)
privateKeys, proTxHashes, thresholdPublicKey := bls12381.CreatePrivLLMQData(numValidators, threshold)
quorumHash := crypto.RandQuorumHash()

for i := 0; i < numValidators; i++ {
privValidators[i] = NewMockPVWithParams(privateKeys[i], proTxHashes[i], quorumHash,
thresholdPublicKey, false, false)
valz[i] = NewValidatorDefaultVotingPower(privateKeys[i].PubKey(), proTxHashes[i])
}

sort.Sort(PrivValidatorsByProTxHash(privValidators))

valSet := NewValidatorSet(valz, thresholdPublicKey, llmqType, quorumHash, true)
voteSet := NewVoteSet("test_chain_id", height, round, tmproto.PrevoteType,
valSet, stateID)

return voteSet, valSet, privValidators
}

// Convenience: Return new vote with different validator address/index
func withValidator(vote *Vote, proTxHash []byte, idx int32) *Vote {
vote = vote.Copy()
Expand Down

0 comments on commit 706c079

Please sign in to comment.