@@ -55,13 +55,13 @@ static int objerror(struct object *obj, const char *err, ...)
5555 return -1 ;
5656}
5757
58- static int objwarning (struct object * obj , const char * err , ...)
58+ static int fsck_error_func (struct object * obj , int type , const char * err , ...)
5959{
6060 va_list params ;
6161 va_start (params , err );
62- objreport (obj , "warning" , err , params );
62+ objreport (obj , ( type == FSCK_WARN ) ? "warning" : "error " , err , params );
6363 va_end (params );
64- return - 1 ;
64+ return ( type == FSCK_WARN ) ? 0 : 1 ;
6565}
6666
6767static int mark_object (struct object * obj , int type , void * data )
@@ -246,256 +246,56 @@ static void check_connectivity(void)
246246 }
247247}
248248
249- /*
250- * The entries in a tree are ordered in the _path_ order,
251- * which means that a directory entry is ordered by adding
252- * a slash to the end of it.
253- *
254- * So a directory called "a" is ordered _after_ a file
255- * called "a.c", because "a/" sorts after "a.c".
256- */
257- #define TREE_UNORDERED (-1)
258- #define TREE_HAS_DUPS (-2)
259-
260- static int verify_ordered (unsigned mode1 , const char * name1 , unsigned mode2 , const char * name2 )
249+ static int fsck_sha1 (const unsigned char * sha1 )
261250{
262- int len1 = strlen (name1 );
263- int len2 = strlen (name2 );
264- int len = len1 < len2 ? len1 : len2 ;
265- unsigned char c1 , c2 ;
266- int cmp ;
267-
268- cmp = memcmp (name1 , name2 , len );
269- if (cmp < 0 )
251+ struct object * obj = parse_object (sha1 );
252+ if (!obj ) {
253+ errors_found |= ERROR_OBJECT ;
254+ return error ("%s: object corrupt or missing" ,
255+ sha1_to_hex (sha1 ));
256+ }
257+ if (obj -> flags & SEEN )
270258 return 0 ;
271- if (cmp > 0 )
272- return TREE_UNORDERED ;
273-
274- /*
275- * Ok, the first <len> characters are the same.
276- * Now we need to order the next one, but turn
277- * a '\0' into a '/' for a directory entry.
278- */
279- c1 = name1 [len ];
280- c2 = name2 [len ];
281- if (!c1 && !c2 )
282- /*
283- * git-write-tree used to write out a nonsense tree that has
284- * entries with the same name, one blob and one tree. Make
285- * sure we do not have duplicate entries.
286- */
287- return TREE_HAS_DUPS ;
288- if (!c1 && S_ISDIR (mode1 ))
289- c1 = '/' ;
290- if (!c2 && S_ISDIR (mode2 ))
291- c2 = '/' ;
292- return c1 < c2 ? 0 : TREE_UNORDERED ;
293- }
294-
295- static int fsck_tree (struct tree * item )
296- {
297- int retval ;
298- int has_full_path = 0 ;
299- int has_empty_name = 0 ;
300- int has_zero_pad = 0 ;
301- int has_bad_modes = 0 ;
302- int has_dup_entries = 0 ;
303- int not_properly_sorted = 0 ;
304- struct tree_desc desc ;
305- unsigned o_mode ;
306- const char * o_name ;
307- const unsigned char * o_sha1 ;
259+ obj -> flags |= SEEN ;
308260
309261 if (verbose )
310- fprintf (stderr , "Checking tree %s\n" ,
311- sha1_to_hex (item -> object .sha1 ));
312-
313- init_tree_desc (& desc , item -> buffer , item -> size );
314-
315- o_mode = 0 ;
316- o_name = NULL ;
317- o_sha1 = NULL ;
318- while (desc .size ) {
319- unsigned mode ;
320- const char * name ;
321- const unsigned char * sha1 ;
322-
323- sha1 = tree_entry_extract (& desc , & name , & mode );
324-
325- if (strchr (name , '/' ))
326- has_full_path = 1 ;
327- if (!* name )
328- has_empty_name = 1 ;
329- has_zero_pad |= * (char * )desc .buffer == '0' ;
330- update_tree_entry (& desc );
331-
332- switch (mode ) {
333- /*
334- * Standard modes..
335- */
336- case S_IFREG | 0755 :
337- case S_IFREG | 0644 :
338- case S_IFLNK :
339- case S_IFDIR :
340- case S_IFGITLINK :
341- break ;
342- /*
343- * This is nonstandard, but we had a few of these
344- * early on when we honored the full set of mode
345- * bits..
346- */
347- case S_IFREG | 0664 :
348- if (!check_strict )
349- break ;
350- default :
351- has_bad_modes = 1 ;
352- }
262+ fprintf (stderr , "Checking %s %s\n" ,
263+ typename (obj -> type ), sha1_to_hex (obj -> sha1 ));
353264
354- if (o_name ) {
355- switch (verify_ordered (o_mode , o_name , mode , name )) {
356- case TREE_UNORDERED :
357- not_properly_sorted = 1 ;
358- break ;
359- case TREE_HAS_DUPS :
360- has_dup_entries = 1 ;
361- break ;
362- default :
363- break ;
364- }
365- }
265+ if (fsck_walk (obj , mark_used , 0 ))
266+ objerror (obj , "broken links" );
267+ if (fsck_object (obj , check_strict , fsck_error_func ))
268+ return -1 ;
366269
367- o_mode = mode ;
368- o_name = name ;
369- o_sha1 = sha1 ;
370- }
371- free (item -> buffer );
372- item -> buffer = NULL ;
270+ if (obj -> type == OBJ_TREE ) {
271+ struct tree * item = (struct tree * ) obj ;
373272
374- retval = 0 ;
375- if (has_full_path ) {
376- objwarning (& item -> object , "contains full pathnames" );
377- }
378- if (has_empty_name ) {
379- objwarning (& item -> object , "contains empty pathname" );
380- }
381- if (has_zero_pad ) {
382- objwarning (& item -> object , "contains zero-padded file modes" );
383- }
384- if (has_bad_modes ) {
385- objwarning (& item -> object , "contains bad file modes" );
273+ free (item -> buffer );
274+ item -> buffer = NULL ;
386275 }
387- if (has_dup_entries ) {
388- retval = objerror (& item -> object , "contains duplicate file entries" );
389- }
390- if (not_properly_sorted ) {
391- retval = objerror (& item -> object , "not properly sorted" );
392- }
393- return retval ;
394- }
395276
396- static int fsck_commit (struct commit * commit )
397- {
398- char * buffer = commit -> buffer ;
399- unsigned char tree_sha1 [20 ], sha1 [20 ];
400- struct commit_graft * graft ;
401- int parents = 0 ;
277+ if (obj -> type == OBJ_COMMIT ) {
278+ struct commit * commit = (struct commit * ) obj ;
402279
403- if (verbose )
404- fprintf (stderr , "Checking commit %s\n" ,
405- sha1_to_hex (commit -> object .sha1 ));
406-
407- if (memcmp (buffer , "tree " , 5 ))
408- return objerror (& commit -> object , "invalid format - expected 'tree' line" );
409- if (get_sha1_hex (buffer + 5 , tree_sha1 ) || buffer [45 ] != '\n' )
410- return objerror (& commit -> object , "invalid 'tree' line format - bad sha1" );
411- buffer += 46 ;
412- while (!memcmp (buffer , "parent " , 7 )) {
413- if (get_sha1_hex (buffer + 7 , sha1 ) || buffer [47 ] != '\n' )
414- return objerror (& commit -> object , "invalid 'parent' line format - bad sha1" );
415- buffer += 48 ;
416- parents ++ ;
417- }
418- graft = lookup_commit_graft (commit -> object .sha1 );
419- if (graft ) {
420- struct commit_list * p = commit -> parents ;
421- parents = 0 ;
422- while (p ) {
423- p = p -> next ;
424- parents ++ ;
425- }
426- if (graft -> nr_parent == -1 && !parents )
427- ; /* shallow commit */
428- else if (graft -> nr_parent != parents )
429- return objerror (& commit -> object , "graft objects missing" );
430- } else {
431- struct commit_list * p = commit -> parents ;
432- while (p && parents ) {
433- p = p -> next ;
434- parents -- ;
435- }
436- if (p || parents )
437- return objerror (& commit -> object , "parent objects missing" );
438- }
439- if (memcmp (buffer , "author " , 7 ))
440- return objerror (& commit -> object , "invalid format - expected 'author' line" );
441- free (commit -> buffer );
442- commit -> buffer = NULL ;
443- if (!commit -> tree )
444- return objerror (& commit -> object , "could not load commit's tree %s" , tree_sha1 );
445- if (!commit -> parents && show_root )
446- printf ("root %s\n" , sha1_to_hex (commit -> object .sha1 ));
447- if (!commit -> date )
448- printf ("bad commit date in %s\n" ,
449- sha1_to_hex (commit -> object .sha1 ));
450- return 0 ;
451- }
280+ free (commit -> buffer );
281+ commit -> buffer = NULL ;
452282
453- static int fsck_tag ( struct tag * tag )
454- {
455- struct object * tagged = tag -> tagged ;
283+ if (! commit -> parents && show_root )
284+ printf ( "root %s\n" , sha1_to_hex ( commit -> object . sha1 ));
285+ }
456286
457- if (verbose )
458- fprintf (stderr , "Checking tag %s\n" ,
459- sha1_to_hex (tag -> object .sha1 ));
287+ if (obj -> type == OBJ_TAG ) {
288+ struct tag * tag = (struct tag * ) obj ;
460289
461- if (!tagged ) {
462- return objerror (& tag -> object , "could not load tagged object" );
290+ if (show_tags && tag -> tagged ) {
291+ printf ("tagged %s %s" , typename (tag -> tagged -> type ), sha1_to_hex (tag -> tagged -> sha1 ));
292+ printf (" (%s) in %s\n" , tag -> tag , sha1_to_hex (tag -> object .sha1 ));
293+ }
463294 }
464- if (!show_tags )
465- return 0 ;
466295
467- printf ("tagged %s %s" , typename (tagged -> type ), sha1_to_hex (tagged -> sha1 ));
468- printf (" (%s) in %s\n" , tag -> tag , sha1_to_hex (tag -> object .sha1 ));
469296 return 0 ;
470297}
471298
472- static int fsck_sha1 (const unsigned char * sha1 )
473- {
474- struct object * obj = parse_object (sha1 );
475- if (!obj ) {
476- errors_found |= ERROR_OBJECT ;
477- return error ("%s: object corrupt or missing" ,
478- sha1_to_hex (sha1 ));
479- }
480- if (obj -> flags & SEEN )
481- return 0 ;
482- obj -> flags |= SEEN ;
483- if (fsck_walk (obj , mark_used , 0 ))
484- objerror (obj , "broken links" );
485- if (obj -> type == OBJ_BLOB )
486- return 0 ;
487- if (obj -> type == OBJ_TREE )
488- return fsck_tree ((struct tree * ) obj );
489- if (obj -> type == OBJ_COMMIT )
490- return fsck_commit ((struct commit * ) obj );
491- if (obj -> type == OBJ_TAG )
492- return fsck_tag ((struct tag * ) obj );
493-
494- /* By now, parse_object() would've returned NULL instead. */
495- return objerror (obj , "unknown type '%d' (internal fsck error)" ,
496- obj -> type );
497- }
498-
499299/*
500300 * This is the sorting chunk size: make it reasonably
501301 * big so that we can sort well..
0 commit comments