func (s *State) ProcessSlots(upTo uint64, view BlockView, c *config.Config) (*EpochTransitionOutput, error) {
	var aggregateOutput EpochTransitionOutput

	for s.Slot < upTo {
		// this only happens when there wasn't a block at the first slot of the epoch
		if s.Slot/c.EpochLength > s.EpochIndex && s.Slot%c.EpochLength == 0 {
			output, err := s.ProcessEpochTransition(c)
			if err != nil {
				return nil, err
			}

			aggregateOutput.Receipts = append(aggregateOutput.Receipts, output.Receipts...)
			aggregateOutput.Crosslinks = append(aggregateOutput.Crosslinks, output.Crosslinks...)
		}

		tip, err := view.Tip()
		if err != nil {
			return nil, err
		}

		err = s.ProcessSlot(tip, c)
		if err != nil {
			return nil, err
		}

		view.SetTipSlot(s.Slot)
	}

	return &aggregateOutput, nil
}
// ProcessSlots uses the current head to process slots up to a certain slot, applying
// slot transitions and epoch transitions, and returns the updated state. Note that this should
// only process up to the current slot number so that the lastBlockHash remains constant.
ProcessSlots uses the current head to process slots up to a certain slot, applying
slot transitions and epoch transitions, and returns the updated state. Note that this should
only process up to the current slot number so that the lastBlockHash remains constant.
// ProcessSlots uses the current head to process slots up to a certain slot applying // slot transitions and epoch transitions and returns the updated state . Note that this should // only process up to the current slot number so that the lastBlockHash remains constant .
func (s *State) ProcessSlots(upTo uint64, view BlockView, c *config.Config) (*EpochTransitionOutput, error) {
	var aggregateOutput EpochTransitionOutput
	for s.Slot < upTo {
		if s.Slot/c.EpochLength > s.EpochIndex && s.Slot%c.EpochLength == 0 {
			output, err := s.ProcessEpochTransition(c)
			if err != nil {
				return nil, err
			}
			aggregateOutput.Receipts = append(aggregateOutput.Receipts, output.Receipts...)
			aggregateOutput.Crosslinks = append(aggregateOutput.Crosslinks, output.Crosslinks...)
		}
		tip, err := view.Tip()
		if err != nil {
			return nil, err
		}
		err = s.ProcessSlot(tip, c)
		if err != nil {
			return nil, err
		}
		view.SetTipSlot(s.Slot)
	}
	return &aggregateOutput, nil
}
func ( s * State ) ProcessSlots ( upTo uint64 , view BlockView , c * config . Config ) ( * EpochTransitionOutput , error ) { var aggregateOutput EpochTransitionOutput for s . Slot < upTo { if s . Slot / c . EpochLength > s . EpochIndex && s . Slot % c . EpochLength == 0 { output , err := s . ProcessEpochTransition ( c ) if err != nil { return nil , err } aggregateOutput . Receipts = append ( aggregateOutput . Receipts , output . Receipts ... ) aggregateOutput . Crosslinks = append ( aggregateOutput . Crosslinks , output . Crosslinks ... ) } tip , err := view . Tip ( ) if err != nil { return nil , err } err = s . ProcessSlot ( tip , c ) if err != nil { return nil , err } view . SetTipSlot ( s . Slot ) } return & aggregateOutput , nil }
ProcessSlots uses the current head to process slots up to a certain slot, applying
slot transitions and epoch transitions, and returns the updated state.
ProcessSlots uses the current head to process slots up to a certain slot applying slot transitions and epoch transitions and returns the updated state .
// this only happens when there wasn't a block at the first slot of the epoch