@@ -9,7 +9,7 @@ use safe_math::*;
99use sp_arithmetic:: helpers_128bit:: sqrt;
1010use substrate_fixed:: types:: U64F64 ;
1111
12- use self :: tick:: { Tick , TickIndex } ;
12+ use self :: tick:: { Layer , Tick , TickIndex , TickIndexBitmap } ;
1313
1414pub mod pallet;
1515mod tick;
@@ -1040,7 +1040,7 @@ where
10401040 /// Get fees above a tick
10411041 ///
10421042 fn get_fees_above ( & mut self , tick_index : TickIndex , quote : bool ) -> U64F64 {
1043- let maybe_tick_index = tick_index . find_closest_lower_active ( & self . state_ops ) ;
1043+ let maybe_tick_index = self . find_closest_lower_active_tick_index ( tick_index ) ;
10441044 let current_tick = self . get_current_tick_index ( ) ;
10451045
10461046 if let Some ( tick_index) = maybe_tick_index {
@@ -1072,7 +1072,7 @@ where
10721072
10731073 /// Get fees below a tick
10741074 fn get_fees_below ( & mut self , tick_index : TickIndex , quote : bool ) -> U64F64 {
1075- let maybe_tick_index = tick_index . find_closest_lower_active ( & self . state_ops ) ;
1075+ let maybe_tick_index = self . find_closest_lower_active_tick_index ( tick_index ) ;
10761076 let current_tick = self . get_current_tick_index ( ) ;
10771077
10781078 if let Some ( tick_index) = maybe_tick_index {
@@ -1115,46 +1115,38 @@ where
11151115 /// Deletion: 2 reads, 1-3 writes
11161116 ///
11171117
1118- // Addresses an index as (word, bit)
1119- fn index_to_address ( index : u32 ) -> ( u32 , u32 ) {
1120- let word: u32 = index. safe_div ( 128 ) ;
1121- let bit: u32 = index. checked_rem ( 128 ) . unwrap_or_default ( ) ;
1122- ( word, bit)
1123- }
1124-
1125- // Reconstructs an index from address in lower level
1126- fn address_to_index ( word : u32 , bit : u32 ) -> u32 {
1127- word. saturating_mul ( 128 ) . saturating_add ( bit)
1128- }
1118+ // Use TickIndexBitmap::layer_to_index instead
11291119
11301120 pub fn insert_active_tick ( & mut self , index : TickIndex ) {
11311121 // Check the range
11321122 if ( index < TickIndex :: MIN ) || ( index > TickIndex :: MAX ) {
11331123 return ;
11341124 }
11351125
1136- // Convert the tick index value to an offset_index for the tree representation
1137- // to avoid working with the sign bit.
1138- let offset_index = ( index. get ( ) + TickIndex :: OFFSET . get ( ) ) as u32 ;
1139-
1140- // Calculate index in each layer
1141- let ( layer2_word, layer2_bit) = Self :: index_to_address ( offset_index) ;
1142- let ( layer1_word, layer1_bit) = Self :: index_to_address ( layer2_word) ;
1143- let ( layer0_word, layer0_bit) = Self :: index_to_address ( layer1_word) ;
1126+ // Convert to bitmap representation
1127+ let bitmap = TickIndexBitmap :: from ( index) ;
11441128
11451129 // Update layer words
1146- let mut word0_value = self . state_ops . get_layer0_word ( layer0_word) ;
1147- let mut word1_value = self . state_ops . get_layer1_word ( layer1_word) ;
1148- let mut word2_value = self . state_ops . get_layer2_word ( layer2_word) ;
1149-
1150- let bit: u128 = 1 ;
1151- word0_value = word0_value | bit. wrapping_shl ( layer0_bit) ;
1152- word1_value = word1_value | bit. wrapping_shl ( layer1_bit) ;
1153- word2_value = word2_value | bit. wrapping_shl ( layer2_bit) ;
1154-
1155- self . state_ops . set_layer0_word ( layer0_word, word0_value) ;
1156- self . state_ops . set_layer1_word ( layer1_word, word1_value) ;
1157- self . state_ops . set_layer2_word ( layer2_word, word2_value) ;
1130+ let mut word0_value = self . state_ops . get_layer0_word ( bitmap. word_at ( Layer :: Top ) ) ;
1131+ let mut word1_value = self
1132+ . state_ops
1133+ . get_layer1_word ( bitmap. word_at ( Layer :: Middle ) ) ;
1134+ let mut word2_value = self
1135+ . state_ops
1136+ . get_layer2_word ( bitmap. word_at ( Layer :: Bottom ) ) ;
1137+
1138+ // Set bits in each layer
1139+ word0_value |= bitmap. bit_mask ( Layer :: Top ) ;
1140+ word1_value |= bitmap. bit_mask ( Layer :: Middle ) ;
1141+ word2_value |= bitmap. bit_mask ( Layer :: Bottom ) ;
1142+
1143+ // Update the storage
1144+ self . state_ops
1145+ . set_layer0_word ( bitmap. word_at ( Layer :: Top ) , word0_value) ;
1146+ self . state_ops
1147+ . set_layer1_word ( bitmap. word_at ( Layer :: Middle ) , word1_value) ;
1148+ self . state_ops
1149+ . set_layer2_word ( bitmap. word_at ( Layer :: Bottom ) , word2_value) ;
11581150 }
11591151
11601152 pub fn remove_active_tick ( & mut self , index : TickIndex ) {
@@ -1163,58 +1155,34 @@ where
11631155 return ;
11641156 }
11651157
1166- // Convert the tick index value to an offset_index for the tree representation
1167- // to avoid working with the sign bit.
1168- let offset_index = ( index. get ( ) + TickIndex :: OFFSET . get ( ) ) as u32 ;
1169-
1170- // Calculate index in each layer
1171- let ( layer2_word, layer2_bit) = Self :: index_to_address ( offset_index) ;
1172- let ( layer1_word, layer1_bit) = Self :: index_to_address ( layer2_word) ;
1173- let ( layer0_word, layer0_bit) = Self :: index_to_address ( layer1_word) ;
1158+ // Convert to bitmap representation
1159+ let bitmap = TickIndexBitmap :: from ( index) ;
11741160
11751161 // Update layer words
1176- let mut word0_value = self . state_ops . get_layer0_word ( layer0_word) ;
1177- let mut word1_value = self . state_ops . get_layer1_word ( layer1_word) ;
1178- let mut word2_value = self . state_ops . get_layer2_word ( layer2_word) ;
1162+ let mut word0_value = self . state_ops . get_layer0_word ( bitmap. word_at ( Layer :: Top ) ) ;
1163+ let mut word1_value = self
1164+ . state_ops
1165+ . get_layer1_word ( bitmap. word_at ( Layer :: Middle ) ) ;
1166+ let mut word2_value = self
1167+ . state_ops
1168+ . get_layer2_word ( bitmap. word_at ( Layer :: Bottom ) ) ;
11791169
11801170 // Turn the bit off (& !bit) and save as needed
1181- let bit: u128 = 1 ;
1182- word2_value = word2_value & !bit. wrapping_shl ( layer2_bit) ;
1183- self . state_ops . set_layer2_word ( layer2_word, word2_value) ;
1171+ word2_value &= !bitmap. bit_mask ( Layer :: Bottom ) ;
1172+ self . state_ops
1173+ . set_layer2_word ( bitmap. word_at ( Layer :: Bottom ) , word2_value) ;
1174+
11841175 if word2_value == 0 {
1185- word1_value = word1_value & !bit. wrapping_shl ( layer1_bit) ;
1186- self . state_ops . set_layer1_word ( layer1_word, word1_value) ;
1187- }
1188- if word1_value == 0 {
1189- word0_value = word0_value & !bit. wrapping_shl ( layer0_bit) ;
1190- self . state_ops . set_layer0_word ( layer0_word, word0_value) ;
1176+ word1_value &= !bitmap. bit_mask ( Layer :: Middle ) ;
1177+ self . state_ops
1178+ . set_layer1_word ( bitmap. word_at ( Layer :: Middle ) , word1_value) ;
11911179 }
1192- }
11931180
1194- // Finds the closest active bit and, if active bit exactly matches bit, then the next one
1195- // Exact match: return Some([next, bit])
1196- // Non-exact match: return Some([next])
1197- // No match: return None
1198- fn find_closest_active_bit_candidates ( & self , word : u128 , bit : u32 , lower : bool ) -> Vec < u32 > {
1199- let mut result = vec ! [ ] ;
1200- let mut mask: u128 = 1_u128 . wrapping_shl ( bit) ;
1201- let mut layer0_active_bit: u32 = bit;
1202- while mask > 0 {
1203- if mask & word != 0 {
1204- result. push ( layer0_active_bit) ;
1205- if layer0_active_bit != bit {
1206- break ;
1207- }
1208- }
1209- mask = if lower {
1210- layer0_active_bit = layer0_active_bit. saturating_sub ( 1 ) ;
1211- mask. wrapping_shr ( 1 )
1212- } else {
1213- layer0_active_bit = layer0_active_bit. saturating_add ( 1 ) ;
1214- mask. wrapping_shl ( 1 )
1215- } ;
1181+ if word1_value == 0 {
1182+ word0_value &= !bitmap. bit_mask ( Layer :: Top ) ;
1183+ self . state_ops
1184+ . set_layer0_word ( bitmap. word_at ( Layer :: Top ) , word0_value) ;
12161185 }
1217- result
12181186 }
12191187
12201188 pub fn find_closest_active_tick_index (
@@ -1227,28 +1195,31 @@ where
12271195 return None ;
12281196 }
12291197
1230- // Convert the tick index value to an offset_index for the tree representation
1231- // to avoid working with the sign bit.
1232- let offset_index = ( index. get ( ) + TickIndex :: OFFSET . get ( ) ) as u32 ;
1198+ // Convert to bitmap representation
1199+ let bitmap = TickIndexBitmap :: from ( index) ;
12331200 let mut found = false ;
12341201 let mut result: u32 = 0 ;
12351202
1236- // Calculate index in each layer
1237- let ( layer2_word, layer2_bit) = Self :: index_to_address ( offset_index) ;
1238- let ( layer1_word, layer1_bit) = Self :: index_to_address ( layer2_word) ;
1239- let ( layer0_word, layer0_bit) = Self :: index_to_address ( layer1_word) ;
1203+ // Layer positions from bitmap
1204+ let layer0_word = bitmap. word_at ( Layer :: Top ) ;
1205+ let layer0_bit = bitmap. bit_at ( Layer :: Top ) ;
1206+ let layer1_word = bitmap. word_at ( Layer :: Middle ) ;
1207+ let layer1_bit = bitmap. bit_at ( Layer :: Middle ) ;
1208+ let layer2_word = bitmap. word_at ( Layer :: Bottom ) ;
1209+ let layer2_bit = bitmap. bit_at ( Layer :: Bottom ) ;
12401210
12411211 // Find the closest active bits in layer 0, then 1, then 2
12421212
12431213 ///////////////
12441214 // Level 0
12451215 let word0 = self . state_ops . get_layer0_word ( layer0_word) ;
1246- let closest_bits_l0 = self . find_closest_active_bit_candidates ( word0, layer0_bit, lower) ;
1216+ let closest_bits_l0 =
1217+ TickIndexBitmap :: find_closest_active_bit_candidates ( word0, layer0_bit, lower) ;
12471218
12481219 closest_bits_l0. iter ( ) . for_each ( |& closest_bit_l0| {
12491220 ///////////////
12501221 // Level 1
1251- let word1_index = Self :: address_to_index ( 0 , closest_bit_l0) ;
1222+ let word1_index = TickIndexBitmap :: layer_to_index ( 0 , closest_bit_l0) ;
12521223
12531224 // Layer 1 words are different, shift the bit to the word edge
12541225 let start_from_l1_bit = if word1_index < layer1_word {
@@ -1260,12 +1231,15 @@ where
12601231 } ;
12611232 let word1_value = self . state_ops . get_layer1_word ( word1_index) ;
12621233
1263- let closest_bits_l1 =
1264- self . find_closest_active_bit_candidates ( word1_value, start_from_l1_bit, lower) ;
1234+ let closest_bits_l1 = TickIndexBitmap :: find_closest_active_bit_candidates (
1235+ word1_value,
1236+ start_from_l1_bit,
1237+ lower,
1238+ ) ;
12651239 closest_bits_l1. iter ( ) . for_each ( |& closest_bit_l1| {
12661240 ///////////////
12671241 // Level 2
1268- let word2_index = Self :: address_to_index ( word1_index, closest_bit_l1) ;
1242+ let word2_index = TickIndexBitmap :: layer_to_index ( word1_index, closest_bit_l1) ;
12691243
12701244 // Layer 2 words are different, shift the bit to the word edge
12711245 let start_from_l2_bit = if word2_index < layer2_word {
@@ -1277,13 +1251,16 @@ where
12771251 } ;
12781252
12791253 let word2_value = self . state_ops . get_layer2_word ( word2_index) ;
1280- let closest_bits_l2 =
1281- self . find_closest_active_bit_candidates ( word2_value, start_from_l2_bit, lower) ;
1254+ let closest_bits_l2 = TickIndexBitmap :: find_closest_active_bit_candidates (
1255+ word2_value,
1256+ start_from_l2_bit,
1257+ lower,
1258+ ) ;
12821259
12831260 if closest_bits_l2. len ( ) > 0 {
12841261 // The active tick is found, restore its full index and return
12851262 let offset_found_index =
1286- Self :: address_to_index ( word2_index, closest_bits_l2[ 0 ] ) ;
1263+ TickIndexBitmap :: layer_to_index ( word2_index, closest_bits_l2[ 0 ] ) ;
12871264
12881265 if lower {
12891266 if ( offset_found_index > result) || ( !found) {
@@ -1300,13 +1277,12 @@ where
13001277 } ) ;
13011278 } ) ;
13021279
1303- if found {
1304- // Convert the tree offset_index back to a tick index value
1305- let tick_value = ( result as i32 ) . saturating_sub ( TickIndex :: OFFSET . get ( ) ) ;
1306- Some ( TickIndex :: new_unchecked ( tick_value) )
1307- } else {
1308- None
1280+ if !found {
1281+ return None ;
13091282 }
1283+
1284+ // Convert the result offset_index back to a tick index
1285+ TickIndex :: from_offset_index ( result) . ok ( )
13101286 }
13111287
13121288 pub fn find_closest_lower_active_tick_index ( & self , index : TickIndex ) -> Option < TickIndex > {
0 commit comments