Skip to content

Commit

Permalink
Withdrawal credentials operations in advance.
Browse files Browse the repository at this point in the history
Allow withdrawal credentials change operations to be generated prior to
the Capella hard fork, allowing queueing if the beacon node supports it.
  • Loading branch information
mcdee committed Nov 29, 2022
1 parent 9d00f6b commit 16a94d7
Show file tree
Hide file tree
Showing 4 changed files with 63 additions and 14 deletions.
3 changes: 3 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
1.26.1
- add ability to generate validator credentials change operations prior to the fork in which they become usable

1.26.0
- add commands and documentation to set user validator credentials (not usable until capella)

Expand Down
68 changes: 57 additions & 11 deletions cmd/validator/credentials/set/process.go
Original file line number Diff line number Diff line change
Expand Up @@ -114,24 +114,70 @@ func (c *command) populateChainInfo(ctx context.Context) error {
}

// Obtain genesis validators root.
genesis, err := c.consensusClient.(consensusclient.GenesisProvider).Genesis(ctx)
if err != nil {
return errors.Wrap(err, "failed to obtain genesis information")
if c.genesisValidatorsRoot != "" {
// Genesis validators root supplied manually.
genesisValidatorsRoot, err := hex.DecodeString(strings.TrimPrefix(c.genesisValidatorsRoot, "0x"))
if err != nil {
return errors.Wrap(err, "invalid genesis validators root supplied")
}
if len(genesisValidatorsRoot) != phase0.RootLength {
return errors.New("invalid length for genesis validators root")
}
copy(c.chainInfo.GenesisValidatorsRoot[:], genesisValidatorsRoot)
} else {
// Genesis validators root obtained from beacon node.
genesis, err := c.consensusClient.(consensusclient.GenesisProvider).Genesis(ctx)
if err != nil {
return errors.Wrap(err, "failed to obtain genesis information")
}
c.chainInfo.GenesisValidatorsRoot = genesis.GenesisValidatorsRoot
}
if c.debug {
fmt.Printf("Genesis validators root is %#x\n", c.chainInfo.GenesisValidatorsRoot)
}
c.chainInfo.GenesisValidatorsRoot = genesis.GenesisValidatorsRoot

// Obtain epoch.
c.chainInfo.Epoch = c.chainTime.CurrentEpoch()

// Obtain fork version.
forkSchedule, err := c.consensusClient.(consensusclient.ForkScheduleProvider).ForkSchedule(ctx)
if err != nil {
return errors.Wrap(err, "failed to obtain fork schedule")
}
for i := range forkSchedule {
if forkSchedule[i].Epoch <= c.chainInfo.Epoch {
c.chainInfo.ForkVersion = forkSchedule[i].CurrentVersion
if c.forkVersion != "" {
// Fork version supplied manually.
forkVersion, err := hex.DecodeString(strings.TrimPrefix(c.forkVersion, "0x"))
if err != nil {
return errors.Wrap(err, "invalid fork version supplied")
}
if len(forkVersion) != phase0.ForkVersionLength {
return errors.New("invalid length for fork version")
}
copy(c.chainInfo.ForkVersion[:], forkVersion)
} else {
// Fork version obtained from beacon node.
forkSchedule, err := c.consensusClient.(consensusclient.ForkScheduleProvider).ForkSchedule(ctx)
if err != nil {
return errors.Wrap(err, "failed to obtain fork schedule")
}
if len(forkSchedule) < 4 {
return errors.New("beacon node not providing capella fork schedule; provide manually with --fork-version")
}
for i := range forkSchedule {
// Need to be at least fork 3 (i.e. capella)
if i < 3 {
continue
}
if i == 3 {
// Force use of capella even if we aren't there yet, to allow credential
// change operations to be signed in advance with a signature that will be
// valid once capella goes live.
c.chainInfo.ForkVersion = forkSchedule[i].CurrentVersion
continue
}
if forkSchedule[i].Epoch <= c.chainInfo.Epoch {
c.chainInfo.ForkVersion = forkSchedule[i].CurrentVersion
}
}
}
if c.debug {
fmt.Printf("Fork version is %#x\n", c.chainInfo.ForkVersion)
}

// Calculate domain.
Expand Down
4 changes: 2 additions & 2 deletions cmd/validatorcredentialsset.go
Original file line number Diff line number Diff line change
Expand Up @@ -60,8 +60,8 @@ func init() {
validatorCredentialsSetCmd.Flags().String("signed-operation", "", "Use pre-defined JSON signed operation as created by --json to transmit the credentials change operation")
validatorCredentialsSetCmd.Flags().Bool("json", false, "Generate JSON data containing a signed operation rather than broadcast it to the network (implied when offline)")
validatorCredentialsSetCmd.Flags().Bool("offline", false, "Do not attempt to connect to a beacon node to obtain information for the operation")
validatorCredentialsSetCmd.Flags().String("fork-version", "", "Fork version to use for signing (offline only)")
validatorCredentialsSetCmd.Flags().String("genesis-validators-root", "", "Genesis validators root to use for signing (offline only)")
validatorCredentialsSetCmd.Flags().String("fork-version", "", "Fork version to use for signing (overrides fetching from beacon node)")
validatorCredentialsSetCmd.Flags().String("genesis-validators-root", "", "Genesis validators root to use for signing (overrides fetching from beacon node)")
}

func validatorCredentialsSetBindings() {
Expand Down
2 changes: 1 addition & 1 deletion cmd/version.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ import (

// ReleaseVersion is the release version of the codebase.
// Usually overridden by tag names when building binaries.
var ReleaseVersion = "local build (latest release 1.26.0)"
var ReleaseVersion = "local build (latest release 1.26.1)"

// versionCmd represents the version command
var versionCmd = &cobra.Command{
Expand Down

0 comments on commit 16a94d7

Please sign in to comment.