3333
3434struct fsck_ctx {
3535 flux_t * h ;
36+ bool validate_available ;
3637 json_t * root ;
3738 int sequence ;
3839 int repair_count ;
@@ -61,9 +62,7 @@ static void fsck_treeobj (struct fsck_ctx *ctx,
6162 const char * path ,
6263 json_t * treeobj );
6364
64- static void valref_validate (struct fsck_valref_data * fvd ,
65- json_t * treeobj ,
66- int index );
65+ static void valref_validate (struct fsck_valref_data * fvd );
6766
6867static void read_verror (const char * fmt , va_list ap )
6968{
@@ -128,40 +127,36 @@ static void valref_validate_continuation (flux_future_t *f, void *arg)
128127 fvd -> in_flight -- ;
129128
130129 if (fvd -> index < fvd -> count ) {
131- valref_validate (fvd , fvd -> treeobj , fvd -> index );
130+ valref_validate (fvd );
132131 fvd -> in_flight ++ ;
133132 fvd -> index ++ ;
134133 }
135134
136135 flux_future_destroy (f );
137136}
138137
139- static void valref_validate (struct fsck_valref_data * fvd ,
140- json_t * treeobj ,
141- int index )
138+ static void valref_validate (struct fsck_valref_data * fvd )
142139{
140+ const char * topic = fvd -> ctx -> validate_available ?
141+ "content-backing.validate" : "content-backing.load" ;
143142 uint32_t hash [BLOBREF_MAX_DIGEST_SIZE ];
144143 ssize_t hash_size ;
145144 const char * blobref ;
146145 flux_future_t * f ;
147146 int * indexp ;
148147
149- blobref = treeobj_get_blobref (treeobj , index );
148+ blobref = treeobj_get_blobref (fvd -> treeobj , fvd -> index );
150149
151150 if ((hash_size = blobref_strtohash (blobref , hash , sizeof (hash ))) < 0 )
152151 log_err_exit ("cannot get hash from ref string" );
153152
154- if (!(f = flux_rpc_raw (fvd -> ctx -> h ,
155- "content-backing.validate" ,
156- hash ,
157- hash_size ,
158- 0 ,
159- 0 ))
160- || flux_future_then (f , -1 , valref_validate_continuation , fvd ) < 0 )
153+ if (!(f = flux_rpc_raw (fvd -> ctx -> h , topic , hash , hash_size , 0 , 0 )))
154+ log_err_exit ("failed to validate valref blob" );
155+ if (flux_future_then (f , -1 , valref_validate_continuation , fvd ) < 0 )
161156 log_err_exit ("cannot validate valref blob" );
162157 if (!(indexp = (int * )malloc (sizeof (int ))))
163158 log_err_exit ("cannot allocate index memory" );
164- (* indexp ) = index ;
159+ (* indexp ) = fvd -> index ;
165160 if (flux_future_aux_set (f , "index" , indexp , free ) < 0 )
166161 log_err_exit ("could not save index value" );
167162}
@@ -334,7 +329,7 @@ static void fsck_valref (struct fsck_ctx *ctx,
334329
335330 while (fvd .in_flight < BLOBREF_ASYNC_MAX
336331 && fvd .index < fvd .count ) {
337- valref_validate (& fvd , treeobj , fvd . index );
332+ valref_validate (& fvd );
338333 fvd .in_flight ++ ;
339334 fvd .index ++ ;
340335 }
@@ -357,6 +352,7 @@ static void fsck_valref (struct fsck_ctx *ctx,
357352
358353 /* can only recover if errors were all bad references */
359354 if (ctx -> repair
355+ && fvd .missing_indexes
360356 && fvd .errorcount == zlist_size (fvd .missing_indexes )) {
361357 json_t * repaired = repair_valref (ctx , treeobj , & fvd );
362358
@@ -639,6 +635,32 @@ static void sync_checkpoint (struct fsck_ctx *ctx)
639635 fprintf (stderr , "Updated primary checkpoint to include lost+found\n" );
640636}
641637
638+ /* "validate" support added in v0.77.0. Use "load" for backwards
639+ * compatibility if "validate" is not available.
640+ */
641+ static void check_validate_available (struct fsck_ctx * ctx , const char * blobref )
642+ {
643+ uint32_t hash [BLOBREF_MAX_DIGEST_SIZE ];
644+ ssize_t hash_size ;
645+ flux_future_t * f ;
646+
647+ if ((hash_size = blobref_strtohash (blobref , hash , sizeof (hash ))) < 0 )
648+ log_err_exit ("cannot get hash from ref string" );
649+
650+ ctx -> validate_available = true;
651+ // doesn't matter if the request is correct, we are looking for ENOSYS
652+ if ((f = flux_rpc_raw (ctx -> h ,
653+ "content-backing.validate" ,
654+ hash ,
655+ hash_size ,
656+ 0 ,
657+ 0 ))
658+ && flux_rpc_get (f , NULL ) < 0
659+ && errno == ENOSYS )
660+ ctx -> validate_available = false;
661+ flux_future_destroy (f );
662+ }
663+
642664static int cmd_fsck (optparse_t * p , int ac , char * av [])
643665{
644666 struct fsck_ctx ctx = {0 };
@@ -698,6 +720,8 @@ static int cmd_fsck (optparse_t *p, int ac, char *av[])
698720 ctx .sequence = sequence ;
699721 }
700722
723+ check_validate_available (& ctx , blobref );
724+
701725 fsck_blobref (& ctx , blobref );
702726
703727 flux_future_destroy (f );
0 commit comments