// Prepare configures the result cache to allow accepting and caching inbound // fetch results. func (q *queue) Prepare(offset uint64, mode SyncMode, pivot uint64, head *types.Header) { q.lock.Lock() defer q.lock.Unlock() // Prepare the queue for sync results if q.resultOffset < offset { q.resultOffset = offset } q.fastSyncPivot = pivot q.mode = mode // If long running fast sync, also start up a head stateretrieval immediately if mode == FastSync && pivot > 0 { q.stateScheduler = state.NewStateSync(head.Root, q.stateDatabase) } }
// Schedule adds a set of headers for the download queue for scheduling, returning // the new headers encountered. func (q *queue) Schedule(headers []*types.Header, from uint64) []*types.Header { q.lock.Lock() defer q.lock.Unlock() // Insert all the headers prioritised by the contained block number inserts := make([]*types.Header, 0, len(headers)) for _, header := range headers { // Make sure chain order is honoured and preserved throughout hash := header.Hash() if header.Number == nil || header.Number.Uint64() != from { glog.V(logger.Warn).Infof("Header #%v [%x] broke chain ordering, expected %d", header.Number, hash[:4], from) break } if q.headerHead != (common.Hash{}) && q.headerHead != header.ParentHash { glog.V(logger.Warn).Infof("Header #%v [%x] broke chain ancestry", header.Number, hash[:4]) break } // Make sure no duplicate requests are executed if _, ok := q.blockTaskPool[hash]; ok { glog.V(logger.Warn).Infof("Header #%d [%x] already scheduled for block fetch", header.Number.Uint64(), hash[:4]) continue } if _, ok := q.receiptTaskPool[hash]; ok { glog.V(logger.Warn).Infof("Header #%d [%x] already scheduled for receipt fetch", header.Number.Uint64(), hash[:4]) continue } // Queue the header for content retrieval q.blockTaskPool[hash] = header q.blockTaskQueue.Push(header, -float32(header.Number.Uint64())) if q.mode == FastSync && header.Number.Uint64() <= q.fastSyncPivot { // Fast phase of the fast sync, retrieve receipts too q.receiptTaskPool[hash] = header q.receiptTaskQueue.Push(header, -float32(header.Number.Uint64())) } if q.mode == FastSync && header.Number.Uint64() == q.fastSyncPivot { // Pivoting point of the fast sync, retrieve the state tries q.stateSchedLock.Lock() q.stateScheduler = state.NewStateSync(header.Root, q.stateDatabase) q.stateSchedLock.Unlock() } inserts = append(inserts, header) q.headerHead = hash from++ } return inserts }