Skip to content

Commit

Permalink
Add test for Snowstorm transaction being rejected multiple times (ava…
Browse files Browse the repository at this point in the history
  • Loading branch information
StephenButtolph committed Mar 28, 2023
1 parent b0531bd commit 05808a0
Show file tree
Hide file tree
Showing 2 changed files with 74 additions and 0 deletions.
69 changes: 69 additions & 0 deletions snow/consensus/snowstorm/consensus_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ var (
AcceptingDependencyTest,
AcceptingSlowDependencyTest,
RejectingDependencyTest,
RejectMultipleTimesTest,
VacuouslyAcceptedTest,
ConflictsTest,
VirtuousDependsOnRogueTest,
Expand Down Expand Up @@ -1322,6 +1323,74 @@ func RejectingDependencyTest(t *testing.T, factory Factory) {
}
}

func RejectMultipleTimesTest(t *testing.T, factory Factory) {
require := require.New(t)

purple := &TestTx{
TestDecidable: choices.TestDecidable{
IDV: ids.Empty.Prefix(7),
StatusV: choices.Processing,
},
DependenciesV: []Tx{Green},
InputIDsV: []ids.ID{ids.Empty.Prefix(8)},
}
yellow := &TestTx{
TestDecidable: choices.TestDecidable{
IDV: ids.Empty.Prefix(9),
StatusV: choices.Processing,
},
InputIDsV: []ids.ID{ids.Empty.Prefix(8)},
}

graph := factory.New()

params := sbcon.Parameters{
K: 1,
Alpha: 1,
BetaVirtuous: 1,
BetaRogue: 1,
ConcurrentRepolls: 1,
OptimalProcessing: 1,
MaxOutstandingItems: 1,
MaxItemProcessingTime: 1,
}
require.NoError(graph.Initialize(snow.DefaultConsensusContextTest(), params))
require.NoError(graph.Add(context.Background(), Red))
require.NoError(graph.Add(context.Background(), yellow))
require.NoError(graph.Add(context.Background(), Green))
require.NoError(graph.Add(context.Background(), purple))

prefs := graph.Preferences()
require.Len(prefs, 2)
require.Contains(prefs, Red.ID())
require.Contains(prefs, yellow.ID())

y := bag.Bag[ids.ID]{}
y.Add(yellow.ID())

updated, err := graph.RecordPoll(context.Background(), y)
require.NoError(err)
require.True(updated)
require.Equal(choices.Processing, Red.Status())
require.Equal(choices.Accepted, yellow.Status())
require.Equal(choices.Processing, Green.Status())
require.Equal(choices.Rejected, purple.Status())

r := bag.Bag[ids.ID]{}
r.Add(Red.ID())

// Accepting Red rejects Green which was a dependency of purple. This
// results in purple being rejected for a second time.
updated, err = graph.RecordPoll(context.Background(), r)
require.NoError(err)
require.True(updated)
require.True(graph.Finalized())
require.Equal(choices.Accepted, Red.Status())
require.Equal(choices.Accepted, yellow.Status())
require.Equal(choices.Rejected, Green.Status())
require.Equal(choices.Rejected, purple.Status())
}

func VacuouslyAcceptedTest(t *testing.T, factory Factory) {
graph := factory.New()

Expand Down
5 changes: 5 additions & 0 deletions snow/consensus/snowstorm/directed.go
Original file line number Diff line number Diff line change
Expand Up @@ -567,6 +567,11 @@ func (dg *Directed) reject(ctx context.Context, conflictIDs set.Set[ids.ID]) err
for conflictKey := range conflictIDs {
conflict, exists := dg.txs[conflictKey]
if !exists {
// Transaction dependencies are cleaned up when the dependency is
// either accepted or rejected. However, a transaction may have
// already been rejected due to a conflict of its own. In this case,
// the transaction has already been cleaned up from memory and there
// is nothing more to be done.
continue
}
// This tx is no longer an option for consuming the UTXOs from its
Expand Down

0 comments on commit 05808a0

Please sign in to comment.