@@ -6,6 +6,7 @@ use std::convert::TryInto;
6
6
7
7
use anyhow:: { anyhow, Context } ;
8
8
use cid:: Cid ;
9
+ use fil_actors_runtime:: network:: EPOCHS_IN_DAY ;
9
10
use fil_actors_runtime:: runtime:: Policy ;
10
11
use fil_actors_runtime:: { ActorDowncast , Array } ;
11
12
use fvm_ipld_amt:: { Error as AmtError , ValueMut } ;
@@ -776,47 +777,63 @@ impl<'db, BS: Blockstore> ExpirationQueue<'db, BS> {
776
777
sector_size : SectorSize ,
777
778
sectors : & [ SectorOnChainInfo ] ,
778
779
) -> anyhow:: Result < Vec < SectorExpirationSet > > {
779
- let mut declared_expirations = BTreeMap :: < ChainEpoch , bool > :: new ( ) ;
780
+ if sectors. is_empty ( ) {
781
+ return Ok ( Vec :: new ( ) ) ;
782
+ }
783
+
780
784
let mut sectors_by_number = BTreeMap :: < u64 , & SectorOnChainInfo > :: new ( ) ;
781
785
let mut all_remaining = BTreeSet :: < u64 > :: new ( ) ;
782
786
787
+ let mut min_expire = i64:: MAX ;
788
+ let mut max_expire = i64:: MIN ;
783
789
for sector in sectors {
784
- let q_expiration = self . quant . quantize_up ( sector. expiration ) ;
785
- declared_expirations. insert ( q_expiration, true ) ;
790
+ if sector. expiration < min_expire {
791
+ min_expire = sector. expiration ;
792
+ }
793
+ if sector. expiration > max_expire {
794
+ max_expire = sector. expiration ;
795
+ }
786
796
all_remaining. insert ( sector. sector_number ) ;
787
797
sectors_by_number. insert ( sector. sector_number , sector) ;
788
798
}
789
799
790
- let mut expiration_groups =
791
- Vec :: < SectorExpirationSet > :: with_capacity ( declared_expirations. len ( ) ) ;
800
+ let mut expiration_groups = Vec :: < SectorExpirationSet > :: with_capacity ( sectors. len ( ) ) ;
792
801
793
- for ( & expiration, _) in declared_expirations. iter ( ) {
794
- let es = self . may_get ( expiration) ?;
802
+ let end_epoch = ( max_expire + EPOCHS_IN_DAY ) as u64 ;
803
+ self . amt . for_each_while_ranged ( Some ( min_expire as u64 ) , None , |epoch, es| {
804
+ if epoch > end_epoch {
805
+ return Ok ( false ) ;
806
+ }
795
807
796
808
let group = group_expiration_set (
797
809
sector_size,
798
810
& sectors_by_number,
799
811
& mut all_remaining,
800
812
es,
801
- expiration ,
813
+ epoch as ChainEpoch ,
802
814
) ;
803
815
if !group. sector_epoch_set . sectors . is_empty ( ) {
804
816
expiration_groups. push ( group) ;
805
817
}
806
- }
818
+
819
+ Ok ( !all_remaining. is_empty ( ) )
820
+ } ) ?;
807
821
808
822
// If sectors remain, traverse next in epoch order. Remaining sectors should be
809
823
// rescheduled to expire soon, so this traversal should exit early.
810
824
if !all_remaining. is_empty ( ) {
825
+ // avoid type cast in the for_each_while below
826
+ let min_expire = min_expire as u64 ;
811
827
self . amt . for_each_while ( |epoch, es| {
812
- let epoch = epoch as ChainEpoch ;
813
- // If this set's epoch is one of our declared epochs, we've already processed it
828
+ // If this set's epoch is in range [min_expire, end_epoch], we've already processed it
814
829
// in the loop above, so skip processing here. Sectors rescheduled to this epoch
815
830
// would have been included in the earlier processing.
816
- if declared_expirations . contains_key ( & epoch) {
831
+ if epoch >= min_expire && epoch <= end_epoch {
817
832
return Ok ( true ) ;
818
833
}
819
834
835
+ let epoch = epoch as ChainEpoch ;
836
+
820
837
// Sector should not be found in EarlyExpirations which holds faults. An implicit assumption
821
838
// of grouping is that it only returns sectors with active power. ExpirationQueue should not
822
839
// provide operations that allow this to happen.
@@ -826,7 +843,7 @@ impl<'db, BS: Blockstore> ExpirationQueue<'db, BS> {
826
843
sector_size,
827
844
& sectors_by_number,
828
845
& mut all_remaining,
829
- es. clone ( ) ,
846
+ es,
830
847
epoch,
831
848
) ;
832
849
@@ -911,7 +928,7 @@ fn group_expiration_set(
911
928
sector_size : SectorSize ,
912
929
sectors : & BTreeMap < u64 , & SectorOnChainInfo > ,
913
930
include_set : & mut BTreeSet < u64 > ,
914
- es : ExpirationSet ,
931
+ es : & ExpirationSet ,
915
932
expiration : ChainEpoch ,
916
933
) -> SectorExpirationSet {
917
934
let mut sector_numbers = Vec :: new ( ) ;
@@ -927,14 +944,26 @@ fn group_expiration_set(
927
944
}
928
945
}
929
946
930
- SectorExpirationSet {
931
- sector_epoch_set : SectorEpochSet {
932
- epoch : expiration,
933
- sectors : sector_numbers,
934
- power : total_power,
935
- pledge : total_pledge,
936
- } ,
937
- expiration_set : es,
947
+ if sector_numbers. is_empty ( ) {
948
+ SectorExpirationSet {
949
+ sector_epoch_set : SectorEpochSet {
950
+ epoch : expiration,
951
+ sectors : sector_numbers,
952
+ power : total_power,
953
+ pledge : total_pledge,
954
+ } ,
955
+ expiration_set : ExpirationSet :: default ( ) ,
956
+ }
957
+ } else {
958
+ SectorExpirationSet {
959
+ sector_epoch_set : SectorEpochSet {
960
+ epoch : expiration,
961
+ sectors : sector_numbers,
962
+ power : total_power,
963
+ pledge : total_pledge,
964
+ } ,
965
+ expiration_set : es. clone ( ) , // lazy clone
966
+ }
938
967
}
939
968
}
940
969
0 commit comments