code.vegaprotocol.io/vega@v0.79.0/core/banking/asset_action.go (about)

     1  // Copyright (C) 2023 Gobalsky Labs Limited
     2  //
     3  // This program is free software: you can redistribute it and/or modify
     4  // it under the terms of the GNU Affero General Public License as
     5  // published by the Free Software Foundation, either version 3 of the
     6  // License, or (at your option) any later version.
     7  //
     8  // This program is distributed in the hope that it will be useful,
     9  // but WITHOUT ANY WARRANTY; without even the implied warranty of
    10  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    11  // GNU Affero General Public License for more details.
    12  //
    13  // You should have received a copy of the GNU Affero General Public License
    14  // along with this program.  If not, see <http://www.gnu.org/licenses/>.
    15  
    16  package banking
    17  
    18  import (
    19  	"context"
    20  	"errors"
    21  	"fmt"
    22  	"sync/atomic"
    23  
    24  	"code.vegaprotocol.io/vega/core/assets"
    25  	"code.vegaprotocol.io/vega/core/assets/common"
    26  	"code.vegaprotocol.io/vega/core/types"
    27  	snapshot "code.vegaprotocol.io/vega/protos/vega/snapshot/v1"
    28  )
    29  
    30  var ErrUnknownAssetAction = errors.New("unknown asset action")
    31  
    32  type assetAction struct {
    33  	id    string
    34  	state *atomic.Uint32
    35  	asset *assets.Asset
    36  
    37  	// erc20 specifics
    38  	blockHeight uint64
    39  	logIndex    uint64
    40  	txHash      string
    41  	chainID     string
    42  
    43  	// all deposit related types
    44  	builtinD *types.BuiltinAssetDeposit
    45  	erc20D   *types.ERC20Deposit
    46  	erc20AL  *types.ERC20AssetList
    47  
    48  	erc20AssetLimitsUpdated *types.ERC20AssetLimitsUpdated
    49  
    50  	erc20BridgeStopped *types.ERC20EventBridgeStopped
    51  	erc20BridgeResumed *types.ERC20EventBridgeResumed
    52  
    53  	bridgeView ERC20BridgeView
    54  }
    55  
    56  func (t *assetAction) GetID() string {
    57  	return t.id
    58  }
    59  
    60  func (t *assetAction) GetType() types.NodeVoteType {
    61  	switch {
    62  	case t.IsBuiltinAssetDeposit():
    63  		return types.NodeVoteTypeFundsDeposited
    64  	case t.IsERC20Deposit():
    65  		return types.NodeVoteTypeFundsDeposited
    66  	case t.IsERC20AssetList():
    67  		return types.NodeVoteTypeAssetListed
    68  	case t.IsERC20AssetLimitsUpdated():
    69  		return types.NodeVoteTypeAssetLimitsUpdated
    70  	case t.IsERC20BridgeStopped():
    71  		return types.NodeVoteTypeBridgeStopped
    72  	case t.IsERC20BridgeResumed():
    73  		return types.NodeVoteTypeBridgeResumed
    74  	default:
    75  		return types.NodeVoteTypeUnspecified
    76  	}
    77  }
    78  
    79  func (t *assetAction) GetChainID() string {
    80  	return t.chainID
    81  }
    82  
    83  func (t *assetAction) IsBuiltinAssetDeposit() bool {
    84  	return t.builtinD != nil
    85  }
    86  
    87  func (t *assetAction) IsERC20BridgeStopped() bool {
    88  	return t.erc20BridgeStopped != nil
    89  }
    90  
    91  func (t *assetAction) IsERC20BridgeResumed() bool {
    92  	return t.erc20BridgeResumed != nil
    93  }
    94  
    95  func (t *assetAction) IsERC20Deposit() bool {
    96  	return t.erc20D != nil
    97  }
    98  
    99  func (t *assetAction) IsERC20AssetLimitsUpdated() bool {
   100  	return t.erc20AssetLimitsUpdated != nil
   101  }
   102  
   103  func (t *assetAction) IsERC20AssetList() bool {
   104  	return t.erc20AL != nil
   105  }
   106  
   107  func (t *assetAction) BuiltinAssetDesposit() *types.BuiltinAssetDeposit {
   108  	return t.builtinD
   109  }
   110  
   111  func (t *assetAction) ERC20Deposit() *types.ERC20Deposit {
   112  	return t.erc20D
   113  }
   114  
   115  func (t *assetAction) ERC20AssetLimitsUpdated() *types.ERC20AssetLimitsUpdated {
   116  	return t.erc20AssetLimitsUpdated
   117  }
   118  
   119  func (t *assetAction) ERC20AssetList() *types.ERC20AssetList {
   120  	return t.erc20AL
   121  }
   122  
   123  func (t *assetAction) String() string {
   124  	switch {
   125  	case t.IsBuiltinAssetDeposit():
   126  		return fmt.Sprintf("builtinAssetDeposit(%s)", t.builtinD.String())
   127  	case t.IsERC20Deposit():
   128  		return fmt.Sprintf("erc20Deposit(%s)", t.erc20D.String())
   129  	case t.IsERC20AssetList():
   130  		return fmt.Sprintf("erc20AssetList(%s)", t.erc20AL.String())
   131  	case t.IsERC20AssetLimitsUpdated():
   132  		return fmt.Sprintf("erc20AssetLimitsUpdated(%s)", t.erc20AssetLimitsUpdated.String())
   133  	case t.IsERC20BridgeStopped():
   134  		return fmt.Sprintf("erc20BridgeStopped(%s)", t.erc20BridgeStopped.String())
   135  	case t.IsERC20BridgeResumed():
   136  		return fmt.Sprintf("erc20BridgeResumed(%s)", t.erc20BridgeResumed.String())
   137  	default:
   138  		return ""
   139  	}
   140  }
   141  
   142  func (t *assetAction) Check(_ context.Context) error {
   143  	switch {
   144  	case t.IsBuiltinAssetDeposit():
   145  		return t.checkBuiltinAssetDeposit()
   146  	case t.IsERC20Deposit():
   147  		return t.checkERC20Deposit()
   148  	case t.IsERC20AssetList():
   149  		return t.checkERC20AssetList()
   150  	case t.IsERC20AssetLimitsUpdated():
   151  		return t.checkERC20AssetLimitsUpdated()
   152  	case t.IsERC20BridgeStopped():
   153  		return t.checkERC20BridgeStopped()
   154  	case t.IsERC20BridgeResumed():
   155  		return t.checkERC20BridgeResumed()
   156  	default:
   157  		return ErrUnknownAssetAction
   158  	}
   159  }
   160  
   161  func (t *assetAction) checkBuiltinAssetDeposit() error {
   162  	return nil
   163  }
   164  
   165  func (t *assetAction) checkERC20BridgeStopped() error {
   166  	return t.bridgeView.FindBridgeStopped(
   167  		t.erc20BridgeStopped, t.blockHeight, t.logIndex, t.txHash)
   168  }
   169  
   170  func (t *assetAction) checkERC20BridgeResumed() error {
   171  	return t.bridgeView.FindBridgeResumed(
   172  		t.erc20BridgeResumed, t.blockHeight, t.logIndex, t.txHash)
   173  }
   174  
   175  func (t *assetAction) checkERC20Deposit() error {
   176  	asset, _ := t.asset.ERC20()
   177  	return t.bridgeView.FindDeposit(
   178  		t.erc20D, t.blockHeight, t.logIndex, asset.Address(), t.txHash,
   179  	)
   180  }
   181  
   182  func (t *assetAction) checkERC20AssetList() error {
   183  	return t.bridgeView.FindAssetList(t.erc20AL, t.blockHeight, t.logIndex, t.txHash)
   184  }
   185  
   186  func (t *assetAction) checkERC20AssetLimitsUpdated() error {
   187  	asset, _ := t.asset.ERC20()
   188  	return t.bridgeView.FindAssetLimitsUpdated(
   189  		t.erc20AssetLimitsUpdated, t.blockHeight, t.logIndex, asset.Address(), t.txHash,
   190  	)
   191  }
   192  
   193  func (t *assetAction) getRef() snapshot.TxRef {
   194  	switch {
   195  	case t.IsBuiltinAssetDeposit():
   196  		return snapshot.TxRef{Asset: string(common.Builtin), BlockNr: 0, Hash: t.txHash, LogIndex: 0}
   197  	case t.IsERC20Deposit():
   198  		return snapshot.TxRef{Asset: string(common.ERC20), BlockNr: t.blockHeight, Hash: t.txHash, LogIndex: t.logIndex, ChainId: t.chainID}
   199  	case t.IsERC20AssetList():
   200  		return snapshot.TxRef{Asset: string(common.ERC20), BlockNr: t.blockHeight, Hash: t.txHash, LogIndex: t.logIndex, ChainId: t.chainID}
   201  	case t.IsERC20AssetLimitsUpdated():
   202  		return snapshot.TxRef{Asset: string(common.ERC20), BlockNr: t.blockHeight, Hash: t.txHash, LogIndex: t.logIndex, ChainId: t.chainID}
   203  	case t.IsERC20BridgeStopped():
   204  		return snapshot.TxRef{Asset: string(common.ERC20), BlockNr: t.blockHeight, Hash: t.txHash, LogIndex: t.logIndex, ChainId: t.chainID}
   205  	case t.IsERC20BridgeResumed():
   206  		return snapshot.TxRef{Asset: string(common.ERC20), BlockNr: t.blockHeight, Hash: t.txHash, LogIndex: t.logIndex, ChainId: t.chainID}
   207  	default:
   208  		return snapshot.TxRef{} // this is basically unreachable
   209  	}
   210  }