66 "strings"
77
88 "github.com/gagliardetto/solana-go"
9+ "github.com/gagliardetto/solana-go/rpc"
910 "github.com/smartcontractkit/mcms"
1011 mcmsTypes "github.com/smartcontractkit/mcms/types"
1112
@@ -106,7 +107,7 @@ type SetUpgradeAuthorityConfig struct {
106107}
107108
108109func RotateBaseSignerNopsChangeset (e cldf.Environment , c RotateBaseSignerNopsConfig ) (cldf.ChangesetOutput , error ) {
109- e .Logger .Infow ("Rotating Base signer nops" , "chain_selector" , c .ChainSelector , "removing" , c .NopKeysToAdd , "adding" , c .NopKeysToAdd )
110+ e .Logger .Infow ("Rotating Base signer nops" , "chain_selector" , c .ChainSelector , "removing" , c .NopKeysToRemove , "adding" , c .NopKeysToAdd )
110111 chain := e .BlockChains .SolanaChains ()[c .ChainSelector ]
111112 err := c .Validate (e )
112113 if err != nil {
@@ -175,25 +176,25 @@ func (c RotateBaseSignerNopsConfig) Validate(e cldf.Environment) error {
175176 keysToRemoveParsed [i ] = parsed
176177 }
177178
178- var signersAccount signer_registry.Signers
179- signersPda , _ , _ := solana .FindProgramAddress ([][]byte {[]byte ("signers" )}, signer_registry .ProgramID )
180-
181179 chain := e .BlockChains .SolanaChains ()[c .ChainSelector ]
182- if err := chain .GetAccountDataBorshInto (e .GetContext (), signersPda , & signersAccount ); err != nil {
183- return fmt .Errorf ("failed to get signers: %w" , err )
184- }
180+ if len (c .NopKeysToRemove ) > 0 {
181+ signersPda , _ , _ := solana .FindProgramAddress ([][]byte {[]byte ("signers" )}, signer_registry .ProgramID )
185182
186- // Check that all NopKeysToRemove exist in signersAccount
187- for i , keyBytes := range keysToRemoveParsed {
188- if ! keyExistsInSigners (keyBytes , signersAccount .Signers ) {
189- return fmt .Errorf ("NopKeysToRemove[%d] (%s) does not exist in current signers" , i , c .NopKeysToRemove [i ])
183+ data , err := GetAccountData (e , & chain , signersPda )
184+ if err != nil {
185+ return fmt .Errorf ("failed to get signers: %w" , err )
190186 }
191- }
192187
193- // Check that none of NopKeysToAdd already exist in signersAccount
194- for i , keyBytes := range keysToAddParsed {
195- if keyExistsInSigners (keyBytes , signersAccount .Signers ) {
196- return fmt .Errorf ("NopKeysToAdd[%d] (%s) already exists in current signers" , i , c .NopKeysToAdd [i ])
188+ signersAccount , err := signer_registry .ParseAccount_Signers (data )
189+
190+ if err != nil {
191+ return fmt .Errorf ("failed to get signers: %w" , err )
192+ }
193+ // Check that all NopKeysToRemove exist in signersAccount
194+ for i , keyBytes := range keysToRemoveParsed {
195+ if ! keyExistsInSigners (keyBytes , signersAccount .Signers ) {
196+ return fmt .Errorf ("NopKeysToRemove[%d] (%s) does not exist in current signers" , i , c .NopKeysToRemove [i ])
197+ }
197198 }
198199 }
199200
@@ -206,14 +207,6 @@ func (c RotateBaseSignerNopsConfig) Validate(e cldf.Environment) error {
206207 }
207208 }
208209
209- // Check that the final number of signers doesn't exceed 20
210- currentSignerCount := len (signersAccount .Signers )
211- finalSignerCount := currentSignerCount - len (keysToRemoveParsed ) + len (keysToAddParsed )
212- if finalSignerCount > 20 {
213- return fmt .Errorf ("final signer count would be %d, which exceeds the maximum of 20 (current: %d, removing: %d, adding: %d)" ,
214- finalSignerCount , currentSignerCount , len (keysToRemoveParsed ), len (keysToAddParsed ))
215- }
216-
217210 return solanastateview .ValidateOwnershipSolana (& e , chain , c .MCMS != nil , signer_registry .ProgramID , shared .SVMSignerRegistry , solana.PublicKey {})
218211}
219212
@@ -282,13 +275,15 @@ func (c AddGreenKeysConfig) Validate(e cldf.Environment) error {
282275 }
283276
284277 // Get current signers account
285- var signersAccount signer_registry.Signers
286278 signersPda , _ , _ := solana .FindProgramAddress ([][]byte {[]byte ("signers" )}, signer_registry .ProgramID )
287279
288- if err := chain .GetAccountDataBorshInto (e .GetContext (), signersPda , & signersAccount ); err != nil {
280+ data , err := GetAccountData (e , & chain , signersPda )
281+ if err != nil {
289282 return fmt .Errorf ("failed to get signers: %w" , err )
290283 }
291284
285+ signersAccount , err := signer_registry .ParseAccount_Signers (data )
286+
292287 // Check that all blue keys exist in signersAccount (either as EvmAddress or NewEvmAddress)
293288 for i , blueKey := range blueKeysParsed {
294289 if ! keyExistsInSigners (blueKey , signersAccount .Signers ) {
@@ -371,13 +366,15 @@ func (c PromoteKeysConfig) Validate(e cldf.Environment) error {
371366 }
372367
373368 // Get current signers account
374- var signersAccount signer_registry.Signers
375369 signersPda , _ , _ := solana .FindProgramAddress ([][]byte {[]byte ("signers" )}, signer_registry .ProgramID )
376370
377- if err := chain .GetAccountDataBorshInto (e .GetContext (), signersPda , & signersAccount ); err != nil {
371+ data , err := GetAccountData (e , & chain , signersPda )
372+ if err != nil {
378373 return fmt .Errorf ("failed to get signers: %w" , err )
379374 }
380375
376+ signersAccount , err := signer_registry .ParseAccount_Signers (data )
377+
381378 // Check that each key exists and has an active blue/green pair
382379 for i , keyBytes := range keysParsed {
383380 signer := findSignerWithKey (keyBytes , signersAccount .Signers )
@@ -488,3 +485,23 @@ func findSignerWithKey(key [20]uint8, signers []signer_registry.Signer) *signer_
488485 }
489486 return nil
490487}
488+
489+ func GetAccountData (
490+ e cldf.Environment ,
491+ chain * cldf_solana.Chain ,
492+ account solana.PublicKey ,
493+
494+ ) ([]byte , error ) {
495+ resp , err := chain .Client .GetAccountInfoWithOpts (
496+ e .GetContext (),
497+ account ,
498+ & rpc.GetAccountInfoOpts {
499+ Commitment : rpc .CommitmentFinalized ,
500+ DataSlice : nil ,
501+ },
502+ )
503+ if err != nil {
504+ return nil , err
505+ }
506+ return resp .Value .Data .GetBinary (), nil
507+ }
0 commit comments