Subject: Re: fsck segfault

From: Junio C Hamano <[email-masked]>
Date: Mon, 11 Jul 2022 12:39:16 -0700

SZEDER Gábor <[email-masked]> writes:

>> +		for (i = 0; i < 3; i++) {
>> +			struct object *obj;
>> +
>> +			if (!ru->mode[i] || !S_ISREG(ru->mode[i]))
>> +				continue;
>> +
>> +			obj = parse_object(the_repository, &ru->oid[i]);
>
> parse_object() can return NULL ...
>
>> +			if (!obj) {
>
> ... and here is the if statement to show an error in that case ...
>
>> +				error(_("%s: invalid sha1 pointer in resolve-undo"),
>> +				      oid_to_hex(&ru->oid[i]));
>> +				errors_found |= ERROR_REFS;
>> +			}
>> +			obj->flags |= USED;
>
> ... but then there is this line which might dereference that NULL
> pointer.
>
> Perhaps all we would need is a 'continue' at the end of that 'if
> (!obj)' block, or an else block for the last three statements, which
> should result in the same control flow?  Dunno.

Thanks for spotting.  Looking at how fsck_cache_tree() and
fsck_walk_tree() handles missing object, it sounds like the right
approach to continue after setting the errors_found bit.

>> +			fsck_put_object_name(&fsck_walk_options, &ru->oid[i],
>> +					     ":(%d):%s", i, path);
>> +			mark_object_reachable(obj);
>> +		}
>> +	}
>> +	return 0;
>> +}