github.com/Gessiux/neatchain@v1.3.1/internal/neatapi/api.go (about) 1 // Copyright 2015 The go-ethereum Authors 2 // This file is part of the go-ethereum library. 3 // 4 // The go-ethereum library is free software: you can redistribute it and/or modify 5 // it under the terms of the GNU Lesser General Public License as published by 6 // the Free Software Foundation, either version 3 of the License, or 7 // (at your option) any later version. 8 // 9 // The go-ethereum library is distributed in the hope that it will be useful, 10 // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 // GNU Lesser General Public License for more details. 13 // 14 // You should have received a copy of the GNU Lesser General Public License 15 // along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>. 16 17 package neatapi 18 19 import ( 20 "bytes" 21 "context" 22 "errors" 23 "fmt" 24 "math/big" 25 "strings" 26 "time" 27 28 "github.com/Gessiux/neatchain/chain/consensus" 29 "github.com/Gessiux/neatchain/chain/consensus/neatcon/epoch" 30 "github.com/Gessiux/neatchain/chain/core/state" 31 32 goCrypto "github.com/Gessiux/go-crypto" 33 "github.com/Gessiux/neatchain/chain/accounts" 34 "github.com/Gessiux/neatchain/chain/accounts/keystore" 35 "github.com/Gessiux/neatchain/chain/core" 36 "github.com/Gessiux/neatchain/chain/core/rawdb" 37 "github.com/Gessiux/neatchain/chain/core/types" 38 "github.com/Gessiux/neatchain/chain/core/vm" 39 "github.com/Gessiux/neatchain/chain/log" 40 neatAbi "github.com/Gessiux/neatchain/neatabi/abi" 41 "github.com/Gessiux/neatchain/network/p2p" 42 "github.com/Gessiux/neatchain/network/rpc" 43 "github.com/Gessiux/neatchain/params" 44 "github.com/Gessiux/neatchain/utilities/common" 45 "github.com/Gessiux/neatchain/utilities/common/hexutil" 46 "github.com/Gessiux/neatchain/utilities/common/math" 47 "github.com/Gessiux/neatchain/utilities/crypto" 48 "github.com/Gessiux/neatchain/utilities/rlp" 49 "github.com/syndtr/goleveldb/leveldb" 50 ) 51 52 const ( 53 defaultGasPrice = params.GWei 54 updateValidatorThreshold = 100 55 ) 56 57 // PublicNEATChainAPI provides an API to access neatchain related information. 58 // It offers only methods that operate on public data that is freely available to anyone. 59 type PublicNEATChainAPI struct { 60 b Backend 61 } 62 63 // NewPublicNEATChainAPI creates a new neatchain protocol API. 64 func NewPublicNEATChainAPI(b Backend) *PublicNEATChainAPI { 65 return &PublicNEATChainAPI{b} 66 } 67 68 // GasPrice returns a suggestion for a gas price. 69 func (s *PublicNEATChainAPI) GasPrice(ctx context.Context) (*hexutil.Big, error) { 70 price, err := s.b.SuggestPrice(ctx) 71 return (*hexutil.Big)(price), err 72 } 73 74 // ProtocolVersion returns the current neatchain protocol version this node supports 75 func (s *PublicNEATChainAPI) ProtocolVersion() hexutil.Uint { 76 return hexutil.Uint(s.b.ProtocolVersion()) 77 } 78 79 // Syncing returns false in case the node is currently not syncing with the network. It can be up to date or has not 80 // yet received the latest block headers from its pears. In case it is synchronizing: 81 // - startingBlock: block number this node started to synchronise from 82 // - currentBlock: block number this node is currently importing 83 // - highestBlock: block number of the highest block header this node has received from peers 84 // - pulledStates: number of state entries processed until now 85 // - knownStates: number of known state entries that still need to be pulled 86 func (s *PublicNEATChainAPI) Syncing() (interface{}, error) { 87 progress := s.b.Downloader().Progress() 88 89 // Return not syncing if the synchronisation already completed 90 if progress.CurrentBlock >= progress.HighestBlock { 91 return false, nil 92 } 93 // Otherwise gather the block sync stats 94 return map[string]interface{}{ 95 "startingBlock": hexutil.Uint64(progress.StartingBlock), 96 "currentBlock": hexutil.Uint64(progress.CurrentBlock), 97 "highestBlock": hexutil.Uint64(progress.HighestBlock), 98 "pulledStates": hexutil.Uint64(progress.PulledStates), 99 "knownStates": hexutil.Uint64(progress.KnownStates), 100 }, nil 101 } 102 103 // PublicTxPoolAPI offers and API for the transaction pool. It only operates on data that is non confidential. 104 type PublicTxPoolAPI struct { 105 b Backend 106 } 107 108 // NewPublicTxPoolAPI creates a new tx pool service that gives information about the transaction pool. 109 func NewPublicTxPoolAPI(b Backend) *PublicTxPoolAPI { 110 return &PublicTxPoolAPI{b} 111 } 112 113 // Content returns the transactions contained within the transaction pool. 114 func (s *PublicTxPoolAPI) Content() map[string]map[string]map[string]*RPCTransaction { 115 content := map[string]map[string]map[string]*RPCTransaction{ 116 "pending": make(map[string]map[string]*RPCTransaction), 117 "queued": make(map[string]map[string]*RPCTransaction), 118 } 119 pending, queue := s.b.TxPoolContent() 120 121 // Flatten the pending transactions 122 for account, txs := range pending { 123 dump := make(map[string]*RPCTransaction) 124 for _, tx := range txs { 125 dump[fmt.Sprintf("%d", tx.Nonce())] = newRPCPendingTransaction(tx) 126 } 127 //content["pending"][account.Hex()] = dump 128 content["pending"][account.String()] = dump 129 } 130 // Flatten the queued transactions 131 for account, txs := range queue { 132 dump := make(map[string]*RPCTransaction) 133 for _, tx := range txs { 134 dump[fmt.Sprintf("%d", tx.Nonce())] = newRPCPendingTransaction(tx) 135 } 136 //content["queued"][account.Hex()] = dump 137 content["queued"][account.String()] = dump 138 } 139 return content 140 } 141 142 // Status returns the number of pending and queued transaction in the pool. 143 func (s *PublicTxPoolAPI) Status() map[string]hexutil.Uint { 144 pending, queue := s.b.Stats() 145 return map[string]hexutil.Uint{ 146 "pending": hexutil.Uint(pending), 147 "queued": hexutil.Uint(queue), 148 } 149 } 150 151 // Inspect retrieves the content of the transaction pool and flattens it into an 152 // easily inspectable list. 153 func (s *PublicTxPoolAPI) Inspect() map[string]map[string]map[string]string { 154 content := map[string]map[string]map[string]string{ 155 "pending": make(map[string]map[string]string), 156 "queued": make(map[string]map[string]string), 157 } 158 pending, queue := s.b.TxPoolContent() 159 160 // Define a formatter to flatten a transaction into a string 161 var format = func(tx *types.Transaction) string { 162 if to := tx.To(); to != nil { 163 //return fmt.Sprintf("%s: %v wei + %v gas × %v wei", tx.To().Hex(), tx.Value(), tx.Gas(), tx.GasPrice()) 164 return fmt.Sprintf("%s: %v wei + %v gas × %v wei", tx.To().String(), tx.Value(), tx.Gas(), tx.GasPrice()) 165 } 166 return fmt.Sprintf("contract creation: %v wei + %v gas × %v wei", tx.Value(), tx.Gas(), tx.GasPrice()) 167 } 168 // Flatten the pending transactions 169 for account, txs := range pending { 170 dump := make(map[string]string) 171 for _, tx := range txs { 172 dump[fmt.Sprintf("%d", tx.Nonce())] = format(tx) 173 } 174 //content["pending"][account.Hex()] = dump 175 content["pending"][account.String()] = dump 176 } 177 // Flatten the queued transactions 178 for account, txs := range queue { 179 dump := make(map[string]string) 180 for _, tx := range txs { 181 dump[fmt.Sprintf("%d", tx.Nonce())] = format(tx) 182 } 183 //content["queued"][account.Hex()] = dump 184 content["queued"][account.String()] = dump 185 } 186 return content 187 } 188 189 // PublicAccountAPI provides an API to access accounts managed by this node. 190 // It offers only methods that can retrieve accounts. 191 type PublicAccountAPI struct { 192 am *accounts.Manager 193 } 194 195 // NewPublicAccountAPI creates a new PublicAccountAPI. 196 func NewPublicAccountAPI(am *accounts.Manager) *PublicAccountAPI { 197 return &PublicAccountAPI{am: am} 198 } 199 200 // Accounts returns the collection of accounts this node manages 201 func (s *PublicAccountAPI) Accounts() []string { 202 addresses := make([]string, 0) // return [] instead of nil if empty 203 for _, wallet := range s.am.Wallets() { 204 for _, account := range wallet.Accounts() { 205 addresses = append(addresses, account.Address.String()) // return string address 206 } 207 } 208 return addresses 209 } 210 211 // PrivateAccountAPI provides an API to access accounts managed by this node. 212 // It offers methods to create, (un)lock en list accounts. Some methods accept 213 // passwords and are therefore considered private by default. 214 type PrivateAccountAPI struct { 215 am *accounts.Manager 216 nonceLock *AddrLocker 217 b Backend 218 } 219 220 // NewPrivateAccountAPI create a new PrivateAccountAPI. 221 func NewPrivateAccountAPI(b Backend, nonceLock *AddrLocker) *PrivateAccountAPI { 222 return &PrivateAccountAPI{ 223 am: b.AccountManager(), 224 nonceLock: nonceLock, 225 b: b, 226 } 227 } 228 229 // ListAccounts will return a list of addresses for accounts this node manages. 230 //修改帐户列表返回地址类型为 string 231 func (s *PrivateAccountAPI) ListAccounts() []string { 232 addresses := make([]string, 0) // return [] instead of nil if empty 233 for _, wallet := range s.am.Wallets() { 234 for _, account := range wallet.Accounts() { 235 addresses = append(addresses, account.Address.String()) 236 } 237 } 238 return addresses 239 } 240 241 // rawWallet is a JSON representation of an accounts.Wallet interface, with its 242 // data contents extracted into plain fields. 243 type rawWallet struct { 244 URL string `json:"url"` 245 Status string `json:"status"` 246 Failure string `json:"failure,omitempty"` 247 Accounts []accounts.Account `json:"accounts,omitempty"` 248 } 249 250 // ListWallets will return a list of wallets this node manages. 251 func (s *PrivateAccountAPI) ListWallets() []rawWallet { 252 wallets := make([]rawWallet, 0) // return [] instead of nil if empty 253 for _, wallet := range s.am.Wallets() { 254 status, failure := wallet.Status() 255 256 raw := rawWallet{ 257 URL: wallet.URL().String(), 258 Status: status, 259 Accounts: wallet.Accounts(), 260 } 261 if failure != nil { 262 raw.Failure = failure.Error() 263 } 264 wallets = append(wallets, raw) 265 } 266 return wallets 267 } 268 269 // OpenWallet initiates a hardware wallet opening procedure, establishing a USB 270 // connection and attempting to authenticate via the provided passphrase. Note, 271 // the method may return an extra challenge requiring a second open (e.g. the 272 // Trezor PIN matrix challenge). 273 func (s *PrivateAccountAPI) OpenWallet(url string, passphrase *string) error { 274 wallet, err := s.am.Wallet(url) 275 if err != nil { 276 return err 277 } 278 pass := "" 279 if passphrase != nil { 280 pass = *passphrase 281 } 282 return wallet.Open(pass) 283 } 284 285 // DeriveAccount requests a HD wallet to derive a new account, optionally pinning 286 // it for later reuse. 287 func (s *PrivateAccountAPI) DeriveAccount(url string, path string, pin *bool) (accounts.Account, error) { 288 wallet, err := s.am.Wallet(url) 289 if err != nil { 290 return accounts.Account{}, err 291 } 292 derivPath, err := accounts.ParseDerivationPath(path) 293 if err != nil { 294 return accounts.Account{}, err 295 } 296 if pin == nil { 297 pin = new(bool) 298 } 299 return wallet.Derive(derivPath, *pin) 300 } 301 302 // NewAccount will create a new account and returns the address for the new account. 303 func (s *PrivateAccountAPI) NewAccount(password string) (string, error) { 304 acc, err := fetchKeystore(s.am).NewAccount(password) 305 if err == nil { 306 return acc.Address.String(), nil // modified address format as string of newAccount 307 } 308 return "", err 309 } 310 311 // fetchKeystore retrives the encrypted keystore from the account manager. 312 func fetchKeystore(am *accounts.Manager) *keystore.KeyStore { 313 return am.Backends(keystore.KeyStoreType)[0].(*keystore.KeyStore) 314 } 315 316 // ImportRawKey stores the given hex encoded ECDSA key into the key directory, 317 // encrypting it with the passphrase. 318 func (s *PrivateAccountAPI) ImportRawKey(privkey string, password string) (string, error) { 319 key, err := crypto.HexToECDSA(privkey) 320 if err != nil { 321 return "", err 322 } 323 acc, err := fetchKeystore(s.am).ImportECDSA(key, password) 324 return acc.Address.String(), err 325 } 326 327 // UnlockAccount will unlock the account associated with the given address with 328 // the given password for duration seconds. If duration is nil it will use a 329 // default of 300 seconds. It returns an indication if the account was unlocked. 330 func (s *PrivateAccountAPI) UnlockAccount(addr common.Address, password string, duration *uint64) (bool, error) { 331 const max = uint64(time.Duration(math.MaxInt64) / time.Second) 332 var d time.Duration 333 if duration == nil { 334 d = 300 * time.Second 335 } else if *duration > max { 336 return false, errors.New("unlock duration too large") 337 } else { 338 d = time.Duration(*duration) * time.Second 339 } 340 err := fetchKeystore(s.am).TimedUnlock(accounts.Account{Address: addr}, password, d) 341 return err == nil, err 342 } 343 344 // LockAccount will lock the account associated with the given address when it's unlocked. 345 func (s *PrivateAccountAPI) LockAccount(addr common.Address) bool { 346 return fetchKeystore(s.am).Lock(addr) == nil 347 } 348 349 // signTransactions sets defaults and signs the given transaction 350 // NOTE: the caller needs to ensure that the nonceLock is held, if applicable, 351 // and release it after the transaction has been submitted to the tx pool 352 func (s *PrivateAccountAPI) signTransaction(ctx context.Context, args SendTxArgs, passwd string) (*types.Transaction, error) { 353 // Look up the wallet containing the requested signer 354 account := accounts.Account{Address: args.From} 355 wallet, err := s.am.Find(account) 356 if err != nil { 357 return nil, err 358 } 359 // Set some sanity defaults and terminate on failure 360 if err := args.setDefaults(ctx, s.b); err != nil { 361 return nil, err 362 } 363 // Assemble the transaction and sign with the wallet 364 tx := args.toTransaction() 365 366 var chainID *big.Int 367 if config := s.b.ChainConfig(); config.IsEIP155(s.b.CurrentBlock().Number()) { 368 chainID = config.ChainId 369 } 370 return wallet.SignTxWithPassphrase(account, passwd, tx, chainID) 371 } 372 373 // SendTransaction will create a transaction from the given arguments and 374 // tries to sign it with the key associated with args.To. If the given passwd isn't 375 // able to decrypt the key it fails. 376 func (s *PrivateAccountAPI) SendTransaction(ctx context.Context, args SendTxArgs, passwd string) (common.Hash, error) { 377 fmt.Printf("transaction args PrivateAccountAPI args %v\n", args) 378 if args.Nonce == nil { 379 // Hold the addresse's mutex around signing to prevent concurrent assignment of 380 // the same nonce to multiple accounts. 381 s.nonceLock.LockAddr(args.From) 382 defer s.nonceLock.UnlockAddr(args.From) 383 } 384 signed, err := s.signTransaction(ctx, args, passwd) 385 if err != nil { 386 return common.Hash{}, err 387 } 388 return submitTransaction(ctx, s.b, signed) 389 } 390 391 // SignTransaction will create a transaction from the given arguments and 392 // tries to sign it with the key associated with args.To. If the given passwd isn't 393 // able to decrypt the key it fails. The transaction is returned in RLP-form, not broadcast 394 // to other nodes 395 func (s *PrivateAccountAPI) SignTransaction(ctx context.Context, args SendTxArgs, passwd string) (*SignTransactionResult, error) { 396 // No need to obtain the noncelock mutex, since we won't be sending this 397 // tx into the transaction pool, but right back to the user 398 if args.Gas == nil { 399 return nil, fmt.Errorf("gas not specified") 400 } 401 if args.GasPrice == nil { 402 return nil, fmt.Errorf("gasPrice not specified") 403 } 404 if args.Nonce == nil { 405 return nil, fmt.Errorf("nonce not specified") 406 } 407 signed, err := s.signTransaction(ctx, args, passwd) 408 if err != nil { 409 return nil, err 410 } 411 data, err := rlp.EncodeToBytes(signed) 412 if err != nil { 413 return nil, err 414 } 415 return &SignTransactionResult{data, signed}, nil 416 } 417 418 // signHash is a helper function that calculates a hash for the given message that can be 419 // safely used to calculate a signature from. 420 // 421 // The hash is calulcated as 422 // keccak256("\x19NEAT Chain Signed Message:\n"${message length}${message}). 423 // 424 // This gives context to the signed message and prevents signing of transactions. 425 func signHash(data []byte) []byte { 426 msg := fmt.Sprintf("\x19NEAT Chain Signed Message:\n%d%s", len(data), data) 427 return crypto.Keccak256([]byte(msg)) 428 } 429 430 // Sign calculates an NEAT Chain ECDSA signature for: 431 // keccack256("\x19NEAT Chain Signed Message:\n" + len(message) + message)) 432 // 433 // Note, the produced signature conforms to the secp256k1 curve R, S and V values, 434 // where the V value will be 27 or 28 for legacy reasons. 435 // 436 // The key used to calculate the signature is decrypted with the given password. 437 // 438 // https://github.com/Gessiux/neatchain/wiki/Management-APIs#personal_sign 439 func (s *PrivateAccountAPI) Sign(ctx context.Context, data hexutil.Bytes, addr common.Address, passwd string) (hexutil.Bytes, error) { 440 // Look up the wallet containing the requested signer 441 account := accounts.Account{Address: addr} 442 443 wallet, err := s.b.AccountManager().Find(account) 444 if err != nil { 445 return nil, err 446 } 447 // Assemble sign the data with the wallet 448 signature, err := wallet.SignHashWithPassphrase(account, passwd, signHash(data)) 449 if err != nil { 450 return nil, err 451 } 452 signature[64] += 27 // Transform V from 0/1 to 27/28 according to the yellow paper 453 return signature, nil 454 } 455 456 // EcRecover returns the address for the account that was used to create the signature. 457 // Note, this function is compatible with eth_sign and personal_sign. As such it recovers 458 // the address of: 459 // hash = keccak256("\x19NEAT Chain Signed Message:\n"${message length}${message}) 460 // addr = ecrecover(hash, signature) 461 // 462 // Note, the signature must conform to the secp256k1 curve R, S and V values, where 463 // the V value must be 27 or 28 for legacy reasons. 464 // 465 // https://github.com/Gessiux/neatchain/wiki/Management-APIs#personal_ecRecover 466 func (s *PrivateAccountAPI) EcRecover(ctx context.Context, data, sig hexutil.Bytes) (string, error) { 467 if len(sig) != 65 { 468 return "", fmt.Errorf("signature must be 65 bytes long") 469 } 470 if sig[64] != 27 && sig[64] != 28 { 471 return "", fmt.Errorf("invalid NEAT Chain signature (V is not 27 or 28)") 472 } 473 sig[64] -= 27 // Transform yellow paper V from 27/28 to 0/1 474 475 rpk, err := crypto.SigToPub(signHash(data), sig) 476 if err != nil { 477 return "", err 478 } 479 return crypto.PubkeyToAddress(*rpk).String(), nil 480 } 481 482 // SignAndSendTransaction was renamed to SendTransaction. This method is deprecated 483 // and will be removed in the future. It primary goal is to give clients time to update. 484 func (s *PrivateAccountAPI) SignAndSendTransaction(ctx context.Context, args SendTxArgs, passwd string) (common.Hash, error) { 485 return s.SendTransaction(ctx, args, passwd) 486 } 487 488 // PublicBlockChainAPI provides an API to access the NEAT blockchain. 489 // It offers only methods that operate on public data that is freely available to anyone. 490 type PublicBlockChainAPI struct { 491 b Backend 492 } 493 494 // NewPublicBlockChainAPI creates a new NEAT blockchain API. 495 func NewPublicBlockChainAPI(b Backend) *PublicBlockChainAPI { 496 return &PublicBlockChainAPI{b} 497 } 498 499 // ChainId returns the chainID value for transaction replay protection. 500 func (s *PublicBlockChainAPI) ChainId() *hexutil.Big { 501 return (*hexutil.Big)(s.b.ChainConfig().ChainId) 502 } 503 504 // BlockNumber returns the block number of the chain head. 505 func (s *PublicBlockChainAPI) BlockNumber() hexutil.Uint64 { 506 header, _ := s.b.HeaderByNumber(context.Background(), rpc.LatestBlockNumber) // latest header should always be available 507 return hexutil.Uint64(header.Number.Uint64()) 508 } 509 510 // GetBalance returns the amount of wei for the given address in the state of the 511 // given block number. The rpc.LatestBlockNumber and rpc.PendingBlockNumber meta 512 // block numbers are also allowed. 513 func (s *PublicBlockChainAPI) GetBalance(ctx context.Context, address common.Address, blockNr rpc.BlockNumber) (*hexutil.Big, error) { 514 state, _, err := s.b.StateAndHeaderByNumber(ctx, blockNr) 515 if state == nil || err != nil { 516 return nil, err 517 } 518 return (*hexutil.Big)(state.GetBalance(address)), state.Error() 519 } 520 521 func (s *PublicBlockChainAPI) GetCandidateSetByBlockNumber(ctx context.Context, blockNr rpc.BlockNumber) ([]string, error) { 522 state, _, err := s.b.StateAndHeaderByNumber(ctx, blockNr) 523 if state == nil || err != nil { 524 return nil, err 525 } 526 527 var candidateList = make([]string, 0) 528 529 for addr := range state.GetCandidateSet() { 530 candidateList = append(candidateList, addr.String()) 531 } 532 533 return candidateList, nil 534 } 535 536 // GetBalanceDetail returns the amount of wei for the given address in the state of the 537 // given block number. The rpc.LatestBlockNumber and rpc.PendingBlockNumber meta 538 // block numbers are also allowed. 539 func (s *PublicBlockChainAPI) GetBalanceDetail(ctx context.Context, address common.Address, blockNr rpc.BlockNumber, fullDetail bool) (map[string]interface{}, error) { 540 state, _, err := s.b.StateAndHeaderByNumber(ctx, blockNr) 541 if state == nil || err != nil { 542 return nil, err 543 } 544 545 fields := map[string]interface{}{ 546 "balance": (*hexutil.Big)(state.GetBalance(address)), 547 "depositBalance": (*hexutil.Big)(state.GetDepositBalance(address)), 548 "delegateBalance": (*hexutil.Big)(state.GetDelegateBalance(address)), 549 "proxiedBalance": (*hexutil.Big)(state.GetTotalProxiedBalance(address)), 550 "depositProxiedBalance": (*hexutil.Big)(state.GetTotalDepositProxiedBalance(address)), 551 "pendingRefundBalance": (*hexutil.Big)(state.GetTotalPendingRefundBalance(address)), 552 "rewardBalance": (*hexutil.Big)(state.GetTotalRewardBalance(address)), 553 } 554 555 if fullDetail { 556 proxied_detail := make(map[string]struct { 557 ProxiedBalance *hexutil.Big 558 DepositProxiedBalance *hexutil.Big 559 PendingRefundBalance *hexutil.Big 560 }) 561 state.ForEachProxied(address, func(key common.Address, proxiedBalance, depositProxiedBalance, pendingRefundBalance *big.Int) bool { 562 proxied_detail[key.String()] = struct { 563 ProxiedBalance *hexutil.Big 564 DepositProxiedBalance *hexutil.Big 565 PendingRefundBalance *hexutil.Big 566 }{ 567 ProxiedBalance: (*hexutil.Big)(proxiedBalance), 568 DepositProxiedBalance: (*hexutil.Big)(depositProxiedBalance), 569 PendingRefundBalance: (*hexutil.Big)(pendingRefundBalance), 570 } 571 return true 572 }) 573 574 fields["proxiedDetail"] = proxied_detail 575 576 reward_detail := make(map[string]*hexutil.Big) 577 state.ForEachReward(address, func(key common.Address, rewardBalance *big.Int) bool { 578 reward_detail[key.String()] = (*hexutil.Big)(rewardBalance) 579 return true 580 }) 581 582 fields["rewardDetail"] = reward_detail 583 } 584 return fields, state.Error() 585 } 586 587 type EpochLabel uint64 588 589 func (e EpochLabel) MarshalText() ([]byte, error) { 590 output := fmt.Sprintf("epoch_%d", e) 591 return []byte(output), nil 592 } 593 594 // GetBlockByNumber returns the requested block. When blockNr is -1 the chain head is returned. When fullTx is true all 595 // transactions in the block are returned in full detail, otherwise only the transaction hash is returned. 596 func (s *PublicBlockChainAPI) GetBlockByNumber(ctx context.Context, blockNr rpc.BlockNumber, fullTx bool) (map[string]interface{}, error) { 597 block, err := s.b.BlockByNumber(ctx, blockNr) 598 if block != nil { 599 response, err := s.rpcOutputBlock(block, true, fullTx) 600 if err == nil && blockNr == rpc.PendingBlockNumber { 601 // Pending blocks need to nil out a few fields 602 for _, field := range []string{"hash", "nonce", "miner"} { 603 response[field] = nil 604 } 605 } 606 return response, err 607 } 608 return nil, err 609 } 610 611 // GetBlockByHash returns the requested block. When fullTx is true all transactions in the block are returned in full 612 // detail, otherwise only the transaction hash is returned. 613 func (s *PublicBlockChainAPI) GetBlockByHash(ctx context.Context, blockHash common.Hash, fullTx bool) (map[string]interface{}, error) { 614 block, err := s.b.GetBlock(ctx, blockHash) 615 if block != nil { 616 return s.rpcOutputBlock(block, true, fullTx) 617 } 618 return nil, err 619 } 620 621 // GetUncleByBlockNumberAndIndex returns the uncle block for the given block hash and index. When fullTx is true 622 // all transactions in the block are returned in full detail, otherwise only the transaction hash is returned. 623 func (s *PublicBlockChainAPI) GetUncleByBlockNumberAndIndex(ctx context.Context, blockNr rpc.BlockNumber, index hexutil.Uint) (map[string]interface{}, error) { 624 block, err := s.b.BlockByNumber(ctx, blockNr) 625 if block != nil { 626 uncles := block.Uncles() 627 if index >= hexutil.Uint(len(uncles)) { 628 log.Debug("Requested uncle not found", "number", blockNr, "hash", block.Hash(), "index", index) 629 return nil, nil 630 } 631 block = types.NewBlockWithHeader(uncles[index]) 632 return s.rpcOutputBlock(block, false, false) 633 } 634 return nil, err 635 } 636 637 // GetUncleByBlockHashAndIndex returns the uncle block for the given block hash and index. When fullTx is true 638 // all transactions in the block are returned in full detail, otherwise only the transaction hash is returned. 639 func (s *PublicBlockChainAPI) GetUncleByBlockHashAndIndex(ctx context.Context, blockHash common.Hash, index hexutil.Uint) (map[string]interface{}, error) { 640 block, err := s.b.GetBlock(ctx, blockHash) 641 if block != nil { 642 uncles := block.Uncles() 643 if index >= hexutil.Uint(len(uncles)) { 644 log.Debug("Requested uncle not found", "number", block.Number(), "hash", blockHash, "index", index) 645 return nil, nil 646 } 647 block = types.NewBlockWithHeader(uncles[index]) 648 return s.rpcOutputBlock(block, false, false) 649 } 650 return nil, err 651 } 652 653 // GetUncleCountByBlockNumber returns number of uncles in the block for the given block number 654 func (s *PublicBlockChainAPI) GetUncleCountByBlockNumber(ctx context.Context, blockNr rpc.BlockNumber) *hexutil.Uint { 655 if block, _ := s.b.BlockByNumber(ctx, blockNr); block != nil { 656 n := hexutil.Uint(len(block.Uncles())) 657 return &n 658 } 659 return nil 660 } 661 662 // GetUncleCountByBlockHash returns number of uncles in the block for the given block hash 663 func (s *PublicBlockChainAPI) GetUncleCountByBlockHash(ctx context.Context, blockHash common.Hash) *hexutil.Uint { 664 if block, _ := s.b.GetBlock(ctx, blockHash); block != nil { 665 n := hexutil.Uint(len(block.Uncles())) 666 return &n 667 } 668 return nil 669 } 670 671 // GetCode returns the code stored at the given address in the state for the given block number. 672 func (s *PublicBlockChainAPI) GetCode(ctx context.Context, address common.Address, blockNr rpc.BlockNumber) (hexutil.Bytes, error) { 673 state, _, err := s.b.StateAndHeaderByNumber(ctx, blockNr) 674 if state == nil || err != nil { 675 return nil, err 676 } 677 code := state.GetCode(address) 678 return code, state.Error() 679 } 680 681 // GetStorageAt returns the storage from the state at the given address, key and 682 // block number. The rpc.LatestBlockNumber and rpc.PendingBlockNumber meta block 683 // numbers are also allowed. 684 func (s *PublicBlockChainAPI) GetStorageAt(ctx context.Context, address common.Address, key string, blockNr rpc.BlockNumber) (hexutil.Bytes, error) { 685 state, _, err := s.b.StateAndHeaderByNumber(ctx, blockNr) 686 if state == nil || err != nil { 687 return nil, err 688 } 689 res := state.GetState(address, common.HexToHash(key)) 690 return res[:], state.Error() 691 } 692 693 // CallArgs represents the arguments for a call. 694 type CallArgs struct { 695 From common.Address `json:"from"` 696 To *common.Address `json:"to"` 697 Gas hexutil.Uint64 `json:"gas"` 698 GasPrice hexutil.Big `json:"gasPrice"` 699 Value hexutil.Big `json:"value"` 700 Data hexutil.Bytes `json:"data"` 701 } 702 703 func (s *PublicBlockChainAPI) doCall(ctx context.Context, args CallArgs, blockNr rpc.BlockNumber, vmCfg vm.Config, timeout time.Duration) ([]byte, uint64, bool, error) { 704 defer func(start time.Time) { log.Debug("Executing EVM call finished", "runtime", time.Since(start)) }(time.Now()) 705 706 state, header, err := s.b.StateAndHeaderByNumber(ctx, blockNr) 707 if state == nil || err != nil { 708 return nil, 0, false, err 709 } 710 // Set sender address or use a default if none specified 711 addr := args.From 712 if addr == (common.Address{}) { 713 if wallets := s.b.AccountManager().Wallets(); len(wallets) > 0 { 714 if accounts := wallets[0].Accounts(); len(accounts) > 0 { 715 addr = accounts[0].Address 716 } 717 } 718 } 719 // Set default gas & gas price if none were set 720 gas, gasPrice := uint64(args.Gas), args.GasPrice.ToInt() 721 if gas == 0 { 722 gas = math.MaxUint64 / 2 723 } 724 if gasPrice.Sign() == 0 { 725 gasPrice = new(big.Int).SetUint64(defaultGasPrice) 726 } 727 728 // Create new call message 729 msg := types.NewMessage(addr, args.To, 0, args.Value.ToInt(), gas, gasPrice, args.Data, false) 730 731 // Setup context so it may be cancelled the call has completed 732 // or, in case of unmetered gas, setup a context with a timeout. 733 var cancel context.CancelFunc 734 if timeout > 0 { 735 ctx, cancel = context.WithTimeout(ctx, timeout) 736 } else { 737 ctx, cancel = context.WithCancel(ctx) 738 } 739 // Make sure the context is cancelled when the call has completed 740 // this makes sure resources are cleaned up. 741 defer cancel() 742 743 // Get a new instance of the EVM. 744 evm, vmError, err := s.b.GetEVM(ctx, msg, state, header, vmCfg) 745 if err != nil { 746 return nil, 0, false, err 747 } 748 // Wait for the context to be done and cancel the evm. Even if the 749 // EVM has finished, cancelling may be done (repeatedly) 750 go func() { 751 <-ctx.Done() 752 evm.Cancel() 753 }() 754 755 // Setup the gas pool (also for unmetered requests) 756 // and apply the message. 757 gp := new(core.GasPool).AddGas(math.MaxUint64) 758 res, gas, failed, err := core.ApplyMessage(evm, msg, gp) 759 if err := vmError(); err != nil { 760 return nil, 0, false, err 761 } 762 return res, gas, failed, err 763 } 764 765 // Call executes the given transaction on the state for the given block number. 766 // It doesn't make and changes in the state/blockchain and is useful to execute and retrieve values. 767 func (s *PublicBlockChainAPI) Call(ctx context.Context, args CallArgs, blockNr rpc.BlockNumber) (hexutil.Bytes, error) { 768 result, _, _, err := s.doCall(ctx, args, blockNr, vm.Config{}, 5*time.Second) 769 return (hexutil.Bytes)(result), err 770 } 771 772 // EstimateGas returns an estimate of the amount of gas needed to execute the 773 // given transaction against the current pending block. 774 func (s *PublicBlockChainAPI) EstimateGas(ctx context.Context, args CallArgs) (hexutil.Uint64, error) { 775 fmt.Printf("+++++++++++++++++++++++++++++++++++++++++++++estimate gas %v\n", args) 776 // Binary search the gas requirement, as it may be higher than the amount used 777 var ( 778 lo uint64 = params.TxGas - 1 779 hi uint64 780 cap uint64 781 ) 782 if uint64(args.Gas) >= params.TxGas { 783 hi = uint64(args.Gas) 784 } else { 785 // Retrieve the current pending block to act as the gas ceiling 786 block, err := s.b.BlockByNumber(ctx, rpc.PendingBlockNumber) 787 if err != nil { 788 return 0, err 789 } 790 hi = block.GasLimit() 791 } 792 cap = hi 793 794 // Create a helper to check if a gas allowance results in an executable transaction 795 executable := func(gas uint64) bool { 796 args.Gas = hexutil.Uint64(gas) 797 798 _, _, failed, err := s.doCall(ctx, args, rpc.PendingBlockNumber, vm.Config{}, 0) 799 if err != nil || failed { 800 return false 801 } 802 return true 803 } 804 // Execute the binary search and hone in on an executable gas limit 805 for lo+1 < hi { 806 mid := (hi + lo) / 2 807 if !executable(mid) { 808 lo = mid 809 } else { 810 hi = mid 811 } 812 } 813 // Reject the transaction as invalid if it still fails at the highest allowance 814 if hi == cap { 815 if !executable(hi) { 816 return 0, fmt.Errorf("gas required exceeds allowance or always failing transaction") 817 } 818 } 819 return hexutil.Uint64(hi), nil 820 } 821 822 // ExecutionResult groups all structured logs emitted by the EVM 823 // while replaying a transaction in debug mode as well as transaction 824 // execution status, the amount of gas used and the return value 825 type ExecutionResult struct { 826 Gas uint64 `json:"gas"` 827 Failed bool `json:"failed"` 828 ReturnValue string `json:"returnValue"` 829 StructLogs []StructLogRes `json:"structLogs"` 830 } 831 832 // StructLogRes stores a structured log emitted by the EVM while replaying a 833 // transaction in debug mode 834 type StructLogRes struct { 835 Pc uint64 `json:"pc"` 836 Op string `json:"op"` 837 Gas uint64 `json:"gas"` 838 GasCost uint64 `json:"gasCost"` 839 Depth int `json:"depth"` 840 Error error `json:"error,omitempty"` 841 Stack *[]string `json:"stack,omitempty"` 842 Memory *[]string `json:"memory,omitempty"` 843 Storage *map[string]string `json:"storage,omitempty"` 844 } 845 846 // formatLogs formats EVM returned structured logs for json output 847 func FormatLogs(logs []vm.StructLog) []StructLogRes { 848 formatted := make([]StructLogRes, len(logs)) 849 for index, trace := range logs { 850 formatted[index] = StructLogRes{ 851 Pc: trace.Pc, 852 Op: trace.Op.String(), 853 Gas: trace.Gas, 854 GasCost: trace.GasCost, 855 Depth: trace.Depth, 856 Error: trace.Err, 857 } 858 if trace.Stack != nil { 859 stack := make([]string, len(trace.Stack)) 860 for i, stackValue := range trace.Stack { 861 stack[i] = fmt.Sprintf("%x", math.PaddedBigBytes(stackValue, 32)) 862 } 863 formatted[index].Stack = &stack 864 } 865 if trace.Memory != nil { 866 memory := make([]string, 0, (len(trace.Memory)+31)/32) 867 for i := 0; i+32 <= len(trace.Memory); i += 32 { 868 memory = append(memory, fmt.Sprintf("%x", trace.Memory[i:i+32])) 869 } 870 formatted[index].Memory = &memory 871 } 872 if trace.Storage != nil { 873 storage := make(map[string]string) 874 for i, storageValue := range trace.Storage { 875 storage[fmt.Sprintf("%x", i)] = fmt.Sprintf("%x", storageValue) 876 } 877 formatted[index].Storage = &storage 878 } 879 } 880 return formatted 881 } 882 883 // rpcOutputBlock converts the given block to the RPC output which depends on fullTx. If inclTx is true transactions are 884 // returned. When fullTx is true the returned block contains full transaction details, otherwise it will only contain 885 // transaction hashes. 886 func (s *PublicBlockChainAPI) rpcOutputBlock(b *types.Block, inclTx bool, fullTx bool) (map[string]interface{}, error) { 887 head := b.Header() // copies the header once 888 fields := map[string]interface{}{ 889 "number": (*hexutil.Big)(head.Number), 890 "mainchainNumber": (*hexutil.Big)(head.MainChainNumber), 891 "hash": b.Hash(), 892 "parentHash": head.ParentHash, 893 "nonce": head.Nonce, 894 "mixHash": head.MixDigest, 895 "sha3Uncles": head.UncleHash, 896 "logsBloom": head.Bloom, 897 "stateRoot": head.Root, 898 "miner": head.Coinbase.String(), // modified as string 899 "difficulty": (*hexutil.Big)(head.Difficulty), 900 "totalDifficulty": (*hexutil.Big)(s.b.GetTd(b.Hash())), 901 "extraData": hexutil.Bytes(head.Extra), 902 "size": hexutil.Uint64(b.Size()), 903 "gasLimit": hexutil.Uint64(head.GasLimit), 904 "gasUsed": hexutil.Uint64(head.GasUsed), 905 "timestamp": (*hexutil.Big)(head.Time), 906 "transactionsRoot": head.TxHash, 907 "receiptsRoot": head.ReceiptHash, 908 } 909 910 if inclTx { 911 formatTx := func(tx *types.Transaction) (interface{}, error) { 912 return tx.Hash(), nil 913 } 914 915 if fullTx { 916 formatTx = func(tx *types.Transaction) (interface{}, error) { 917 return newRPCTransactionFromBlockHash(b, tx.Hash()), nil 918 } 919 } 920 921 txs := b.Transactions() 922 transactions := make([]interface{}, len(txs)) 923 var err error 924 for i, tx := range b.Transactions() { 925 if transactions[i], err = formatTx(tx); err != nil { 926 return nil, err 927 } 928 } 929 fields["transactions"] = transactions 930 } 931 932 uncles := b.Uncles() 933 uncleHashes := make([]common.Hash, len(uncles)) 934 for i, uncle := range uncles { 935 uncleHashes[i] = uncle.Hash() 936 } 937 fields["uncles"] = uncleHashes 938 939 return fields, nil 940 } 941 942 // RPCTransaction represents a transaction that will serialize to the RPC representation of a transaction 943 type RPCTransaction struct { 944 BlockHash common.Hash `json:"blockHash"` 945 BlockNumber *hexutil.Big `json:"blockNumber"` 946 From string `json:"from"` 947 Gas hexutil.Uint64 `json:"gas"` 948 GasPrice *hexutil.Big `json:"gasPrice"` 949 Hash common.Hash `json:"hash"` 950 Input hexutil.Bytes `json:"input"` 951 Nonce hexutil.Uint64 `json:"nonce"` 952 //To *common.Address `json:"to"` 953 To interface{} `json:"to"` 954 TransactionIndex hexutil.Uint `json:"transactionIndex"` 955 Value *hexutil.Big `json:"value"` 956 V *hexutil.Big `json:"v"` 957 R *hexutil.Big `json:"r"` 958 S *hexutil.Big `json:"s"` 959 } 960 961 // newRPCTransaction returns a transaction that will serialize to the RPC 962 // representation, with the given location metadata set (if available). 963 func newRPCTransaction(tx *types.Transaction, blockHash common.Hash, blockNumber uint64, index uint64) *RPCTransaction { 964 var signer types.Signer = types.FrontierSigner{} 965 if tx.Protected() { 966 signer = types.NewEIP155Signer(tx.ChainId()) 967 } 968 from, _ := types.Sender(signer, tx) 969 970 var to interface{} 971 if tx.To() == nil { 972 to = nil 973 } else { 974 to = tx.To().String() 975 } 976 977 v, r, s := tx.RawSignatureValues() 978 result := &RPCTransaction{ 979 From: from.String(), 980 Gas: hexutil.Uint64(tx.Gas()), 981 GasPrice: (*hexutil.Big)(tx.GasPrice()), 982 Hash: tx.Hash(), 983 Input: hexutil.Bytes(tx.Data()), 984 Nonce: hexutil.Uint64(tx.Nonce()), 985 To: to, 986 Value: (*hexutil.Big)(tx.Value()), 987 V: (*hexutil.Big)(v), 988 R: (*hexutil.Big)(r), 989 S: (*hexutil.Big)(s), 990 } 991 if blockHash != (common.Hash{}) { 992 result.BlockHash = blockHash 993 result.BlockNumber = (*hexutil.Big)(new(big.Int).SetUint64(blockNumber)) 994 result.TransactionIndex = hexutil.Uint(index) 995 } 996 return result 997 } 998 999 // newRPCPendingTransaction returns a pending transaction that will serialize to the RPC representation 1000 func newRPCPendingTransaction(tx *types.Transaction) *RPCTransaction { 1001 return newRPCTransaction(tx, common.Hash{}, 0, 0) 1002 } 1003 1004 // newRPCTransactionFromBlockIndex returns a transaction that will serialize to the RPC representation. 1005 func newRPCTransactionFromBlockIndex(b *types.Block, index uint64) *RPCTransaction { 1006 txs := b.Transactions() 1007 if index >= uint64(len(txs)) { 1008 return nil 1009 } 1010 return newRPCTransaction(txs[index], b.Hash(), b.NumberU64(), index) 1011 } 1012 1013 // newRPCRawTransactionFromBlockIndex returns the bytes of a transaction given a block and a transaction index. 1014 func newRPCRawTransactionFromBlockIndex(b *types.Block, index uint64) hexutil.Bytes { 1015 txs := b.Transactions() 1016 if index >= uint64(len(txs)) { 1017 return nil 1018 } 1019 blob, _ := rlp.EncodeToBytes(txs[index]) 1020 return blob 1021 } 1022 1023 // newRPCTransactionFromBlockHash returns a transaction that will serialize to the RPC representation. 1024 func newRPCTransactionFromBlockHash(b *types.Block, hash common.Hash) *RPCTransaction { 1025 for idx, tx := range b.Transactions() { 1026 if tx.Hash() == hash { 1027 return newRPCTransactionFromBlockIndex(b, uint64(idx)) 1028 } 1029 } 1030 return nil 1031 } 1032 1033 // PublicTransactionPoolAPI exposes methods for the RPC interface 1034 type PublicTransactionPoolAPI struct { 1035 b Backend 1036 nonceLock *AddrLocker 1037 } 1038 1039 // NewPublicTransactionPoolAPI creates a new RPC service with methods specific for the transaction pool. 1040 func NewPublicTransactionPoolAPI(b Backend, nonceLock *AddrLocker) *PublicTransactionPoolAPI { 1041 return &PublicTransactionPoolAPI{b, nonceLock} 1042 } 1043 1044 // GetBlockTransactionCountByNumber returns the number of transactions in the block with the given block number. 1045 func (s *PublicTransactionPoolAPI) GetBlockTransactionCountByNumber(ctx context.Context, blockNr rpc.BlockNumber) *hexutil.Uint { 1046 if block, _ := s.b.BlockByNumber(ctx, blockNr); block != nil { 1047 n := hexutil.Uint(len(block.Transactions())) 1048 return &n 1049 } 1050 return nil 1051 } 1052 1053 // GetBlockTransactionCountByHash returns the number of transactions in the block with the given hash. 1054 func (s *PublicTransactionPoolAPI) GetBlockTransactionCountByHash(ctx context.Context, blockHash common.Hash) *hexutil.Uint { 1055 if block, _ := s.b.GetBlock(ctx, blockHash); block != nil { 1056 n := hexutil.Uint(len(block.Transactions())) 1057 return &n 1058 } 1059 return nil 1060 } 1061 1062 // GetTransactionByBlockNumberAndIndex returns the transaction for the given block number and index. 1063 func (s *PublicTransactionPoolAPI) GetTransactionByBlockNumberAndIndex(ctx context.Context, blockNr rpc.BlockNumber, index hexutil.Uint) *RPCTransaction { 1064 if block, _ := s.b.BlockByNumber(ctx, blockNr); block != nil { 1065 return newRPCTransactionFromBlockIndex(block, uint64(index)) 1066 } 1067 return nil 1068 } 1069 1070 // GetTransactionByBlockHashAndIndex returns the transaction for the given block hash and index. 1071 func (s *PublicTransactionPoolAPI) GetTransactionByBlockHashAndIndex(ctx context.Context, blockHash common.Hash, index hexutil.Uint) *RPCTransaction { 1072 if block, _ := s.b.GetBlock(ctx, blockHash); block != nil { 1073 return newRPCTransactionFromBlockIndex(block, uint64(index)) 1074 } 1075 return nil 1076 } 1077 1078 // GetRawTransactionByBlockNumberAndIndex returns the bytes of the transaction for the given block number and index. 1079 func (s *PublicTransactionPoolAPI) GetRawTransactionByBlockNumberAndIndex(ctx context.Context, blockNr rpc.BlockNumber, index hexutil.Uint) hexutil.Bytes { 1080 if block, _ := s.b.BlockByNumber(ctx, blockNr); block != nil { 1081 return newRPCRawTransactionFromBlockIndex(block, uint64(index)) 1082 } 1083 return nil 1084 } 1085 1086 // GetRawTransactionByBlockHashAndIndex returns the bytes of the transaction for the given block hash and index. 1087 func (s *PublicTransactionPoolAPI) GetRawTransactionByBlockHashAndIndex(ctx context.Context, blockHash common.Hash, index hexutil.Uint) hexutil.Bytes { 1088 if block, _ := s.b.GetBlock(ctx, blockHash); block != nil { 1089 return newRPCRawTransactionFromBlockIndex(block, uint64(index)) 1090 } 1091 return nil 1092 } 1093 1094 // GetTransactionCount returns the number of transactions the given address has sent for the given block number 1095 func (s *PublicTransactionPoolAPI) GetTransactionCount(ctx context.Context, address common.Address, blockNr rpc.BlockNumber) (*hexutil.Uint64, error) { 1096 state, _, err := s.b.StateAndHeaderByNumber(ctx, blockNr) 1097 if state == nil || err != nil { 1098 return nil, err 1099 } 1100 nonce := state.GetNonce(address) 1101 return (*hexutil.Uint64)(&nonce), state.Error() 1102 } 1103 1104 // GetTransactionByHash returns the transaction for the given hash 1105 func (s *PublicTransactionPoolAPI) GetTransactionByHash(ctx context.Context, hash common.Hash) *RPCTransaction { 1106 // Try to return an already finalized transaction 1107 if tx, blockHash, blockNumber, index := rawdb.ReadTransaction(s.b.ChainDb(), hash); tx != nil { 1108 return newRPCTransaction(tx, blockHash, blockNumber, index) 1109 } 1110 // No finalized transaction, try to retrieve it from the pool 1111 if tx := s.b.GetPoolTransaction(hash); tx != nil { 1112 return newRPCPendingTransaction(tx) 1113 } 1114 // Transaction unknown, return as such 1115 return nil 1116 } 1117 1118 // GetRawTransactionByHash returns the bytes of the transaction for the given hash. 1119 func (s *PublicTransactionPoolAPI) GetRawTransactionByHash(ctx context.Context, hash common.Hash) (hexutil.Bytes, error) { 1120 var tx *types.Transaction 1121 1122 // Retrieve a finalized transaction, or a pooled otherwise 1123 if tx, _, _, _ = rawdb.ReadTransaction(s.b.ChainDb(), hash); tx == nil { 1124 if tx = s.b.GetPoolTransaction(hash); tx == nil { 1125 // Transaction not found anywhere, abort 1126 return nil, nil 1127 } 1128 } 1129 // Serialize to RLP and return 1130 return rlp.EncodeToBytes(tx) 1131 } 1132 1133 type Log struct { 1134 // Consensus fields: 1135 // address of the contract that generated the event 1136 Address string `json:"address" gencodec:"required"` 1137 // list of topics provided by the contract. 1138 Topics []common.Hash `json:"topics" gencodec:"required"` 1139 // supplied by the contract, usually ABI-encoded 1140 Data string `json:"data" gencodec:"required"` 1141 1142 // Derived fields. These fields are filled in by the node 1143 // but not secured by consensus. 1144 // block in which the transaction was included 1145 BlockNumber uint64 `json:"blockNumber"` 1146 // hash of the transaction 1147 TxHash common.Hash `json:"transactionHash" gencodec:"required"` 1148 // index of the transaction in the block 1149 TxIndex uint `json:"transactionIndex" gencodec:"required"` 1150 // hash of the block in which the transaction was included 1151 BlockHash common.Hash `json:"blockHash"` 1152 // index of the log in the receipt 1153 Index uint `json:"logIndex" gencodec:"required"` 1154 1155 // The Removed field is true if this log was reverted due to a chain reorganisation. 1156 // You must pay attention to this field if you receive logs through a filter query. 1157 Removed bool `json:"removed"` 1158 } 1159 1160 // GetTransactionReceipt returns the transaction receipt for the given transaction hash. 1161 func (s *PublicTransactionPoolAPI) GetTransactionReceipt(ctx context.Context, hash common.Hash) (map[string]interface{}, error) { 1162 tx, blockHash, blockNumber, index := rawdb.ReadTransaction(s.b.ChainDb(), hash) 1163 if tx == nil { 1164 return nil, nil 1165 } 1166 receipts, err := s.b.GetReceipts(ctx, blockHash) 1167 if err != nil { 1168 return nil, err 1169 } 1170 if len(receipts) <= int(index) { 1171 return nil, nil 1172 } 1173 receipt := receipts[index] 1174 1175 var signer types.Signer = types.FrontierSigner{} 1176 if tx.Protected() { 1177 signer = types.NewEIP155Signer(tx.ChainId()) 1178 } 1179 from, _ := types.Sender(signer, tx) 1180 var to interface{} 1181 if tx.To() == nil { 1182 to = nil 1183 } else { 1184 to = tx.To().String() 1185 } 1186 1187 fields := map[string]interface{}{ 1188 "blockHash": blockHash, 1189 "blockNumber": hexutil.Uint64(blockNumber), 1190 "transactionHash": hash, 1191 "transactionIndex": hexutil.Uint64(index), 1192 "from": from.String(), 1193 "to": to, 1194 "gasUsed": hexutil.Uint64(receipt.GasUsed), 1195 "cumulativeGasUsed": hexutil.Uint64(receipt.CumulativeGasUsed), 1196 "contractAddress": nil, 1197 "logs": receipt.Logs, 1198 "logsBloom": receipt.Bloom, 1199 } 1200 1201 // Assign receipt status or post state. 1202 if len(receipt.PostState) > 0 { 1203 fields["root"] = hexutil.Bytes(receipt.PostState) 1204 } else { 1205 fields["status"] = hexutil.Uint(receipt.Status) 1206 } 1207 if receipt.Logs == nil { 1208 fields["logs"] = [][]*types.Log{} 1209 } else { 1210 var log []*Log 1211 for _, l := range receipt.Logs { 1212 newLog := &Log{ 1213 Address: l.Address.String(), 1214 Topics: l.Topics, 1215 Data: hexutil.Encode(l.Data), 1216 BlockNumber: l.BlockNumber, 1217 TxHash: l.TxHash, 1218 TxIndex: l.TxIndex, 1219 BlockHash: l.BlockHash, 1220 Index: l.Index, 1221 Removed: l.Removed, 1222 } 1223 log = append(log, newLog) 1224 } 1225 fields["logs"] = log 1226 } 1227 1228 // If the ContractAddress is 32 0x0 bytes, assume it is not a contract creation 1229 if receipt.ContractAddress != (common.Address{}) { 1230 fields["contractAddress"] = receipt.ContractAddress.String() 1231 } 1232 return fields, nil 1233 } 1234 1235 // sign is a helper function that signs a transaction with the private key of the given address. 1236 func (s *PublicTransactionPoolAPI) sign(addr common.Address, tx *types.Transaction) (*types.Transaction, error) { 1237 // Look up the wallet containing the requested signer 1238 account := accounts.Account{Address: addr} 1239 1240 wallet, err := s.b.AccountManager().Find(account) 1241 if err != nil { 1242 return nil, err 1243 } 1244 // Request the wallet to sign the transaction 1245 var chainID *big.Int 1246 if config := s.b.ChainConfig(); config.IsEIP155(s.b.CurrentBlock().Number()) { 1247 chainID = config.ChainId 1248 } 1249 return wallet.SignTxWithAddress(account, tx, chainID) 1250 } 1251 1252 // SendTxArgs represents the arguments to sumbit a new transaction into the transaction pool. 1253 type SendTxArgs struct { 1254 From common.Address `json:"from"` 1255 To *common.Address `json:"to"` 1256 Gas *hexutil.Uint64 `json:"gas"` 1257 GasPrice *hexutil.Big `json:"gasPrice"` 1258 Value *hexutil.Big `json:"value"` 1259 Nonce *hexutil.Uint64 `json:"nonce"` 1260 // We accept "data" and "input" for backwards-compatibility reasons. "input" is the 1261 // newer name and should be preferred by clients. 1262 Data *hexutil.Bytes `json:"data"` 1263 Input *hexutil.Bytes `json:"input"` 1264 } 1265 1266 // setDefaults is a helper function that fills in default values for unspecified tx fields. 1267 func (args *SendTxArgs) setDefaults(ctx context.Context, b Backend) error { 1268 1269 var function = neatAbi.Unknown 1270 if neatAbi.IsNeatChainContractAddr(args.To) { 1271 var input []byte 1272 if args.Data != nil { 1273 input = *args.Data 1274 } else if args.Input != nil { 1275 input = *args.Input 1276 } 1277 if len(input) == 0 { 1278 return errors.New(`neatchain contract without any data provided`) 1279 } 1280 1281 var err error 1282 function, err = neatAbi.FunctionTypeFromId(input[:4]) 1283 if err != nil { 1284 return err 1285 } 1286 } 1287 1288 // force GasLimit to 0 for DepositInSideChain/WithdrawFromMainChain/SaveDataToMainChain in order to avoid being dropped by TxPool. 1289 if function == neatAbi.DepositInSideChain || function == neatAbi.WithdrawFromMainChain || function == neatAbi.SaveDataToMainChain { 1290 args.Gas = new(hexutil.Uint64) 1291 *(*uint64)(args.Gas) = 0 1292 } else { 1293 if args.Gas == nil { 1294 args.Gas = new(hexutil.Uint64) 1295 *(*uint64)(args.Gas) = 90000 1296 } 1297 } 1298 1299 if args.GasPrice == nil { 1300 price, err := b.SuggestPrice(ctx) 1301 if err != nil { 1302 return err 1303 } 1304 args.GasPrice = (*hexutil.Big)(price) 1305 } 1306 if args.Value == nil { 1307 args.Value = new(hexutil.Big) 1308 } 1309 if args.Data != nil && args.Input != nil && !bytes.Equal(*args.Data, *args.Input) { 1310 return errors.New(`Both "data" and "input" are set and not equal. Please use "input" to pass transaction call data.`) 1311 } 1312 if args.To == nil { 1313 // Contract creation 1314 var input []byte 1315 if args.Data != nil { 1316 input = *args.Data 1317 } else if args.Input != nil { 1318 input = *args.Input 1319 } 1320 if len(input) == 0 { 1321 return errors.New(`contract creation without any data provided`) 1322 } 1323 } else if !crypto.ValidateNEATAddr(string(args.To[:])) { // added on 2019年11月02日 1324 return errors.New(`invalid address`) 1325 } 1326 1327 if args.Nonce == nil { 1328 nonce, err := b.GetPoolNonce(ctx, args.From) 1329 if err != nil { 1330 return err 1331 } 1332 args.Nonce = (*hexutil.Uint64)(&nonce) 1333 } 1334 1335 return nil 1336 } 1337 1338 func (args *SendTxArgs) toTransaction() *types.Transaction { 1339 var input []byte 1340 if args.Data != nil { 1341 input = *args.Data 1342 } else if args.Input != nil { 1343 input = *args.Input 1344 } 1345 if args.To == nil { 1346 return types.NewContractCreation(uint64(*args.Nonce), (*big.Int)(args.Value), uint64(*args.Gas), (*big.Int)(args.GasPrice), input) 1347 } 1348 return types.NewTransaction(uint64(*args.Nonce), *args.To, (*big.Int)(args.Value), uint64(*args.Gas), (*big.Int)(args.GasPrice), input) 1349 } 1350 1351 // submitTransaction is a helper function that submits tx to txPool and logs a message. 1352 func submitTransaction(ctx context.Context, b Backend, tx *types.Transaction) (common.Hash, error) { 1353 if err := b.SendTx(ctx, tx); err != nil { 1354 return common.Hash{}, err 1355 } 1356 if tx.To() == nil { 1357 signer := types.MakeSigner(b.ChainConfig(), b.CurrentBlock().Number()) 1358 from, err := types.Sender(signer, tx) 1359 if err != nil { 1360 return common.Hash{}, err 1361 } 1362 addr := crypto.CreateAddress(from, tx.Nonce()) 1363 //log.Info("Submitted contract creation", "fullhash", tx.Hash().Hex(), "contract", addr.Hex()) 1364 log.Info("Submitted contract creation", "fullhash", tx.Hash().Hex(), "contract", addr.String()) 1365 } else { 1366 log.Info("Submitted transaction", "fullhash", tx.Hash().Hex(), "recipient", tx.To()) 1367 } 1368 return tx.Hash(), nil 1369 } 1370 1371 // SendTransaction creates a transaction for the given argument, sign it and submit it to the 1372 // transaction pool. 1373 func (s *PublicTransactionPoolAPI) SendTransaction(ctx context.Context, args SendTxArgs) (common.Hash, error) { 1374 fmt.Printf("transaction args PublicTransactionPoolAPI args %v\n", args) 1375 // Look up the wallet containing the requested signer 1376 account := accounts.Account{Address: args.From} 1377 1378 wallet, err := s.b.AccountManager().Find(account) 1379 if err != nil { 1380 return common.Hash{}, err 1381 } 1382 1383 if args.Nonce == nil { 1384 // Hold the addresse's mutex around signing to prevent concurrent assignment of 1385 // the same nonce to multiple accounts. 1386 s.nonceLock.LockAddr(args.From) 1387 defer s.nonceLock.UnlockAddr(args.From) 1388 } 1389 1390 // Set some sanity defaults and terminate on failure 1391 if err := args.setDefaults(ctx, s.b); err != nil { 1392 return common.Hash{}, err 1393 } 1394 // Assemble the transaction and sign with the wallet 1395 tx := args.toTransaction() 1396 1397 var chainID *big.Int 1398 if config := s.b.ChainConfig(); config.IsEIP155(s.b.CurrentBlock().Number()) { 1399 chainID = config.ChainId 1400 } 1401 signed, err := wallet.SignTxWithAddress(account, tx, chainID) 1402 if err != nil { 1403 return common.Hash{}, err 1404 } 1405 return submitTransaction(ctx, s.b, signed) 1406 } 1407 1408 func SendTransaction(ctx context.Context, args SendTxArgs, am *accounts.Manager, b Backend, nonceLock *AddrLocker) (common.Hash, error) { 1409 fmt.Printf("transaction args PublicTransactionPoolAPI args %v\n", args) 1410 // Look up the wallet containing the requested signer 1411 account := accounts.Account{Address: args.From} 1412 1413 wallet, err := am.Find(account) 1414 if err != nil { 1415 return common.Hash{}, err 1416 } 1417 1418 if args.Nonce == nil { 1419 // Hold the addresse's mutex around signing to prevent concurrent assignment of 1420 // the same nonce to multiple accounts. 1421 nonceLock.LockAddr(args.From) 1422 defer nonceLock.UnlockAddr(args.From) 1423 } 1424 1425 // Set some sanity defaults and terminate on failure 1426 if err := args.setDefaults(ctx, b); err != nil { 1427 return common.Hash{}, err 1428 } 1429 // Assemble the transaction and sign with the wallet 1430 tx := args.toTransaction() 1431 1432 var chainID *big.Int 1433 if config := b.ChainConfig(); config.IsEIP155(b.CurrentBlock().Number()) { 1434 chainID = config.ChainId 1435 } 1436 signed, err := wallet.SignTxWithAddress(account, tx, chainID) 1437 if err != nil { 1438 return common.Hash{}, err 1439 } 1440 return submitTransaction(ctx, b, signed) 1441 } 1442 1443 // SendRawTransaction will add the signed transaction to the transaction pool. 1444 // The sender is responsible for signing the transaction and using the correct nonce. 1445 func (s *PublicTransactionPoolAPI) SendRawTransaction(ctx context.Context, encodedTx hexutil.Bytes) (common.Hash, error) { 1446 tx := new(types.Transaction) 1447 if err := rlp.DecodeBytes(encodedTx, tx); err != nil { 1448 return common.Hash{}, err 1449 } 1450 return submitTransaction(ctx, s.b, tx) 1451 } 1452 1453 // Sign calculates an ECDSA signature for: 1454 // keccack256("\x19NEAT Chain Signed Message:\n" + len(message) + message). 1455 // 1456 // Note, the produced signature conforms to the secp256k1 curve R, S and V values, 1457 // where the V value will be 27 or 28 for legacy reasons. 1458 // 1459 // The account associated with addr must be unlocked. 1460 // 1461 func (s *PublicTransactionPoolAPI) Sign(addr common.Address, data hexutil.Bytes) (hexutil.Bytes, error) { 1462 // Look up the wallet containing the requested signer 1463 account := accounts.Account{Address: addr} 1464 1465 wallet, err := s.b.AccountManager().Find(account) 1466 if err != nil { 1467 return nil, err 1468 } 1469 // Sign the requested hash with the wallet 1470 signature, err := wallet.SignHash(account, signHash(data)) 1471 if err == nil { 1472 signature[64] += 27 // Transform V from 0/1 to 27/28 according to the yellow paper 1473 } 1474 return signature, err 1475 } 1476 1477 // SignTransactionResult represents a RLP encoded signed transaction. 1478 type SignTransactionResult struct { 1479 Raw hexutil.Bytes `json:"raw"` 1480 Tx *types.Transaction `json:"tx"` 1481 } 1482 1483 // SignTransaction will sign the given transaction with the from account. 1484 // The node needs to have the private key of the account corresponding with 1485 // the given from address and it needs to be unlocked. 1486 func (s *PublicTransactionPoolAPI) SignTransaction(ctx context.Context, args SendTxArgs) (*SignTransactionResult, error) { 1487 if args.Gas == nil { 1488 return nil, fmt.Errorf("gas not specified") 1489 } 1490 if args.GasPrice == nil { 1491 return nil, fmt.Errorf("gasPrice not specified") 1492 } 1493 if args.Nonce == nil { 1494 return nil, fmt.Errorf("nonce not specified") 1495 } 1496 if err := args.setDefaults(ctx, s.b); err != nil { 1497 return nil, err 1498 } 1499 tx, err := s.sign(args.From, args.toTransaction()) 1500 if err != nil { 1501 return nil, err 1502 } 1503 data, err := rlp.EncodeToBytes(tx) 1504 if err != nil { 1505 return nil, err 1506 } 1507 return &SignTransactionResult{data, tx}, nil 1508 } 1509 1510 // PendingTransactions returns the transactions that are in the transaction pool and have a from address that is one of 1511 // the accounts this node manages. 1512 func (s *PublicTransactionPoolAPI) PendingTransactions() ([]*RPCTransaction, error) { 1513 pending, err := s.b.GetPoolTransactions() 1514 if err != nil { 1515 return nil, err 1516 } 1517 1518 transactions := make([]*RPCTransaction, 0, len(pending)) 1519 for _, tx := range pending { 1520 var signer types.Signer = types.HomesteadSigner{} 1521 if tx.Protected() { 1522 signer = types.NewEIP155Signer(tx.ChainId()) 1523 } 1524 from, _ := types.Sender(signer, tx) 1525 if _, err := s.b.AccountManager().Find(accounts.Account{Address: from}); err == nil { 1526 transactions = append(transactions, newRPCPendingTransaction(tx)) 1527 } 1528 } 1529 return transactions, nil 1530 } 1531 1532 // Resend accepts an existing transaction and a new gas price and limit. It will remove 1533 // the given transaction from the pool and reinsert it with the new gas price and limit. 1534 func (s *PublicTransactionPoolAPI) Resend(ctx context.Context, sendArgs SendTxArgs, gasPrice *hexutil.Big, gasLimit *hexutil.Uint64) (common.Hash, error) { 1535 if sendArgs.Nonce == nil { 1536 return common.Hash{}, fmt.Errorf("missing transaction nonce in transaction spec") 1537 } 1538 if err := sendArgs.setDefaults(ctx, s.b); err != nil { 1539 return common.Hash{}, err 1540 } 1541 matchTx := sendArgs.toTransaction() 1542 pending, err := s.b.GetPoolTransactions() 1543 if err != nil { 1544 return common.Hash{}, err 1545 } 1546 1547 for _, p := range pending { 1548 var signer types.Signer = types.HomesteadSigner{} 1549 if p.Protected() { 1550 signer = types.NewEIP155Signer(p.ChainId()) 1551 } 1552 wantSigHash := signer.Hash(matchTx) 1553 1554 if pFrom, err := types.Sender(signer, p); err == nil && pFrom == sendArgs.From && signer.Hash(p) == wantSigHash { 1555 // Match. Re-sign and send the transaction. 1556 if gasPrice != nil && (*big.Int)(gasPrice).Sign() != 0 { 1557 sendArgs.GasPrice = gasPrice 1558 } 1559 if gasLimit != nil && *gasLimit != 0 { 1560 sendArgs.Gas = gasLimit 1561 } 1562 signedTx, err := s.sign(sendArgs.From, sendArgs.toTransaction()) 1563 if err != nil { 1564 return common.Hash{}, err 1565 } 1566 if err = s.b.SendTx(ctx, signedTx); err != nil { 1567 return common.Hash{}, err 1568 } 1569 return signedTx.Hash(), nil 1570 } 1571 } 1572 1573 return common.Hash{}, fmt.Errorf("Transaction %#x not found", matchTx.Hash()) 1574 } 1575 1576 // PublicDebugAPI is the collection of NEAT Chain APIs exposed over the public 1577 // debugging endpoint. 1578 type PublicDebugAPI struct { 1579 b Backend 1580 } 1581 1582 // NewPublicDebugAPI creates a new API definition for the public debug methods 1583 // of the NEAT Chain service. 1584 func NewPublicDebugAPI(b Backend) *PublicDebugAPI { 1585 return &PublicDebugAPI{b: b} 1586 } 1587 1588 // GetBlockRlp retrieves the RLP encoded for of a single block. 1589 func (api *PublicDebugAPI) GetBlockRlp(ctx context.Context, number uint64) (string, error) { 1590 block, _ := api.b.BlockByNumber(ctx, rpc.BlockNumber(number)) 1591 if block == nil { 1592 return "", fmt.Errorf("block #%d not found", number) 1593 } 1594 encoded, err := rlp.EncodeToBytes(block) 1595 if err != nil { 1596 return "", err 1597 } 1598 return fmt.Sprintf("%x", encoded), nil 1599 } 1600 1601 // PrintBlock retrieves a block and returns its pretty printed form. 1602 func (api *PublicDebugAPI) PrintBlock(ctx context.Context, number uint64) (string, error) { 1603 block, _ := api.b.BlockByNumber(ctx, rpc.BlockNumber(number)) 1604 if block == nil { 1605 return "", fmt.Errorf("block #%d not found", number) 1606 } 1607 return block.String(), nil 1608 } 1609 1610 // PrivateDebugAPI is the collection of NEAT Chain APIs exposed over the private 1611 // debugging endpoint. 1612 type PrivateDebugAPI struct { 1613 b Backend 1614 } 1615 1616 // NewPrivateDebugAPI creates a new API definition for the private debug methods 1617 // of the NEAT Chain service. 1618 func NewPrivateDebugAPI(b Backend) *PrivateDebugAPI { 1619 return &PrivateDebugAPI{b: b} 1620 } 1621 1622 // ChaindbProperty returns leveldb properties of the chain database. 1623 func (api *PrivateDebugAPI) ChaindbProperty(property string) (string, error) { 1624 ldb, ok := api.b.ChainDb().(interface { 1625 LDB() *leveldb.DB 1626 }) 1627 if !ok { 1628 return "", fmt.Errorf("chaindbProperty does not work for memory databases") 1629 } 1630 if property == "" { 1631 property = "leveldb.stats" 1632 } else if !strings.HasPrefix(property, "leveldb.") { 1633 property = "leveldb." + property 1634 } 1635 return ldb.LDB().GetProperty(property) 1636 } 1637 1638 func (api *PrivateDebugAPI) ChaindbCompact() error { 1639 for b := byte(0); b < 255; b++ { 1640 log.Info("Compacting chain database", "range", fmt.Sprintf("0x%0.2X-0x%0.2X", b, b+1)) 1641 if err := api.b.ChainDb().Compact([]byte{b}, []byte{b + 1}); err != nil { 1642 log.Error("Database compaction failed", "err", err) 1643 return err 1644 } 1645 } 1646 return nil 1647 } 1648 1649 // SetHead rewinds the head of the blockchain to a previous block. 1650 func (api *PrivateDebugAPI) SetHead(number hexutil.Uint64) { 1651 api.b.SetHead(uint64(number)) 1652 } 1653 1654 // PublicNetAPI offers network related RPC methods 1655 type PublicNetAPI struct { 1656 net *p2p.Server 1657 networkVersion uint64 1658 } 1659 1660 // NewPublicNetAPI creates a new net API instance. 1661 func NewPublicNetAPI(net *p2p.Server, networkVersion uint64) *PublicNetAPI { 1662 return &PublicNetAPI{net, networkVersion} 1663 } 1664 1665 // Listening returns an indication if the node is listening for network connections. 1666 func (s *PublicNetAPI) Listening() bool { 1667 return true // always listening 1668 } 1669 1670 // PeerCount returns the number of connected peers 1671 func (s *PublicNetAPI) PeerCount() hexutil.Uint { 1672 return hexutil.Uint(s.net.PeerCount()) 1673 } 1674 1675 // Version returns the current neatchain protocol version. 1676 func (s *PublicNetAPI) Version() string { 1677 return fmt.Sprintf("%d", s.networkVersion) 1678 } 1679 1680 var ( 1681 minimumRegisterAmount = math.MustParseBig256("1000000000000000000") // 1 * e18 1682 1683 maxCandidateNumber = 1000 1684 1685 maxDelegationAddresses = 1000 1686 1687 maxEditValidatorLength = 100 1688 ) 1689 1690 type PublicNEATAPI struct { 1691 am *accounts.Manager 1692 b Backend 1693 nonceLock *AddrLocker 1694 } 1695 1696 // NewPublicNEATAPI creates a new NEAT API instance. 1697 func NewPublicNEATAPI(b Backend, nonceLock *AddrLocker) *PublicNEATAPI { 1698 return &PublicNEATAPI{b.AccountManager(), b, nonceLock} 1699 } 1700 1701 func (s *PublicNEATAPI) SignAddress(from common.Address, consensusPrivateKey hexutil.Bytes) (goCrypto.Signature, error) { 1702 if len(consensusPrivateKey) != 32 { 1703 return nil, errors.New("invalid consensus private key") 1704 } 1705 1706 var blsPriv goCrypto.BLSPrivKey 1707 copy(blsPriv[:], consensusPrivateKey) 1708 1709 blsSign := blsPriv.Sign(from.Bytes()) 1710 1711 return blsSign, nil 1712 } 1713 1714 func (api *PublicNEATAPI) WithdrawReward(ctx context.Context, from common.Address, delegateAddress common.Address, gasPrice *hexutil.Big) (common.Hash, error) { 1715 input, err := neatAbi.ChainABI.Pack(neatAbi.WithdrawReward.String(), delegateAddress) 1716 if err != nil { 1717 return common.Hash{}, err 1718 } 1719 1720 defaultGas := neatAbi.WithdrawReward.RequiredGas() 1721 1722 args := SendTxArgs{ 1723 From: from, 1724 To: &neatAbi.ChainContractMagicAddr, 1725 Gas: (*hexutil.Uint64)(&defaultGas), 1726 GasPrice: gasPrice, 1727 Value: nil, 1728 Input: (*hexutil.Bytes)(&input), 1729 Nonce: nil, 1730 } 1731 1732 return SendTransaction(ctx, args, api.am, api.b, api.nonceLock) 1733 } 1734 1735 func (api *PublicNEATAPI) Delegate(ctx context.Context, from, candidate common.Address, amount *hexutil.Big, gasPrice *hexutil.Big) (common.Hash, error) { 1736 1737 input, err := neatAbi.ChainABI.Pack(neatAbi.Delegate.String(), candidate) 1738 if err != nil { 1739 return common.Hash{}, err 1740 } 1741 1742 defaultGas := neatAbi.Delegate.RequiredGas() 1743 1744 args := SendTxArgs{ 1745 From: from, 1746 To: &neatAbi.ChainContractMagicAddr, 1747 Gas: (*hexutil.Uint64)(&defaultGas), 1748 GasPrice: gasPrice, 1749 Value: amount, 1750 Input: (*hexutil.Bytes)(&input), 1751 Nonce: nil, 1752 } 1753 return SendTransaction(ctx, args, api.am, api.b, api.nonceLock) 1754 } 1755 1756 func (api *PublicNEATAPI) UnDelegate(ctx context.Context, from, candidate common.Address, amount *hexutil.Big, gasPrice *hexutil.Big) (common.Hash, error) { 1757 1758 input, err := neatAbi.ChainABI.Pack(neatAbi.UnDelegate.String(), candidate, (*big.Int)(amount)) 1759 if err != nil { 1760 return common.Hash{}, err 1761 } 1762 1763 defaultGas := neatAbi.UnDelegate.RequiredGas() 1764 1765 args := SendTxArgs{ 1766 From: from, 1767 To: &neatAbi.ChainContractMagicAddr, 1768 Gas: (*hexutil.Uint64)(&defaultGas), 1769 GasPrice: gasPrice, 1770 Value: nil, 1771 Input: (*hexutil.Bytes)(&input), 1772 Nonce: nil, 1773 } 1774 1775 return SendTransaction(ctx, args, api.am, api.b, api.nonceLock) 1776 } 1777 1778 func (api *PublicNEATAPI) Register(ctx context.Context, from common.Address, registerAmount *hexutil.Big, pubkey goCrypto.BLSPubKey, signature hexutil.Bytes, commission uint8, gasPrice *hexutil.Big) (common.Hash, error) { 1779 1780 input, err := neatAbi.ChainABI.Pack(neatAbi.Register.String(), pubkey.Bytes(), signature, commission) 1781 if err != nil { 1782 return common.Hash{}, err 1783 } 1784 1785 defaultGas := neatAbi.Register.RequiredGas() 1786 1787 args := SendTxArgs{ 1788 From: from, 1789 To: &neatAbi.ChainContractMagicAddr, 1790 Gas: (*hexutil.Uint64)(&defaultGas), 1791 GasPrice: gasPrice, 1792 Value: registerAmount, 1793 Input: (*hexutil.Bytes)(&input), 1794 Nonce: nil, 1795 } 1796 return SendTransaction(ctx, args, api.am, api.b, api.nonceLock) 1797 } 1798 1799 func (api *PublicNEATAPI) UnRegister(ctx context.Context, from common.Address, gasPrice *hexutil.Big) (common.Hash, error) { 1800 1801 input, err := neatAbi.ChainABI.Pack(neatAbi.UnRegister.String()) 1802 if err != nil { 1803 return common.Hash{}, err 1804 } 1805 1806 defaultGas := neatAbi.UnRegister.RequiredGas() 1807 1808 args := SendTxArgs{ 1809 From: from, 1810 To: &neatAbi.ChainContractMagicAddr, 1811 Gas: (*hexutil.Uint64)(&defaultGas), 1812 GasPrice: gasPrice, 1813 Value: nil, 1814 Input: (*hexutil.Bytes)(&input), 1815 Nonce: nil, 1816 } 1817 return SendTransaction(ctx, args, api.am, api.b, api.nonceLock) 1818 } 1819 1820 func (api *PublicNEATAPI) CheckCandidate(ctx context.Context, address common.Address, blockNr rpc.BlockNumber) (map[string]interface{}, error) { 1821 state, _, err := api.b.StateAndHeaderByNumber(ctx, blockNr) 1822 if state == nil || err != nil { 1823 return nil, err 1824 } 1825 1826 fields := map[string]interface{}{ 1827 "candidate": state.IsCandidate(address), 1828 "commission": state.GetCommission(address), 1829 } 1830 return fields, state.Error() 1831 } 1832 1833 func (api *PublicNEATAPI) GetForbiddenStatus(ctx context.Context, address common.Address, blockNr rpc.BlockNumber) (map[string]interface{}, error) { 1834 state, _, err := api.b.StateAndHeaderByNumber(ctx, blockNr) 1835 if state == nil || err != nil { 1836 return nil, err 1837 } 1838 1839 fields := map[string]interface{}{ 1840 "forbidden": state.GetForbidden(address), 1841 "forbiddenEpoch": state.GetForbiddenTime(address), 1842 "blocks": state.GetMinedBlocks(address), 1843 } 1844 return fields, state.Error() 1845 } 1846 1847 func (api *PublicNEATAPI) SetCommission(ctx context.Context, from common.Address, commission uint8, gasPrice *hexutil.Big) (common.Hash, error) { 1848 input, err := neatAbi.ChainABI.Pack(neatAbi.SetCommission.String(), commission) 1849 if err != nil { 1850 return common.Hash{}, err 1851 } 1852 1853 defaultGas := neatAbi.SetCommission.RequiredGas() 1854 1855 args := SendTxArgs{ 1856 From: from, 1857 To: &neatAbi.ChainContractMagicAddr, 1858 Gas: (*hexutil.Uint64)(&defaultGas), 1859 GasPrice: gasPrice, 1860 Value: nil, 1861 Input: (*hexutil.Bytes)(&input), 1862 Nonce: nil, 1863 } 1864 1865 return SendTransaction(ctx, args, api.am, api.b, api.nonceLock) 1866 } 1867 1868 func (api *PublicNEATAPI) EditValidator(ctx context.Context, from common.Address, moniker, website string, identity string, details string, gasPrice *hexutil.Big) (common.Hash, error) { 1869 input, err := neatAbi.ChainABI.Pack(neatAbi.EditValidator.String(), moniker, website, identity, details) 1870 if err != nil { 1871 return common.Hash{}, err 1872 } 1873 1874 defaultGas := neatAbi.EditValidator.RequiredGas() 1875 1876 args := SendTxArgs{ 1877 From: from, 1878 To: &neatAbi.ChainContractMagicAddr, 1879 Gas: (*hexutil.Uint64)(&defaultGas), 1880 GasPrice: gasPrice, 1881 Value: nil, 1882 Input: (*hexutil.Bytes)(&input), 1883 Nonce: nil, 1884 } 1885 1886 return SendTransaction(ctx, args, api.am, api.b, api.nonceLock) 1887 } 1888 1889 func (api *PublicNEATAPI) UnForbidden(ctx context.Context, from common.Address, gasPrice *hexutil.Big) (common.Hash, error) { 1890 input, err := neatAbi.ChainABI.Pack(neatAbi.UnForbidden.String()) 1891 if err != nil { 1892 return common.Hash{}, err 1893 } 1894 1895 defaultGas := neatAbi.UnForbidden.RequiredGas() 1896 1897 args := SendTxArgs{ 1898 From: from, 1899 To: &neatAbi.ChainContractMagicAddr, 1900 Gas: (*hexutil.Uint64)(&defaultGas), 1901 GasPrice: gasPrice, 1902 Value: nil, 1903 Input: (*hexutil.Bytes)(&input), 1904 Nonce: nil, 1905 } 1906 1907 return SendTransaction(ctx, args, api.am, api.b, api.nonceLock) 1908 } 1909 1910 func init() { 1911 // Withdraw reward 1912 core.RegisterValidateCb(neatAbi.WithdrawReward, withdrawRewardValidateCb) 1913 core.RegisterApplyCb(neatAbi.WithdrawReward, withdrawRewardApplyCb) 1914 1915 // Delegate 1916 core.RegisterValidateCb(neatAbi.Delegate, delegateValidateCb) 1917 core.RegisterApplyCb(neatAbi.Delegate, delegateApplyCb) 1918 1919 // Cancel Delegate 1920 core.RegisterValidateCb(neatAbi.UnDelegate, unDelegateValidateCb) 1921 core.RegisterApplyCb(neatAbi.UnDelegate, unDelegateApplyCb) 1922 1923 // Register 1924 core.RegisterValidateCb(neatAbi.Register, registerValidateCb) 1925 core.RegisterApplyCb(neatAbi.Register, registerApplyCb) 1926 1927 // Cancel Register 1928 core.RegisterValidateCb(neatAbi.UnRegister, unRegisterValidateCb) 1929 core.RegisterApplyCb(neatAbi.UnRegister, unRegisterApplyCb) 1930 1931 // Set Commission 1932 core.RegisterValidateCb(neatAbi.SetCommission, setCommisstionValidateCb) 1933 core.RegisterApplyCb(neatAbi.SetCommission, setCommisstionApplyCb) 1934 1935 // Edit Validator 1936 core.RegisterValidateCb(neatAbi.EditValidator, editValidatorValidateCb) 1937 1938 // UnForbidden 1939 core.RegisterValidateCb(neatAbi.UnForbidden, unForbiddenValidateCb) 1940 core.RegisterApplyCb(neatAbi.UnForbidden, unForbiddenApplyCb) 1941 } 1942 1943 func withdrawRewardValidateCb(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain) error { 1944 from := derivedAddressFromTx(tx) 1945 _, err := withDrawRewardValidation(from, tx, state, bc) 1946 if err != nil { 1947 return err 1948 } 1949 1950 return nil 1951 } 1952 1953 func withdrawRewardApplyCb(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain, ops *types.PendingOps) error { 1954 from := derivedAddressFromTx(tx) 1955 1956 args, err := withDrawRewardValidation(from, tx, state, bc) 1957 if err != nil { 1958 return err 1959 } 1960 1961 reward := state.GetRewardBalanceByDelegateAddress(from, args.DelegateAddress) 1962 state.SubRewardBalanceByDelegateAddress(from, args.DelegateAddress, reward) 1963 state.AddBalance(from, reward) 1964 1965 return nil 1966 } 1967 1968 func withDrawRewardValidation(from common.Address, tx *types.Transaction, state *state.StateDB, bc *core.BlockChain) (*neatAbi.WithdrawRewardArgs, error) { 1969 1970 var args neatAbi.WithdrawRewardArgs 1971 data := tx.Data() 1972 if err := neatAbi.ChainABI.UnpackMethodInputs(&args, neatAbi.WithdrawReward.String(), data[4:]); err != nil { 1973 return nil, err 1974 } 1975 1976 reward := state.GetRewardBalanceByDelegateAddress(from, args.DelegateAddress) 1977 1978 if reward.Sign() < 1 { 1979 return nil, fmt.Errorf("have no reward to withdraw") 1980 } 1981 1982 //if args.Amount.Cmp(reward) == 1 { 1983 // return nil, fmt.Errorf("reward balance not enough, withdraw amount %v, but balance %v, delegate address %v", args.Amount, reward, args.DelegateAddress) 1984 //} 1985 return &args, nil 1986 } 1987 1988 // register and unregister 1989 func registerValidateCb(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain) error { 1990 from := derivedAddressFromTx(tx) 1991 _, verror := registerValidation(from, tx, state, bc) 1992 if verror != nil { 1993 return verror 1994 } 1995 return nil 1996 } 1997 1998 func registerApplyCb(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain, ops *types.PendingOps) error { 1999 // Validate first 2000 from := derivedAddressFromTx(tx) 2001 args, verror := registerValidation(from, tx, state, bc) 2002 if verror != nil { 2003 return verror 2004 } 2005 2006 // block height validation 2007 verror = updateValidation(bc) 2008 if verror != nil { 2009 return verror 2010 } 2011 2012 amount := tx.Value() 2013 // Add minimum register amount to self 2014 state.SubBalance(from, amount) 2015 state.AddDelegateBalance(from, amount) 2016 state.AddProxiedBalanceByUser(from, from, amount) 2017 // Become a Candidate 2018 2019 var blsPK goCrypto.BLSPubKey 2020 copy(blsPK[:], args.Pubkey) 2021 fmt.Printf("register pubkey unmarshal json start\n") 2022 if verror != nil { 2023 return verror 2024 } 2025 fmt.Printf("register pubkey %v\n", blsPK) 2026 state.ApplyForCandidate(from, blsPK.KeyString(), args.Commission) 2027 2028 // mark address candidate 2029 state.MarkAddressCandidate(from) 2030 2031 verror = updateNextEpochValidatorVoteSet(tx, state, bc, from, ops) 2032 if verror != nil { 2033 return verror 2034 } 2035 2036 return nil 2037 } 2038 2039 func registerValidation(from common.Address, tx *types.Transaction, state *state.StateDB, bc *core.BlockChain) (*neatAbi.RegisterArgs, error) { 2040 candidateSet := state.GetCandidateSet() 2041 if len(candidateSet) > maxCandidateNumber { 2042 return nil, core.ErrMaxCandidate 2043 } 2044 2045 // Check cleaned Candidate 2046 if !state.IsCleanAddress(from) { 2047 return nil, core.ErrAlreadyCandidate 2048 } 2049 2050 // Check minimum register amount 2051 if tx.Value().Cmp(minimumRegisterAmount) == -1 { 2052 return nil, core.ErrMinimumRegisterAmount 2053 } 2054 2055 var args neatAbi.RegisterArgs 2056 data := tx.Data() 2057 if err := neatAbi.ChainABI.UnpackMethodInputs(&args, neatAbi.Register.String(), data[4:]); err != nil { 2058 return nil, err 2059 } 2060 2061 if err := goCrypto.CheckConsensusPubKey(from, args.Pubkey, args.Signature); err != nil { 2062 return nil, err 2063 } 2064 2065 // Check Commission Range 2066 if args.Commission > 100 { 2067 return nil, core.ErrCommission 2068 } 2069 2070 // Annual/SemiAnnual supernode can not become candidate 2071 var ep *epoch.Epoch 2072 if nc, ok := bc.Engine().(consensus.NeatCon); ok { 2073 ep = nc.GetEpoch().GetEpochByBlockNumber(bc.CurrentBlock().NumberU64()) 2074 } 2075 if _, supernode := ep.Validators.GetByAddress(from.Bytes()); supernode != nil && supernode.RemainingEpoch > 0 { 2076 return nil, core.ErrCannotCandidate 2077 } 2078 2079 return &args, nil 2080 } 2081 2082 func unRegisterValidateCb(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain) error { 2083 from := derivedAddressFromTx(tx) 2084 verror := unRegisterValidation(from, tx, state, bc) 2085 if verror != nil { 2086 return verror 2087 } 2088 return nil 2089 } 2090 2091 func unRegisterApplyCb(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain, ops *types.PendingOps) error { 2092 // Validate first 2093 from := derivedAddressFromTx(tx) 2094 verror := unRegisterValidation(from, tx, state, bc) 2095 if verror != nil { 2096 return verror 2097 } 2098 2099 // Do job 2100 allRefund := true 2101 // Refund all the amount back to users 2102 state.ForEachProxied(from, func(key common.Address, proxiedBalance, depositProxiedBalance, pendingRefundBalance *big.Int) bool { 2103 // Refund Proxied Amount 2104 state.SubProxiedBalanceByUser(from, key, proxiedBalance) 2105 state.SubDelegateBalance(key, proxiedBalance) 2106 state.AddBalance(key, proxiedBalance) 2107 2108 if depositProxiedBalance.Sign() > 0 { 2109 allRefund = false 2110 // Refund Deposit to PendingRefund if deposit > 0 2111 state.AddPendingRefundBalanceByUser(from, key, depositProxiedBalance) 2112 // TODO Add Pending Refund Set, Commit the Refund Set 2113 state.MarkDelegateAddressRefund(from) 2114 } 2115 return true 2116 }) 2117 2118 state.CancelCandidate(from, allRefund) 2119 2120 fmt.Printf("candidate set bug, unregiser clear candidate before\n") 2121 fmt.Printf("candidate set bug, unregiser clear candidate before %v\n", state.GetCandidateSet()) 2122 // remove address form candidate set 2123 state.ClearCandidateSetByAddress(from) 2124 fmt.Printf("candidate set bug, unregiser clear candidate after\n") 2125 fmt.Printf("candidate set bug, unregiser clear candidate after %v\n", state.GetCandidateSet()) 2126 2127 return nil 2128 } 2129 2130 func unRegisterValidation(from common.Address, tx *types.Transaction, state *state.StateDB, bc *core.BlockChain) error { 2131 // Check already Candidate 2132 if !state.IsCandidate(from) { 2133 return core.ErrNotCandidate 2134 } 2135 2136 // Forbidden candidate can't unregister 2137 if state.GetForbidden(from) { 2138 return core.ErrForbiddenUnRegister 2139 } 2140 2141 // Super node can't unregister 2142 var ep *epoch.Epoch 2143 if nc, ok := bc.Engine().(consensus.NeatCon); ok { 2144 ep = nc.GetEpoch().GetEpochByBlockNumber(bc.CurrentBlock().NumberU64()) 2145 } 2146 if _, supernode := ep.Validators.GetByAddress(from.Bytes()); supernode != nil && supernode.RemainingEpoch > 0 { 2147 return core.ErrCannotUnRegister 2148 } 2149 2150 // Check Epoch Height 2151 if _, err := getEpoch(bc); err != nil { 2152 return err 2153 } 2154 2155 return nil 2156 } 2157 2158 // delegate and unDelegate 2159 func delegateValidateCb(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain) error { 2160 from := derivedAddressFromTx(tx) 2161 _, verror := delegateValidation(from, tx, state, bc) 2162 if verror != nil { 2163 return verror 2164 } 2165 return nil 2166 } 2167 2168 func delegateApplyCb(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain, ops *types.PendingOps) error { 2169 // Validate first 2170 from := derivedAddressFromTx(tx) 2171 args, verror := delegateValidation(from, tx, state, bc) 2172 if verror != nil { 2173 return verror 2174 } 2175 2176 // block height validation 2177 verror = updateValidation(bc) 2178 if verror != nil { 2179 return verror 2180 } 2181 2182 // Do job 2183 amount := tx.Value() 2184 // Move Balance to delegate balance 2185 state.SubBalance(from, amount) 2186 state.AddDelegateBalance(from, amount) 2187 // Add Balance to Candidate's Proxied Balance 2188 state.AddProxiedBalanceByUser(args.Candidate, from, amount) 2189 2190 // if forbidden, don't add to next epoch validator vote set 2191 if !state.GetForbidden(from) { 2192 verror = updateNextEpochValidatorVoteSet(tx, state, bc, args.Candidate, ops) 2193 if verror != nil { 2194 return verror 2195 } 2196 } 2197 2198 return nil 2199 } 2200 2201 func delegateValidation(from common.Address, tx *types.Transaction, state *state.StateDB, bc *core.BlockChain) (*neatAbi.DelegateArgs, error) { 2202 // Check minimum delegate amount 2203 if tx.Value().Sign() == -1 { 2204 return nil, core.ErrDelegateAmount 2205 } 2206 2207 var args neatAbi.DelegateArgs 2208 data := tx.Data() 2209 if err := neatAbi.ChainABI.UnpackMethodInputs(&args, neatAbi.Delegate.String(), data[4:]); err != nil { 2210 return nil, err 2211 } 2212 2213 // Check Candidate 2214 if !state.IsCandidate(args.Candidate) { 2215 return nil, core.ErrNotCandidate 2216 } 2217 2218 depositBalance := state.GetDepositProxiedBalanceByUser(args.Candidate, from) 2219 if depositBalance.Sign() == 0 { 2220 // Check if exceed the limit of delegated addresses 2221 // if exceed the limit of delegation address number, return error 2222 delegatedAddressNumber := state.GetProxiedAddressNumber(args.Candidate) 2223 if delegatedAddressNumber >= maxDelegationAddresses { 2224 return nil, core.ErrExceedDelegationAddressLimit 2225 } 2226 } 2227 2228 // If Candidate is supernode, only allow to increase the stack(whitelist proxied list), not allow to create the new stack 2229 var ep *epoch.Epoch 2230 if nc, ok := bc.Engine().(consensus.NeatCon); ok { 2231 ep = nc.GetEpoch().GetEpochByBlockNumber(bc.CurrentBlock().NumberU64()) 2232 } 2233 if _, supernode := ep.Validators.GetByAddress(args.Candidate.Bytes()); supernode != nil && supernode.RemainingEpoch > 0 { 2234 if depositBalance.Sign() == 0 { 2235 return nil, core.ErrCannotDelegate 2236 } 2237 } 2238 2239 // Check Epoch Height 2240 //if _, err := getEpoch(bc); err != nil { 2241 // return nil, err 2242 //} 2243 return &args, nil 2244 } 2245 2246 func unDelegateValidateCb(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain) error { 2247 from := derivedAddressFromTx(tx) 2248 _, verror := unDelegateValidation(from, tx, state, bc) 2249 if verror != nil { 2250 return verror 2251 } 2252 return nil 2253 } 2254 2255 func unDelegateApplyCb(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain, ops *types.PendingOps) error { 2256 // Validate first 2257 from := derivedAddressFromTx(tx) 2258 args, verror := unDelegateValidation(from, tx, state, bc) 2259 if verror != nil { 2260 return verror 2261 } 2262 2263 // block height validation 2264 verror = updateValidation(bc) 2265 if verror != nil { 2266 return verror 2267 } 2268 2269 // Apply Logic 2270 // if request amount < proxied amount, refund it immediately 2271 // otherwise, refund the proxied amount, and put the rest to pending refund balance 2272 proxiedBalance := state.GetProxiedBalanceByUser(args.Candidate, from) 2273 var immediatelyRefund *big.Int 2274 if args.Amount.Cmp(proxiedBalance) <= 0 { 2275 immediatelyRefund = args.Amount 2276 } else { 2277 immediatelyRefund = proxiedBalance 2278 restRefund := new(big.Int).Sub(args.Amount, proxiedBalance) 2279 state.AddPendingRefundBalanceByUser(args.Candidate, from, restRefund) 2280 // TODO Add Pending Refund Set, Commit the Refund Set 2281 state.MarkDelegateAddressRefund(args.Candidate) 2282 } 2283 2284 state.SubProxiedBalanceByUser(args.Candidate, from, immediatelyRefund) 2285 state.SubDelegateBalance(from, immediatelyRefund) 2286 state.AddBalance(from, immediatelyRefund) 2287 2288 //verror = updateNextEpochValidatorVoteSet(tx, state, bc, args.Candidate) 2289 //if verror != nil { 2290 // return verror 2291 //} 2292 2293 return nil 2294 } 2295 2296 func unDelegateValidation(from common.Address, tx *types.Transaction, state *state.StateDB, bc *core.BlockChain) (*neatAbi.UnDelegateArgs, error) { 2297 2298 var args neatAbi.UnDelegateArgs 2299 data := tx.Data() 2300 if err := neatAbi.ChainABI.UnpackMethodInputs(&args, neatAbi.UnDelegate.String(), data[4:]); err != nil { 2301 return nil, err 2302 } 2303 2304 // Check Self Address 2305 if from == args.Candidate { 2306 return nil, core.ErrCancelSelfDelegate 2307 } 2308 2309 // Super node Candidate can't decrease balance 2310 var ep *epoch.Epoch 2311 if nc, ok := bc.Engine().(consensus.NeatCon); ok { 2312 ep = nc.GetEpoch().GetEpochByBlockNumber(bc.CurrentBlock().NumberU64()) 2313 } 2314 if _, supernode := ep.Validators.GetByAddress(args.Candidate.Bytes()); supernode != nil && supernode.RemainingEpoch > 0 { 2315 return nil, core.ErrCannotUnBond 2316 } 2317 2318 // Check Proxied Amount in Candidate Balance 2319 proxiedBalance := state.GetProxiedBalanceByUser(args.Candidate, from) 2320 depositProxiedBalance := state.GetDepositProxiedBalanceByUser(args.Candidate, from) 2321 pendingRefundBalance := state.GetPendingRefundBalanceByUser(args.Candidate, from) 2322 // net = deposit - pending refund 2323 netDeposit := new(big.Int).Sub(depositProxiedBalance, pendingRefundBalance) 2324 // available = proxied + net 2325 availableRefundBalance := new(big.Int).Add(proxiedBalance, netDeposit) 2326 if args.Amount.Cmp(availableRefundBalance) == 1 { 2327 return nil, core.ErrInsufficientProxiedBalance 2328 } 2329 2330 // if left, the left must be greater than the min delegate amount 2331 //remainingBalance := new(big.Int).Sub(availableRefundBalance, args.Amount) 2332 //if remainingBalance.Sign() == 1 && remainingBalance.Cmp(minimumDelegationAmount) == -1 { 2333 // return nil, core.ErrDelegateAmount 2334 //} 2335 2336 // Check Epoch Height 2337 if _, err := getEpoch(bc); err != nil { 2338 return nil, err 2339 } 2340 2341 return &args, nil 2342 } 2343 2344 // set commission 2345 func setCommisstionValidateCb(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain) error { 2346 from := derivedAddressFromTx(tx) 2347 _, err := setCommissionValidation(from, tx, state, bc) 2348 if err != nil { 2349 return err 2350 } 2351 2352 return nil 2353 } 2354 2355 func setCommisstionApplyCb(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain, ops *types.PendingOps) error { 2356 from := derivedAddressFromTx(tx) 2357 args, err := setCommissionValidation(from, tx, state, bc) 2358 if err != nil { 2359 return err 2360 } 2361 2362 state.SetCommission(from, args.Commission) 2363 2364 return nil 2365 } 2366 2367 func setCommissionValidation(from common.Address, tx *types.Transaction, state *state.StateDB, bc *core.BlockChain) (*neatAbi.SetCommissionArgs, error) { 2368 if !state.IsCandidate(from) { 2369 return nil, core.ErrNotCandidate 2370 } 2371 2372 var args neatAbi.SetCommissionArgs 2373 data := tx.Data() 2374 if err := neatAbi.ChainABI.UnpackMethodInputs(&args, neatAbi.SetCommission.String(), data[4:]); err != nil { 2375 return nil, err 2376 } 2377 2378 if args.Commission > 100 { 2379 return nil, core.ErrCommission 2380 } 2381 2382 return &args, nil 2383 } 2384 2385 func editValidatorValidateCb(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain) error { 2386 from := derivedAddressFromTx(tx) 2387 if !state.IsCandidate(from) { 2388 return errors.New("you are not a validator or candidate") 2389 } 2390 2391 var args neatAbi.EditValidatorArgs 2392 data := tx.Data() 2393 if err := neatAbi.ChainABI.UnpackMethodInputs(&args, neatAbi.EditValidator.String(), data[4:]); err != nil { 2394 return err 2395 } 2396 2397 if len([]byte(args.Details)) > maxEditValidatorLength || 2398 len([]byte(args.Identity)) > maxEditValidatorLength || 2399 len([]byte(args.Moniker)) > maxEditValidatorLength || 2400 len([]byte(args.Website)) > maxEditValidatorLength { 2401 //fmt.Printf("args details length %v, identity length %v, moniker lenth %v, website length %v\n", len([]byte(args.Details)),len([]byte(args.Identity)),len([]byte(args.Moniker)),len([]byte(args.Website))) 2402 return fmt.Errorf("args length too long, more than %v", maxEditValidatorLength) 2403 } 2404 2405 return nil 2406 } 2407 2408 func unForbiddenValidateCb(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain) error { 2409 from := derivedAddressFromTx(tx) 2410 2411 err := unForbiddenValidation(from, state, bc) 2412 if err != nil { 2413 return err 2414 } 2415 2416 return nil 2417 } 2418 2419 func unForbiddenApplyCb(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain, ops *types.PendingOps) error { 2420 from := derivedAddressFromTx(tx) 2421 err := unForbiddenValidation(from, state, bc) 2422 if err != nil { 2423 return err 2424 } 2425 2426 state.SetForbidden(from, false) 2427 2428 // remove address from forbidden set 2429 state.ClearForbiddenSetByAddress(from) 2430 2431 return nil 2432 } 2433 2434 func unForbiddenValidation(from common.Address, state *state.StateDB, bc *core.BlockChain) error { 2435 if !state.IsCandidate(from) { 2436 return core.ErrNotCandidate 2437 } 2438 2439 //ep, err := getEpoch(bc) 2440 //if err != nil { 2441 // return err 2442 //} 2443 2444 // block height validation 2445 verror := updateValidation(bc) 2446 if verror != nil { 2447 return verror 2448 } 2449 2450 if !state.GetForbidden(from) { 2451 return fmt.Errorf("should not unforbidden") 2452 } 2453 2454 forbiddenEpoch := state.GetForbiddenTime(from) 2455 fmt.Printf("Unforbiddenden validation, forbidden epoch %v\n", forbiddenEpoch) 2456 2457 if forbiddenEpoch.Cmp(common.Big0) == 1 { 2458 return fmt.Errorf("please unforbidden %v epoch later", forbiddenEpoch) 2459 } 2460 2461 return nil 2462 } 2463 2464 func concatCopyPreAllocate(slices [][]byte) []byte { 2465 var totalLen int 2466 for _, s := range slices { 2467 totalLen += len(s) 2468 } 2469 tmp := make([]byte, totalLen) 2470 var i int 2471 for _, s := range slices { 2472 i += copy(tmp[i:], s) 2473 } 2474 return tmp 2475 } 2476 2477 func getEpoch(bc *core.BlockChain) (*epoch.Epoch, error) { 2478 var ep *epoch.Epoch 2479 if nc, ok := bc.Engine().(consensus.NeatCon); ok { 2480 ep = nc.GetEpoch().GetEpochByBlockNumber(bc.CurrentBlock().NumberU64()) 2481 } 2482 2483 if ep == nil { 2484 return nil, errors.New("epoch is nil, are you running on NeatCon Consensus Engine") 2485 } 2486 2487 return ep, nil 2488 } 2489 2490 func derivedAddressFromTx(tx *types.Transaction) (from common.Address) { 2491 signer := types.NewEIP155Signer(tx.ChainId()) 2492 from, _ = types.Sender(signer, tx) 2493 return 2494 } 2495 2496 func updateValidation(bc *core.BlockChain) error { 2497 ep, err := getEpoch(bc) 2498 if err != nil { 2499 return err 2500 } 2501 2502 currHeight := bc.CurrentBlock().NumberU64() 2503 2504 if currHeight == 1 || currHeight == ep.StartBlock || currHeight == ep.StartBlock+1 || currHeight == ep.EndBlock { 2505 return errors.New("incorrect block height, please retry later") 2506 } 2507 2508 return nil 2509 } 2510 2511 func updateNextEpochValidatorVoteSet(tx *types.Transaction, state *state.StateDB, bc *core.BlockChain, candidate common.Address, ops *types.PendingOps) error { 2512 var update bool 2513 ep, err := getEpoch(bc) 2514 if err != nil { 2515 return err 2516 } 2517 2518 // calculate the net proxied balance of this candidate 2519 proxiedBalance := state.GetTotalProxiedBalance(candidate) 2520 depositProxiedBalance := state.GetTotalDepositProxiedBalance(candidate) 2521 pendingRefundBalance := state.GetTotalPendingRefundBalance(candidate) 2522 netProxied := new(big.Int).Sub(new(big.Int).Add(proxiedBalance, depositProxiedBalance), pendingRefundBalance) 2523 2524 if netProxied.Sign() == -1 { 2525 return errors.New("validator voting power can not be negative") 2526 } 2527 2528 fmt.Printf("update next epoch voteset %v\n", ep.GetEpochValidatorVoteSet()) 2529 currentEpochVoteSet := ep.GetEpochValidatorVoteSet() 2530 fmt.Printf("update next epoch current epoch voteset %v\n", ep.GetEpochValidatorVoteSet()) 2531 2532 // whether update next epoch vote set 2533 if currentEpochVoteSet == nil { 2534 update = true 2535 } else { 2536 // if current validator size bigger than updateValidatorThreshold and the netProxied is bigger then one of the current validator voting power 2537 if len(currentEpochVoteSet.Votes) >= updateValidatorThreshold { 2538 for _, val := range currentEpochVoteSet.Votes { 2539 // TODO whether need compare 2540 if val.Amount.Cmp(netProxied) == -1 { 2541 update = true 2542 break 2543 } 2544 } 2545 } else { 2546 update = true 2547 } 2548 } 2549 2550 // update is true and the address is candidate, then update next epoch validator vote set 2551 if update && state.IsCandidate(candidate) { 2552 // Move delegate amount first if Candidate 2553 state.ForEachProxied(candidate, func(key common.Address, proxiedBalance, depositProxiedBalance, pendingRefundBalance *big.Int) bool { 2554 // Move Proxied Amount to Deposit Proxied Amount 2555 state.SubProxiedBalanceByUser(candidate, key, proxiedBalance) 2556 state.AddDepositProxiedBalanceByUser(candidate, key, proxiedBalance) 2557 return true 2558 }) 2559 2560 var pubkey string 2561 pubkey = state.GetPubkey(candidate) 2562 pubkeyBytes := common.FromHex(pubkey) 2563 if pubkey == "" || len(pubkeyBytes) != 128 { 2564 return errors.New("wrong format of required field 'pub_key'") 2565 } 2566 var blsPK goCrypto.BLSPubKey 2567 copy(blsPK[:], pubkeyBytes) 2568 2569 op := types.UpdateNextEpochOp{ 2570 From: candidate, 2571 PubKey: blsPK, 2572 Amount: netProxied, 2573 Salt: "neatchain", 2574 TxHash: tx.Hash(), 2575 } 2576 2577 if ok := ops.Append(&op); !ok { 2578 return fmt.Errorf("pending ops conflict: %v", op) 2579 } 2580 } 2581 2582 return nil 2583 }