From 2312a7932080f17c2847ec3ce5dddbc65c2e0b41 Mon Sep 17 00:00:00 2001 From: Michael Haggerty Date: Mon, 22 Apr 2013 21:52:21 +0200 Subject: [PATCH] peel_ref(): fix return value for non-peelable, not-current reference The old version was inconsistent: when a reference was REF_KNOWS_PEELED but with a null peeled value, it returned non-zero for the current reference but zero for other references. Change the behavior for non-current references to match that of current_ref, which is what callers expect. Document the behavior. Current callers only call peel_ref() from within a for_each_ref-style iteration and only for the current ref; therefore, the buggy code path was never reached. Signed-off-by: Michael Haggerty Signed-off-by: Junio C Hamano --- refs.c | 5 ++++- refs.h | 8 ++++++++ 2 files changed, 12 insertions(+), 1 deletion(-) diff --git a/refs.c b/refs.c index 7405d1c962..787db21dfc 100644 --- a/refs.c +++ b/refs.c @@ -119,7 +119,8 @@ struct ref_value { /* * If REF_KNOWS_PEELED, then this field holds the peeled value * of this reference, or null if the reference is known not to - * be peelable. + * be peelable. See the documentation for peel_ref() for an + * exact definition of "peelable". */ unsigned char peeled[20]; }; @@ -1340,6 +1341,8 @@ int peel_ref(const char *refname, unsigned char *sha1) struct ref_entry *r = get_packed_ref(refname); if (r && (r->flag & REF_KNOWS_PEELED)) { + if (is_null_sha1(r->u.value.peeled)) + return -1; hashcpy(sha1, r->u.value.peeled); return 0; } diff --git a/refs.h b/refs.h index f111024a18..3fc97a2e4a 100644 --- a/refs.h +++ b/refs.h @@ -74,6 +74,14 @@ extern void add_packed_ref(const char *refname, const unsigned char *sha1); extern int ref_exists(const char *); +/* + * If refname is a non-symbolic reference that refers to a tag object, + * and the tag can be (recursively) dereferenced to a non-tag object, + * store the SHA1 of the referred-to object to sha1 and return 0. If + * any of these conditions are not met, return a non-zero value. + * Symbolic references are considered unpeelable, even if they + * ultimately resolve to a peelable tag. + */ extern int peel_ref(const char *refname, unsigned char *sha1); /** Locks a "refs/" ref returning the lock on success and NULL on failure. **/ -- 2.40.0