diff --git a/cmd/blockchaincmd/add_validator.go b/cmd/blockchaincmd/add_validator.go index 7ddcb7dbc..ebbe52d8c 100644 --- a/cmd/blockchaincmd/add_validator.go +++ b/cmd/blockchaincmd/add_validator.go @@ -66,7 +66,7 @@ var ( aggregatorAllowPrivatePeers bool clusterNameFlagValue string createLocalValidator bool - multisigValidatorManagerOwner bool + externalValidatorManagerOwner bool ) const ( @@ -126,7 +126,7 @@ Testnet or Mainnet.`, cmd.Flags().StringVar(&subnetIDstr, "subnet-id", "", "subnet ID (only if blockchain name is not provided)") cmd.Flags().StringVar(&validatorManagerOwnerAddress, "validator-manager-owner", "", "validator manager owner address (only if blockchain name is not provided)") cmd.Flags().Uint64Var(&weight, validatorWeightFlag, uint64(constants.DefaultStakeWeight), "set the weight of the validator") - cmd.Flags().BoolVar(&multisigValidatorManagerOwner, "multisig-validator-manager-ower", false, "validator manager owner is multisig, make hex dump of ech evm transactions, so they can be signed in a separate flow") + cmd.Flags().BoolVar(&externalValidatorManagerOwner, "external-validator-manager-owner", false, "validator manager owner is external, make hex dump of ech evm transactions, so they can be signed in a separate flow") return cmd } @@ -409,7 +409,7 @@ func CallAddValidator( validatorManagerAddress = sc.Networks[network.Name()].ValidatorManagerAddress var ownerPrivateKey string - if !multisigValidatorManagerOwner { + if !externalValidatorManagerOwner { var ownerPrivateKeyFound bool ownerPrivateKeyFound, _, _, ownerPrivateKey, err = contract.SearchForManagedKey( app, @@ -436,6 +436,13 @@ func CallAddValidator( } } } + + if sc.UseACP99 { + ux.Logger.PrintToUser(logging.Yellow.Wrap("Validator Manager Protocol: ACP99")) + } else { + ux.Logger.PrintToUser(logging.Yellow.Wrap("Validator Manager Protocol: v1.0.0")) + } + ux.Logger.PrintToUser(logging.Yellow.Wrap("Validation manager owner %s pays for the initialization of the validator's registration (Blockchain gas token)"), sc.ValidatorManagerOwner) if rpcURL == "" { @@ -537,7 +544,7 @@ func CallAddValidator( network, rpcURL, chainSpec, - multisigValidatorManagerOwner, + externalValidatorManagerOwner, sc.ValidatorManagerOwner, ownerPrivateKey, nodeID, @@ -553,6 +560,7 @@ func CallAddValidator( delegationFee, duration, validatorManagerAddress, + sc.UseACP99, ) if err != nil { return err @@ -591,7 +599,7 @@ func CallAddValidator( network, rpcURL, chainSpec, - multisigValidatorManagerOwner, + externalValidatorManagerOwner, sc.ValidatorManagerOwner, ownerPrivateKey, validationID, diff --git a/cmd/blockchaincmd/change_weight.go b/cmd/blockchaincmd/change_weight.go index be8a7b9b7..7c01fd9eb 100644 --- a/cmd/blockchaincmd/change_weight.go +++ b/cmd/blockchaincmd/change_weight.go @@ -3,25 +3,34 @@ package blockchaincmd import ( + "encoding/hex" "fmt" + "strings" + "github.com/ava-labs/avalanche-cli/pkg/blockchain" "github.com/ava-labs/avalanche-cli/pkg/cobrautils" "github.com/ava-labs/avalanche-cli/pkg/constants" "github.com/ava-labs/avalanche-cli/pkg/contract" "github.com/ava-labs/avalanche-cli/pkg/key" "github.com/ava-labs/avalanche-cli/pkg/keychain" + "github.com/ava-labs/avalanche-cli/pkg/models" "github.com/ava-labs/avalanche-cli/pkg/networkoptions" "github.com/ava-labs/avalanche-cli/pkg/node" "github.com/ava-labs/avalanche-cli/pkg/prompts" "github.com/ava-labs/avalanche-cli/pkg/subnet" "github.com/ava-labs/avalanche-cli/pkg/utils" "github.com/ava-labs/avalanche-cli/pkg/ux" + "github.com/ava-labs/avalanche-cli/pkg/validatormanager" + sdkutils "github.com/ava-labs/avalanche-cli/sdk/utils" "github.com/ava-labs/avalanche-cli/sdk/validator" "github.com/ava-labs/avalanchego/ids" "github.com/ava-labs/avalanchego/utils/crypto/bls" "github.com/ava-labs/avalanchego/utils/formatting" "github.com/ava-labs/avalanchego/utils/formatting/address" + "github.com/ava-labs/avalanchego/utils/logging" "github.com/ava-labs/avalanchego/utils/units" + + "github.com/ethereum/go-ethereum/common" "github.com/spf13/cobra" ) @@ -47,6 +56,12 @@ The L1 has to be a Proof of Authority L1.`, cmd.Flags().StringVar(&nodeEndpoint, "node-endpoint", "", "gather node id/bls from publicly available avalanchego apis on the given endpoint") cmd.Flags().BoolVarP(&useLedger, "ledger", "g", false, "use ledger instead of key (always true on mainnet, defaults to false on fuji/devnet)") cmd.Flags().StringSliceVar(&ledgerAddresses, "ledger-addrs", []string{}, "use the given ledger addresses") + cmd.Flags().BoolVar(&externalValidatorManagerOwner, "external-validator-manager-owner", false, "validator manager owner is external, make hex dump of ech evm transactions, so they can be signed in a separate flow") + cmd.Flags().StringSliceVar(&aggregatorExtraEndpoints, "aggregator-extra-endpoints", nil, "endpoints for extra nodes that are needed in signature aggregation") + cmd.Flags().BoolVar(&aggregatorAllowPrivatePeers, "aggregator-allow-private-peers", true, "allow the signature aggregator to connect to peers with private IP") + cmd.Flags().StringVar(&aggregatorLogLevel, "aggregator-log-level", constants.DefaultAggregatorLogLevel, "log level to use with signature aggregator") + cmd.Flags().BoolVar(&aggregatorLogToStdout, "aggregator-log-to-stdout", false, "use stdout for signature aggregator logs") + cmd.Flags().StringVar(&rpcURL, "rpc", "", "connect to validator manager at the given rpc endpoint") return cmd } @@ -190,6 +205,21 @@ func setWeight(_ *cobra.Command, args []string) error { return fmt.Errorf("can't make change: desired validator weight %d exceeds max allowed weight change of %d", newWeight, uint64(allowedChange)) } + deployer := subnet.NewPublicDeployer(app, kc, network) + + if sc.UseACP99 { + ux.Logger.PrintToUser(logging.Yellow.Wrap("Validator Manager Protocol: ACP99")) + return changeWeightACP99( + deployer, + network, + blockchainName, + nodeID, + newWeight, + ) + } else { + ux.Logger.PrintToUser(logging.Yellow.Wrap("Validator Manager Protocol: v1.0.0")) + } + publicKey, err = formatting.Encode(formatting.HexNC, bls.PublicKeyToCompressedBytes(validatorInfo.PublicKey)) if err != nil { return err @@ -202,8 +232,6 @@ func setWeight(_ *cobra.Command, args []string) error { } } - deployer := subnet.NewPublicDeployer(app, kc, network) - var remainingBalanceOwnerAddr, disableOwnerAddr string hrp := key.GetHRP(network.ID) if validatorInfo.RemainingBalanceOwner != nil && len(validatorInfo.RemainingBalanceOwner.Addrs) > 0 { @@ -260,3 +288,155 @@ func setWeight(_ *cobra.Command, args []string) error { sc, ) } + +func changeWeightACP99( + deployer *subnet.PublicDeployer, + network models.Network, + blockchainName string, + nodeID ids.NodeID, + weight uint64, +) error { + chainSpec := contract.ChainSpec{ + BlockchainName: blockchainName, + } + + sc, err := app.LoadSidecar(chainSpec.BlockchainName) + if err != nil { + return fmt.Errorf("failed to load sidecar: %w", err) + } + var ownerPrivateKey string + if !externalValidatorManagerOwner { + var ownerPrivateKeyFound bool + ownerPrivateKeyFound, _, _, ownerPrivateKey, err = contract.SearchForManagedKey( + app, + network, + common.HexToAddress(sc.ValidatorManagerOwner), + true, + ) + if err != nil { + return err + } + if !ownerPrivateKeyFound { + return fmt.Errorf("not private key found for Validator manager owner %s", sc.ValidatorManagerOwner) + } + } + ux.Logger.PrintToUser(logging.Yellow.Wrap("Validator manager owner %s pays for the initialization of the validator's weight change (Blockchain gas token)"), sc.ValidatorManagerOwner) + + if sc.Networks[network.Name()].ValidatorManagerAddress == "" { + return fmt.Errorf("unable to find Validator Manager address") + } + validatorManagerAddress = sc.Networks[network.Name()].ValidatorManagerAddress + + ux.Logger.PrintToUser(logging.Yellow.Wrap("RPC Endpoint: %s"), rpcURL) + + clusterName := sc.Networks[network.Name()].ClusterName + extraAggregatorPeers, err := blockchain.GetAggregatorExtraPeers(app, clusterName, aggregatorExtraEndpoints) + if err != nil { + return err + } + aggregatorLogger, err := utils.NewLogger( + constants.SignatureAggregatorLogName, + aggregatorLogLevel, + constants.DefaultAggregatorLogLevel, + app.GetAggregatorLogDir(clusterName), + aggregatorLogToStdout, + ux.Logger.PrintToUser, + ) + if err != nil { + return err + } + + aggregatorCtx, aggregatorCancel := sdkutils.GetTimedContext(constants.SignatureAggregatorTimeout) + defer aggregatorCancel() + + // try to remove the validator. If err is "delegator ineligible for rewards" confirm with user and force remove + signedMessage, validationID, rawTx, err := validatormanager.InitValidatorWeightChange( + aggregatorCtx, + app, + network, + rpcURL, + chainSpec, + externalValidatorManagerOwner, + sc.ValidatorManagerOwner, + ownerPrivateKey, + nodeID, + extraAggregatorPeers, + aggregatorAllowPrivatePeers, + aggregatorLogger, + validatorManagerAddress, + weight, + ) + if err != nil { + return err + } + if rawTx != nil { + bs, err := rawTx.MarshalBinary() + if err != nil { + return fmt.Errorf("failure marshalling raw evm tx: %w", err) + } + ux.Logger.PrintToUser("Raw Tx Dump For Initializing Validator Weight Change. Please sign and commit it.") + ux.Logger.PrintToUser("0x%s", hex.EncodeToString(bs)) + return nil + } + + ux.Logger.PrintToUser("ValidationID: %s", validationID) + + validatorInfo, err := validator.GetValidatorInfo(network.SDKNetwork(), validationID) + if err != nil { + return err + } + if validatorInfo.Weight == newWeight { + ux.Logger.PrintToUser(logging.LightBlue.Wrap("The new Weight was already set on the P-Chain. Proceeding to the next step")) + } else { + txID, _, err := deployer.SetL1ValidatorWeight(signedMessage) + if err != nil { + if !strings.Contains(err.Error(), "could not load L1 validator: not found") { + return err + } + ux.Logger.PrintToUser(logging.LightBlue.Wrap("The Validation ID was already removed on the P-Chain. Proceeding to the next step")) + } else { + ux.Logger.PrintToUser("SetL1ValidatorWeightTx ID: %s", txID) + if err := blockchain.UpdatePChainHeight( + "Waiting for P-Chain to update validator information ...", + ); err != nil { + return err + } + } + } + + aggregatorCtx, aggregatorCancel = sdkutils.GetTimedContext(constants.SignatureAggregatorTimeout) + defer aggregatorCancel() + rawTx, err = validatormanager.FinishValidatorWeightChange( + aggregatorCtx, + app, + network, + rpcURL, + chainSpec, + externalValidatorManagerOwner, + sc.ValidatorManagerOwner, + ownerPrivateKey, + validationID, + extraAggregatorPeers, + aggregatorAllowPrivatePeers, + aggregatorLogger, + validatorManagerAddress, + signedMessage, + newWeight, + ) + if err != nil { + return err + } + if rawTx != nil { + bs, err := rawTx.MarshalBinary() + if err != nil { + return fmt.Errorf("failure marshalling raw evm tx: %w", err) + } + ux.Logger.PrintToUser("Raw Tx Dump For Finish Validator Weight Change. Please sign and commit it.") + ux.Logger.PrintToUser("0x%s", hex.EncodeToString(bs)) + return nil + } + + ux.Logger.GreenCheckmarkToUser("Weight change successfully made") + + return nil +} diff --git a/cmd/blockchaincmd/convert.go b/cmd/blockchaincmd/convert.go index 085af091e..0356bfb85 100644 --- a/cmd/blockchaincmd/convert.go +++ b/cmd/blockchaincmd/convert.go @@ -261,7 +261,14 @@ func InitializeValidatorManager( pos bool, validatorManagerAddrStr string, proxyContractOwner string, + useACP99 bool, ) (bool, error) { + if useACP99 { + ux.Logger.PrintToUser(logging.Yellow.Wrap("Validator Manager Protocol: ACP99")) + } else { + ux.Logger.PrintToUser(logging.Yellow.Wrap("Validator Manager Protocol: v1.0.0")) + } + var err error clusterName := clusterNameFlagValue switch { @@ -403,6 +410,7 @@ func InitializeValidatorManager( aggregatorAllowPrivatePeers, aggregatorLogger, validatorManagerAddrStr, + useACP99, ); err != nil { return tracked, err } @@ -768,6 +776,7 @@ func convertBlockchain(_ *cobra.Command, args []string) error { sidecar.ValidatorManagement == models.ProofOfStake, validatorManagerAddress, sidecar.ProxyContractOwner, + sidecar.UseACP99, ); err != nil { return err } diff --git a/cmd/blockchaincmd/create.go b/cmd/blockchaincmd/create.go index 69da4c362..f43e7642e 100644 --- a/cmd/blockchaincmd/create.go +++ b/cmd/blockchaincmd/create.go @@ -55,6 +55,7 @@ type CreateFlags struct { validatorManagerOwner string proxyContractOwner string enableDebugging bool + useACP99 bool } var ( @@ -123,6 +124,7 @@ configuration, pass the -f flag.`, cmd.Flags().BoolVar(&sovereign, "sovereign", true, "set to false if creating non-sovereign blockchain") cmd.Flags().Uint64Var(&createFlags.rewardBasisPoints, "reward-basis-points", 100, "(PoS only) reward basis points for PoS Reward Calculator") cmd.Flags().BoolVar(&createFlags.enableDebugging, "debug", true, "enable blockchain debugging") + cmd.Flags().BoolVar(&createFlags.useACP99, "acp99", true, "use ACP99 contracts instead of v1.0.0 for validator managers") return cmd } @@ -335,6 +337,7 @@ func createBlockchainConfig(cmd *cobra.Command, args []string) error { createFlags.addICMRegistryToGenesis, sc.ProxyContractOwner, createFlags.rewardBasisPoints, + createFlags.useACP99, ) if err != nil { return err @@ -348,6 +351,7 @@ func createBlockchainConfig(cmd *cobra.Command, args []string) error { tokenSymbol, true, sovereign, + createFlags.useACP99, ); err != nil { return err } diff --git a/cmd/blockchaincmd/deploy.go b/cmd/blockchaincmd/deploy.go index 7081612ed..d76e8e22f 100644 --- a/cmd/blockchaincmd/deploy.go +++ b/cmd/blockchaincmd/deploy.go @@ -820,6 +820,7 @@ func deployBlockchain(cmd *cobra.Command, args []string) error { sidecar.ValidatorManagement == models.ProofOfStake, validatorManagerStr, sidecar.ProxyContractOwner, + sidecar.UseACP99, ) if err != nil { return err diff --git a/cmd/blockchaincmd/describe.go b/cmd/blockchaincmd/describe.go index deaeeb7d0..3cba54cf4 100644 --- a/cmd/blockchaincmd/describe.go +++ b/cmd/blockchaincmd/describe.go @@ -352,6 +352,11 @@ func printSmartContracts(sc models.Sidecar, genesis core.Genesis) { } else { description = "Native Token Staking Manager" } + if sc.UseACP99 { + description = "ACP99 Compatible " + description + } else { + description = "v1.0.0 Compatible " + description + } case address == common.HexToAddress(validatorManagerSDK.ProxyContractAddress): description = "Transparent Proxy" case address == common.HexToAddress(validatorManagerSDK.ProxyAdminContractAddress): diff --git a/cmd/blockchaincmd/export_test.go b/cmd/blockchaincmd/export_test.go index 1b4295a33..4537ad872 100644 --- a/cmd/blockchaincmd/export_test.go +++ b/cmd/blockchaincmd/export_test.go @@ -45,6 +45,7 @@ func TestExportImportSubnet(t *testing.T) { "Test", false, true, + true, ) require.NoError(err) err = app.WriteGenesisFile(testSubnet, genBytes) diff --git a/cmd/blockchaincmd/remove_validator.go b/cmd/blockchaincmd/remove_validator.go index 941c24873..09c13539d 100644 --- a/cmd/blockchaincmd/remove_validator.go +++ b/cmd/blockchaincmd/remove_validator.go @@ -3,6 +3,7 @@ package blockchaincmd import ( + "encoding/hex" "errors" "fmt" "os" @@ -27,9 +28,8 @@ import ( "github.com/ava-labs/avalanchego/api/info" "github.com/ava-labs/avalanchego/ids" "github.com/ava-labs/avalanchego/utils/logging" - "github.com/ava-labs/avalanchego/vms/platformvm/warp" - "github.com/ethereum/go-ethereum/common" + "github.com/ethereum/go-ethereum/common" "github.com/spf13/cobra" ) @@ -66,6 +66,7 @@ these prompts by providing the values with flags.`, cmd.Flags().BoolVar(&aggregatorLogToStdout, "aggregator-log-to-stdout", false, "use stdout for signature aggregator logs") cmd.Flags().Uint64Var(&uptimeSec, "uptime", 0, "validator's uptime in seconds. If not provided, it will be automatically calculated") cmd.Flags().BoolVar(&force, "force", false, "force validator removal even if it's not getting rewarded") + cmd.Flags().BoolVar(&externalValidatorManagerOwner, "external-validator-manager-owner", false, "validator manager owner is external, make hex dump of ech evm transactions, so they can be signed in a separate flow") return cmd } @@ -142,10 +143,39 @@ func removeValidator(_ *cobra.Command, args []string) error { } } - validatorKind, err := validatorsdk.IsSovereignValidator(network.SDKNetwork(), subnetID, nodeID) + chainSpec := contract.ChainSpec{ + BlockchainName: blockchainName, + } + if rpcURL == "" { + rpcURL, _, err = contract.GetBlockchainEndpoints( + app, + network, + chainSpec, + true, + false, + ) + if err != nil { + return err + } + } + validatorManagerAddress = sc.Networks[network.Name()].ValidatorManagerAddress + validationID, err := validatorsdk.GetRegisteredValidator( + rpcURL, + common.HexToAddress(validatorManagerAddress), + nodeID, + ) if err != nil { return err } + var validatorKind validatorsdk.ValidatorKind + if validationID != ids.Empty { + validatorKind = validatorsdk.SovereignValidator + } else { + validatorKind, err = validatorsdk.IsSovereignValidator(network.SDKNetwork(), subnetID, nodeID) + if err != nil { + return err + } + } if validatorKind == validatorsdk.NonValidator { return fmt.Errorf("node %s is not a validator of subnet %s on %s", nodeID, subnetID, network.Name()) } @@ -234,18 +264,29 @@ func removeValidatorSOV( if err != nil { return fmt.Errorf("failed to load sidecar: %w", err) } - ownerPrivateKeyFound, _, _, ownerPrivateKey, err := contract.SearchForManagedKey( - app, - network, - common.HexToAddress(sc.ValidatorManagerOwner), - true, - ) - if err != nil { - return err + var ownerPrivateKey string + if !externalValidatorManagerOwner { + var ownerPrivateKeyFound bool + ownerPrivateKeyFound, _, _, ownerPrivateKey, err = contract.SearchForManagedKey( + app, + network, + common.HexToAddress(sc.ValidatorManagerOwner), + true, + ) + if err != nil { + return err + } + if !ownerPrivateKeyFound { + return fmt.Errorf("not private key found for Validator manager owner %s", sc.ValidatorManagerOwner) + } } - if !ownerPrivateKeyFound { - return fmt.Errorf("not private key found for Validator manager owner %s", sc.ValidatorManagerOwner) + + if sc.UseACP99 { + ux.Logger.PrintToUser(logging.Yellow.Wrap("Validator Manager Protocol: ACP99")) + } else { + ux.Logger.PrintToUser(logging.Yellow.Wrap("Validator Manager Protocol: v1.0.0")) } + ux.Logger.PrintToUser(logging.Yellow.Wrap("Validator manager owner %s pays for the initialization of the validator's removal (Blockchain gas token)"), sc.ValidatorManagerOwner) if sc.Networks[network.Name()].ValidatorManagerAddress == "" { @@ -253,18 +294,6 @@ func removeValidatorSOV( } validatorManagerAddress = sc.Networks[network.Name()].ValidatorManagerAddress - if rpcURL == "" { - rpcURL, _, err = contract.GetBlockchainEndpoints( - app, - network, - chainSpec, - true, - false, - ) - if err != nil { - return err - } - } ux.Logger.PrintToUser(logging.Yellow.Wrap("RPC Endpoint: %s"), rpcURL) clusterName := sc.Networks[network.Name()].ClusterName extraAggregatorPeers, err := blockchain.GetAggregatorExtraPeers(app, clusterName, aggregatorExtraEndpoints) @@ -275,7 +304,7 @@ func removeValidatorSOV( constants.SignatureAggregatorLogName, aggregatorLogLevel, constants.DefaultAggregatorLogLevel, - app.GetAggregatorLogDir(clusterNameFlagValue), + app.GetAggregatorLogDir(clusterName), aggregatorLogToStdout, ux.Logger.PrintToUser, ) @@ -286,19 +315,18 @@ func removeValidatorSOV( ux.Logger.PrintToUser(logging.Yellow.Wrap("Forcing removal of %s as it is a PoS bootstrap validator"), nodeID) } - var ( - signedMessage *warp.Message - validationID ids.ID - ) aggregatorCtx, aggregatorCancel := sdkutils.GetTimedContext(constants.SignatureAggregatorTimeout) defer aggregatorCancel() + // try to remove the validator. If err is "delegator ineligible for rewards" confirm with user and force remove - signedMessage, validationID, err = validatormanager.InitValidatorRemoval( + signedMessage, validationID, rawTx, err := validatormanager.InitValidatorRemoval( aggregatorCtx, app, network, rpcURL, chainSpec, + externalValidatorManagerOwner, + sc.ValidatorManagerOwner, ownerPrivateKey, nodeID, extraAggregatorPeers, @@ -308,6 +336,7 @@ func removeValidatorSOV( uptimeSec, isBootstrapValidator || force, validatorManagerAddress, + sc.UseACP99, ) if err != nil && errors.Is(err, validatormanagerSDK.ErrValidatorIneligibleForRewards) { ux.Logger.PrintToUser("Calculated rewards is zero. Validator %s is not eligible for rewards", nodeID) @@ -320,12 +349,14 @@ func removeValidatorSOV( } aggregatorCtx, aggregatorCancel = sdkutils.GetTimedContext(constants.SignatureAggregatorTimeout) defer aggregatorCancel() - signedMessage, validationID, err = validatormanager.InitValidatorRemoval( + signedMessage, validationID, _, err = validatormanager.InitValidatorRemoval( aggregatorCtx, app, network, rpcURL, chainSpec, + externalValidatorManagerOwner, + sc.ValidatorManagerOwner, ownerPrivateKey, nodeID, extraAggregatorPeers, @@ -335,6 +366,7 @@ func removeValidatorSOV( uptimeSec, true, // force validatorManagerAddress, + sc.UseACP99, ) if err != nil { return err @@ -342,6 +374,15 @@ func removeValidatorSOV( } else if err != nil { return err } + if rawTx != nil { + bs, err := rawTx.MarshalBinary() + if err != nil { + return fmt.Errorf("failure marshalling raw evm tx: %w", err) + } + ux.Logger.PrintToUser("Raw Tx Dump For Initializing Validator Removal. Please sign and commit it.") + ux.Logger.PrintToUser("0x%s", hex.EncodeToString(bs)) + return nil + } ux.Logger.PrintToUser("ValidationID: %s", validationID) txID, _, err := deployer.SetL1ValidatorWeight(signedMessage) @@ -361,21 +402,35 @@ func removeValidatorSOV( aggregatorCtx, aggregatorCancel = sdkutils.GetTimedContext(constants.SignatureAggregatorTimeout) defer aggregatorCancel() - if err := validatormanager.FinishValidatorRemoval( + rawTx, err = validatormanager.FinishValidatorRemoval( aggregatorCtx, app, network, rpcURL, chainSpec, + externalValidatorManagerOwner, + sc.ValidatorManagerOwner, ownerPrivateKey, validationID, extraAggregatorPeers, aggregatorAllowPrivatePeers, aggregatorLogger, validatorManagerAddress, - ); err != nil { + sc.UseACP99, + ) + if err != nil { return err } + if rawTx != nil { + bs, err := rawTx.MarshalBinary() + if err != nil { + return fmt.Errorf("failure marshalling raw evm tx: %w", err) + } + ux.Logger.PrintToUser("Raw Tx Dump For Finish Validator Removal. Please sign and commit it.") + ux.Logger.PrintToUser("0x%s", hex.EncodeToString(bs)) + return nil + } + ux.Logger.GreenCheckmarkToUser("Validator successfully removed from the Subnet") return nil diff --git a/cmd/contractcmd/init_validator_manager.go b/cmd/contractcmd/init_validator_manager.go index 6f9efeeb3..03fbc8de9 100644 --- a/cmd/contractcmd/init_validator_manager.go +++ b/cmd/contractcmd/init_validator_manager.go @@ -210,6 +210,7 @@ func initValidatorManager(_ *cobra.Command, args []string) error { validatorManagerFlags.aggregatorAllowPrivatePeers, aggregatorLogger, validatorManagerAddress, + sc.UseACP99, ); err != nil { return err } diff --git a/cmd/nodecmd/local.go b/cmd/nodecmd/local.go index a83c47e83..c4864002a 100644 --- a/cmd/nodecmd/local.go +++ b/cmd/nodecmd/local.go @@ -63,6 +63,7 @@ var ( latestAvagoReleaseVersion bool latestAvagoPreReleaseVersion bool validatorManagerAddress string + useACP99 bool ) // const snapshotName = "local_snapshot" @@ -289,6 +290,7 @@ This command can only be used to validate Proof of Stake L1.`, cmd.Flags().StringVar(&disableOwnerAddr, "disable-owner", "", "P-Chain address that will able to disable the validator with a P-Chain transaction") cmd.Flags().Uint64Var(&minimumStakeDuration, "minimum-stake-duration", constants.PoSL1MinimumStakeDurationSeconds, "minimum stake duration (in seconds)") cmd.Flags().StringVar(&validatorManagerAddress, "validator-manager-address", "", "validator manager address") + cmd.Flags().BoolVar(&useACP99, "acp99", true, "use ACP99 contracts instead of v1.0.0 for validator managers") return cmd } @@ -477,6 +479,12 @@ func localValidate(_ *cobra.Command, args []string) error { return err } + if useACP99 { + ux.Logger.PrintToUser(logging.Yellow.Wrap("Validator Manager Protocol: ACP99")) + } else { + ux.Logger.PrintToUser(logging.Yellow.Wrap("Validator Manager Protocol: v1.0.0")) + } + for _, node := range status.ClusterInfo.NodeInfos { if err = addAsValidator(network, node.Name, @@ -488,6 +496,7 @@ func localValidate(_ *cobra.Command, args []string) error { balance, payerPrivateKey, validatorManagerAddress, + useACP99, ); err != nil { return err } @@ -508,6 +517,7 @@ func addAsValidator(network models.Network, balance uint64, payerPrivateKey string, validatorManagerAddressStr string, + useACP99 bool, ) error { var nodeIDStr string // get node data @@ -563,6 +573,7 @@ func addAsValidator(network models.Network, delegationFee, time.Duration(minimumStakeDuration)*time.Second, validatorManagerAddressStr, + useACP99, ) if err != nil { return err diff --git a/pkg/contract/contract.go b/pkg/contract/contract.go index f013a5c00..8eb32632a 100644 --- a/pkg/contract/contract.go +++ b/pkg/contract/contract.go @@ -6,7 +6,6 @@ import ( _ "embed" "encoding/hex" "encoding/json" - "errors" "fmt" "math/big" "reflect" @@ -358,13 +357,10 @@ func TxToMethod( ux.Logger.PrintToUser("Verify --debug flag value when calling 'blockchain create'") return tx, nil, err } - if errorFromSignature, err := evm.GetErrorFromTrace(trace, errorSignatureToError); err != nil && !errors.Is(err, evm.ErrUnknownErrorSelector) { - ux.Logger.RedXToUser("failed to match error selector on trace: %s", err) - ux.Logger.PrintToUser("error trace for %s error:", description) - ux.Logger.PrintToUser("%#v", trace) - } else if errorFromSignature != nil { + if errorFromSignature, err := evm.GetErrorFromTrace(trace, errorSignatureToError); errorFromSignature != nil { return tx, nil, errorFromSignature } else { + ux.Logger.RedXToUser("failed to match error selector on trace: %s", err) ux.Logger.PrintToUser("error trace for %s error:", description) ux.Logger.PrintToUser("%#v", trace) } @@ -489,13 +485,11 @@ func handleFailedReceiptStatus( ux.Logger.PrintToUser("Verify --debug flag value when calling 'blockchain create'") return tx, receipt, err } - if errorFromSignature, err := evm.GetErrorFromTrace(trace, errorSignatureToError); err != nil && !errors.Is(err, evm.ErrUnknownErrorSelector) { - printFailedReceiptStatusMessage(rpcURL, description, tx) - ux.Logger.RedXToUser("failed to match error selector on trace: %s", err) - } else if errorFromSignature != nil { + if errorFromSignature, err := evm.GetErrorFromTrace(trace, errorSignatureToError); errorFromSignature != nil { return tx, receipt, errorFromSignature } else { printFailedReceiptStatusMessage(rpcURL, description, tx) + ux.Logger.RedXToUser("failed to match error selector on trace: %s", err) ux.Logger.PrintToUser("error trace:") ux.Logger.PrintToUser("%#v", trace) } diff --git a/pkg/models/sidecar.go b/pkg/models/sidecar.go index 00bfd5b43..a7a8688ae 100644 --- a/pkg/models/sidecar.go +++ b/pkg/models/sidecar.go @@ -50,6 +50,7 @@ type Sidecar struct { ProxyContractOwner string // Subnet defaults to Sovereign post ACP-77 Sovereign bool + UseACP99 bool } func (sc Sidecar) GetVMID() (string, error) { diff --git a/pkg/utils/common.go b/pkg/utils/common.go index b2c109448..f9e5c1a79 100644 --- a/pkg/utils/common.go +++ b/pkg/utils/common.go @@ -643,3 +643,12 @@ func VMID(vmName string) (ids.ID, error) { copy(b, []byte(vmName)) return ids.ToID(b) } + +func PointersSlice[T any](input []T) []*T { + output := make([]*T, 0, len(input)) + for _, e := range input { + e := e + output = append(output, &e) + } + return output +} diff --git a/pkg/validatormanager/deployed_validator_manager_bytecode_acp99.txt b/pkg/validatormanager/deployed_validator_manager_bytecode_acp99.txt new file mode 100644 index 000000000..ff56f4dce --- /dev/null +++ b/pkg/validatormanager/deployed_validator_manager_bytecode_acp99.txt @@ -0,0 +1,2 @@ +0x608060405234801561000f575f80fd5b5060043610610187575f3560e01c8063a3a65e48116100d9578063c974d1b611610093578063df93d8de1161006e578063df93d8de1461039e578063ed285ae1146103a8578063f2fde38b146103bb578063fd7ac5e7146103ce575f80fd5b8063c974d1b614610346578063ce161f141461034e578063d5f20ff61461037e575f80fd5b8063a3a65e48146102d0578063b6e6a2ca146102e3578063b771b3bc146102f6578063bb0b193814610304578063bc5fbfec1461030c578063bee0a03f14610333575f80fd5b80636610966911610144578063736c87be1161011f578063736c87be1461024c5780638280a25a1461025f5780638da5cb5b146102795780639681d940146102bd575f80fd5b8063661096691461020b578063715018a61461023d578063732214f814610245575f80fd5b80630322ed981461018b57806309c1df66146101a057806320d91b7a146101c55780635dc1f535146101d857806360305d62146101ee57806363e2ca97146101ee575b5f80fd5b61019e610199366004612893565b6103e1565b005b6101a8610674565b6040516001600160401b0390911681526020015b60405180910390f35b61019e6101d33660046128d3565b61068f565b6101e0610c48565b6040519081526020016101bc565b6101f6601481565b60405163ffffffff90911681526020016101bc565b61021e61021936600461293c565b610c57565b604080516001600160401b0390931683526020830191909152016101bc565b61019e610c77565b6101e05f81565b61019e61025a36600461296a565b610c8a565b610267603081565b60405160ff90911681526020016101bc565b7f9016d09d72d40fdae2fd8ceac6b6234c7706214fd39c1cd1e609a0528c199300546001600160a01b03165b6040516001600160a01b0390911681526020016101bc565b6101e06102cb36600461298b565b610d96565b6101e06102de36600461298b565b61114a565b61019e6102f1366004612893565b611341565b6102a56005600160991b0181565b6101a8611355565b6101e07fe92546d698950ddd38910d2e15ed1d923cd0a7b3dde9e2a6a3f380565559cb0081565b61019e610341366004612893565b611377565b610267601481565b61036161035c36600461298b565b611498565b604080519283526001600160401b039091166020830152016101bc565b61039161038c366004612893565b611623565b6040516101bc9190612a25565b6101a86202a30081565b6101e06103b6366004612cbe565b6117aa565b61019e6103c9366004612d82565b6117cc565b6101e06103dc366004612d9d565b611806565b5f6103ea61183f565b5f838152600580830160205260408083208151610100810190925280549495509293909291839160ff1690811115610424576104246129a4565b6005811115610435576104356129a4565b815260200160018201805461044990612e08565b80601f016020809104026020016040519081016040528092919081815260200182805461047590612e08565b80156104c05780601f10610497576101008083540402835291602001916104c0565b820191905f5260205f20905b8154815290600101906020018083116104a357829003601f168201915b505050918352505060028201546001600160401b038082166020840152600160401b80830482166040850152600160801b830482166060850152600160c01b9092048116608084015260039384015480821660a0850152919091041660c09091015290915081516005811115610538576105386129a4565b14610574575f8381526005830160205260409081902054905163170cc93360e21b815261056b9160ff1690600401612e3a565b60405180910390fd5b606081015160405163854a893f60e01b8152600481018590526001600160401b0390911660248201525f60448201526005600160991b019063ee5b48eb9073__$fd0c147b4031eef6079b0498cbafa865f0$__9063854a893f906064015f60405180830381865af41580156105eb573d5f803e3d5ffd5b505050506040513d5f823e601f3d908101601f191682016040526106129190810190612e92565b6040518263ffffffff1660e01b815260040161062e9190612ec3565b6020604051808303815f875af115801561064a573d5f803e3d5ffd5b505050506040513d601f19601f8201168201806040525081019061066e9190612ed5565b50505050565b5f61067d61183f565b600101546001600160401b0316919050565b5f61069861183f565b600781015490915060ff16156106c157604051637fab81e560e01b815260040160405180910390fd5b6005600160991b016001600160a01b0316634213cf786040518163ffffffff1660e01b8152600401602060405180830381865afa158015610704573d5f803e3d5ffd5b505050506040513d601f19601f820116820180604052508101906107289190612ed5565b836020013514610751576040516372b0a7e760e11b81526020840135600482015260240161056b565b306107626060850160408601612d82565b6001600160a01b0316146107a5576107806060840160408501612d82565b604051632f88120d60e21b81526001600160a01b03909116600482015260240161056b565b5f6107b36060850185612eec565b905090505f805b828163ffffffff161015610a39575f6107d66060880188612eec565b8363ffffffff168181106107ec576107ec612f31565b90506020028101906107fe9190612f45565b61080790612f63565b80516040519192505f91600688019161081f91612fde565b9081526020016040518091039020541461084f57805160405163a41f772f60e01b815261056b9190600401612ec3565b805151601414610875578051604051633e08a12560e11b815261056b9190600401612ec3565b5f6002885f0135846040516020016108a492919091825260e01b6001600160e01b031916602082015260240190565b60408051601f19818403018152908290526108be91612fde565b602060405180830381855afa1580156108d9573d5f803e3d5ffd5b5050506040513d601f19601f820116820180604052508101906108fc9190612ed5565b90508086600601835f01516040516109149190612fde565b90815260408051918290036020908101909220929092555f8381526005890190915220805460ff191660021781558251600190910190610954908261303a565b50604082810180515f84815260058a016020529290922060028101805492516001600160401b0394851667ffffffffffffffff60801b90941693909317600160c01b858516021790556003018054429093166001600160801b0319909316929092179091556109c39085613109565b8251602001519094506bffffffffffffffffffffffff1916817f9d9c026e2cadfec89cccc2cd72705360eca1beba24774f3363f4bb33faabc7d78460400151604051610a1e91906001600160401b0391909116815260200190565b60405180910390a3505080610a3290613129565b90506107ba565b506003830180546fffffffffffffffff00000000000000001916600160401b6001600160401b0384168102919091179091556001840154606491610a81910460ff168361314b565b6001600160401b03161015610ab457604051633e1a785160e01b81526001600160401b038216600482015260240161056b565b5f73__$fd0c147b4031eef6079b0498cbafa865f0$__634d847884610ad887611863565b604001516040518263ffffffff1660e01b8152600401610af89190612ec3565b602060405180830381865af4158015610b13573d5f803e3d5ffd5b505050506040513d601f19601f82011682018060405250810190610b379190612ed5565b90505f73__$fd0c147b4031eef6079b0498cbafa865f0$__6387418b8e886040518263ffffffff1660e01b8152600401610b7191906132a1565b5f60405180830381865af4158015610b8b573d5f803e3d5ffd5b505050506040513d5f823e601f3d908101601f19168201604052610bb29190810190612e92565b90505f600282604051610bc59190612fde565b602060405180830381855afa158015610be0573d5f803e3d5ffd5b5050506040513d601f19601f82011682018060405250810190610c039190612ed5565b9050828114610c2f5760405163baaea89d60e01b8152600481018290526024810184905260440161056b565b5050506007909201805460ff1916600117905550505050565b5f610c5161183f565b54919050565b5f80610c61611979565b610c6b84846119d4565b915091505b9250929050565b610c7f611979565b610c885f611b9c565b565b7ff0c57e16840df040f15088dc2f81fe391c3923bec73e23a9662efc9c229c6a008054600160401b810460ff1615906001600160401b03165f81158015610cce5750825b90505f826001600160401b03166001148015610ce95750303b155b905081158015610cf7575080155b15610d155760405163f92ee8a960e01b815260040160405180910390fd5b845467ffffffffffffffff191660011785558315610d3f57845460ff60401b1916600160401b1785555b610d4886611c0c565b8315610d8e57845460ff60401b19168555604051600181527fc7f505b2f371ae2175ee4913f4499e1f2633a7b5936321eed1cdaeb6115181d29060200160405180910390a15b505050505050565b5f610d9f611979565b5f610da861183f565b90505f8073__$fd0c147b4031eef6079b0498cbafa865f0$__63021de88f610dcf87611863565b604001516040518263ffffffff1660e01b8152600401610def9190612ec3565b6040805180830381865af4158015610e09573d5f803e3d5ffd5b505050506040513d601f19601f82011682018060405250810190610e2d9190613344565b915091508015610e5457604051632d07135360e01b8152811515600482015260240161056b565b5f8281526005808501602052604080832081516101008101909252805491929091839160ff90911690811115610e8c57610e8c6129a4565b6005811115610e9d57610e9d6129a4565b8152602001600182018054610eb190612e08565b80601f0160208091040260200160405190810160405280929190818152602001828054610edd90612e08565b8015610f285780601f10610eff57610100808354040283529160200191610f28565b820191905f5260205f20905b815481529060010190602001808311610f0b57829003601f168201915b505050918352505060028201546001600160401b038082166020840152600160401b80830482166040850152600160801b830482166060850152600160c01b9092048116608084015260039384015480821660a0850152919091041660c09091015290915081516005811115610fa057610fa06129a4565b14158015610fc15750600181516005811115610fbe57610fbe6129a4565b14155b15610fe257805160405163170cc93360e21b815261056b9190600401612e3a565b600381516005811115610ff757610ff76129a4565b03611005576004815261100a565b600581525b8360060181602001516040516110209190612fde565b90815260408051602092819003830190205f90819055858152600587810190935220825181548493839160ff1916906001908490811115611063576110636129a4565b02179055506020820151600182019061107c908261303a565b506040828101516002830180546060860151608087015160a08801516001600160401b039586166001600160801b031994851617600160401b9387168402176001600160801b0316600160801b928716929092026001600160c01b031691909117600160c01b918616919091021790925560c08601516003909501805460e09097015195841696909116959095179390911602919091179091555183907fafaccef7080649a725bc30a35359a257a4a27225be352875c80bdf6b5f04080c905f90a25090925050505b919050565b5f611153611979565b5f61115c61183f565b90505f8073__$fd0c147b4031eef6079b0498cbafa865f0$__63021de88f61118387611863565b604001516040518263ffffffff1660e01b81526004016111a39190612ec3565b6040805180830381865af41580156111bd573d5f803e3d5ffd5b505050506040513d601f19601f820116820180604052508101906111e19190613344565b915091508061120757604051632d07135360e01b8152811515600482015260240161056b565b5f8281526004840160205260409020805461122190612e08565b90505f036112455760405163089938b360e11b81526004810183905260240161056b565b60015f838152600580860160205260409091205460ff169081111561126c5761126c6129a4565b1461129f575f8281526005840160205260409081902054905163170cc93360e21b815261056b9160ff1690600401612e3a565b5f82815260048401602052604081206112b791612849565b5f828152600584016020908152604091829020805460ff1916600290811782556003820180546001600160401b0342811667ffffffffffffffff19909216919091179091559101549251600160c01b90930416825283917f967ae87813a3b5f201dd9bcba778d457176eafe6f41facee1c718091d3952d06910160405180910390a2509392505050565b611349611979565b61135281611c32565b50565b5f61135e61183f565b60030154600160401b90046001600160401b0316919050565b5f61138061183f565b5f838152600482016020526040902080549192509061139e90612e08565b90505f036113c25760405163089938b360e11b81526004810183905260240161056b565b60015f838152600580840160205260409091205460ff16908111156113e9576113e96129a4565b1461141c575f8281526005820160205260409081902054905163170cc93360e21b815261056b9160ff1690600401612e3a565b5f8281526004808301602052604091829020915163ee5b48eb60e01b81526005600160991b019263ee5b48eb926114539201613365565b6020604051808303815f875af115801561146f573d5f803e3d5ffd5b505050506040513d601f19601f820116820180604052508101906114939190612ed5565b505050565b5f806114a2611979565b5f6114ac84611863565b90505f805f73__$fd0c147b4031eef6079b0498cbafa865f0$__6350782b0f85604001516040518263ffffffff1660e01b81526004016114ec9190612ec3565b606060405180830381865af4158015611507573d5f803e3d5ffd5b505050506040513d601f19601f8201168201806040525081019061152b91906133ef565b9250925092505f61153a61183f565b5f8581526005820160205260409020600201549091506001600160401b03808516600160401b90920416101561158e57604051632e19bc2d60e11b81526001600160401b038416600482015260240161056b565b5f8481526005820160205260409081902060020180546001600160401b038616600160801b0267ffffffffffffffff60801b199091161790555184907fc917996591802ecedcfced71321d4bb5320f7dfbacf5477dffe1dbf8b8839ff99061160e90869086906001600160401b0392831681529116602082015260400190565b60405180910390a25091945092505050915091565b60408051610100810182525f8082526060602083018190529282018190529181018290526080810182905260a0810182905260c0810182905260e081018290529061166c61183f565b5f84815260058083016020526040918290208251610100810190935280549394509192839160ff909116908111156116a6576116a66129a4565b60058111156116b7576116b76129a4565b81526020016001820180546116cb90612e08565b80601f01602080910402602001604051908101604052809291908181526020018280546116f790612e08565b80156117425780601f1061171957610100808354040283529160200191611742565b820191905f5260205f20905b81548152906001019060200180831161172557829003601f168201915b505050918352505060028201546001600160401b038082166020840152600160401b80830482166040850152600160801b830482166060850152600160c01b9092048116608084015260039093015480841660a08401520490911660c0909101529392505050565b5f6117b3611979565b6117c1878787878787611f1d565b979650505050505050565b6117d4611979565b6001600160a01b0381166117fd57604051631e4fbdf760e01b81525f600482015260240161056b565b61135281611b9c565b5f8061181061183f565b905080600601848460405161182692919061342f565b9081526020016040518091039020549150505b92915050565b7fe92546d698950ddd38910d2e15ed1d923cd0a7b3dde9e2a6a3f380565559cb0090565b60408051606080820183525f8083526020830152918101919091526040516306f8253560e41b815263ffffffff831660048201525f9081906005600160991b0190636f825350906024015f60405180830381865afa1580156118c7573d5f803e3d5ffd5b505050506040513d5f823e601f3d908101601f191682016040526118ee919081019061343e565b915091508061191057604051636b2f19e960e01b815260040160405180910390fd5b815115611936578151604051636ba589a560e01b8152600481019190915260240161056b565b60208201516001600160a01b031615611972576020820151604051624de75d60e31b81526001600160a01b03909116600482015260240161056b565b5092915050565b336119ab7f9016d09d72d40fdae2fd8ceac6b6234c7706214fd39c1cd1e609a0528c199300546001600160a01b031690565b6001600160a01b031614610c885760405163118cdaa760e01b815233600482015260240161056b565b5f805f6119df61183f565b5f868152600582016020526040902060020154909150600160c01b90046001600160401b0316611a0f8582612307565b5f611a1987612574565b5f88815260058501602052604080822060020180546001600160c01b0316600160c01b6001600160401b038c811691820292909217909255915163854a893f60e01b8152600481018c905291841660248301526044820152919250906005600160991b019063ee5b48eb9073__$fd0c147b4031eef6079b0498cbafa865f0$__9063854a893f906064015f60405180830381865af4158015611abd573d5f803e3d5ffd5b505050506040513d5f823e601f3d908101601f19168201604052611ae49190810190612e92565b6040518263ffffffff1660e01b8152600401611b009190612ec3565b6020604051808303815f875af1158015611b1c573d5f803e3d5ffd5b505050506040513d601f19601f82011682018060405250810190611b409190612ed5565b604080516001600160401b038581168252602082018490528a1681830152905191925089917f6e350dd49b060d87f297206fd309234ed43156d890ced0f139ecf704310481d39181900360600190a29097909650945050505050565b7f9016d09d72d40fdae2fd8ceac6b6234c7706214fd39c1cd1e609a0528c19930080546001600160a01b031981166001600160a01b03848116918217845560405192169182907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0905f90a3505050565b611c146125dd565b611c29611c246020830183612d82565b612626565b61135281612637565b5f611c3b61183f565b5f838152600580830160205260408083208151610100810190925280549495509293909291839160ff1690811115611c7557611c756129a4565b6005811115611c8657611c866129a4565b8152602001600182018054611c9a90612e08565b80601f0160208091040260200160405190810160405280929190818152602001828054611cc690612e08565b8015611d115780601f10611ce857610100808354040283529160200191611d11565b820191905f5260205f20905b815481529060010190602001808311611cf457829003601f168201915b50505091835250506002828101546001600160401b038082166020850152600160401b80830482166040860152600160801b830482166060860152600160c01b9092048116608085015260039094015480851660a08501520490921660c09091015290915081516005811115611d8957611d896129a4565b14611dbc575f8381526005830160205260409081902054905163170cc93360e21b815261056b9160ff1690600401612e3a565b60038152426001600160401b031660e08201525f83815260058381016020526040909120825181548493839160ff1916906001908490811115611e0157611e016129a4565b021790555060208201516001820190611e1a908261303a565b5060408201516002820180546060850151608086015160a08701516001600160401b039586166001600160801b031994851617600160401b9387168402176001600160801b0316600160801b928716929092026001600160c01b031691909117600160c01b918616919091021790925560c08501516003909401805460e090960151948416959091169490941792909116021790555f611eba84826119d4565b915050837fbae388a94e7f18411fe57098f12f418b8e1a8273e0532a90188a3a059b897273828460a0015142604051611f0f939291909283526001600160401b03918216602084015216604082015260600190565b60405180910390a250505050565b5f611f2661183f565b6007015460ff16611f4a57604051637fab81e560e01b815260040160405180910390fd5b5f611f5361183f565b905042866001600160401b0316111580611f825750611f756202a300426134cb565b866001600160401b031610155b15611fab57604051635879da1360e11b81526001600160401b038716600482015260240161056b565b60038101546001600160401b0390611fce90600160401b900482168583166134cb565b1115611ff857604051633e1a785160e01b81526001600160401b038416600482015260240161056b565b6120018561271e565b61200a8461271e565b86516030146120315786516040516326475b2f60e11b815260040161056b91815260200190565b87516014146120555787604051633e08a12560e11b815260040161056b9190612ec3565b5f801b816006018960405161206a9190612fde565b90815260200160405180910390205414612099578760405163a41f772f60e01b815260040161056b9190612ec3565b6120a3835f612307565b5f8073__$fd0c147b4031eef6079b0498cbafa865f0$__63eb97ce516040518060e00160405280865f015481526020018d81526020018c81526020018b6001600160401b031681526020018a8152602001898152602001886001600160401b03168152506040518263ffffffff1660e01b81526004016121239190613544565b5f60405180830381865af415801561213d573d5f803e3d5ffd5b505050506040513d5f823e601f3d908101601f1916820160405261216491908101906135fb565b5f82815260048601602052604090209193509150612182828261303a565b5081836006018b6040516121969190612fde565b9081526040519081900360200181209190915563ee5b48eb60e01b81525f906005600160991b019063ee5b48eb906121d2908590600401612ec3565b6020604051808303815f875af11580156121ee573d5f803e3d5ffd5b505050506040513d601f19601f820116820180604052508101906122129190612ed5565b5f8481526005860160205260409020805460ff1916600190811782559192500161223c8c8261303a565b505f8381526005850160205260409020600281018054600160c01b6001600160401b038a1690810267ffffffffffffffff60801b9092161717905560030180546001600160801b03191690556122938b6020015190565b6bffffffffffffffffffffffff1916837f5881be437bdcb008bfa5f20e32d3e335ccf8ab90ef2818852a251625260af35d838c8a6040516122f0939291909283526001600160401b03918216602084015216604082015260600190565b60405180910390a350909998505050505050505050565b5f61231061183f565b90505f826001600160401b0316846001600160401b0316111561233e57612337838561363e565b905061234b565b612348848461363e565b90505b60408051608081018252600284015480825260038501546001600160401b038082166020850152600160401b8204811694840194909452600160801b90049092166060820152429115806123b85750600184015481516123b4916001600160401b0316906134cb565b8210155b156123e0576001600160401b03808416606083015282825260408201511660208201526123ff565b82816060018181516123f29190613109565b6001600160401b03169052505b606081015161240f90606461314b565b602082015160018601546001600160401b03929092169161243a9190600160401b900460ff1661314b565b6001600160401b0316101561247357606081015160405163dfae880160e01b81526001600160401b03909116600482015260240161056b565b85816040018181516124859190613109565b6001600160401b03169052506040810180518691906124a590839061363e565b6001600160401b0316905250600184015460408201516064916124d391600160401b90910460ff169061314b565b6001600160401b0316101561250c576040808201519051633e1a785160e01b81526001600160401b03909116600482015260240161056b565b8051600285015560208101516003909401805460408301516060909301516001600160401b03908116600160801b0267ffffffffffffffff60801b19948216600160401b026001600160801b0319909316919097161717919091169390931790925550505050565b5f8061257e61183f565b5f84815260058201602052604090206002018054919250906008906125b290600160401b90046001600160401b031661365e565b91906101000a8154816001600160401b0302191690836001600160401b031602179055915050919050565b7ff0c57e16840df040f15088dc2f81fe391c3923bec73e23a9662efc9c229c6a0054600160401b900460ff16610c8857604051631afcd79f60e31b815260040160405180910390fd5b61262e6125dd565b61135281612841565b61263f6125dd565b5f61264861183f565b60208301358155905060146126636080840160608501613679565b60ff161180612682575061267d6080830160608401613679565b60ff16155b156126b6576126976080830160608401613679565b604051634a59bbff60e11b815260ff909116600482015260240161056b565b6126c66080830160608401613679565b60018201805460ff92909216600160401b0260ff60401b199092169190911790556126f76060830160408401613699565b600191909101805467ffffffffffffffff19166001600160401b0390921691909117905550565b805163ffffffff16158015612737575060208101515115155b1561276b57805160208201515160405163c08a0f1d60e01b815263ffffffff9092166004830152602482015260440161056b565b602081015151815163ffffffff1611156127ae57805160208201515160405163c08a0f1d60e01b815263ffffffff9092166004830152602482015260440161056b565b60015b81602001515181101561283d5760208201516127ce6001836136b4565b815181106127de576127de612f31565b60200260200101516001600160a01b03168260200151828151811061280557612805612f31565b60200260200101516001600160a01b0316101561283557604051630dbc8d5f60e31b815260040160405180910390fd5b6001016127b1565b5050565b6117d46125dd565b50805461285590612e08565b5f825580601f10612864575050565b601f0160209004905f5260205f209081019061135291905b8082111561288f575f815560010161287c565b5090565b5f602082840312156128a3575f80fd5b5035919050565b5f608082840312156128ba575f80fd5b50919050565b803563ffffffff81168114611145575f80fd5b5f80604083850312156128e4575f80fd5b82356001600160401b038111156128f9575f80fd5b612905858286016128aa565b925050612914602084016128c0565b90509250929050565b6001600160401b0381168114611352575f80fd5b80356111458161291d565b5f806040838503121561294d575f80fd5b82359150602083013561295f8161291d565b809150509250929050565b5f6080828403121561297a575f80fd5b61298483836128aa565b9392505050565b5f6020828403121561299b575f80fd5b612984826128c0565b634e487b7160e01b5f52602160045260245ffd5b600681106129d457634e487b7160e01b5f52602160045260245ffd5b9052565b5f5b838110156129f25781810151838201526020016129da565b50505f910152565b5f8151808452612a118160208601602086016129d8565b601f01601f19169290920160200192915050565b60208152612a376020820183516129b8565b5f6020830151610100806040850152612a546101208501836129fa565b915060408501516001600160401b03808216606087015280606088015116608087015250506080850151612a9360a08601826001600160401b03169052565b5060a08501516001600160401b03811660c08601525060c08501516001600160401b03811660e08601525060e08501516001600160401b038116858301525090949350505050565b634e487b7160e01b5f52604160045260245ffd5b604080519081016001600160401b0381118282101715612b1157612b11612adb565b60405290565b604051606081016001600160401b0381118282101715612b1157612b11612adb565b604051601f8201601f191681016001600160401b0381118282101715612b6157612b61612adb565b604052919050565b5f6001600160401b03821115612b8157612b81612adb565b50601f01601f191660200190565b5f82601f830112612b9e575f80fd5b8135612bb1612bac82612b69565b612b39565b818152846020838601011115612bc5575f80fd5b816020850160208301375f918101602001919091529392505050565b6001600160a01b0381168114611352575f80fd5b5f60408284031215612c05575f80fd5b612c0d612aef565b9050612c18826128c0565b81526020808301356001600160401b0380821115612c34575f80fd5b818501915085601f830112612c47575f80fd5b813581811115612c5957612c59612adb565b8060051b9150612c6a848301612b39565b8181529183018401918481019088841115612c83575f80fd5b938501935b83851015612cad5784359250612c9d83612be1565b8282529385019390850190612c88565b808688015250505050505092915050565b5f805f805f8060c08789031215612cd3575f80fd5b86356001600160401b0380821115612ce9575f80fd5b612cf58a838b01612b8f565b97506020890135915080821115612d0a575f80fd5b612d168a838b01612b8f565b9650612d2460408a01612931565b95506060890135915080821115612d39575f80fd5b612d458a838b01612bf5565b94506080890135915080821115612d5a575f80fd5b50612d6789828a01612bf5565b925050612d7660a08801612931565b90509295509295509295565b5f60208284031215612d92575f80fd5b813561298481612be1565b5f8060208385031215612dae575f80fd5b82356001600160401b0380821115612dc4575f80fd5b818501915085601f830112612dd7575f80fd5b813581811115612de5575f80fd5b866020828501011115612df6575f80fd5b60209290920196919550909350505050565b600181811c90821680612e1c57607f821691505b6020821081036128ba57634e487b7160e01b5f52602260045260245ffd5b6020810161183982846129b8565b5f82601f830112612e57575f80fd5b8151612e65612bac82612b69565b818152846020838601011115612e79575f80fd5b612e8a8260208301602087016129d8565b949350505050565b5f60208284031215612ea2575f80fd5b81516001600160401b03811115612eb7575f80fd5b612e8a84828501612e48565b602081525f61298460208301846129fa565b5f60208284031215612ee5575f80fd5b5051919050565b5f808335601e19843603018112612f01575f80fd5b8301803591506001600160401b03821115612f1a575f80fd5b6020019150600581901b3603821315610c70575f80fd5b634e487b7160e01b5f52603260045260245ffd5b5f8235605e19833603018112612f59575f80fd5b9190910192915050565b5f60608236031215612f73575f80fd5b612f7b612b17565b82356001600160401b0380821115612f91575f80fd5b612f9d36838701612b8f565b83526020850135915080821115612fb2575f80fd5b50612fbf36828601612b8f565b6020830152506040830135612fd38161291d565b604082015292915050565b5f8251612f598184602087016129d8565b601f82111561149357805f5260205f20601f840160051c810160208510156130145750805b601f840160051c820191505b81811015613033575f8155600101613020565b5050505050565b81516001600160401b0381111561305357613053612adb565b613067816130618454612e08565b84612fef565b602080601f83116001811461309a575f84156130835750858301515b5f19600386901b1c1916600185901b178555610d8e565b5f85815260208120601f198616915b828110156130c8578886015182559484019460019091019084016130a9565b50858210156130e557878501515f19600388901b60f8161c191681555b5050505050600190811b01905550565b634e487b7160e01b5f52601160045260245ffd5b6001600160401b03818116838216019080821115611972576119726130f5565b5f63ffffffff808316818103613141576131416130f5565b6001019392505050565b6001600160401b0381811683821602808216919082811461316e5761316e6130f5565b505092915050565b5f808335601e1984360301811261318b575f80fd5b83016020810192503590506001600160401b038111156131a9575f80fd5b803603821315610c70575f80fd5b81835281816020850137505f828201602090810191909152601f909101601f19169091010190565b5f8383855260208086019550808560051b830101845f5b8781101561329457848303601f19018952813536889003605e1901811261321b575f80fd5b870160606132298280613176565b82875261323983880182846131b7565b9250505061324986830183613176565b8683038888015261325b8382846131b7565b9250505060408083013592506132708361291d565b6001600160401b0392909216949091019390935297830197908301906001016131f6565b5090979650505050505050565b6020815281356020820152602082013560408201525f60408301356132c581612be1565b6001600160a01b031660608381019190915283013536849003601e190181126132ec575f80fd5b83016020810190356001600160401b03811115613307575f80fd5b8060051b3603821315613318575f80fd5b60808085015261332c60a0850182846131df565b95945050505050565b80518015158114611145575f80fd5b5f8060408385031215613355575f80fd5b8251915061291460208401613335565b5f60208083525f845461337781612e08565b806020870152604060018084165f811461339857600181146133b4576133e1565b60ff19851660408a0152604084151560051b8a010195506133e1565b895f5260205f205f5b858110156133d85781548b82018601529083019088016133bd565b8a016040019650505b509398975050505050505050565b5f805f60608486031215613401575f80fd5b8351925060208401516134138161291d565b60408501519092506134248161291d565b809150509250925092565b818382375f9101908152919050565b5f806040838503121561344f575f80fd5b82516001600160401b0380821115613465575f80fd5b9084019060608287031215613478575f80fd5b613480612b17565b82518152602083015161349281612be1565b60208201526040830151828111156134a8575f80fd5b6134b488828601612e48565b604083015250935061291491505060208401613335565b80820180821115611839576118396130f5565b5f6040830163ffffffff8351168452602080840151604060208701528281518085526060880191506020830194505f92505b808310156135395784516001600160a01b03168252938301936001929092019190830190613510565b509695505050505050565b60208152815160208201525f602083015160e0604084015261356a6101008401826129fa565b90506040840151601f198085840301606086015261358883836129fa565b92506001600160401b03606087015116608086015260808601519150808584030160a08601526135b883836134de565b925060a08601519150808584030160c0860152506135d682826134de565b91505060c08401516135f360e08501826001600160401b03169052565b509392505050565b5f806040838503121561360c575f80fd5b8251915060208301516001600160401b03811115613628575f80fd5b61363485828601612e48565b9150509250929050565b6001600160401b03828116828216039080821115611972576119726130f5565b5f6001600160401b03808316818103613141576131416130f5565b5f60208284031215613689575f80fd5b813560ff81168114612984575f80fd5b5f602082840312156136a9575f80fd5b81356129848161291d565b81810381811115611839576118396130f556fea164736f6c6343000819000a + diff --git a/pkg/validatormanager/deployed_validator_messages_bytecode_acp99.txt b/pkg/validatormanager/deployed_validator_messages_bytecode_acp99.txt new file mode 100644 index 000000000..958cb7422 --- /dev/null +++ b/pkg/validatormanager/deployed_validator_messages_bytecode_acp99.txt @@ -0,0 +1,2 @@ +0x73000000000000000000000000000000000000000030146080604052600436106100b1575f3560e01c8063854a893f11610079578063854a893f146101b257806387418b8e1461020f5780639b83546514610222578063a699c13514610242578063e1d68f3014610255578063eb97ce5114610268575f80fd5b8063021de88f146100b5578063088c2463146100e25780634d8478841461011257806350782b0f146101335780637f7c427a1461016b575b5f80fd5b6100c86100c33660046118a9565b610289565b604080519283529015156020830152015b60405180910390f35b6100f56100f03660046118a9565b61044a565b604080519283526001600160401b039091166020830152016100d9565b6101256101203660046118a9565b61063b565b6040519081526020016100d9565b6101466101413660046118a9565b6107c8565b604080519384526001600160401b0392831660208501529116908201526060016100d9565b6101a56101793660046118e2565b604080515f60208201819052602282015260268082019390935281518082039093018352604601905290565b6040516100d99190611946565b6101a56101c036600461197a565b604080515f6020820152600360e01b602282015260268101949094526001600160c01b031960c093841b811660468601529190921b16604e830152805180830360360181526056909201905290565b6101a561021d3660046119eb565b610a1e565b6102356102303660046118a9565b610b60565b6040516100d99190611bb4565b6101a5610250366004611c6b565b6114ab565b6101a5610263366004611c9d565b6114ef565b61027b610276366004611d80565b611525565b6040516100d9929190611e7c565b5f8082516027146102c457825160405163cc92daa160e01b815263ffffffff9091166004820152602760248201526044015b60405180910390fd5b5f805b6002811015610313576102db816001611ea8565b6102e6906008611ebb565b61ffff168582815181106102fc576102fc611ed2565b016020015160f81c901b91909117906001016102c7565b5061ffff81161561033d5760405163407b587360e01b815261ffff821660048201526024016102bb565b5f805b600481101561039857610354816003611ea8565b61035f906008611ebb565b63ffffffff1686610371836002611ee6565b8151811061038157610381611ed2565b016020015160f81c901b9190911790600101610340565b5063ffffffff81166002146103c057604051635b60892f60e01b815260040160405180910390fd5b5f805b6020811015610415576103d781601f611ea8565b6103e2906008611ebb565b876103ee836006611ee6565b815181106103fe576103fe611ed2565b016020015160f81c901b91909117906001016103c3565b505f8660268151811061042a5761042a611ed2565b016020015191976001600160f81b03199092161515965090945050505050565b5f808251602e1461048057825160405163cc92daa160e01b815263ffffffff9091166004820152602e60248201526044016102bb565b5f805b60028110156104cf57610497816001611ea8565b6104a2906008611ebb565b61ffff168582815181106104b8576104b8611ed2565b016020015160f81c901b9190911790600101610483565b5061ffff8116156104f95760405163407b587360e01b815261ffff821660048201526024016102bb565b5f805b600481101561055457610510816003611ea8565b61051b906008611ebb565b63ffffffff168661052d836002611ee6565b8151811061053d5761053d611ed2565b016020015160f81c901b91909117906001016104fc565b5063ffffffff81161561057a57604051635b60892f60e01b815260040160405180910390fd5b5f805b60208110156105cf5761059181601f611ea8565b61059c906008611ebb565b876105a8836006611ee6565b815181106105b8576105b8611ed2565b016020015160f81c901b919091179060010161057d565b505f805b600881101561062e576105e7816007611ea8565b6105f2906008611ebb565b6001600160401b031688610607836026611ee6565b8151811061061757610617611ed2565b016020015160f81c901b91909117906001016105d3565b5090969095509350505050565b5f815160261461067057815160405163cc92daa160e01b815263ffffffff9091166004820152602660248201526044016102bb565b5f805b60028110156106bf57610687816001611ea8565b610692906008611ebb565b61ffff168482815181106106a8576106a8611ed2565b016020015160f81c901b9190911790600101610673565b5061ffff8116156106e95760405163407b587360e01b815261ffff821660048201526024016102bb565b5f805b600481101561074457610700816003611ea8565b61070b906008611ebb565b63ffffffff168561071d836002611ee6565b8151811061072d5761072d611ed2565b016020015160f81c901b91909117906001016106ec565b5063ffffffff81161561076a57604051635b60892f60e01b815260040160405180910390fd5b5f805b60208110156107bf5761078181601f611ea8565b61078c906008611ebb565b86610798836006611ee6565b815181106107a8576107a8611ed2565b016020015160f81c901b919091179060010161076d565b50949350505050565b5f805f83516036146107ff57835160405163cc92daa160e01b815263ffffffff9091166004820152603660248201526044016102bb565b5f805b600281101561084e57610816816001611ea8565b610821906008611ebb565b61ffff1686828151811061083757610837611ed2565b016020015160f81c901b9190911790600101610802565b5061ffff8116156108785760405163407b587360e01b815261ffff821660048201526024016102bb565b5f805b60048110156108d35761088f816003611ea8565b61089a906008611ebb565b63ffffffff16876108ac836002611ee6565b815181106108bc576108bc611ed2565b016020015160f81c901b919091179060010161087b565b5063ffffffff81166003146108fb57604051635b60892f60e01b815260040160405180910390fd5b5f805b60208110156109505761091281601f611ea8565b61091d906008611ebb565b88610929836006611ee6565b8151811061093957610939611ed2565b016020015160f81c901b91909117906001016108fe565b505f805b60088110156109af57610968816007611ea8565b610973906008611ebb565b6001600160401b031689610988836026611ee6565b8151811061099857610998611ed2565b016020015160f81c901b9190911790600101610954565b505f805b6008811015610a0e576109c7816007611ea8565b6109d2906008611ebb565b6001600160401b03168a6109e783602e611ee6565b815181106109f7576109f7611ed2565b016020015160f81c901b91909117906001016109b3565b5091989097509095509350505050565b80516020808301516040808501516060868101515192515f95810186905260228101969096526042860193909352600560e21b60628601526bffffffffffffffffffffffff1990831b16606685015260e01b6001600160e01b031916607a84015291607e0160405160208183030381529060405290505f5b836060015151811015610b59578184606001518281518110610aba57610aba611ed2565b60200260200101515f01515185606001518381518110610adc57610adc611ed2565b60200260200101515f015186606001518481518110610afd57610afd611ed2565b60200260200101516020015187606001518581518110610b1f57610b1f611ed2565b602002602001015160400151604051602001610b3f959493929190611ef9565b60408051601f198184030181529190529150600101610a96565b5092915050565b610b68611712565b5f610b71611712565b5f805b6002811015610bcf57610b88816001611ea8565b610b93906008611ebb565b61ffff1686610ba863ffffffff871684611ee6565b81518110610bb857610bb8611ed2565b016020015160f81c901b9190911790600101610b74565b5061ffff811615610bf95760405163407b587360e01b815261ffff821660048201526024016102bb565b610c04600284611f72565b9250505f805b6004811015610c6957610c1e816003611ea8565b610c29906008611ebb565b63ffffffff16868563ffffffff1683610c429190611ee6565b81518110610c5257610c52611ed2565b016020015160f81c901b9190911790600101610c0a565b5063ffffffff8116600114610c9157604051635b60892f60e01b815260040160405180910390fd5b610c9c600484611f72565b9250505f805b6020811015610cf957610cb681601f611ea8565b610cc1906008611ebb565b86610cd263ffffffff871684611ee6565b81518110610ce257610ce2611ed2565b016020015160f81c901b9190911790600101610ca2565b50808252610d08602084611f72565b9250505f805b6004811015610d6d57610d22816003611ea8565b610d2d906008611ebb565b63ffffffff16868563ffffffff1683610d469190611ee6565b81518110610d5657610d56611ed2565b016020015160f81c901b9190911790600101610d0e565b50610d79600484611f72565b92505f8163ffffffff166001600160401b03811115610d9a57610d9a61176c565b6040519080825280601f01601f191660200182016040528015610dc4576020820181803683370190505b5090505f5b8263ffffffff16811015610e335786610de863ffffffff871683611ee6565b81518110610df857610df8611ed2565b602001015160f81c60f81b828281518110610e1557610e15611ed2565b60200101906001600160f81b03191690815f1a905350600101610dc9565b5060208301819052610e458285611f72565b604080516030808252606082019092529195505f92506020820181803683370190505090505f5b6030811015610ed15786610e8663ffffffff871683611ee6565b81518110610e9657610e96611ed2565b602001015160f81c60f81b828281518110610eb357610eb3611ed2565b60200101906001600160f81b03191690815f1a905350600101610e6c565b5060408301819052610ee4603085611f72565b9350505f805b6008811015610f4a57610efe816007611ea8565b610f09906008611ebb565b6001600160401b031687610f2363ffffffff881684611ee6565b81518110610f3357610f33611ed2565b016020015160f81c901b9190911790600101610eea565b506001600160401b0381166060840152610f65600885611f72565b9350505f805f5b6004811015610fcb57610f80816003611ea8565b610f8b906008611ebb565b63ffffffff16888763ffffffff1683610fa49190611ee6565b81518110610fb457610fb4611ed2565b016020015160f81c901b9190911790600101610f6c565b50610fd7600486611f72565b94505f5b600481101561103a57610fef816003611ea8565b610ffa906008611ebb565b63ffffffff16888763ffffffff16836110139190611ee6565b8151811061102357611023611ed2565b016020015160f81c901b9290921791600101610fdb565b50611046600486611f72565b94505f8263ffffffff166001600160401b038111156110675761106761176c565b604051908082528060200260200182016040528015611090578160200160208202803683370190505b5090505f5b8363ffffffff16811015611178576040805160148082528183019092525f916020820181803683370190505090505f5b601481101561112a578a6110df63ffffffff8b1683611ee6565b815181106110ef576110ef611ed2565b602001015160f81c60f81b82828151811061110c5761110c611ed2565b60200101906001600160f81b03191690815f1a9053506001016110c5565b505f601482015190508084848151811061114657611146611ed2565b6001600160a01b039092166020928302919091019091015261116960148a611f72565b98505050806001019050611095565b506040805180820190915263ffffffff9092168252602082015260808401525f80805b60048110156111fa576111af816003611ea8565b6111ba906008611ebb565b63ffffffff16898863ffffffff16836111d39190611ee6565b815181106111e3576111e3611ed2565b016020015160f81c901b919091179060010161119b565b50611206600487611f72565b95505f5b60048110156112695761121e816003611ea8565b611229906008611ebb565b63ffffffff16898863ffffffff16836112429190611ee6565b8151811061125257611252611ed2565b016020015160f81c901b929092179160010161120a565b50611275600487611f72565b95505f8263ffffffff166001600160401b038111156112965761129661176c565b6040519080825280602002602001820160405280156112bf578160200160208202803683370190505b5090505f5b8363ffffffff168110156113a7576040805160148082528183019092525f916020820181803683370190505090505f5b6014811015611359578b61130e63ffffffff8c1683611ee6565b8151811061131e5761131e611ed2565b602001015160f81c60f81b82828151811061133b5761133b611ed2565b60200101906001600160f81b03191690815f1a9053506001016112f4565b505f601482015190508084848151811061137557611375611ed2565b6001600160a01b039092166020928302919091019091015261139860148b611f72565b995050508060010190506112c4565b506040805180820190915263ffffffff9092168252602082015260a08501525f6113d18284611f72565b6113dc906014611f8f565b6113e785607a611f72565b6113f19190611f72565b90508063ffffffff1688511461142d57875160405163cc92daa160e01b815263ffffffff918216600482015290821660248201526044016102bb565b5f805b600881101561149057611444816007611ea8565b61144f906008611ebb565b6001600160401b03168a61146963ffffffff8b1684611ee6565b8151811061147957611479611ed2565b016020015160f81c901b9190911790600101611430565b506001600160401b031660c086015250929695505050505050565b6040515f6020820152600160e11b60228201526026810183905281151560f81b60468201526060906047015b60405160208183030381529060405290505b92915050565b6040515f602082018190526022820152602681018390526001600160c01b031960c083901b166046820152606090604e016114d7565b5f606082604001515160301461154e5760405163180ffa0d60e01b815260040160405180910390fd5b82516020808501518051604080880151606089015160808a01518051908701515193515f9861158f988a986001989297929690959094909390929101611fb7565b60405160208183030381529060405290505f5b84608001516020015151811015611601578185608001516020015182815181106115ce576115ce611ed2565b60200260200101516040516020016115e7929190612071565b60408051601f1981840301815291905291506001016115a2565b5060a08401518051602091820151516040516116219385939291016120a7565b60405160208183030381529060405290505f5b8460a00151602001515181101561169357818560a0015160200151828151811061166057611660611ed2565b6020026020010151604051602001611679929190612071565b60408051601f198184030181529190529150600101611634565b5060c08401516040516116aa9183916020016120e2565b60405160208183030381529060405290506002816040516116cb9190612113565b602060405180830381855afa1580156116e6573d5f803e3d5ffd5b5050506040513d601f19601f82011682018060405250810190611709919061212e565b94909350915050565b6040805160e0810182525f808252606060208084018290528385018290528184018390528451808601865283815280820183905260808501528451808601909552918452908301529060a082019081525f60209091015290565b634e487b7160e01b5f52604160045260245ffd5b604051608081016001600160401b03811182821017156117a2576117a261176c565b60405290565b604051606081016001600160401b03811182821017156117a2576117a261176c565b604080519081016001600160401b03811182821017156117a2576117a261176c565b60405160e081016001600160401b03811182821017156117a2576117a261176c565b604051601f8201601f191681016001600160401b03811182821017156118365761183661176c565b604052919050565b5f82601f83011261184d575f80fd5b81356001600160401b038111156118665761186661176c565b611879601f8201601f191660200161180e565b81815284602083860101111561188d575f80fd5b816020850160208301375f918101602001919091529392505050565b5f602082840312156118b9575f80fd5b81356001600160401b038111156118ce575f80fd5b6118da8482850161183e565b949350505050565b5f602082840312156118f2575f80fd5b5035919050565b5f5b838110156119135781810151838201526020016118fb565b50505f910152565b5f81518084526119328160208601602086016118f9565b601f01601f19169290920160200192915050565b602081525f611958602083018461191b565b9392505050565b80356001600160401b0381168114611975575f80fd5b919050565b5f805f6060848603121561198c575f80fd5b8335925061199c6020850161195f565b91506119aa6040850161195f565b90509250925092565b80356001600160a01b0381168114611975575f80fd5b5f6001600160401b038211156119e1576119e161176c565b5060051b60200190565b5f60208083850312156119fc575f80fd5b82356001600160401b0380821115611a12575f80fd5b9084019060808287031215611a25575f80fd5b611a2d611780565b823581528383013584820152611a45604084016119b3565b604082015260608084013583811115611a5c575f80fd5b80850194505087601f850112611a70575f80fd5b8335611a83611a7e826119c9565b61180e565b81815260059190911b8501860190868101908a831115611aa1575f80fd5b8787015b83811015611b3a57803587811115611abb575f80fd5b8801808d03601f1901861315611acf575f80fd5b611ad76117a8565b8a82013589811115611ae7575f80fd5b611af58f8d8386010161183e565b825250604082013589811115611b09575f80fd5b611b178f8d8386010161183e565b8c83015250611b2787830161195f565b6040820152845250918801918801611aa5565b506060850152509198975050505050505050565b5f6040830163ffffffff8351168452602080840151604060208701528281518085526060880191506020830194505f92505b80831015611ba95784516001600160a01b03168252938301936001929092019190830190611b80565b509695505050505050565b60208152815160208201525f602083015160e06040840152611bda61010084018261191b565b90506040840151601f1980858403016060860152611bf8838361191b565b92506001600160401b03606087015116608086015260808601519150808584030160a0860152611c288383611b4e565b925060a08601519150808584030160c086015250611c468282611b4e565b91505060c0840151611c6360e08501826001600160401b03169052565b509392505050565b5f8060408385031215611c7c575f80fd5b8235915060208301358015158114611c92575f80fd5b809150509250929050565b5f8060408385031215611cae575f80fd5b82359150611cbe6020840161195f565b90509250929050565b5f60408284031215611cd7575f80fd5b611cdf6117ca565b9050813563ffffffff81168114611cf4575f80fd5b81526020828101356001600160401b03811115611d0f575f80fd5b8301601f81018513611d1f575f80fd5b8035611d2d611a7e826119c9565b81815260059190911b82018301908381019087831115611d4b575f80fd5b928401925b82841015611d7057611d61846119b3565b82529284019290840190611d50565b8085870152505050505092915050565b5f60208284031215611d90575f80fd5b81356001600160401b0380821115611da6575f80fd5b9083019060e08286031215611db9575f80fd5b611dc16117ec565b82358152602083013582811115611dd6575f80fd5b611de28782860161183e565b602083015250604083013582811115611df9575f80fd5b611e058782860161183e565b604083015250611e176060840161195f565b6060820152608083013582811115611e2d575f80fd5b611e3987828601611cc7565b60808301525060a083013582811115611e50575f80fd5b611e5c87828601611cc7565b60a083015250611e6e60c0840161195f565b60c082015295945050505050565b828152604060208201525f6118da604083018461191b565b634e487b7160e01b5f52601160045260245ffd5b818103818111156114e9576114e9611e94565b80820281158282048414176114e9576114e9611e94565b634e487b7160e01b5f52603260045260245ffd5b808201808211156114e9576114e9611e94565b5f8651611f0a818460208b016118f9565b60e087901b6001600160e01b0319169083019081528551611f32816004840160208a016118f9565b8551910190611f488160048401602089016118f9565b60c09490941b6001600160c01b031916600491909401908101939093525050600c01949350505050565b63ffffffff818116838216019080821115610b5957610b59611e94565b63ffffffff818116838216028082169190828114611faf57611faf611e94565b505092915050565b61ffff60f01b8a60f01b1681525f63ffffffff60e01b808b60e01b166002840152896006840152808960e01b166026840152508651611ffd81602a850160208b016118f9565b86519083019061201481602a840160208b016118f9565b60c087901b6001600160c01b031916602a9290910191820152612046603282018660e01b6001600160e01b0319169052565b61205f603682018560e01b6001600160e01b0319169052565b603a019b9a5050505050505050505050565b5f83516120828184602088016118f9565b60609390931b6bffffffffffffffffffffffff19169190920190815260140192915050565b5f84516120b88184602089016118f9565b6001600160e01b031960e095861b8116919093019081529290931b16600482015260080192915050565b5f83516120f38184602088016118f9565b60c09390931b6001600160c01b0319169190920190815260080192915050565b5f82516121248184602087016118f9565b9190910192915050565b5f6020828403121561213e575f80fd5b505191905056fea164736f6c6343000819000a + diff --git a/pkg/validatormanager/helpers.go b/pkg/validatormanager/helpers.go new file mode 100644 index 000000000..ce89edc3e --- /dev/null +++ b/pkg/validatormanager/helpers.go @@ -0,0 +1,99 @@ +// Copyright (C) 2022, Ava Labs, Inc. All rights reserved. +// See the file LICENSE for licensing terms. +package validatormanager + +import ( + _ "embed" + "fmt" + "math/big" + + "github.com/ava-labs/avalanche-cli/pkg/evm" + "github.com/ava-labs/avalanche-cli/pkg/utils" + "github.com/ava-labs/avalanchego/ids" + warp "github.com/ava-labs/avalanchego/vms/platformvm/warp" + warpMessage "github.com/ava-labs/avalanchego/vms/platformvm/warp/message" + warpPayload "github.com/ava-labs/avalanchego/vms/platformvm/warp/payload" + "github.com/ava-labs/subnet-evm/core/types" + "github.com/ava-labs/subnet-evm/interfaces" + subnetEvmWarp "github.com/ava-labs/subnet-evm/precompile/contracts/warp" + + "github.com/ethereum/go-ethereum/common" +) + +func GetWarpMessagesFromLogs( + logs []*types.Log, +) []*warp.UnsignedMessage { + messages := []*warp.UnsignedMessage{} + for _, txLog := range logs { + msg, err := subnetEvmWarp.UnpackSendWarpEventDataToMessage(txLog.Data) + if err == nil { + messages = append(messages, msg) + } + } + return messages +} + +func GetWarpMessageFromLogs( + logs []*types.Log, +) (*warp.UnsignedMessage, error) { + messages := GetWarpMessagesFromLogs(logs) + if len(messages) == 0 { + return nil, fmt.Errorf("no warp message is present in evm logs") + } + return messages[0], nil +} + +func GetValidatorNonce( + rpcURL string, + validationID ids.ID, +) (uint64, error) { + client, err := evm.GetClient(rpcURL) + if err != nil { + return 0, err + } + ctx, cancel := utils.GetAPILargeContext() + defer cancel() + height, err := client.BlockNumber(ctx) + if err != nil { + return 0, err + } + count := uint64(0) + maxBlock := int64(height) + minBlock := int64(0) + for blockNumber := maxBlock; blockNumber >= minBlock; blockNumber-- { + ctx, cancel := utils.GetAPILargeContext() + defer cancel() + block, err := client.BlockByNumber(ctx, big.NewInt(blockNumber)) + if err != nil { + return 0, err + } + blockHash := block.Hash() + logs, err := client.FilterLogs(ctx, interfaces.FilterQuery{ + BlockHash: &blockHash, + Addresses: []common.Address{subnetEvmWarp.Module.Address}, + }) + if err != nil { + return 0, err + } + msgs := GetWarpMessagesFromLogs(utils.PointersSlice(logs)) + for _, msg := range msgs { + payload := msg.Payload + addressedCall, err := warpPayload.ParseAddressedCall(payload) + if err == nil { + weightMsg, err := warpMessage.ParseL1ValidatorWeight(addressedCall.Payload) + if err == nil { + if weightMsg.ValidationID == validationID { + count++ + } + } + regMsg, err := warpMessage.ParseRegisterL1Validator(addressedCall.Payload) + if err == nil { + if regMsg.ValidationID() == validationID { + return count, nil + } + } + } + } + } + return count, nil +} diff --git a/pkg/validatormanager/registration.go b/pkg/validatormanager/registration.go index a12cf3425..d92ba081a 100644 --- a/pkg/validatormanager/registration.go +++ b/pkg/validatormanager/registration.go @@ -109,18 +109,12 @@ func InitializeValidatorRegistrationPoA( balanceOwners warpMessage.PChainOwner, disableOwners warpMessage.PChainOwner, weight uint64, + useACP99 bool, ) (*types.Transaction, *types.Receipt, error) { type PChainOwner struct { Threshold uint32 Addresses []common.Address } - type ValidatorRegistrationInput struct { - NodeID []byte - BlsPublicKey []byte - RegistrationExpiry uint64 - RemainingBalanceOwner PChainOwner - DisableOwner PChainOwner - } balanceOwnersAux := PChainOwner{ Threshold: balanceOwners.Threshold, Addresses: utils.Map(balanceOwners.Addresses, func(addr ids.ShortID) common.Address { @@ -133,12 +127,31 @@ func InitializeValidatorRegistrationPoA( return common.BytesToAddress(addr[:]) }), } - validatorRegistrationInput := ValidatorRegistrationInput{ - NodeID: nodeID[:], - BlsPublicKey: blsPublicKey, - RegistrationExpiry: expiry, - RemainingBalanceOwner: balanceOwnersAux, - DisableOwner: disableOwnersAux, + if useACP99 { + return contract.TxToMethod( + rpcURL, + generateRawTxOnly, + managerOwnerAddress, + managerOwnerPrivateKey, + managerAddress, + big.NewInt(0), + "initialize validator registration", + validatormanager.ErrorSignatureToError, + "initiateValidatorRegistration(bytes,bytes,uint64,(uint32,[address]),(uint32,[address]),uint64)", + nodeID[:], + blsPublicKey, + expiry, + balanceOwnersAux, + disableOwnersAux, + weight, + ) + } + type ValidatorRegistrationInput struct { + NodeID []byte + BlsPublicKey []byte + RegistrationExpiry uint64 + RemainingBalanceOwner PChainOwner + DisableOwner PChainOwner } return contract.TxToMethod( rpcURL, @@ -150,7 +163,13 @@ func InitializeValidatorRegistrationPoA( "initialize validator registration", validatormanager.ErrorSignatureToError, "initializeValidatorRegistration((bytes,bytes,uint64,(uint32,[address]),(uint32,[address])),uint64)", - validatorRegistrationInput, + ValidatorRegistrationInput{ + NodeID: nodeID[:], + BlsPublicKey: blsPublicKey, + RegistrationExpiry: expiry, + RemainingBalanceOwner: balanceOwnersAux, + DisableOwner: disableOwnersAux, + }, weight, ) } @@ -365,6 +384,7 @@ func InitValidatorRegistration( delegationFee uint16, stakeDuration time.Duration, validatorManagerAddressStr string, + useACP99 bool, ) (*warp.Message, ids.ID, *types.Transaction, error) { subnetID, err := contract.GetSubnetID( app, @@ -434,6 +454,7 @@ func InitValidatorRegistration( balanceOwners, disableOwners, weight, + useACP99, ) if err != nil { if !errors.Is(err, validatormanager.ErrNodeAlreadyRegistered) { @@ -553,10 +574,12 @@ func GetRegistrationMessage( if err != nil { return nil, err } - for blockNumber := uint64(0); blockNumber <= height; blockNumber++ { + maxBlock := int64(height) + minBlock := int64(0) + for blockNumber := maxBlock; blockNumber >= minBlock; blockNumber-- { ctx, cancel := utils.GetAPILargeContext() defer cancel() - block, err := client.BlockByNumber(ctx, big.NewInt(int64(blockNumber))) + block, err := client.BlockByNumber(ctx, big.NewInt(blockNumber)) if err != nil { return nil, err } @@ -568,17 +591,15 @@ func GetRegistrationMessage( if err != nil { return nil, err } - for _, txLog := range logs { - msg, err := subnetEvmWarp.UnpackSendWarpEventDataToMessage(txLog.Data) + msgs := GetWarpMessagesFromLogs(utils.PointersSlice(logs)) + for _, msg := range msgs { + payload := msg.Payload + addressedCall, err := warpPayload.ParseAddressedCall(payload) if err == nil { - payload := msg.Payload - addressedCall, err := warpPayload.ParseAddressedCall(payload) + reg, err := warpMessage.ParseRegisterL1Validator(addressedCall.Payload) if err == nil { - reg, err := warpMessage.ParseRegisterL1Validator(addressedCall.Payload) - if err == nil { - if reg.ValidationID() == validationID { - return msg.Bytes(), nil - } + if reg.ValidationID() == validationID { + return msg.Bytes(), nil } } } diff --git a/pkg/validatormanager/removal.go b/pkg/validatormanager/removal.go index c5d08654c..8e24f2752 100644 --- a/pkg/validatormanager/removal.go +++ b/pkg/validatormanager/removal.go @@ -22,21 +22,24 @@ import ( "github.com/ava-labs/avalanchego/ids" "github.com/ava-labs/avalanchego/utils/logging" warp "github.com/ava-labs/avalanchego/vms/platformvm/warp" - warpMessage "github.com/ava-labs/avalanchego/vms/platformvm/warp/message" warpPayload "github.com/ava-labs/avalanchego/vms/platformvm/warp/payload" "github.com/ava-labs/subnet-evm/core/types" "github.com/ava-labs/subnet-evm/warp/messages" + "github.com/ethereum/go-ethereum/common" ) func InitializeValidatorRemoval( rpcURL string, managerAddress common.Address, + generateRawTxOnly bool, + managerOwnerAddress common.Address, privateKey string, validationID ids.ID, isPoS bool, uptimeProofSignedMessage *warp.Message, force bool, + useACP99 bool, ) (*types.Transaction, *types.Receipt, error) { if isPoS { if force { @@ -73,10 +76,24 @@ func InitializeValidatorRemoval( ) } // PoA case + if useACP99 { + return contract.TxToMethod( + rpcURL, + generateRawTxOnly, + managerOwnerAddress, + privateKey, + managerAddress, + big.NewInt(0), + "POA validator removal initialization", + validatormanager.ErrorSignatureToError, + "initiateValidatorRemoval(bytes32)", + validationID, + ) + } return contract.TxToMethod( rpcURL, - false, - common.Address{}, + generateRawTxOnly, + managerOwnerAddress, privateKey, managerAddress, big.NewInt(0), @@ -129,64 +146,14 @@ func GetUptimeProofMessage( return signatureAggregator.Sign(uptimeProofUnsignedMessage, nil) } -func GetSubnetValidatorWeightMessage( - ctx context.Context, - network models.Network, - aggregatorLogger logging.Logger, - aggregatorQuorumPercentage uint64, - aggregatorAllowPrivateIPs bool, - aggregatorExtraPeerEndpoints []info.Peer, - subnetID ids.ID, - blockchainID ids.ID, - managerAddress common.Address, - validationID ids.ID, - nonce uint64, - weight uint64, -) (*warp.Message, error) { - addressedCallPayload, err := warpMessage.NewL1ValidatorWeight( - validationID, - nonce, - weight, - ) - if err != nil { - return nil, err - } - addressedCall, err := warpPayload.NewAddressedCall( - managerAddress.Bytes(), - addressedCallPayload.Bytes(), - ) - if err != nil { - return nil, err - } - unsignedMessage, err := warp.NewUnsignedMessage( - network.ID, - blockchainID, - addressedCall.Bytes(), - ) - if err != nil { - return nil, err - } - signatureAggregator, err := interchain.NewSignatureAggregator( - ctx, - network, - aggregatorLogger, - subnetID, - aggregatorQuorumPercentage, - aggregatorAllowPrivateIPs, - aggregatorExtraPeerEndpoints, - ) - if err != nil { - return nil, err - } - return signatureAggregator.Sign(unsignedMessage, nil) -} - func InitValidatorRemoval( ctx context.Context, app *application.Avalanche, network models.Network, rpcURL string, chainSpec contract.ChainSpec, + generateRawTxOnly bool, + ownerAddressStr string, ownerPrivateKey string, nodeID ids.NodeID, aggregatorExtraPeerEndpoints []info.Peer, @@ -196,14 +163,15 @@ func InitValidatorRemoval( uptimeSec uint64, force bool, validatorManagerAddressStr string, -) (*warp.Message, ids.ID, error) { + useACP99 bool, +) (*warp.Message, ids.ID, *types.Transaction, error) { subnetID, err := contract.GetSubnetID( app, network, chainSpec, ) if err != nil { - return nil, ids.Empty, err + return nil, ids.Empty, nil, err } blockchainID, err := contract.GetBlockchainID( app, @@ -211,19 +179,20 @@ func InitValidatorRemoval( chainSpec, ) if err != nil { - return nil, ids.Empty, err + return nil, ids.Empty, nil, err } managerAddress := common.HexToAddress(validatorManagerAddressStr) + ownerAddress := common.HexToAddress(ownerAddressStr) validationID, err := validator.GetRegisteredValidator( rpcURL, managerAddress, nodeID, ) if err != nil { - return nil, ids.Empty, err + return nil, ids.Empty, nil, err } if validationID == ids.Empty { - return nil, ids.Empty, fmt.Errorf("node %s is not a L1 validator", nodeID) + return nil, ids.Empty, nil, fmt.Errorf("node %s is not a L1 validator", nodeID) } signedUptimeProof := &warp.Message{} @@ -231,7 +200,7 @@ func InitValidatorRemoval( if uptimeSec == 0 { uptimeSec, err = utils.GetL1ValidatorUptimeSeconds(rpcURL, nodeID) if err != nil { - return nil, ids.Empty, evm.TransactionError(nil, err, "failure getting uptime data for nodeID: %s via %s ", nodeID, rpcURL) + return nil, ids.Empty, nil, evm.TransactionError(nil, err, "failure getting uptime data for nodeID: %s via %s ", nodeID, rpcURL) } } ux.Logger.PrintToUser("Using uptime: %ds", uptimeSec) @@ -247,33 +216,54 @@ func InitValidatorRemoval( uptimeSec, ) if err != nil { - return nil, ids.Empty, evm.TransactionError(nil, err, "failure getting uptime proof") + return nil, ids.Empty, nil, evm.TransactionError(nil, err, "failure getting uptime proof") } } - tx, _, err := InitializeValidatorRemoval( + tx, receipt, err := InitializeValidatorRemoval( rpcURL, managerAddress, + generateRawTxOnly, + ownerAddress, ownerPrivateKey, validationID, initWithPos, signedUptimeProof, // is empty for non-PoS force, + useACP99, ) if err != nil { if !errors.Is(err, validatormanager.ErrInvalidValidatorStatus) { - return nil, ids.Empty, evm.TransactionError(tx, err, "failure initializing validator removal") + return nil, ids.Empty, nil, evm.TransactionError(tx, err, "failure initializing validator removal") } ux.Logger.PrintToUser(logging.LightBlue.Wrap("The validator removal process was already initialized. Proceeding to the next step")) + } else if generateRawTxOnly { + return nil, ids.Empty, tx, nil + } + + var unsignedMessage *warp.UnsignedMessage + if receipt != nil { + unsignedMessage, err = GetWarpMessageFromLogs(receipt.Logs) + if err != nil { + return nil, ids.Empty, nil, err + } + } + + var nonce uint64 + if unsignedMessage == nil { + nonce, err = GetValidatorNonce(rpcURL, validationID) + if err != nil { + return nil, ids.Empty, nil, err + } } - nonce := uint64(1) - signedMsg, err := GetSubnetValidatorWeightMessage( + signedMsg, err := GetL1ValidatorWeightMessage( ctx, network, aggregatorLogger, 0, aggregatorAllowPrivatePeers, aggregatorExtraPeerEndpoints, + unsignedMessage, subnetID, blockchainID, managerAddress, @@ -281,19 +271,37 @@ func InitValidatorRemoval( nonce, 0, ) - return signedMsg, validationID, err + return signedMsg, validationID, nil, err } func CompleteValidatorRemoval( rpcURL string, managerAddress common.Address, + generateRawTxOnly bool, + ownerAddress common.Address, privateKey string, // not need to be owner atm subnetValidatorRegistrationSignedMessage *warp.Message, + useACP99 bool, ) (*types.Transaction, *types.Receipt, error) { + if useACP99 { + return contract.TxToMethodWithWarpMessage( + rpcURL, + generateRawTxOnly, + ownerAddress, + privateKey, + managerAddress, + subnetValidatorRegistrationSignedMessage, + big.NewInt(0), + "complete poa validator removal", + validatormanager.ErrorSignatureToError, + "completeValidatorRemoval(uint32)", + uint32(0), + ) + } return contract.TxToMethodWithWarpMessage( rpcURL, - false, - common.Address{}, + generateRawTxOnly, + ownerAddress, privateKey, managerAddress, subnetValidatorRegistrationSignedMessage, @@ -311,13 +319,16 @@ func FinishValidatorRemoval( network models.Network, rpcURL string, chainSpec contract.ChainSpec, + generateRawTxOnly bool, + ownerAddressStr string, privateKey string, validationID ids.ID, aggregatorExtraPeerEndpoints []info.Peer, aggregatorAllowPrivatePeers bool, aggregatorLogger logging.Logger, validatorManagerAddressStr string, -) error { + useACP99 bool, +) (*types.Transaction, error) { managerAddress := common.HexToAddress(validatorManagerAddressStr) subnetID, err := contract.GetSubnetID( app, @@ -325,7 +336,7 @@ func FinishValidatorRemoval( chainSpec, ) if err != nil { - return err + return nil, err } signedMessage, err := GetPChainSubnetValidatorRegistrationWarpMessage( ctx, @@ -340,22 +351,31 @@ func FinishValidatorRemoval( false, ) if err != nil { - return err + return nil, err } - if err := evm.SetupProposerVM( - rpcURL, - privateKey, - ); err != nil { - ux.Logger.RedXToUser("failure setting proposer VM on L1: %w", err) + if privateKey != "" { + if err := evm.SetupProposerVM( + rpcURL, + privateKey, + ); err != nil { + ux.Logger.RedXToUser("failure setting proposer VM on L1: %w", err) + } } + ownerAddress := common.HexToAddress(ownerAddressStr) tx, _, err := CompleteValidatorRemoval( rpcURL, managerAddress, + generateRawTxOnly, + ownerAddress, privateKey, signedMessage, + useACP99, ) if err != nil { - return evm.TransactionError(tx, err, "failure completing validator removal") + return nil, evm.TransactionError(tx, err, "failure completing validator removal") + } + if generateRawTxOnly { + return tx, nil } - return nil + return nil, nil } diff --git a/pkg/validatormanager/validatormanager.go b/pkg/validatormanager/validatormanager.go index 10b912915..d72f1b478 100644 --- a/pkg/validatormanager/validatormanager.go +++ b/pkg/validatormanager/validatormanager.go @@ -34,6 +34,20 @@ func AddValidatorMessagesContractToAllocations( } } +//go:embed deployed_validator_messages_bytecode_acp99.txt +var deployedValidatorMessagesACP99Bytecode []byte + +func AddValidatorMessagesACP99ContractToAllocations( + allocs core.GenesisAlloc, +) { + deployedValidatorMessagesBytes := common.FromHex(strings.TrimSpace(string(deployedValidatorMessagesACP99Bytecode))) + allocs[common.HexToAddress(validatorManagerSDK.ValidatorMessagesContractAddress)] = core.GenesisAccount{ + Balance: big.NewInt(0), + Code: deployedValidatorMessagesBytes, + Nonce: 1, + } +} + func fillValidatorMessagesAddressPlaceholder(contract string) string { return strings.ReplaceAll( contract, @@ -58,6 +72,22 @@ func AddPoAValidatorManagerContractToAllocations( } } +//go:embed deployed_validator_manager_bytecode_acp99.txt +var deployedPoAValidatorManagerACP99Bytecode []byte + +func AddPoAValidatorManagerACP99ContractToAllocations( + allocs core.GenesisAlloc, +) { + deployedPoaValidatorManagerString := strings.TrimSpace(string(deployedPoAValidatorManagerACP99Bytecode)) + deployedPoaValidatorManagerString = fillValidatorMessagesAddressPlaceholder(deployedPoaValidatorManagerString) + deployedPoaValidatorManagerBytes := common.FromHex(deployedPoaValidatorManagerString) + allocs[common.HexToAddress(validatorManagerSDK.ValidatorContractAddress)] = core.GenesisAccount{ + Balance: big.NewInt(0), + Code: deployedPoaValidatorManagerBytes, + Nonce: 1, + } +} + //go:embed deployed_native_pos_validator_manager_bytecode.txt var deployedPoSValidatorManagerBytecode []byte @@ -186,6 +216,7 @@ func SetupPoA( aggregatorAllowPrivatePeers bool, aggregatorLogger logging.Logger, validatorManagerAddressStr string, + useACP99 bool, ) error { return subnet.InitializeProofOfAuthority( ctx, @@ -195,6 +226,7 @@ func SetupPoA( aggregatorAllowPrivatePeers, aggregatorLogger, validatorManagerAddressStr, + useACP99, ) } diff --git a/pkg/validatormanager/weight_update.go b/pkg/validatormanager/weight_update.go new file mode 100644 index 000000000..acd4de077 --- /dev/null +++ b/pkg/validatormanager/weight_update.go @@ -0,0 +1,434 @@ +// Copyright (C) 2022, Ava Labs, Inc. All rights reserved. +// See the file LICENSE for licensing terms. +package validatormanager + +import ( + "context" + _ "embed" + "fmt" + "math/big" + + "github.com/ava-labs/avalanche-cli/pkg/application" + "github.com/ava-labs/avalanche-cli/pkg/contract" + "github.com/ava-labs/avalanche-cli/pkg/evm" + "github.com/ava-labs/avalanche-cli/pkg/models" + "github.com/ava-labs/avalanche-cli/pkg/utils" + "github.com/ava-labs/avalanche-cli/pkg/ux" + "github.com/ava-labs/avalanche-cli/sdk/interchain" + "github.com/ava-labs/avalanche-cli/sdk/validator" + "github.com/ava-labs/avalanche-cli/sdk/validatormanager" + "github.com/ava-labs/avalanchego/api/info" + "github.com/ava-labs/avalanchego/ids" + avagoconstants "github.com/ava-labs/avalanchego/utils/constants" + "github.com/ava-labs/avalanchego/utils/logging" + warp "github.com/ava-labs/avalanchego/vms/platformvm/warp" + warpMessage "github.com/ava-labs/avalanchego/vms/platformvm/warp/message" + warpPayload "github.com/ava-labs/avalanchego/vms/platformvm/warp/payload" + "github.com/ava-labs/subnet-evm/core/types" + "github.com/ava-labs/subnet-evm/interfaces" + subnetEvmWarp "github.com/ava-labs/subnet-evm/precompile/contracts/warp" + + "github.com/ethereum/go-ethereum/common" +) + +func InitializeValidatorWeightChange( + rpcURL string, + managerAddress common.Address, + generateRawTxOnly bool, + managerOwnerAddress common.Address, + privateKey string, + validationID ids.ID, + weight uint64, +) (*types.Transaction, *types.Receipt, error) { + return contract.TxToMethod( + rpcURL, + generateRawTxOnly, + managerOwnerAddress, + privateKey, + managerAddress, + big.NewInt(0), + "POA validator weight change initialization", + validatormanager.ErrorSignatureToError, + "initiateValidatorWeightUpdate(bytes32,uint64)", + validationID, + weight, + ) +} + +func InitValidatorWeightChange( + ctx context.Context, + app *application.Avalanche, + network models.Network, + rpcURL string, + chainSpec contract.ChainSpec, + generateRawTxOnly bool, + ownerAddressStr string, + ownerPrivateKey string, + nodeID ids.NodeID, + aggregatorExtraPeerEndpoints []info.Peer, + aggregatorAllowPrivatePeers bool, + aggregatorLogger logging.Logger, + validatorManagerAddressStr string, + weight uint64, +) (*warp.Message, ids.ID, *types.Transaction, error) { + subnetID, err := contract.GetSubnetID( + app, + network, + chainSpec, + ) + if err != nil { + return nil, ids.Empty, nil, err + } + blockchainID, err := contract.GetBlockchainID( + app, + network, + chainSpec, + ) + if err != nil { + return nil, ids.Empty, nil, err + } + managerAddress := common.HexToAddress(validatorManagerAddressStr) + ownerAddress := common.HexToAddress(ownerAddressStr) + validationID, err := validator.GetRegisteredValidator( + rpcURL, + managerAddress, + nodeID, + ) + if err != nil { + return nil, ids.Empty, nil, err + } + if validationID == ids.Empty { + return nil, ids.Empty, nil, fmt.Errorf("node %s is not a L1 validator", nodeID) + } + + unsignedMessage, err := GetWeightMessage(rpcURL, validationID, weight) + if err != nil { + return nil, ids.Empty, nil, fmt.Errorf("failure trying to get weight message from evm logs: %w", err) + } + + var receipt *types.Receipt + if unsignedMessage == nil { + var tx *types.Transaction + tx, receipt, err = InitializeValidatorWeightChange( + rpcURL, + managerAddress, + generateRawTxOnly, + ownerAddress, + ownerPrivateKey, + validationID, + weight, + ) + if err != nil { + return nil, ids.Empty, nil, evm.TransactionError(tx, err, "failure initializing validator weight change") + } else if generateRawTxOnly { + return nil, ids.Empty, tx, nil + } + } else { + ux.Logger.PrintToUser(logging.LightBlue.Wrap("The validator weight change process was already initialized. Proceeding to the next step")) + } + + if receipt != nil { + unsignedMessage, err = GetWarpMessageFromLogs(receipt.Logs) + if err != nil { + return nil, ids.Empty, nil, err + } + } + + var nonce uint64 + if unsignedMessage == nil { + nonce, err = GetValidatorNonce(rpcURL, validationID) + if err != nil { + return nil, ids.Empty, nil, err + } + } + + signedMsg, err := GetL1ValidatorWeightMessage( + ctx, + network, + aggregatorLogger, + 0, + aggregatorAllowPrivatePeers, + aggregatorExtraPeerEndpoints, + unsignedMessage, + subnetID, + blockchainID, + managerAddress, + validationID, + nonce, + weight, + ) + return signedMsg, validationID, nil, err +} + +func CompleteValidatorWeightChange( + rpcURL string, + managerAddress common.Address, + generateRawTxOnly bool, + ownerAddress common.Address, + privateKey string, // not need to be owner atm + pchainL1ValidatorRegistrationSignedMessage *warp.Message, +) (*types.Transaction, *types.Receipt, error) { + return contract.TxToMethodWithWarpMessage( + rpcURL, + generateRawTxOnly, + ownerAddress, + privateKey, + managerAddress, + pchainL1ValidatorRegistrationSignedMessage, + big.NewInt(0), + "complete poa validator weight change", + validatormanager.ErrorSignatureToError, + "completeValidatorWeightUpdate(uint32)", + uint32(0), + ) +} + +func FinishValidatorWeightChange( + ctx context.Context, + app *application.Avalanche, + network models.Network, + rpcURL string, + chainSpec contract.ChainSpec, + generateRawTxOnly bool, + ownerAddressStr string, + privateKey string, + validationID ids.ID, + aggregatorExtraPeerEndpoints []info.Peer, + aggregatorAllowPrivatePeers bool, + aggregatorLogger logging.Logger, + validatorManagerAddressStr string, + l1ValidatorRegistrationSignedMessage *warp.Message, + weight uint64, +) (*types.Transaction, error) { + managerAddress := common.HexToAddress(validatorManagerAddressStr) + subnetID, err := contract.GetSubnetID( + app, + network, + chainSpec, + ) + if err != nil { + return nil, err + } + var nonce uint64 + if l1ValidatorRegistrationSignedMessage == nil { + nonce, err = GetValidatorNonce(rpcURL, validationID) + if err != nil { + return nil, err + } + } + signedMessage, err := GetPChainL1ValidatorWeightMessage( + ctx, + network, + aggregatorLogger, + 0, + aggregatorAllowPrivatePeers, + aggregatorExtraPeerEndpoints, + subnetID, + l1ValidatorRegistrationSignedMessage, + validationID, + nonce, + weight, + ) + if err != nil { + return nil, err + } + if privateKey != "" { + if err := evm.SetupProposerVM( + rpcURL, + privateKey, + ); err != nil { + ux.Logger.RedXToUser("failure setting proposer VM on L1: %w", err) + } + } + ownerAddress := common.HexToAddress(ownerAddressStr) + tx, _, err := CompleteValidatorWeightChange( + rpcURL, + managerAddress, + generateRawTxOnly, + ownerAddress, + privateKey, + signedMessage, + ) + if err != nil { + return nil, evm.TransactionError(tx, err, "failure completing validator weight change") + } + if generateRawTxOnly { + return tx, nil + } + return nil, nil +} + +func GetL1ValidatorWeightMessage( + ctx context.Context, + network models.Network, + aggregatorLogger logging.Logger, + aggregatorQuorumPercentage uint64, + aggregatorAllowPrivateIPs bool, + aggregatorExtraPeerEndpoints []info.Peer, + // message is given + unsignedMessage *warp.UnsignedMessage, + // needed to generate message + subnetID ids.ID, + blockchainID ids.ID, + managerAddress common.Address, + validationID ids.ID, + nonce uint64, + weight uint64, +) (*warp.Message, error) { + if unsignedMessage == nil { + addressedCallPayload, err := warpMessage.NewL1ValidatorWeight( + validationID, + nonce, + weight, + ) + if err != nil { + return nil, err + } + addressedCall, err := warpPayload.NewAddressedCall( + managerAddress.Bytes(), + addressedCallPayload.Bytes(), + ) + if err != nil { + return nil, err + } + unsignedMessage, err = warp.NewUnsignedMessage( + network.ID, + blockchainID, + addressedCall.Bytes(), + ) + if err != nil { + return nil, err + } + } + signatureAggregator, err := interchain.NewSignatureAggregator( + ctx, + network, + aggregatorLogger, + subnetID, + aggregatorQuorumPercentage, + aggregatorAllowPrivateIPs, + aggregatorExtraPeerEndpoints, + ) + if err != nil { + return nil, err + } + return signatureAggregator.Sign(unsignedMessage, nil) +} + +func GetPChainL1ValidatorWeightMessage( + ctx context.Context, + network models.Network, + aggregatorLogger logging.Logger, + aggregatorQuorumPercentage uint64, + aggregatorAllowPrivateIPs bool, + aggregatorExtraPeerEndpoints []info.Peer, + subnetID ids.ID, + // message is given + l1SignedMessage *warp.Message, + // needed to generate full message contents + validationID ids.ID, + nonce uint64, + weight uint64, +) (*warp.Message, error) { + if l1SignedMessage != nil { + addressedCall, err := warpPayload.ParseAddressedCall(l1SignedMessage.UnsignedMessage.Payload) + if err != nil { + return nil, err + } + weightMsg, err := warpMessage.ParseL1ValidatorWeight(addressedCall.Payload) + if err != nil { + return nil, err + } + validationID = weightMsg.ValidationID + nonce = weightMsg.Nonce + weight = weightMsg.Weight + } + addressedCallPayload, err := warpMessage.NewL1ValidatorWeight( + validationID, + nonce, + weight, + ) + if err != nil { + return nil, err + } + addressedCall, err := warpPayload.NewAddressedCall( + nil, + addressedCallPayload.Bytes(), + ) + if err != nil { + return nil, err + } + unsignedMessage, err := warp.NewUnsignedMessage( + network.ID, + avagoconstants.PlatformChainID, + addressedCall.Bytes(), + ) + if err != nil { + return nil, err + } + signatureAggregator, err := interchain.NewSignatureAggregator( + ctx, + network, + aggregatorLogger, + subnetID, + aggregatorQuorumPercentage, + aggregatorAllowPrivateIPs, + aggregatorExtraPeerEndpoints, + ) + if err != nil { + return nil, err + } + return signatureAggregator.Sign(unsignedMessage, nil) +} + +func GetWeightMessage( + rpcURL string, + validationID ids.ID, + weight uint64, +) (*warp.UnsignedMessage, error) { + const maxBlocksToSearch = 500 + client, err := evm.GetClient(rpcURL) + if err != nil { + return nil, err + } + ctx, cancel := utils.GetAPILargeContext() + defer cancel() + height, err := client.BlockNumber(ctx) + if err != nil { + return nil, err + } + maxBlock := int64(height) + minBlock := max(maxBlock-maxBlocksToSearch, 0) + for blockNumber := maxBlock; blockNumber >= minBlock; blockNumber-- { + ctx, cancel := utils.GetAPILargeContext() + defer cancel() + block, err := client.BlockByNumber(ctx, big.NewInt(blockNumber)) + if err != nil { + return nil, err + } + blockHash := block.Hash() + logs, err := client.FilterLogs(ctx, interfaces.FilterQuery{ + BlockHash: &blockHash, + Addresses: []common.Address{subnetEvmWarp.Module.Address}, + }) + if err != nil { + return nil, err + } + msgs := GetWarpMessagesFromLogs(utils.PointersSlice(logs)) + for _, msg := range msgs { + payload := msg.Payload + addressedCall, err := warpPayload.ParseAddressedCall(payload) + if err == nil { + weightMsg, err := warpMessage.ParseL1ValidatorWeight(addressedCall.Payload) + if err == nil { + if weightMsg.ValidationID == validationID && weightMsg.Weight == weight { + return msg, nil + } else { + return nil, nil + } + } + } + } + } + return nil, nil +} diff --git a/pkg/vm/create_evm.go b/pkg/vm/create_evm.go index 14dedfdda..6d6cbfaa7 100644 --- a/pkg/vm/create_evm.go +++ b/pkg/vm/create_evm.go @@ -39,6 +39,7 @@ func CreateEvmSidecar( tokenSymbol string, getRPCVersionFromBinary bool, sovereign bool, + useACP99 bool, ) (*models.Sidecar, error) { var ( err error @@ -73,6 +74,7 @@ func CreateEvmSidecar( sc.TokenSymbol = tokenSymbol sc.TokenName = tokenSymbol + " Token" sc.Sovereign = sovereign + sc.UseACP99 = useACP99 return sc, nil } @@ -82,6 +84,7 @@ func CreateEVMGenesis( addICMRegistryToGenesis bool, proxyOwner string, rewardBasisPoints uint64, + useACP99 bool, ) ([]byte, error) { feeConfig := getFeeConfig(params) @@ -127,8 +130,13 @@ func CreateEVMGenesis( } if params.UsePoAValidatorManager { validatormanager.AddTransparentProxyContractToAllocations(params.initialTokenAllocation, proxyOwner) - validatormanager.AddValidatorMessagesContractToAllocations(params.initialTokenAllocation) - validatormanager.AddPoAValidatorManagerContractToAllocations(params.initialTokenAllocation) + if useACP99 { + validatormanager.AddValidatorMessagesACP99ContractToAllocations(params.initialTokenAllocation) + validatormanager.AddPoAValidatorManagerACP99ContractToAllocations(params.initialTokenAllocation) + } else { + validatormanager.AddValidatorMessagesContractToAllocations(params.initialTokenAllocation) + validatormanager.AddPoAValidatorManagerContractToAllocations(params.initialTokenAllocation) + } } else if params.UsePoSValidatorManager { validatormanager.AddTransparentProxyContractToAllocations(params.initialTokenAllocation, proxyOwner) validatormanager.AddValidatorMessagesContractToAllocations(params.initialTokenAllocation) diff --git a/sdk/blockchain/blockchain.go b/sdk/blockchain/blockchain.go index f6f5f4592..9297c4a28 100644 --- a/sdk/blockchain/blockchain.go +++ b/sdk/blockchain/blockchain.go @@ -350,6 +350,7 @@ func (c *Subnet) InitializeProofOfAuthority( aggregatorAllowPrivatePeers bool, aggregatorLogger logging.Logger, validatorManagerAddressStr string, + useACP99 bool, ) error { if c.SubnetID == ids.Empty { return fmt.Errorf("unable to initialize Proof of Authority: %w", errMissingSubnetID) @@ -384,6 +385,7 @@ func (c *Subnet) InitializeProofOfAuthority( privateKey, c.SubnetID, *c.OwnerAddress, + useACP99, ) if err != nil { if !errors.Is(err, validatormanager.ErrAlreadyInitialized) { diff --git a/sdk/validatormanager/root.go b/sdk/validatormanager/root.go index 3b4e8fb3c..f2d258644 100644 --- a/sdk/validatormanager/root.go +++ b/sdk/validatormanager/root.go @@ -23,6 +23,13 @@ import ( "github.com/ethereum/go-ethereum/common" ) +type ACP99ValidatorManagerSettings struct { + Admin common.Address + SubnetID [32]byte + ChurnPeriodSeconds uint64 + MaximumChurnPercentage uint8 +} + type ValidatorManagerSettings struct { SubnetID [32]byte ChurnPeriodSeconds uint64 diff --git a/sdk/validatormanager/validator_manager_poa.go b/sdk/validatormanager/validator_manager_poa.go index f25696221..9cbc8c286 100644 --- a/sdk/validatormanager/validator_manager_poa.go +++ b/sdk/validatormanager/validator_manager_poa.go @@ -23,15 +23,30 @@ func PoAValidatorManagerInitialize( privateKey string, subnetID ids.ID, ownerAddress common.Address, + useACP99 bool, ) (*types.Transaction, *types.Receipt, error) { const ( defaultChurnPeriodSeconds = uint64(0) defaultMaximumChurnPercentage = uint8(20) ) - params := ValidatorManagerSettings{ - SubnetID: subnetID, - ChurnPeriodSeconds: defaultChurnPeriodSeconds, - MaximumChurnPercentage: defaultMaximumChurnPercentage, + if useACP99 { + return contract.TxToMethod( + rpcURL, + false, + common.Address{}, + privateKey, + managerAddress, + nil, + "initialize PoA manager", + ErrorSignatureToError, + "initialize((address, bytes32,uint64,uint8))", + ACP99ValidatorManagerSettings{ + Admin: ownerAddress, + SubnetID: subnetID, + ChurnPeriodSeconds: defaultChurnPeriodSeconds, + MaximumChurnPercentage: defaultMaximumChurnPercentage, + }, + ) } return contract.TxToMethod( rpcURL, @@ -43,7 +58,11 @@ func PoAValidatorManagerInitialize( "initialize PoA manager", ErrorSignatureToError, "initialize((bytes32,uint64,uint8),address)", - params, + ValidatorManagerSettings{ + SubnetID: subnetID, + ChurnPeriodSeconds: defaultChurnPeriodSeconds, + MaximumChurnPercentage: defaultMaximumChurnPercentage, + }, ownerAddress, ) } diff --git a/tests/e2e/testcases/validatormanager/suite.go b/tests/e2e/testcases/validatormanager/suite.go index c0208e73c..3e875f078 100644 --- a/tests/e2e/testcases/validatormanager/suite.go +++ b/tests/e2e/testcases/validatormanager/suite.go @@ -215,7 +215,7 @@ var _ = ginkgo.Describe("[Validator Manager POA Set Up]", ginkgo.Ordered, func() ctx, cancel := utils.GetSignatureAggregatorContext() defer cancel() - err = subnetSDK.InitializeProofOfAuthority(ctx, network, k.PrivKeyHex(), extraAggregatorPeers, true, logging.NoLog{}, ProxyContractAddress) + err = subnetSDK.InitializeProofOfAuthority(ctx, network, k.PrivKeyHex(), extraAggregatorPeers, true, logging.NoLog{}, ProxyContractAddress, true) gomega.Expect(err).Should(gomega.BeNil()) }) })