mirror of
https://github.com/luxfi/node.git
synced 2026-07-27 03:39:39 +00:00
vms/platformvm/... build + vet PASS with pcodecs/txs.Codec gone from the VM. Executor semantics (standard_tx_executor): - registerOwnSet(): shared primitive — per-validator state.L1Validator with native owner blobs (txs.MarshalOwner/UnmarshalOwner, no codec), active-set capacity check, EndAccumulatedFee=balance+accruedFees, SetNetToL1Conversion manager-authority recording (byte-for-byte legacy tail). - ConvertNetworkTx: promote endomorphism (owner-authorized, folds old ConvertNetworkToL1Tx), gated by security.Mode.Manager. - CreateNetworkTx: base (AddNet/SetNetOwner) + sovereign path registers own set. - Deleted CreateSovereignL1Tx + ConvertNetworkToL1Tx. - txs.UnmarshalOwner added: canonical owner marshal/unmarshal pair, no codec. All ~13 txs.Visitor impls carry ConvertNetworkTx; gossip/block Parse(b) codec-free; wallet/network/primary off txs.Codec. KNOWN GAP (pending design decision, NOT silently green): CreateNetworkTx reads tx.Chains() only to derive managerChainID — it does NOT create the genesis chains (no AddChain). Atomic-spawn-with-chains vs decomplect-to-CreateChainTx is the open call. 17 codec-era _test.go parked as .bak for follow-up rewrite. Co-authored-by: Hanzo Dev <dev@hanzo.ai>
192 lines
6.0 KiB
Go
192 lines
6.0 KiB
Go
// Copyright (C) 2019-2025, Lux Industries Inc. All rights reserved.
|
|
// See the file LICENSE for licensing terms.
|
|
|
|
package primary
|
|
|
|
import (
|
|
"context"
|
|
|
|
gethcommon "github.com/luxfi/geth/common"
|
|
|
|
"github.com/luxfi/constants"
|
|
"github.com/luxfi/ids"
|
|
"github.com/luxfi/keychain"
|
|
"github.com/luxfi/math/set"
|
|
"github.com/luxfi/node/vms/platformvm/txs"
|
|
"github.com/luxfi/node/wallet/chain/p"
|
|
"github.com/luxfi/node/wallet/chain/x"
|
|
"github.com/luxfi/node/wallet/network/primary/common"
|
|
"github.com/luxfi/utxo/secp256k1fx"
|
|
|
|
pbuilder "github.com/luxfi/node/wallet/chain/p/builder"
|
|
psigner "github.com/luxfi/node/wallet/chain/p/signer"
|
|
xbuilder "github.com/luxfi/node/wallet/chain/x/builder"
|
|
xsigner "github.com/luxfi/node/wallet/chain/x/signer"
|
|
)
|
|
|
|
var _ Wallet = (*wallet)(nil)
|
|
|
|
// EVMKeychain is the interface for keychains that expose 20-byte
|
|
// account addresses used by EVM-runtime chains (Lux C-Chain, Liquid
|
|
// EVM, Hanzo EVM, and every EVM-compatible chain).
|
|
//
|
|
// Naming: the value IS "EVM-runtime account address". The internal
|
|
// derivation uses Keccak256 of the secp256k1 pubkey — that's HOW it's
|
|
// computed. The data model that consumes it (EVM account) is WHAT it
|
|
// is. UTXO vs EVM is the relevant axis in a multi-chain keychain.
|
|
type EVMKeychain interface {
|
|
GetByEVM(addr gethcommon.Address) (keychain.Signer, bool)
|
|
EVMAddresses() set.Set[gethcommon.Address]
|
|
}
|
|
|
|
// KeychainAdapter adapts secp256k1fx.Keychain to BOTH
|
|
// wallet/keychain.Keychain (UTXO-side) and EVMKeychain (EVM-side).
|
|
type KeychainAdapter struct {
|
|
*secp256k1fx.Keychain
|
|
}
|
|
|
|
// Addresses implements wallet/keychain.Keychain (UTXO-side).
|
|
func (kc *KeychainAdapter) Addresses() set.Set[ids.ShortID] {
|
|
return kc.Keychain.Addrs
|
|
}
|
|
|
|
// Get implements keychain.Keychain (UTXO-side lookup by ShortID).
|
|
func (kc *KeychainAdapter) Get(addr ids.ShortID) (keychain.Signer, bool) {
|
|
return kc.Keychain.Get(addr)
|
|
}
|
|
|
|
// GetByEVM implements EVMKeychain (EVM-side lookup by 20-byte addr).
|
|
func (kc *KeychainAdapter) GetByEVM(addr gethcommon.Address) (keychain.Signer, bool) {
|
|
signer, ok := kc.Keychain.GetByEVM(addr)
|
|
if !ok {
|
|
return nil, false
|
|
}
|
|
// secp256k1fx.luxSigner already implements wallet/keychain.Signer
|
|
return signer.(keychain.Signer), true
|
|
}
|
|
|
|
// EVMAddresses implements EVMKeychain (EVM-side address set).
|
|
func (kc *KeychainAdapter) EVMAddresses() set.Set[gethcommon.Address] {
|
|
return kc.Keychain.EVMAddrs
|
|
}
|
|
|
|
// NewKeychainAdapter creates a KeychainAdapter from a secp256k1fx.Keychain
|
|
func NewKeychainAdapter(kc *secp256k1fx.Keychain) *KeychainAdapter {
|
|
return &KeychainAdapter{Keychain: kc}
|
|
}
|
|
|
|
// Wallet provides chain wallets for the primary network.
|
|
// NOTE: C-Chain wallet is disabled - use github.com/luxfi/evm/ethclient directly
|
|
type Wallet interface {
|
|
P() p.Wallet
|
|
X() x.Wallet
|
|
}
|
|
|
|
type wallet struct {
|
|
p p.Wallet
|
|
x x.Wallet
|
|
}
|
|
|
|
func (w *wallet) P() p.Wallet {
|
|
return w.p
|
|
}
|
|
|
|
func (w *wallet) X() x.Wallet {
|
|
return w.x
|
|
}
|
|
|
|
// Creates a new default wallet
|
|
func NewWallet(pWallet p.Wallet, xWallet x.Wallet) Wallet {
|
|
return &wallet{
|
|
p: pWallet,
|
|
x: xWallet,
|
|
}
|
|
}
|
|
|
|
// Creates a Wallet with the given set of options
|
|
func NewWalletWithOptions(w Wallet, options ...common.Option) Wallet {
|
|
return NewWallet(
|
|
p.NewWalletWithOptions(w.P(), options...),
|
|
x.NewWalletWithOptions(w.X(), options...),
|
|
)
|
|
}
|
|
|
|
type WalletConfig struct {
|
|
// Base URI to use for all node requests.
|
|
URI string // required
|
|
// Keys to use for signing all transactions.
|
|
LUXKeychain keychain.Keychain // required
|
|
EVMKeychain EVMKeychain // optional - for future C-Chain support
|
|
// Set of P-chain transactions that the wallet should know about to be able
|
|
// to generate transactions.
|
|
PChainTxs map[ids.ID]*txs.Tx // optional
|
|
// Set of P-chain transactions that the wallet should fetch to be able to
|
|
// generate transactions.
|
|
PChainTxsToFetch set.Set[ids.ID] // optional
|
|
}
|
|
|
|
// MakeWallet returns a wallet that supports issuing transactions to the chains
|
|
// living in the primary network.
|
|
//
|
|
// On creation, the wallet attaches to the provided uri and fetches all UTXOs
|
|
// that reference any of the provided keys. If the UTXOs are modified through an
|
|
// external issuance process, such as another instance of the wallet, the UTXOs
|
|
// may become out of sync. The wallet will also fetch all requested P-chain
|
|
// transactions.
|
|
//
|
|
// The wallet manages all state locally, and performs all tx signing locally.
|
|
func MakeWallet(ctx context.Context, config *WalletConfig) (Wallet, error) {
|
|
luxAddrs := config.LUXKeychain.Addresses()
|
|
luxState, err := FetchState(ctx, config.URI, luxAddrs)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
|
|
// evmAddrs := config.EVMKeychain.EVMAddresses()
|
|
// evmState, err := FetchEVMState(ctx, config.URI, evmAddrs)
|
|
// if err != nil {
|
|
// return nil, err
|
|
// }
|
|
|
|
pChainTxs := config.PChainTxs
|
|
if pChainTxs == nil {
|
|
pChainTxs = make(map[ids.ID]*txs.Tx)
|
|
}
|
|
|
|
for txID := range config.PChainTxsToFetch {
|
|
txBytes, err := luxState.PClient.GetTx(ctx, txID)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
tx, err := txs.Parse(txBytes)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
pChainTxs[txID] = tx
|
|
}
|
|
|
|
pUTXOs := common.NewChainUTXOs(constants.PlatformChainID, luxState.UTXOs)
|
|
pBackend := p.NewBackend(luxState.PCTX, pUTXOs, pChainTxs)
|
|
pBuilder := pbuilder.New(luxAddrs, luxState.PCTX, pBackend)
|
|
pSigner := psigner.New(config.LUXKeychain, pBackend)
|
|
|
|
xChainID := luxState.XCTX.BlockchainID
|
|
xUTXOs := common.NewChainUTXOs(xChainID, luxState.UTXOs)
|
|
xBackend := x.NewBackend(luxState.XCTX, xUTXOs)
|
|
xBuilder := xbuilder.New(luxAddrs, luxState.XCTX, xBackend)
|
|
xSigner := xsigner.New(config.LUXKeychain, xBackend)
|
|
|
|
// cChainID := luxState.CCTX.BlockchainID
|
|
// cUTXOs := common.NewChainUTXOs(cChainID, luxState.UTXOs)
|
|
// cBackend := c.NewBackend(cUTXOs, ethState.Accounts)
|
|
// cBuilder := c.NewBuilder(luxAddrs, evmAddrs, luxState.CCTX, cBackend)
|
|
// cSigner := c.NewSigner(config.LUXKeychain, config.EVMKeychain, cBackend)
|
|
|
|
pClient := p.NewClient(luxState.PClient, pBackend)
|
|
|
|
return NewWallet(
|
|
p.NewWallet(pClient, pBuilder, pSigner),
|
|
x.NewWallet(xBuilder, xSigner, xBackend),
|
|
), nil
|
|
}
|