@@ -31,6 +31,7 @@ struct stored_bitmap {
3131	struct  object_id  oid ;
3232	struct  ewah_bitmap  * root ;
3333	struct  stored_bitmap  * xor ;
34+ 	size_t  map_pos ;
3435	int  flags ;
3536};
3637
@@ -314,13 +315,14 @@ static struct stored_bitmap *store_bitmap(struct bitmap_index *index,
314315					  struct  ewah_bitmap  * root ,
315316					  const  struct  object_id  * oid ,
316317					  struct  stored_bitmap  * xor_with ,
317- 					  int  flags )
318+ 					  int  flags ,  size_t   map_pos )
318319{
319320	struct  stored_bitmap  * stored ;
320321	khiter_t  hash_pos ;
321322	int  ret ;
322323
323324	stored  =  xmalloc (sizeof (struct  stored_bitmap ));
325+ 	stored -> map_pos  =  map_pos ;
324326	stored -> root  =  root ;
325327	stored -> xor  =  xor_with ;
326328	stored -> flags  =  flags ;
@@ -376,10 +378,12 @@ static int load_bitmap_entries_v1(struct bitmap_index *index)
376378		struct  stored_bitmap  * xor_bitmap  =  NULL ;
377379		uint32_t  commit_idx_pos ;
378380		struct  object_id  oid ;
381+ 		size_t  entry_map_pos ;
379382
380383		if  (index -> map_size  -  index -> map_pos  <  6 )
381384			return  error (_ ("corrupt ewah bitmap: truncated header for entry %d" ), i );
382385
386+ 		entry_map_pos  =  index -> map_pos ;
383387		commit_idx_pos  =  read_be32 (index -> map , & index -> map_pos );
384388		xor_offset  =  read_u8 (index -> map , & index -> map_pos );
385389		flags  =  read_u8 (index -> map , & index -> map_pos );
@@ -402,8 +406,9 @@ static int load_bitmap_entries_v1(struct bitmap_index *index)
402406		if  (!bitmap )
403407			return  -1 ;
404408
405- 		recent_bitmaps [i  % MAX_XOR_OFFSET ] =  store_bitmap (
406- 			index , bitmap , & oid , xor_bitmap , flags );
409+ 		recent_bitmaps [i  % MAX_XOR_OFFSET ] = 
410+ 			store_bitmap (index , bitmap , & oid , xor_bitmap , flags ,
411+ 				     entry_map_pos );
407412	}
408413
409414	return  0 ;
@@ -869,6 +874,7 @@ static struct stored_bitmap *lazy_bitmap_for_commit(struct bitmap_index *bitmap_
869874	int  xor_flags ;
870875	khiter_t  hash_pos ;
871876	struct  bitmap_lookup_table_xor_item  * xor_item ;
877+ 	size_t  entry_map_pos ;
872878
873879	if  (is_corrupt )
874880		return  NULL ;
@@ -928,14 +934,16 @@ static struct stored_bitmap *lazy_bitmap_for_commit(struct bitmap_index *bitmap_
928934			goto corrupt ;
929935		}
930936
937+ 		entry_map_pos  =  bitmap_git -> map_pos ;
931938		bitmap_git -> map_pos  +=  sizeof (uint32_t ) +  sizeof (uint8_t );
932939		xor_flags  =  read_u8 (bitmap_git -> map , & bitmap_git -> map_pos );
933940		bitmap  =  read_bitmap_1 (bitmap_git );
934941
935942		if  (!bitmap )
936943			goto corrupt ;
937944
938- 		xor_bitmap  =  store_bitmap (bitmap_git , bitmap , & xor_item -> oid , xor_bitmap , xor_flags );
945+ 		xor_bitmap  =  store_bitmap (bitmap_git , bitmap , & xor_item -> oid ,
946+ 					  xor_bitmap , xor_flags , entry_map_pos );
939947		xor_items_nr -- ;
940948	}
941949
@@ -969,14 +977,16 @@ static struct stored_bitmap *lazy_bitmap_for_commit(struct bitmap_index *bitmap_
969977	 * Instead, we can skip ahead and immediately read the flags and 
970978	 * ewah bitmap. 
971979	 */ 
980+ 	entry_map_pos  =  bitmap_git -> map_pos ;
972981	bitmap_git -> map_pos  +=  sizeof (uint32_t ) +  sizeof (uint8_t );
973982	flags  =  read_u8 (bitmap_git -> map , & bitmap_git -> map_pos );
974983	bitmap  =  read_bitmap_1 (bitmap_git );
975984
976985	if  (!bitmap )
977986		goto corrupt ;
978987
979- 	return  store_bitmap (bitmap_git , bitmap , oid , xor_bitmap , flags );
988+ 	return  store_bitmap (bitmap_git , bitmap , oid , xor_bitmap , flags ,
989+ 			    entry_map_pos );
980990
981991corrupt :
982992	free (xor_items );
@@ -2857,6 +2867,48 @@ int test_bitmap_commits(struct repository *r)
28572867	return  0 ;
28582868}
28592869
2870+ int  test_bitmap_commits_with_offset (struct  repository  * r )
2871+ {
2872+ 	struct  object_id  oid ;
2873+ 	struct  stored_bitmap  * stored ;
2874+ 	struct  bitmap_index  * bitmap_git ;
2875+ 	size_t  commit_idx_pos_map_pos , xor_offset_map_pos , flag_map_pos ,
2876+ 		ewah_bitmap_map_pos ;
2877+ 
2878+ 	bitmap_git  =  prepare_bitmap_git (r );
2879+ 	if  (!bitmap_git )
2880+ 		die (_ ("failed to load bitmap indexes" ));
2881+ 
2882+ 	/* 
2883+ 	 * Since this function needs to know the position of each individual 
2884+ 	 * bitmap, bypass the commit lookup table (if one exists) by forcing 
2885+ 	 * the bitmap to eagerly load its entries. 
2886+ 	 */ 
2887+ 	if  (bitmap_git -> table_lookup ) {
2888+ 		if  (load_bitmap_entries_v1 (bitmap_git ) <  0 )
2889+ 			die (_ ("failed to load bitmap indexes" ));
2890+ 	}
2891+ 
2892+ 	kh_foreach  (bitmap_git -> bitmaps , oid , stored , {
2893+ 		commit_idx_pos_map_pos  =  stored -> map_pos ;
2894+ 		xor_offset_map_pos  =  stored -> map_pos  +  sizeof (uint32_t );
2895+ 		flag_map_pos  =  xor_offset_map_pos  +  sizeof (uint8_t );
2896+ 		ewah_bitmap_map_pos  =  flag_map_pos  +  sizeof (uint8_t );
2897+ 
2898+ 		printf_ln ("%s %" PRIuMAX " %" PRIuMAX " %" PRIuMAX " %" PRIuMAX ,
2899+ 			  oid_to_hex (& oid ),
2900+ 			  (uintmax_t )commit_idx_pos_map_pos ,
2901+ 			  (uintmax_t )xor_offset_map_pos ,
2902+ 			  (uintmax_t )flag_map_pos ,
2903+ 			  (uintmax_t )ewah_bitmap_map_pos );
2904+ 	})
2905+ 		;
2906+ 
2907+ 	free_bitmap_index (bitmap_git );
2908+ 
2909+ 	return  0 ;
2910+ }
2911+ 
28602912int  test_bitmap_hashes (struct  repository  * r )
28612913{
28622914	struct  bitmap_index  * bitmap_git  =  prepare_bitmap_git (r );
0 commit comments