github.com/Gessiux/neatchain@v1.3.1/chain/core/tx_pool.go (about) 1 // Copyright 2014 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 core 18 19 import ( 20 "errors" 21 "fmt" 22 "math" 23 "math/big" 24 "sort" 25 "sync" 26 "time" 27 28 "github.com/Gessiux/neatchain/utilities/crypto" 29 30 "github.com/Gessiux/neatchain/chain/core/state" 31 "github.com/Gessiux/neatchain/chain/core/types" 32 "github.com/Gessiux/neatchain/chain/log" 33 neatAbi "github.com/Gessiux/neatchain/neatabi/abi" 34 "github.com/Gessiux/neatchain/params" 35 "github.com/Gessiux/neatchain/utilities/common" 36 "github.com/Gessiux/neatchain/utilities/common/prque" 37 "github.com/Gessiux/neatchain/utilities/event" 38 "github.com/Gessiux/neatchain/utilities/metrics" 39 ) 40 41 const ( 42 // chainHeadChanSize is the size of channel listening to ChainHeadEvent. 43 chainHeadChanSize = 10 44 ) 45 46 var ( 47 // ErrInvalidSender is returned if the transaction contains an invalid signature. 48 ErrInvalidSender = errors.New("invalid sender") 49 50 ErrInvalidAddress = errors.New("invalid address") 51 52 // ErrNonceTooLow is returned if the nonce of a transaction is lower than the 53 // one present in the local chain. 54 ErrNonceTooLow = errors.New("nonce too low") 55 56 // ErrUnderpriced is returned if a transaction's gas price is below the minimum 57 // configured for the transaction pool. 58 ErrUnderpriced = errors.New("transaction underpriced") 59 60 // ErrReplaceUnderpriced is returned if a transaction is attempted to be replaced 61 // with a different one without the required price bump. 62 ErrReplaceUnderpriced = errors.New("replacement transaction underpriced") 63 64 // ErrInsufficientFunds is returned if the total cost of executing a transaction 65 // is higher than the balance of the user's account. 66 ErrInsufficientFunds = errors.New("insufficient funds for gas * price + value") 67 68 // ErrIntrinsicGas is returned if the transaction is specified to use less gas 69 // than required to start the invocation. 70 ErrIntrinsicGas = errors.New("intrinsic gas too low") 71 72 // ErrGasLimit is returned if a transaction's requested gas limit exceeds the 73 // maximum allowance of the current block. 74 ErrGasLimit = errors.New("exceeds block gas limit") 75 76 // ErrNegativeValue is a sanity error to ensure noone is able to specify a 77 // transaction with a negative value. 78 ErrNegativeValue = errors.New("negative value") 79 80 // ErrOversizedData is returned if the input data of a transaction is greater 81 // than some meaningful limit a user might use. This is not a consensus error 82 // making the transaction invalid, rather a DOS protection. 83 ErrOversizedData = errors.New("oversized data") 84 ) 85 86 var ( 87 evictionInterval = time.Minute // Time interval to check for evictable transactions 88 statsReportInterval = 8 * time.Second // Time interval to report transaction pool stats 89 ) 90 91 var ( 92 // Metrics for the pending pool 93 pendingDiscardCounter = metrics.NewRegisteredCounter("txpool/pending/discard", nil) 94 pendingReplaceCounter = metrics.NewRegisteredCounter("txpool/pending/replace", nil) 95 pendingRateLimitCounter = metrics.NewRegisteredCounter("txpool/pending/ratelimit", nil) // Dropped due to rate limiting 96 pendingNofundsCounter = metrics.NewRegisteredCounter("txpool/pending/nofunds", nil) // Dropped due to out-of-funds 97 98 // Metrics for the queued pool 99 queuedDiscardCounter = metrics.NewRegisteredCounter("txpool/queued/discard", nil) 100 queuedReplaceCounter = metrics.NewRegisteredCounter("txpool/queued/replace", nil) 101 queuedRateLimitCounter = metrics.NewRegisteredCounter("txpool/queued/ratelimit", nil) // Dropped due to rate limiting 102 queuedNofundsCounter = metrics.NewRegisteredCounter("txpool/queued/nofunds", nil) // Dropped due to out-of-funds 103 104 // General tx metrics 105 invalidTxCounter = metrics.NewRegisteredCounter("txpool/invalid", nil) 106 underpricedTxCounter = metrics.NewRegisteredCounter("txpool/underpriced", nil) 107 ) 108 109 // TxStatus is the current status of a transaction as seen by the pool. 110 type TxStatus uint 111 112 const ( 113 TxStatusUnknown TxStatus = iota 114 TxStatusQueued 115 TxStatusPending 116 TxStatusIncluded 117 ) 118 119 // blockChain provides the state of blockchain and current gas limit to do 120 // some pre checks in tx pool and event subscribers. 121 type blockChain interface { 122 CurrentBlock() *types.Block 123 GetBlock(hash common.Hash, number uint64) *types.Block 124 StateAt(root common.Hash) (*state.StateDB, error) 125 126 SubscribeChainHeadEvent(ch chan<- ChainHeadEvent) event.Subscription 127 } 128 129 // TxPoolConfig are the configuration parameters of the transaction pool. 130 type TxPoolConfig struct { 131 NoLocals bool // Whether local transaction handling should be disabled 132 Journal string // Journal of local transactions to survive node restarts 133 Rejournal time.Duration // Time interval to regenerate the local transaction journal 134 135 PriceLimit uint64 // Minimum gas price to enforce for acceptance into the pool 136 PriceBump uint64 // Minimum price bump percentage to replace an already existing transaction (nonce) 137 138 AccountSlots uint64 // Minimum number of executable transaction slots guaranteed per account 139 GlobalSlots uint64 // Maximum number of executable transaction slots for all accounts 140 AccountQueue uint64 // Maximum number of non-executable transaction slots permitted per account 141 GlobalQueue uint64 // Maximum number of non-executable transaction slots for all accounts 142 143 Lifetime time.Duration // Maximum amount of time non-executable transaction are queued 144 } 145 146 // DefaultTxPoolConfig contains the default configurations for the transaction 147 // pool. 148 var DefaultTxPoolConfig = TxPoolConfig{ 149 Journal: "transactions.rlp", 150 Rejournal: time.Hour, 151 152 PriceLimit: 1, 153 PriceBump: 10, 154 155 AccountSlots: 16000, 156 //GlobalSlots: 4096, 157 GlobalSlots: 40960, 158 AccountQueue: 6400, 159 //GlobalQueue: 1024, 160 GlobalQueue: 10240, 161 162 Lifetime: 3 * time.Hour, 163 } 164 165 // sanitize checks the provided user configurations and changes anything that's 166 // unreasonable or unworkable. 167 func (config *TxPoolConfig) sanitize() TxPoolConfig { 168 conf := *config 169 if conf.Rejournal < time.Second { 170 log.Warn("Sanitizing invalid txpool journal time", "provided", conf.Rejournal, "updated", time.Second) 171 conf.Rejournal = time.Second 172 } 173 if conf.PriceLimit < 1 { 174 log.Warn("Sanitizing invalid txpool price limit", "provided", conf.PriceLimit, "updated", DefaultTxPoolConfig.PriceLimit) 175 conf.PriceLimit = DefaultTxPoolConfig.PriceLimit 176 } 177 if conf.PriceBump < 1 { 178 log.Warn("Sanitizing invalid txpool price bump", "provided", conf.PriceBump, "updated", DefaultTxPoolConfig.PriceBump) 179 conf.PriceBump = DefaultTxPoolConfig.PriceBump 180 } 181 return conf 182 } 183 184 // TxPool contains all currently known transactions. Transactions 185 // enter the pool when they are received from the network or submitted 186 // locally. They exit the pool when they are included in the blockchain. 187 // 188 // The pool separates processable transactions (which can be applied to the 189 // current state) and future transactions. Transactions move between those 190 // two states over time as they are received and processed. 191 type TxPool struct { 192 config TxPoolConfig 193 chainconfig *params.ChainConfig 194 chain blockChain 195 gasPrice *big.Int 196 txFeed event.Feed 197 scope event.SubscriptionScope 198 chainHeadCh chan ChainHeadEvent 199 chainHeadSub event.Subscription 200 signer types.Signer 201 mu sync.RWMutex 202 203 currentState *state.StateDB // Current state in the blockchain head 204 pendingState *state.ManagedState // Pending state tracking virtual nonces 205 currentMaxGas uint64 // Current gas limit for transaction caps 206 207 locals *accountSet // Set of local transaction to exempt from eviction rules 208 journal *txJournal // Journal of local transaction to back up to disk 209 210 pending map[common.Address]*txList // All currently processable transactions 211 queue map[common.Address]*txList // Queued but non-processable transactions 212 beats map[common.Address]time.Time // Last heartbeat from each known account 213 all map[common.Hash]*types.Transaction // All transactions to allow lookups 214 priced *txPricedList // All transactions sorted by price 215 216 wg sync.WaitGroup // for shutdown sync 217 218 cch CrossChainHelper 219 } 220 221 var TxPoolSigner types.Signer = nil 222 223 // NewTxPool creates a new transaction pool to gather, sort and filter inbound 224 // transactions from the network. 225 func NewTxPool(config TxPoolConfig, chainconfig *params.ChainConfig, chain blockChain, cch CrossChainHelper) *TxPool { 226 // Sanitize the input to ensure no vulnerable gas prices are set 227 config = (&config).sanitize() 228 229 // Create the transaction pool with its initial settings 230 pool := &TxPool{ 231 config: config, 232 chainconfig: chainconfig, 233 chain: chain, 234 signer: types.NewEIP155Signer(chainconfig.ChainId), 235 pending: make(map[common.Address]*txList), 236 queue: make(map[common.Address]*txList), 237 beats: make(map[common.Address]time.Time), 238 all: make(map[common.Hash]*types.Transaction), 239 chainHeadCh: make(chan ChainHeadEvent, chainHeadChanSize), 240 gasPrice: new(big.Int).SetUint64(config.PriceLimit), 241 cch: cch, 242 } 243 pool.locals = newAccountSet(pool.signer) 244 pool.priced = newTxPricedList(&pool.all) 245 pool.reset(nil, chain.CurrentBlock().Header()) 246 247 // If local transactions and journaling is enabled, load from disk 248 if !config.NoLocals && config.Journal != "" { 249 pool.journal = newTxJournal(config.Journal) 250 251 log.Debug("Load transaction journal", "journal", pool.journal) 252 if err := pool.journal.load(pool.AddLocal); err != nil { 253 log.Warn("Failed to load transaction journal", "err", err) 254 } 255 if err := pool.journal.rotate(pool.local()); err != nil { 256 log.Warn("Failed to rotate transaction journal", "err", err) 257 } 258 } 259 260 TxPoolSigner = pool.signer 261 262 // Subscribe events from blockchain 263 pool.chainHeadSub = pool.chain.SubscribeChainHeadEvent(pool.chainHeadCh) 264 265 // Start the event loop and return 266 pool.wg.Add(1) 267 go pool.loop() 268 269 return pool 270 } 271 272 // loop is the transaction pool's main event loop, waiting for and reacting to 273 // outside blockchain events as well as for various reporting and transaction 274 // eviction events. 275 func (pool *TxPool) loop() { 276 defer pool.wg.Done() 277 278 // Start the stats reporting and transaction eviction tickers 279 var prevPending, prevQueued, prevStales int 280 281 report := time.NewTicker(statsReportInterval) 282 defer report.Stop() 283 284 evict := time.NewTicker(evictionInterval) 285 defer evict.Stop() 286 287 journal := time.NewTicker(pool.config.Rejournal) 288 defer journal.Stop() 289 290 // Track the previous head headers for transaction reorgs 291 head := pool.chain.CurrentBlock() 292 293 // Keep waiting for and reacting to the various events 294 for { 295 select { 296 // Handle ChainHeadEvent 297 case ev := <-pool.chainHeadCh: 298 if ev.Block != nil { 299 pool.mu.Lock() 300 pool.reset(head.Header(), ev.Block.Header()) 301 head = ev.Block 302 pool.mu.Unlock() 303 } 304 // Be unsubscribed due to system stopped 305 case <-pool.chainHeadSub.Err(): 306 return 307 308 // Handle stats reporting ticks 309 case <-report.C: 310 pool.mu.RLock() 311 pending, queued := pool.stats() 312 stales := pool.priced.stales 313 pool.mu.RUnlock() 314 315 if pending != prevPending || queued != prevQueued || stales != prevStales { 316 log.Debug("Transaction pool status report", "executable", pending, "queued", queued, "stales", stales) 317 prevPending, prevQueued, prevStales = pending, queued, stales 318 } 319 320 // Handle inactive account transaction eviction 321 case <-evict.C: 322 pool.mu.Lock() 323 for addr := range pool.queue { 324 // Skip local transactions from the eviction mechanism 325 if pool.locals.contains(addr) { 326 continue 327 } 328 // Any non-locals old enough should be removed 329 if time.Since(pool.beats[addr]) > pool.config.Lifetime { 330 for _, tx := range pool.queue[addr].Flatten() { 331 pool.removeTx(tx.Hash()) 332 } 333 } 334 } 335 pool.mu.Unlock() 336 337 // Handle local transaction journal rotation 338 case <-journal.C: 339 if pool.journal != nil { 340 pool.mu.Lock() 341 if err := pool.journal.rotate(pool.local()); err != nil { 342 log.Warn("Failed to rotate local tx journal", "err", err) 343 } 344 pool.mu.Unlock() 345 } 346 } 347 } 348 } 349 350 // lockedReset is a wrapper around reset to allow calling it in a thread safe 351 // manner. This method is only ever used in the tester! 352 func (pool *TxPool) lockedReset(oldHead, newHead *types.Header) { 353 pool.mu.Lock() 354 defer pool.mu.Unlock() 355 356 pool.reset(oldHead, newHead) 357 } 358 359 // reset retrieves the current state of the blockchain and ensures the content 360 // of the transaction pool is valid with regard to the chain state. 361 func (pool *TxPool) reset(oldHead, newHead *types.Header) { 362 // If we're reorging an old state, reinject all dropped transactions 363 var reinject types.Transactions 364 365 if oldHead != nil && oldHead.Hash() != newHead.ParentHash { 366 // If the reorg is too deep, avoid doing it (will happen during fast sync) 367 oldNum := oldHead.Number.Uint64() 368 newNum := newHead.Number.Uint64() 369 370 if depth := uint64(math.Abs(float64(oldNum) - float64(newNum))); depth > 64 { 371 log.Debug("Skipping deep transaction reorg", "depth", depth) 372 } else { 373 // Reorg seems shallow enough to pull in all transactions into memory 374 var discarded, included types.Transactions 375 376 var ( 377 rem = pool.chain.GetBlock(oldHead.Hash(), oldHead.Number.Uint64()) 378 add = pool.chain.GetBlock(newHead.Hash(), newHead.Number.Uint64()) 379 ) 380 for rem.NumberU64() > add.NumberU64() { 381 discarded = append(discarded, rem.Transactions()...) 382 if rem = pool.chain.GetBlock(rem.ParentHash(), rem.NumberU64()-1); rem == nil { 383 log.Error("Unrooted old chain seen by tx pool", "block", oldHead.Number, "hash", oldHead.Hash()) 384 return 385 } 386 } 387 for add.NumberU64() > rem.NumberU64() { 388 included = append(included, add.Transactions()...) 389 if add = pool.chain.GetBlock(add.ParentHash(), add.NumberU64()-1); add == nil { 390 log.Error("Unrooted new chain seen by tx pool", "block", newHead.Number, "hash", newHead.Hash()) 391 return 392 } 393 } 394 for rem.Hash() != add.Hash() { 395 discarded = append(discarded, rem.Transactions()...) 396 if rem = pool.chain.GetBlock(rem.ParentHash(), rem.NumberU64()-1); rem == nil { 397 log.Error("Unrooted old chain seen by tx pool", "block", oldHead.Number, "hash", oldHead.Hash()) 398 return 399 } 400 included = append(included, add.Transactions()...) 401 if add = pool.chain.GetBlock(add.ParentHash(), add.NumberU64()-1); add == nil { 402 log.Error("Unrooted new chain seen by tx pool", "block", newHead.Number, "hash", newHead.Hash()) 403 return 404 } 405 } 406 reinject = types.TxDifference(discarded, included) 407 } 408 } 409 // Initialize the internal state to the current head 410 if newHead == nil { 411 newHead = pool.chain.CurrentBlock().Header() // Special case during testing 412 } 413 statedb, err := pool.chain.StateAt(newHead.Root) 414 if err != nil { 415 log.Error("Failed to reset txpool state", "err", err) 416 return 417 } 418 pool.currentState = statedb 419 pool.pendingState = state.ManageState(statedb) 420 pool.currentMaxGas = newHead.GasLimit 421 422 // Inject any transactions discarded due to reorgs 423 log.Debug("Reinjecting stale transactions", "count", len(reinject)) 424 pool.addTxsLocked(reinject, false) 425 426 // validate the pool of pending transactions, this will remove 427 // any transactions that have been included in the block or 428 // have been invalidated because of another transaction (e.g. 429 // higher gas price) 430 pool.demoteUnexecutables() 431 432 // Update all accounts to the latest known pending nonce 433 for addr, list := range pool.pending { 434 txs := list.Flatten() // Heavy but will be cached and is needed by the miner anyway 435 pool.pendingState.SetNonce(addr, txs[len(txs)-1].Nonce()+1) 436 } 437 // Check the queue and move transactions over to the pending if possible 438 // or remove those that have become invalid 439 pool.promoteExecutables(nil) 440 } 441 442 // Stop terminates the transaction pool. 443 func (pool *TxPool) Stop() { 444 // Unsubscribe all subscriptions registered from txpool 445 pool.scope.Close() 446 447 // Unsubscribe subscriptions registered from blockchain 448 pool.chainHeadSub.Unsubscribe() 449 pool.wg.Wait() 450 451 if pool.journal != nil { 452 pool.journal.close() 453 } 454 log.Info("Transaction pool stopped") 455 } 456 457 // SubscribeTxPreEvent registers a subscription of TxPreEvent and 458 // starts sending event to the given channel. 459 func (pool *TxPool) SubscribeTxPreEvent(ch chan<- TxPreEvent) event.Subscription { 460 return pool.scope.Track(pool.txFeed.Subscribe(ch)) 461 } 462 463 // GasPrice returns the current gas price enforced by the transaction pool. 464 func (pool *TxPool) GasPrice() *big.Int { 465 pool.mu.RLock() 466 defer pool.mu.RUnlock() 467 468 return new(big.Int).Set(pool.gasPrice) 469 } 470 471 // SetGasPrice updates the minimum price required by the transaction pool for a 472 // new transaction, and drops all transactions below this threshold. 473 func (pool *TxPool) SetGasPrice(price *big.Int) { 474 pool.mu.Lock() 475 defer pool.mu.Unlock() 476 477 pool.gasPrice = price 478 for _, tx := range pool.priced.Cap(price, pool.locals) { 479 pool.removeTx(tx.Hash()) 480 } 481 log.Info("Transaction pool price threshold updated", "price", price) 482 } 483 484 // State returns the virtual managed state of the transaction pool. 485 func (pool *TxPool) State() *state.ManagedState { 486 pool.mu.RLock() 487 defer pool.mu.RUnlock() 488 489 return pool.pendingState 490 } 491 492 // Stats retrieves the current pool stats, namely the number of pending and the 493 // number of queued (non-executable) transactions. 494 func (pool *TxPool) Stats() (int, int) { 495 pool.mu.RLock() 496 defer pool.mu.RUnlock() 497 498 return pool.stats() 499 } 500 501 // stats retrieves the current pool stats, namely the number of pending and the 502 // number of queued (non-executable) transactions. 503 func (pool *TxPool) stats() (int, int) { 504 pending := 0 505 for _, list := range pool.pending { 506 pending += list.Len() 507 } 508 queued := 0 509 for _, list := range pool.queue { 510 queued += list.Len() 511 } 512 return pending, queued 513 } 514 515 // Content retrieves the data content of the transaction pool, returning all the 516 // pending as well as queued transactions, grouped by account and sorted by nonce. 517 func (pool *TxPool) Content() (map[common.Address]types.Transactions, map[common.Address]types.Transactions) { 518 pool.mu.Lock() 519 defer pool.mu.Unlock() 520 521 pending := make(map[common.Address]types.Transactions) 522 for addr, list := range pool.pending { 523 pending[addr] = list.Flatten() 524 } 525 queued := make(map[common.Address]types.Transactions) 526 for addr, list := range pool.queue { 527 queued[addr] = list.Flatten() 528 } 529 return pending, queued 530 } 531 532 // Pending retrieves all currently processable transactions, groupped by origin 533 // account and sorted by nonce. The returned transaction set is a copy and can be 534 // freely modified by calling code. 535 func (pool *TxPool) Pending() (map[common.Address]types.Transactions, error) { 536 pool.mu.Lock() 537 defer pool.mu.Unlock() 538 539 pending := make(map[common.Address]types.Transactions) 540 for addr, list := range pool.pending { 541 pending[addr] = list.Flatten() 542 } 543 return pending, nil 544 } 545 546 // local retrieves all currently known local transactions, groupped by origin 547 // account and sorted by nonce. The returned transaction set is a copy and can be 548 // freely modified by calling code. 549 func (pool *TxPool) local() map[common.Address]types.Transactions { 550 txs := make(map[common.Address]types.Transactions) 551 for addr := range pool.locals.accounts { 552 if pending := pool.pending[addr]; pending != nil { 553 txs[addr] = append(txs[addr], pending.Flatten()...) 554 } 555 if queued := pool.queue[addr]; queued != nil { 556 txs[addr] = append(txs[addr], queued.Flatten()...) 557 } 558 } 559 return txs 560 } 561 562 // validateTx checks whether a transaction is valid according to the consensus 563 // rules and adheres to some heuristic limits of the local node (price and size). 564 func (pool *TxPool) validateTx(tx *types.Transaction, local bool) error { 565 // Heuristic limit, reject transactions over 32KB to prevent DOS attacks 566 if tx.Size() > 32*1024 { 567 return ErrOversizedData 568 } 569 570 // Transactions can't be negative. This may never happen using RLP decoded 571 // transactions but may occur if you create a transaction using the RPC. 572 if tx.Value().Sign() < 0 { 573 return ErrNegativeValue 574 } 575 // Ensure the transaction doesn't exceed the current block limit gas. 576 if pool.currentMaxGas < tx.Gas() { 577 return ErrGasLimit 578 } 579 580 // Make sure the transaction is signed properly 581 from, err := types.Sender(pool.signer, tx) 582 if err != nil { 583 return ErrInvalidSender 584 } 585 // Drop non-local transactions under our own minimal accepted gas price 586 local = local || pool.locals.contains(from) // account may be local even if the transaction arrived from the network 587 if !local && pool.gasPrice.Cmp(tx.GasPrice()) > 0 { 588 return ErrUnderpriced 589 } 590 // Ensure the transaction adheres to nonce ordering 591 if pool.currentState.GetNonce(from) > tx.Nonce() { 592 return ErrNonceTooLow 593 } 594 595 // Transactor should have enough funds to cover the costs 596 // cost == V + GP * GL 597 if pool.currentState.GetBalance(from).Cmp(tx.Cost()) < 0 { 598 return ErrInsufficientFunds 599 } 600 601 // check address 602 if tx.To() != nil && !crypto.ValidateNEATAddr(string(tx.To()[:])) { 603 return ErrInvalidAddress 604 } 605 606 if !neatAbi.IsNeatChainContractAddr(tx.To()) { 607 intrGas, err := IntrinsicGas(tx.Data(), tx.To() == nil, true) 608 if err != nil { 609 return err 610 } 611 if tx.Gas() < intrGas { 612 return ErrIntrinsicGas 613 } 614 } else { 615 // the first 4 bytes is the function identifier 616 data := tx.Data() 617 function, err := neatAbi.FunctionTypeFromId(data[:4]) 618 if err != nil { 619 return err 620 } 621 622 // check Function main/side flag 623 if pool.chainconfig.IsMainChain() && !function.AllowInMainChain() { 624 return ErrNotAllowedInMainChain 625 } else if !pool.chainconfig.IsMainChain() && !function.AllowInSideChain() { 626 return ErrNotAllowedInSideChain 627 } 628 629 log.Infof("validateTx Chain Function %v", function.String()) 630 if validateCb := GetValidateCb(function); validateCb != nil { 631 if function.IsCrossChainType() { 632 if fn, ok := validateCb.(CrossChainValidateCb); ok { 633 pool.cch.GetMutex().Lock() 634 err := fn(tx, pool.currentState, pool.cch) 635 pool.cch.GetMutex().Unlock() 636 if err != nil { 637 return err 638 } 639 } else { 640 panic("callback func is wrong, this should not happened, please check the code") 641 } 642 } else { 643 if fn, ok := validateCb.(NonCrossChainValidateCb); ok { 644 if err := fn(tx, pool.currentState, pool.chain.(*BlockChain)); err != nil { 645 return err 646 } 647 } else { 648 panic("callback func is wrong, this should not happened, please check the code") 649 } 650 } 651 } 652 } 653 654 return nil 655 } 656 657 // add validates a transaction and inserts it into the non-executable queue for 658 // later pending promotion and execution. If the transaction is a replacement for 659 // an already pending or queued one, it overwrites the previous and returns this 660 // so outer code doesn't uselessly call promote. 661 // 662 // If a newly added transaction is marked as local, its sending account will be 663 // whitelisted, preventing any associated transaction from being dropped out of 664 // the pool due to pricing constraints. 665 func (pool *TxPool) add(tx *types.Transaction, local bool) (bool, error) { 666 // If the transaction is already known, discard it 667 hash := tx.Hash() 668 if pool.all[hash] != nil { 669 log.Trace("Discarding already known transaction", "hash", hash) 670 return false, fmt.Errorf("known transaction: %x", hash) 671 } 672 // If the transaction fails basic validation, discard it 673 if err := pool.validateTx(tx, local); err != nil { 674 log.Trace("Discarding invalid transaction", "hash", hash, "err", err) 675 invalidTxCounter.Inc(1) 676 return false, err 677 } 678 679 // If the transaction pool is full, discard underpriced transactions 680 if !params.GenCfg.PerfTest && 681 uint64(len(pool.all)) >= pool.config.GlobalSlots+pool.config.GlobalQueue { 682 // If the new transaction is underpriced, don't accept it 683 if pool.priced.Underpriced(tx, pool.locals) { 684 log.Trace("Discarding underpriced transaction", "hash", hash, "price", tx.GasPrice()) 685 underpricedTxCounter.Inc(1) 686 return false, ErrUnderpriced 687 } 688 // New transaction is better than our worse ones, make room for it 689 drop := pool.priced.Discard(len(pool.all)-int(pool.config.GlobalSlots+pool.config.GlobalQueue-1), pool.locals) 690 for _, tx := range drop { 691 log.Trace("Discarding freshly underpriced transaction", "hash", tx.Hash(), "price", tx.GasPrice()) 692 underpricedTxCounter.Inc(1) 693 pool.removeTx(tx.Hash()) 694 } 695 } 696 697 // If the transaction is replacing an already pending one, do directly 698 from, _ := types.Sender(pool.signer, tx) // already validated 699 if list := pool.pending[from]; list != nil && list.Overlaps(tx) { 700 // Nonce already pending, check if required price bump is met 701 inserted, old := list.Add(tx, pool.config.PriceBump) 702 if !inserted { 703 pendingDiscardCounter.Inc(1) 704 return false, ErrReplaceUnderpriced 705 } 706 // New transaction is better, replace old one 707 if old != nil { 708 delete(pool.all, old.Hash()) 709 pool.priced.Removed() 710 pendingReplaceCounter.Inc(1) 711 } 712 pool.all[tx.Hash()] = tx 713 pool.priced.Put(tx) 714 pool.journalTx(from, tx) 715 716 log.Trace("Pooled new executable transaction", "hash", hash, "from", from, "to", tx.To()) 717 718 // We've directly injected a replacement transaction, notify subsystems 719 go pool.txFeed.Send(TxPreEvent{tx}) 720 721 return old != nil, nil 722 } 723 724 // New transaction isn't replacing a pending one, push into queue 725 replace, err := pool.enqueueTx(hash, tx) 726 if err != nil { 727 return false, err 728 } 729 // Mark local addresses and journal local transactions 730 if local { 731 pool.locals.add(from) 732 } 733 pool.journalTx(from, tx) 734 735 log.Trace("Pooled new future transaction", "hash", hash, "from", from, "to", tx.To()) 736 return replace, nil 737 } 738 739 // enqueueTx inserts a new transaction into the non-executable transaction queue. 740 // 741 // Note, this method assumes the pool lock is held! 742 func (pool *TxPool) enqueueTx(hash common.Hash, tx *types.Transaction) (bool, error) { 743 // Try to insert the transaction into the future queue 744 from, _ := types.Sender(pool.signer, tx) // already validated 745 if pool.queue[from] == nil { 746 pool.queue[from] = newTxList(false) 747 } 748 inserted, old := pool.queue[from].Add(tx, pool.config.PriceBump) 749 if !inserted { 750 // An older transaction was better, discard this 751 queuedDiscardCounter.Inc(1) 752 return false, ErrReplaceUnderpriced 753 } 754 // Discard any previous transaction and mark this 755 if old != nil { 756 delete(pool.all, old.Hash()) 757 pool.priced.Removed() 758 queuedReplaceCounter.Inc(1) 759 } 760 pool.all[hash] = tx 761 pool.priced.Put(tx) 762 return old != nil, nil 763 } 764 765 // journalTx adds the specified transaction to the local disk journal if it is 766 // deemed to have been sent from a local account. 767 func (pool *TxPool) journalTx(from common.Address, tx *types.Transaction) { 768 // Only journal if it's enabled and the transaction is local 769 if pool.journal == nil || !pool.locals.contains(from) { 770 return 771 } 772 if err := pool.journal.insert(tx); err != nil { 773 log.Warn("Failed to journal local transaction", "err", err) 774 } 775 } 776 777 // promoteTx adds a transaction to the pending (processable) list of transactions. 778 // 779 // Note, this method assumes the pool lock is held! 780 func (pool *TxPool) promoteTx(addr common.Address, hash common.Hash, tx *types.Transaction) { 781 // Try to insert the transaction into the pending queue 782 if pool.pending[addr] == nil { 783 pool.pending[addr] = newTxList(true) 784 } 785 list := pool.pending[addr] 786 787 inserted, old := list.Add(tx, pool.config.PriceBump) 788 if !inserted { 789 // An older transaction was better, discard this 790 delete(pool.all, hash) 791 pool.priced.Removed() 792 793 pendingDiscardCounter.Inc(1) 794 return 795 } 796 // Otherwise discard any previous transaction and mark this 797 if old != nil { 798 delete(pool.all, old.Hash()) 799 pool.priced.Removed() 800 801 pendingReplaceCounter.Inc(1) 802 } 803 // Failsafe to work around direct pending inserts (tests) 804 if pool.all[hash] == nil { 805 pool.all[hash] = tx 806 pool.priced.Put(tx) 807 } 808 // Set the potentially new pending nonce and notify any subsystems of the new tx 809 pool.beats[addr] = time.Now() 810 pool.pendingState.SetNonce(addr, tx.Nonce()+1) 811 812 go pool.txFeed.Send(TxPreEvent{tx}) 813 } 814 815 // AddLocal enqueues a single transaction into the pool if it is valid, marking 816 // the sender as a local one in the mean time, ensuring it goes around the local 817 // pricing constraints. 818 func (pool *TxPool) AddLocal(tx *types.Transaction) error { 819 return pool.addTx(tx, !pool.config.NoLocals) 820 } 821 822 // AddRemote enqueues a single transaction into the pool if it is valid. If the 823 // sender is not among the locally tracked ones, full pricing constraints will 824 // apply. 825 func (pool *TxPool) AddRemote(tx *types.Transaction) error { 826 return pool.addTx(tx, false) 827 } 828 829 // AddLocals enqueues a batch of transactions into the pool if they are valid, 830 // marking the senders as a local ones in the mean time, ensuring they go around 831 // the local pricing constraints. 832 func (pool *TxPool) AddLocals(txs []*types.Transaction) []error { 833 return pool.addTxs(txs, !pool.config.NoLocals) 834 } 835 836 // AddRemotes enqueues a batch of transactions into the pool if they are valid. 837 // If the senders are not among the locally tracked ones, full pricing constraints 838 // will apply. 839 func (pool *TxPool) AddRemotes(txs []*types.Transaction) []error { 840 return pool.addTxs(txs, false) 841 } 842 843 // addTx enqueues a single transaction into the pool if it is valid. 844 func (pool *TxPool) addTx(tx *types.Transaction, local bool) error { 845 pool.mu.Lock() 846 defer pool.mu.Unlock() 847 848 // Try to inject the transaction and update any state 849 replace, err := pool.add(tx, local) 850 if err != nil { 851 return err 852 } 853 // If we added a new transaction, run promotion checks and return 854 if !replace { 855 from, _ := types.Sender(pool.signer, tx) // already validated 856 pool.promoteExecutables([]common.Address{from}) 857 } 858 return nil 859 } 860 861 // addTxs attempts to queue a batch of transactions if they are valid. 862 func (pool *TxPool) addTxs(txs []*types.Transaction, local bool) []error { 863 pool.mu.Lock() 864 defer pool.mu.Unlock() 865 return pool.addTxsLocked(txs, local) 866 } 867 868 // addTxsLocked attempts to queue a batch of transactions if they are valid, 869 // whilst assuming the transaction pool lock is already held. 870 func (pool *TxPool) addTxsLocked(txs []*types.Transaction, local bool) []error { 871 // Add the batch of transaction, tracking the accepted ones 872 dirty := make(map[common.Address]struct{}) 873 errs := make([]error, len(txs)) 874 for i, tx := range txs { 875 var replace bool 876 if replace, errs[i] = pool.add(tx, local); errs[i] == nil { 877 if !replace { 878 from, _ := types.Sender(pool.signer, tx) // already validated 879 dirty[from] = struct{}{} 880 } 881 } 882 } 883 // Only reprocess the internal state if something was actually added 884 if len(dirty) > 0 { 885 addrs := make([]common.Address, 0, len(dirty)) 886 for addr := range dirty { 887 addrs = append(addrs, addr) 888 } 889 pool.promoteExecutables(addrs) 890 } 891 892 return errs 893 } 894 895 // Status returns the status (unknown/pending/queued) of a batch of transactions 896 // identified by their hashes. 897 func (pool *TxPool) Status(hashes []common.Hash) []TxStatus { 898 pool.mu.RLock() 899 defer pool.mu.RUnlock() 900 901 status := make([]TxStatus, len(hashes)) 902 for i, hash := range hashes { 903 if tx := pool.all[hash]; tx != nil { 904 from, _ := types.Sender(pool.signer, tx) // already validated 905 if pool.pending[from] != nil && pool.pending[from].txs.items[tx.Nonce()] != nil { 906 status[i] = TxStatusPending 907 } else { 908 status[i] = TxStatusQueued 909 } 910 } 911 } 912 return status 913 } 914 915 // Get returns a transaction if it is contained in the pool 916 // and nil otherwise. 917 func (pool *TxPool) Get(hash common.Hash) *types.Transaction { 918 pool.mu.RLock() 919 defer pool.mu.RUnlock() 920 921 return pool.all[hash] 922 } 923 924 // RemoveTxs remove transaction due to validate failed during mining (commit transaction) 925 // (eg: tx4 validate pass when addtx but failed during executing, because tx4 can be validated only when tx3 proof available in local tx3 db) 926 func (pool *TxPool) RemoveTxs(txs types.Transactions) { 927 pool.mu.Lock() 928 defer pool.mu.Unlock() 929 930 for _, tx := range txs { 931 pool.removeTx(tx.Hash()) 932 } 933 } 934 935 // removeTx removes a single transaction from the queue, moving all subsequent 936 // transactions back to the future queue. 937 func (pool *TxPool) removeTx(hash common.Hash) { 938 // Fetch the transaction we wish to delete 939 tx, ok := pool.all[hash] 940 if !ok { 941 return 942 } 943 addr, _ := types.Sender(pool.signer, tx) // already validated during insertion 944 945 // Remove it from the list of known transactions 946 delete(pool.all, hash) 947 pool.priced.Removed() 948 949 // Remove the transaction from the pending lists and reset the account nonce 950 if pending := pool.pending[addr]; pending != nil { 951 if removed, invalids := pending.Remove(tx); removed { 952 // If no more pending transactions are left, remove the list 953 if pending.Empty() { 954 delete(pool.pending, addr) 955 delete(pool.beats, addr) 956 } 957 // Postpone any invalidated transactions 958 for _, tx := range invalids { 959 pool.enqueueTx(tx.Hash(), tx) 960 } 961 // Update the account nonce if needed 962 if nonce := tx.Nonce(); pool.pendingState.GetNonce(addr) > nonce { 963 pool.pendingState.SetNonce(addr, nonce) 964 } 965 return 966 } 967 } 968 // Transaction is in the future queue 969 if future := pool.queue[addr]; future != nil { 970 future.Remove(tx) 971 if future.Empty() { 972 delete(pool.queue, addr) 973 } 974 } 975 } 976 977 // promoteExecutables moves transactions that have become processable from the 978 // future queue to the set of pending transactions. During this process, all 979 // invalidated transactions (low nonce, low balance) are deleted. 980 func (pool *TxPool) promoteExecutables(accounts []common.Address) { 981 // Gather all the accounts potentially needing updates 982 if accounts == nil { 983 accounts = make([]common.Address, 0, len(pool.queue)) 984 for addr := range pool.queue { 985 accounts = append(accounts, addr) 986 } 987 } 988 // Iterate over all accounts and promote any executable transactions 989 for _, addr := range accounts { 990 list := pool.queue[addr] 991 if list == nil { 992 continue // Just in case someone calls with a non existing account 993 } 994 // Drop all transactions that are deemed too old (low nonce) 995 for _, tx := range list.Forward(pool.currentState.GetNonce(addr)) { 996 hash := tx.Hash() 997 log.Trace("Removed old queued transaction", "hash", hash) 998 delete(pool.all, hash) 999 pool.priced.Removed() 1000 } 1001 // Drop all transactions that are too costly (low balance or out of gas) 1002 drops, _ := list.Filter(pool.currentState.GetBalance(addr), pool.currentMaxGas) 1003 for _, tx := range drops { 1004 hash := tx.Hash() 1005 log.Trace("Removed unpayable queued transaction", "hash", hash) 1006 delete(pool.all, hash) 1007 pool.priced.Removed() 1008 queuedNofundsCounter.Inc(1) 1009 } 1010 // Gather all executable transactions and promote them 1011 for _, tx := range list.Ready(pool.pendingState.GetNonce(addr)) { 1012 hash := tx.Hash() 1013 log.Trace("Promoting queued transaction", "hash", hash) 1014 pool.promoteTx(addr, hash, tx) 1015 } 1016 // Drop all transactions over the allowed limit 1017 if !pool.locals.contains(addr) { 1018 for _, tx := range list.Cap(int(pool.config.AccountQueue)) { 1019 hash := tx.Hash() 1020 delete(pool.all, hash) 1021 pool.priced.Removed() 1022 queuedRateLimitCounter.Inc(1) 1023 log.Trace("Removed cap-exceeding queued transaction", "hash", hash) 1024 } 1025 } 1026 // Delete the entire queue entry if it became empty. 1027 if list.Empty() { 1028 delete(pool.queue, addr) 1029 } 1030 } 1031 // If the pending limit is overflown, start equalizing allowances 1032 pending := uint64(0) 1033 for _, list := range pool.pending { 1034 pending += uint64(list.Len()) 1035 } 1036 if pending > pool.config.GlobalSlots { 1037 pendingBeforeCap := pending 1038 // Assemble a spam order to penalize large transactors first 1039 spammers := prque.New(nil) 1040 for addr, list := range pool.pending { 1041 // Only evict transactions from high rollers 1042 if !pool.locals.contains(addr) && uint64(list.Len()) > pool.config.AccountSlots { 1043 spammers.Push(addr, int64(list.Len())) 1044 } 1045 } 1046 // Gradually drop transactions from offenders 1047 offenders := []common.Address{} 1048 for pending > pool.config.GlobalSlots && !spammers.Empty() { 1049 // Retrieve the next offender if not local address 1050 offender, _ := spammers.Pop() 1051 offenders = append(offenders, offender.(common.Address)) 1052 1053 // Equalize balances until all the same or below threshold 1054 if len(offenders) > 1 { 1055 // Calculate the equalization threshold for all current offenders 1056 threshold := pool.pending[offender.(common.Address)].Len() 1057 1058 // Iteratively reduce all offenders until below limit or threshold reached 1059 for pending > pool.config.GlobalSlots && pool.pending[offenders[len(offenders)-2]].Len() > threshold { 1060 for i := 0; i < len(offenders)-1; i++ { 1061 list := pool.pending[offenders[i]] 1062 for _, tx := range list.Cap(list.Len() - 1) { 1063 // Drop the transaction from the global pools too 1064 hash := tx.Hash() 1065 delete(pool.all, hash) 1066 pool.priced.Removed() 1067 1068 // Update the account nonce to the dropped transaction 1069 if nonce := tx.Nonce(); pool.pendingState.GetNonce(offenders[i]) > nonce { 1070 pool.pendingState.SetNonce(offenders[i], nonce) 1071 } 1072 log.Trace("Removed fairness-exceeding pending transaction", "hash", hash) 1073 } 1074 pending-- 1075 } 1076 } 1077 } 1078 } 1079 // If still above threshold, reduce to limit or min allowance 1080 if pending > pool.config.GlobalSlots && len(offenders) > 0 { 1081 for pending > pool.config.GlobalSlots && uint64(pool.pending[offenders[len(offenders)-1]].Len()) > pool.config.AccountSlots { 1082 for _, addr := range offenders { 1083 list := pool.pending[addr] 1084 for _, tx := range list.Cap(list.Len() - 1) { 1085 // Drop the transaction from the global pools too 1086 hash := tx.Hash() 1087 delete(pool.all, hash) 1088 pool.priced.Removed() 1089 1090 // Update the account nonce to the dropped transaction 1091 if nonce := tx.Nonce(); pool.pendingState.GetNonce(addr) > nonce { 1092 pool.pendingState.SetNonce(addr, nonce) 1093 } 1094 log.Trace("Removed fairness-exceeding pending transaction", "hash", hash) 1095 } 1096 pending-- 1097 } 1098 } 1099 } 1100 pendingRateLimitCounter.Inc(int64(pendingBeforeCap - pending)) 1101 } 1102 // If we've queued more transactions than the hard limit, drop oldest ones 1103 queued := uint64(0) 1104 for _, list := range pool.queue { 1105 queued += uint64(list.Len()) 1106 } 1107 if queued > pool.config.GlobalQueue { 1108 // Sort all accounts with queued transactions by heartbeat 1109 addresses := make(addresssByHeartbeat, 0, len(pool.queue)) 1110 for addr := range pool.queue { 1111 if !pool.locals.contains(addr) { // don't drop locals 1112 addresses = append(addresses, addressByHeartbeat{addr, pool.beats[addr]}) 1113 } 1114 } 1115 sort.Sort(addresses) 1116 1117 // Drop transactions until the total is below the limit or only locals remain 1118 for drop := queued - pool.config.GlobalQueue; drop > 0 && len(addresses) > 0; { 1119 addr := addresses[len(addresses)-1] 1120 list := pool.queue[addr.address] 1121 1122 addresses = addresses[:len(addresses)-1] 1123 1124 // Drop all transactions if they are less than the overflow 1125 if size := uint64(list.Len()); size <= drop { 1126 for _, tx := range list.Flatten() { 1127 pool.removeTx(tx.Hash()) 1128 } 1129 drop -= size 1130 queuedRateLimitCounter.Inc(int64(size)) 1131 continue 1132 } 1133 // Otherwise drop only last few transactions 1134 txs := list.Flatten() 1135 for i := len(txs) - 1; i >= 0 && drop > 0; i-- { 1136 pool.removeTx(txs[i].Hash()) 1137 drop-- 1138 queuedRateLimitCounter.Inc(1) 1139 } 1140 } 1141 } 1142 } 1143 1144 // demoteUnexecutables removes invalid and processed transactions from the pools 1145 // executable/pending queue and any subsequent transactions that become unexecutable 1146 // are moved back into the future queue. 1147 func (pool *TxPool) demoteUnexecutables() { 1148 // Iterate over all accounts and demote any non-executable transactions 1149 for addr, list := range pool.pending { 1150 nonce := pool.currentState.GetNonce(addr) 1151 1152 // Drop all transactions that are deemed too old (low nonce) 1153 for _, tx := range list.Forward(nonce) { 1154 hash := tx.Hash() 1155 log.Trace("Removed old pending transaction", "hash", hash) 1156 delete(pool.all, hash) 1157 pool.priced.Removed() 1158 } 1159 // Drop all transactions that are too costly (low balance or out of gas), and queue any invalids back for later 1160 drops, invalids := list.Filter(pool.currentState.GetBalance(addr), pool.currentMaxGas) 1161 for _, tx := range drops { 1162 hash := tx.Hash() 1163 log.Trace("Removed unpayable pending transaction", "hash", hash) 1164 delete(pool.all, hash) 1165 pool.priced.Removed() 1166 pendingNofundsCounter.Inc(1) 1167 } 1168 for _, tx := range invalids { 1169 hash := tx.Hash() 1170 log.Trace("Demoting pending transaction", "hash", hash) 1171 pool.enqueueTx(hash, tx) 1172 } 1173 // If there's a gap in front, warn (should never happen) and postpone all transactions 1174 if list.Len() > 0 && list.txs.Get(nonce) == nil { 1175 for _, tx := range list.Cap(0) { 1176 hash := tx.Hash() 1177 log.Error("Demoting invalidated transaction", "hash", hash) 1178 pool.enqueueTx(hash, tx) 1179 } 1180 } 1181 // Delete the entire queue entry if it became empty. 1182 if list.Empty() { 1183 delete(pool.pending, addr) 1184 delete(pool.beats, addr) 1185 } 1186 } 1187 } 1188 1189 // addressByHeartbeat is an account address tagged with its last activity timestamp. 1190 type addressByHeartbeat struct { 1191 address common.Address 1192 heartbeat time.Time 1193 } 1194 1195 type addresssByHeartbeat []addressByHeartbeat 1196 1197 func (a addresssByHeartbeat) Len() int { return len(a) } 1198 func (a addresssByHeartbeat) Less(i, j int) bool { return a[i].heartbeat.Before(a[j].heartbeat) } 1199 func (a addresssByHeartbeat) Swap(i, j int) { a[i], a[j] = a[j], a[i] } 1200 1201 // accountSet is simply a set of addresses to check for existence, and a signer 1202 // capable of deriving addresses from transactions. 1203 type accountSet struct { 1204 accounts map[common.Address]struct{} 1205 signer types.Signer 1206 } 1207 1208 // newAccountSet creates a new address set with an associated signer for sender 1209 // derivations. 1210 func newAccountSet(signer types.Signer) *accountSet { 1211 return &accountSet{ 1212 accounts: make(map[common.Address]struct{}), 1213 signer: signer, 1214 } 1215 } 1216 1217 // contains checks if a given address is contained within the set. 1218 func (as *accountSet) contains(addr common.Address) bool { 1219 _, exist := as.accounts[addr] 1220 return exist 1221 } 1222 1223 // containsTx checks if the sender of a given tx is within the set. If the sender 1224 // cannot be derived, this method returns false. 1225 func (as *accountSet) containsTx(tx *types.Transaction) bool { 1226 if addr, err := types.Sender(as.signer, tx); err == nil { 1227 return as.contains(addr) 1228 } 1229 return false 1230 } 1231 1232 // add inserts a new address into the set to track. 1233 func (as *accountSet) add(addr common.Address) { 1234 as.accounts[addr] = struct{}{} 1235 }