Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
N
nebula
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
exchain
nebula
Commits
e441f6dc
Unverified
Commit
e441f6dc
authored
Jun 29, 2023
by
OptimismBot
Committed by
GitHub
Jun 29, 2023
Browse files
Options
Browse Files
Download
Plain Diff
Merge pull request #6207 from ethereum-optimism/jg/game_prep_for_step
op-challenger: Get Pre/Post claim for Step function
parents
e4ca19e1
63fcc9c1
Changes
4
Hide whitespace changes
Inline
Side-by-side
Showing
4 changed files
with
178 additions
and
58 deletions
+178
-58
game.go
op-challenger/fault/game.go
+54
-1
game_test.go
op-challenger/fault/game_test.go
+115
-56
loader_test.go
op-challenger/fault/loader_test.go
+8
-0
orchestrator.go
op-challenger/fault/orchestrator.go
+1
-1
No files found.
op-challenger/fault/game.go
View file @
e441f6dc
...
...
@@ -25,6 +25,14 @@ type Game interface {
// IsDuplicate returns true if the provided [Claim] already exists in the game state.
IsDuplicate
(
claim
Claim
)
bool
// PreStateClaim gets the claim which commits to the pre-state of this specific claim.
// This will return an error if it is called with a non-leaf claim.
PreStateClaim
(
claim
Claim
)
(
Claim
,
error
)
// PostStateClaim gets the claim which commits to the pre-state of this specific claim.
// This will return an error if it is called with a non-leaf claim.
PostStateClaim
(
claim
Claim
)
(
Claim
,
error
)
}
type
extendedClaim
struct
{
...
...
@@ -38,11 +46,12 @@ type extendedClaim struct {
type
gameState
struct
{
root
ClaimData
claims
map
[
ClaimData
]
*
extendedClaim
depth
uint64
}
// NewGameState returns a new game state.
// The provided [Claim] is used as the root node.
func
NewGameState
(
root
Claim
)
*
gameState
{
func
NewGameState
(
root
Claim
,
depth
uint64
)
*
gameState
{
claims
:=
make
(
map
[
ClaimData
]
*
extendedClaim
)
claims
[
root
.
ClaimData
]
=
&
extendedClaim
{
self
:
root
,
...
...
@@ -52,6 +61,7 @@ func NewGameState(root Claim) *gameState {
return
&
gameState
{
root
:
root
.
ClaimData
,
claims
:
claims
,
depth
:
depth
,
}
}
...
...
@@ -115,3 +125,46 @@ func (g *gameState) getParent(claim Claim) (Claim, error) {
return
parent
.
self
,
nil
}
}
func
(
g
*
gameState
)
PreStateClaim
(
claim
Claim
)
(
Claim
,
error
)
{
// Do checks in PreStateClaim because these do not hold while walking the tree
if
claim
.
Depth
()
!=
int
(
g
.
depth
)
{
return
Claim
{},
errors
.
New
(
"Only leaf claims have pre or post state"
)
}
// If the claim is the far left most claim, the pre-state is pulled from the contracts & we can supply at contract index.
if
claim
.
IndexAtDepth
()
==
0
{
return
Claim
{
ContractIndex
:
-
1
,
},
nil
}
return
g
.
preStateClaim
(
claim
)
}
// preStateClaim is the internal tree walker which does not do error handling
func
(
g
*
gameState
)
preStateClaim
(
claim
Claim
)
(
Claim
,
error
)
{
parent
,
_
:=
g
.
getParent
(
claim
)
if
claim
.
DefendsParent
()
{
return
parent
,
nil
}
else
{
return
g
.
preStateClaim
(
parent
)
}
}
func
(
g
*
gameState
)
PostStateClaim
(
claim
Claim
)
(
Claim
,
error
)
{
// Do checks in PostStateClaim because these do not hold while walking the tree
if
claim
.
Depth
()
!=
int
(
g
.
depth
)
{
return
Claim
{},
errors
.
New
(
"Only leaf claims have pre or post state"
)
}
return
g
.
postStateClaim
(
claim
)
}
// postStateClaim is the internal tree walker which does not do error handling
func
(
g
*
gameState
)
postStateClaim
(
claim
Claim
)
(
Claim
,
error
)
{
parent
,
_
:=
g
.
getParent
(
claim
)
if
claim
.
DefendsParent
()
{
return
g
.
postStateClaim
(
parent
)
}
else
{
return
parent
,
nil
}
}
op-challenger/fault/game_test.go
View file @
e441f6dc
...
...
@@ -7,19 +7,29 @@ import (
"github.com/stretchr/testify/require"
)
func
createTestClaims
()
(
Claim
,
Claim
,
Claim
)
{
top
:=
Claim
{
const
testMaxDepth
=
3
func
createTestClaims
()
(
Claim
,
Claim
,
Claim
,
Claim
)
{
// root & middle are from the trace "abcdexyz"
// top & bottom are from the trace "abcdefgh"
root
:=
Claim
{
ClaimData
:
ClaimData
{
Value
:
common
.
HexToHash
(
"0x00000000000000000000000000000000000000000000000000000000000007
68
"
),
Value
:
common
.
HexToHash
(
"0x00000000000000000000000000000000000000000000000000000000000007
7a
"
),
Position
:
NewPosition
(
0
,
0
),
},
Parent
:
ClaimData
{},
// Root claim has no parent
}
middle
:=
Claim
{
top
:=
Claim
{
ClaimData
:
ClaimData
{
Value
:
common
.
HexToHash
(
"0x0000000000000000000000000000000000000000000000000000000000000364"
),
Position
:
NewPosition
(
1
,
1
),
Position
:
NewPosition
(
1
,
0
),
},
Parent
:
root
.
ClaimData
,
}
middle
:=
Claim
{
ClaimData
:
ClaimData
{
Value
:
common
.
HexToHash
(
"0x0000000000000000000000000000000000000000000000000000000000000578"
),
Position
:
NewPosition
(
2
,
2
),
},
Parent
:
top
.
ClaimData
,
}
...
...
@@ -27,71 +37,83 @@ func createTestClaims() (Claim, Claim, Claim) {
bottom
:=
Claim
{
ClaimData
:
ClaimData
{
Value
:
common
.
HexToHash
(
"0x0000000000000000000000000000000000000000000000000000000000000465"
),
Position
:
NewPosition
(
2
,
2
),
Position
:
NewPosition
(
3
,
4
),
},
Parent
:
middle
.
ClaimData
,
}
return
top
,
middle
,
bottom
return
root
,
top
,
middle
,
bottom
}
func
TestIsDuplicate
(
t
*
testing
.
T
)
{
// Setup the game state.
top
,
middle
,
bottom
:=
createTestClaims
()
g
:=
NewGameState
(
top
)
err
:=
g
.
Put
(
middle
)
require
.
NoError
(
t
,
err
)
root
,
top
,
middle
,
bottom
:=
createTestClaims
()
g
:=
NewGameState
(
root
,
testMaxDepth
)
require
.
NoError
(
t
,
g
.
Put
(
top
))
// Top + Middle should be duplicates
// Root + Top should be duplicates
require
.
True
(
t
,
g
.
IsDuplicate
(
root
))
require
.
True
(
t
,
g
.
IsDuplicate
(
top
))
require
.
True
(
t
,
g
.
IsDuplicate
(
middle
))
// Bottom should not be a duplicate
// Middle + Bottom should not be a duplicate
require
.
False
(
t
,
g
.
IsDuplicate
(
middle
))
require
.
False
(
t
,
g
.
IsDuplicate
(
bottom
))
}
// TestGame_Put_RootAlreadyExists tests the [Game.Put] method using a [gameState]
// instance errors when the root claim already exists in state.
func
TestGame_Put_RootAlreadyExists
(
t
*
testing
.
T
)
{
// Setup the game state.
top
,
_
,
_
,
_
:=
createTestClaims
()
g
:=
NewGameState
(
top
,
testMaxDepth
)
// Try to put the root claim into the game state again.
err
:=
g
.
Put
(
top
)
require
.
ErrorIs
(
t
,
err
,
ErrClaimExists
)
}
// TestGame_PutAll_RootAlreadyExists tests the [Game.PutAll] method using a [gameState]
// instance errors when the root claim already exists in state.
func
TestGame_PutAll_RootAlreadyExists
(
t
*
testing
.
T
)
{
// Setup the game state.
top
,
_
,
_
:=
createTestClaims
()
g
:=
NewGameState
(
top
)
root
,
_
,
_
,
_
:=
createTestClaims
()
g
:=
NewGameState
(
root
,
testMaxDepth
)
// Try to put the root claim into the game state again.
err
:=
g
.
PutAll
([]
Claim
{
top
})
err
:=
g
.
PutAll
([]
Claim
{
root
})
require
.
ErrorIs
(
t
,
err
,
ErrClaimExists
)
}
// TestGame_PutAll_AlreadyExists tests the [Game.PutAll] method using a [gameState]
// instance errors when the given claim already exists in state.
func
TestGame_PutAll_AlreadyExists
(
t
*
testing
.
T
)
{
// Setup the game state.
top
,
middle
,
_
:=
createTestClaims
()
g
:=
NewGameState
(
top
)
root
,
top
,
middle
,
bottom
:=
createTestClaims
()
g
:=
NewGameState
(
root
,
testMaxDepth
)
// Put the next claim into state.
err
:=
g
.
PutAll
([]
Claim
{
middle
})
err
:=
g
.
PutAll
([]
Claim
{
top
,
middle
})
require
.
NoError
(
t
,
err
)
// Try to put the root claim into the game state again.
err
=
g
.
PutAll
([]
Claim
{
middle
})
err
=
g
.
PutAll
([]
Claim
{
middle
,
bottom
})
require
.
ErrorIs
(
t
,
err
,
ErrClaimExists
)
}
// TestGame_PutAll_ParentsAndChildren tests the [Game.PutAll] method using a [gameState] instance.
func
TestGame_PutAll_ParentsAndChildren
(
t
*
testing
.
T
)
{
// Setup the game state.
top
,
middle
,
bottom
:=
createTestClaims
()
g
:=
NewGameState
(
top
)
root
,
top
,
middle
,
bottom
:=
createTestClaims
()
g
:=
NewGameState
(
root
,
testMaxDepth
)
// We should not be able to get the parent of the root claim.
parent
,
err
:=
g
.
getParent
(
top
)
parent
,
err
:=
g
.
getParent
(
root
)
require
.
ErrorIs
(
t
,
err
,
ErrClaimNotFound
)
require
.
Equal
(
t
,
parent
,
Claim
{})
// Put the rest of the claims in the state.
err
=
g
.
PutAll
([]
Claim
{
middle
,
bottom
})
err
=
g
.
PutAll
([]
Claim
{
top
,
middle
,
bottom
})
require
.
NoError
(
t
,
err
)
parent
,
err
=
g
.
getParent
(
top
)
require
.
NoError
(
t
,
err
)
require
.
Equal
(
t
,
parent
,
root
)
parent
,
err
=
g
.
getParent
(
middle
)
require
.
NoError
(
t
,
err
)
require
.
Equal
(
t
,
parent
,
top
)
...
...
@@ -100,24 +122,12 @@ func TestGame_PutAll_ParentsAndChildren(t *testing.T) {
require
.
Equal
(
t
,
parent
,
middle
)
}
// TestGame_Put_RootAlreadyExists tests the [Game.Put] method using a [gameState]
// instance errors when the root claim already exists in state.
func
TestGame_Put_RootAlreadyExists
(
t
*
testing
.
T
)
{
// Setup the game state.
top
,
_
,
_
:=
createTestClaims
()
g
:=
NewGameState
(
top
)
// Try to put the root claim into the game state again.
err
:=
g
.
Put
(
top
)
require
.
ErrorIs
(
t
,
err
,
ErrClaimExists
)
}
// TestGame_Put_AlreadyExists tests the [Game.Put] method using a [gameState]
// instance errors when the given claim already exists in state.
func
TestGame_Put_AlreadyExists
(
t
*
testing
.
T
)
{
// Setup the game state.
top
,
middle
,
_
:=
createTestClaims
()
g
:=
NewGameState
(
top
)
top
,
middle
,
_
,
_
:=
createTestClaims
()
g
:=
NewGameState
(
top
,
testMaxDepth
)
// Put the next claim into state.
err
:=
g
.
Put
(
middle
)
...
...
@@ -131,24 +141,29 @@ func TestGame_Put_AlreadyExists(t *testing.T) {
// TestGame_Put_ParentsAndChildren tests the [Game.Put] method using a [gameState] instance.
func
TestGame_Put_ParentsAndChildren
(
t
*
testing
.
T
)
{
// Setup the game state.
top
,
middle
,
bottom
:=
createTestClaims
()
g
:=
NewGameState
(
top
)
root
,
top
,
middle
,
bottom
:=
createTestClaims
()
g
:=
NewGameState
(
root
,
testMaxDepth
)
// We should not be able to get the parent of the root claim.
parent
,
err
:=
g
.
getParent
(
top
)
parent
,
err
:=
g
.
getParent
(
root
)
require
.
ErrorIs
(
t
,
err
,
ErrClaimNotFound
)
require
.
Equal
(
t
,
parent
,
Claim
{})
// Put the middle claim into the game state.
// We should expect no parent to exist, yet.
// Put + Check Top
err
=
g
.
Put
(
top
)
require
.
NoError
(
t
,
err
)
parent
,
err
=
g
.
getParent
(
top
)
require
.
NoError
(
t
,
err
)
require
.
Equal
(
t
,
parent
,
root
)
// Put + Check Top Middle
err
=
g
.
Put
(
middle
)
require
.
NoError
(
t
,
err
)
parent
,
err
=
g
.
getParent
(
middle
)
require
.
NoError
(
t
,
err
)
require
.
Equal
(
t
,
parent
,
top
)
// Put the bottom claim into the game state.
// We should expect the parent to be the claim we just added.
// Put + Check Top Bottom
err
=
g
.
Put
(
bottom
)
require
.
NoError
(
t
,
err
)
parent
,
err
=
g
.
getParent
(
bottom
)
...
...
@@ -159,11 +174,15 @@ func TestGame_Put_ParentsAndChildren(t *testing.T) {
// TestGame_ClaimPairs tests the [Game.ClaimPairs] method using a [gameState] instance.
func
TestGame_ClaimPairs
(
t
*
testing
.
T
)
{
// Setup the game state.
top
,
middle
,
bottom
:=
createTestClaims
()
g
:=
NewGameState
(
top
)
root
,
top
,
middle
,
bottom
:=
createTestClaims
()
g
:=
NewGameState
(
root
,
testMaxDepth
)
// Add middle claim to the game state.
err
:=
g
.
Put
(
middle
)
// Add top claim to the game state.
err
:=
g
.
Put
(
top
)
require
.
NoError
(
t
,
err
)
// Add the middle claim to the game state.
err
=
g
.
Put
(
middle
)
require
.
NoError
(
t
,
err
)
// Add the bottom claim to the game state.
...
...
@@ -171,7 +190,47 @@ func TestGame_ClaimPairs(t *testing.T) {
require
.
NoError
(
t
,
err
)
// Validate claim pairs.
expected
:=
[]
Claim
{
top
,
middle
,
bottom
}
expected
:=
[]
Claim
{
root
,
top
,
middle
,
bottom
}
claims
:=
g
.
Claims
()
require
.
ElementsMatch
(
t
,
expected
,
claims
)
}
// TestPrePostStateOnlyOnLeafClaim tests that if PreStateClaim or PostStateClaim is called with an non-leaf claim
// those functions return an error.
func
TestPrePostStateOnlyOnLeafClaim
(
t
*
testing
.
T
)
{
root
,
top
,
middle
,
bottom
:=
createTestClaims
()
g
:=
NewGameState
(
root
,
testMaxDepth
)
require
.
NoError
(
t
,
g
.
PutAll
([]
Claim
{
top
,
middle
,
bottom
}))
_
,
err
:=
g
.
PreStateClaim
(
middle
)
require
.
Error
(
t
,
err
)
_
,
err
=
g
.
PostStateClaim
(
middle
)
require
.
Error
(
t
,
err
)
}
func
TestPreStateClaim
(
t
*
testing
.
T
)
{
root
,
top
,
middle
,
bottom
:=
createTestClaims
()
g
:=
NewGameState
(
root
,
testMaxDepth
)
require
.
NoError
(
t
,
g
.
Put
(
top
))
require
.
NoError
(
t
,
g
.
Put
(
middle
))
require
.
NoError
(
t
,
g
.
Put
(
bottom
))
// Bottom trace index is 4. Pre trace index is then 3
pre
,
err
:=
g
.
PreStateClaim
(
bottom
)
require
.
NoError
(
t
,
err
)
require
.
Equal
(
t
,
top
,
pre
)
}
func
TestPostStateClaim
(
t
*
testing
.
T
)
{
root
,
top
,
middle
,
bottom
:=
createTestClaims
()
g
:=
NewGameState
(
root
,
testMaxDepth
)
require
.
NoError
(
t
,
g
.
Put
(
top
))
require
.
NoError
(
t
,
g
.
Put
(
middle
))
require
.
NoError
(
t
,
g
.
Put
(
bottom
))
// Bottom trace index is 4. Post trace index is then 5
post
,
err
:=
g
.
PostStateClaim
(
bottom
)
require
.
NoError
(
t
,
err
)
require
.
Equal
(
t
,
middle
,
post
)
}
op-challenger/fault/loader_test.go
View file @
e441f6dc
...
...
@@ -47,6 +47,14 @@ func (m *mockGameState) IsDuplicate(claim Claim) bool {
return
false
}
func
(
m
*
mockGameState
)
PreStateClaim
(
claim
Claim
)
(
Claim
,
error
)
{
panic
(
"unimplemented"
)
}
func
(
m
*
mockGameState
)
PostStateClaim
(
claim
Claim
)
(
Claim
,
error
)
{
panic
(
"unimplemented"
)
}
type
mockClaimFetcher
struct
{
claimDataError
bool
claimLenError
bool
...
...
op-challenger/fault/orchestrator.go
View file @
e441f6dc
...
...
@@ -22,7 +22,7 @@ func NewOrchestrator(maxDepth uint64, traces []TraceProvider, names []string, ro
}
log
.
Info
(
"Starting game"
,
"root_letter"
,
string
(
root
.
Value
[
31
:
]))
for
i
,
trace
:=
range
traces
{
game
:=
NewGameState
(
root
)
game
:=
NewGameState
(
root
,
maxDepth
)
o
.
agents
[
i
]
=
NewAgent
(
game
,
int
(
maxDepth
),
trace
,
&
o
,
log
.
New
(
"role"
,
names
[
i
]))
o
.
outputChs
[
i
]
=
make
(
chan
Claim
)
}
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment