Subject: [PATCH 05/14] lock_packed_refs: pass error message back through a strbuf

From: Jonathan Nieder <[email-masked]>
Date: Tue, 2 Dec 2014 21:16:15 -0800

This saves us from having to be careful about preserving errno and
makes it more explicit in the die-on-error case that the caller is
exiting without a chance to clean up.

Signed-off-by: Jonathan Nieder <[email-masked]>
---
 builtin/clone.c |  6 +++++-
 refs.c          | 17 ++++++++++-------
 refs.h          |  8 ++------
 3 files changed, 17 insertions(+), 14 deletions(-)

diff --git a/builtin/clone.c b/builtin/clone.c
index d5e7532..b07d740 100644
--- a/builtin/clone.c
+++ b/builtin/clone.c
@@ -495,8 +495,10 @@ static struct ref *wanted_peer_refs(const struct ref *refs,
 static void write_remote_refs(const struct ref *local_refs)
 {
 	const struct ref *r;
+	struct strbuf err = STRBUF_INIT;
 
-	lock_packed_refs(LOCK_DIE_ON_ERROR);
+	if (lock_packed_refs(&err))
+		die("%s", err.buf);
 
 	for (r = local_refs; r; r = r->next) {
 		if (!r->peer_ref)
@@ -506,6 +508,8 @@ static void write_remote_refs(const struct ref *local_refs)
 
 	if (commit_packed_refs())
 		die_errno("unable to overwrite old ref-pack file");
+
+	strbuf_release(&err);
 }
 
 static void write_followtags(const struct ref *refs, const char *msg)
diff --git a/refs.c b/refs.c
index 5ff457e..917f8fc 100644
--- a/refs.c
+++ b/refs.c
@@ -2371,13 +2371,15 @@ static int write_packed_entry_fn(struct ref_entry *entry, void *cb_data)
 	return 0;
 }
 
-/* This should return a meaningful errno on failure */
-int lock_packed_refs(int flags)
+int lock_packed_refs(struct strbuf *err)
 {
 	struct packed_ref_cache *packed_ref_cache;
 
-	if (hold_lock_file_for_update(&packlock, git_path("packed-refs"), flags) < 0)
+	if (hold_lock_file_for_update(&packlock, git_path("packed-refs"), 0) < 0) {
+		unable_to_lock_message(git_path("packed-refs"), errno, err);
 		return -1;
+	}
+
 	/*
 	 * Get the current packed-refs while holding the lock.  If the
 	 * packed-refs file has been modified since we last read it,
@@ -2565,11 +2567,13 @@ static void prune_refs(struct ref_to_prune *r)
 int pack_refs(unsigned int flags)
 {
 	struct pack_refs_cb_data cbdata;
+	struct strbuf err = STRBUF_INIT;
 
 	memset(&cbdata, 0, sizeof(cbdata));
 	cbdata.flags = flags;
 
-	lock_packed_refs(LOCK_DIE_ON_ERROR);
+	if (lock_packed_refs(&err))
+		die("%s", err.buf);
 	cbdata.packed_refs = get_packed_refs(&ref_cache);
 
 	do_for_each_entry_in_dir(get_loose_refs(&ref_cache), 0,
@@ -2579,6 +2583,7 @@ int pack_refs(unsigned int flags)
 		die_errno("unable to overwrite old ref-pack file");
 
 	prune_refs(cbdata.ref_to_prune);
+	strbuf_release(&err);
 	return 0;
 }
 
@@ -2657,10 +2662,8 @@ int repack_without_refs(const char **refnames, int n, struct strbuf *err)
 	if (i == n)
 		return 0; /* no refname exists in packed refs */
 
-	if (lock_packed_refs(0)) {
-		unable_to_lock_message(git_path("packed-refs"), errno, err);
+	if (lock_packed_refs(err))
 		return -1;
-	}
 	packed = get_packed_refs(&ref_cache);
 
 	/* Remove refnames from the cache */
diff --git a/refs.h b/refs.h
index 2bc3556..ca6a567 100644
--- a/refs.h
+++ b/refs.h
@@ -119,12 +119,8 @@ extern int for_each_rawref(each_ref_fn, void *);
 extern void warn_dangling_symref(FILE *fp, const char *msg_fmt, const char *refname);
 extern void warn_dangling_symrefs(FILE *fp, const char *msg_fmt, const struct string_list *refnames);
 
-/*
- * Lock the packed-refs file for writing.  Flags is passed to
- * hold_lock_file_for_update().  Return 0 on success.
- * Errno is set to something meaningful on error.
- */
-extern int lock_packed_refs(int flags);
+/* Lock the packed-refs file for writing.  Returns 0 on success. */
+extern int lock_packed_refs(struct strbuf *err);
 
 /*
  * Add a reference to the in-memory packed reference cache.  This may
-- 
2.2.0.rc0.207.ga3a616c