try_remove_empty_parents(): don't trash argument contents
authorMichael Haggerty <mhagger@alum.mit.edu>
Fri, 6 Jan 2017 16:22:41 +0000 (17:22 +0100)
committerJunio C Hamano <gitster@pobox.com>
Sun, 8 Jan 2017 03:30:09 +0000 (19:30 -0800)
It's bad manners and surprising and therefore error-prone.

Signed-off-by: Michael Haggerty <mhagger@alum.mit.edu>
Reviewed-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
refs/files-backend.c
index 92a9d99ba535081d61af6347d38ebfa10faf9877..88f8c7aa4b2be898712f90be4394e6233dee9f80 100644 (file)
@@ -2282,13 +2282,15 @@ static int pack_if_possible_fn(struct ref_entry *entry, void *cb_data)
 
 /*
  * Remove empty parents, but spare refs/ and immediate subdirs.
 
 /*
  * Remove empty parents, but spare refs/ and immediate subdirs.
- * Note: munges *refname.
  */
  */
-static void try_remove_empty_parents(char *refname)
+static void try_remove_empty_parents(const char *refname)
 {
 {
+       struct strbuf buf = STRBUF_INIT;
        char *p, *q;
        int i;
        char *p, *q;
        int i;
-       p = refname;
+
+       strbuf_addstr(&buf, refname);
+       p = buf.buf;
        for (i = 0; i < 2; i++) { /* refs/{heads,tags,...}/ */
                while (*p && *p != '/')
                        p++;
        for (i = 0; i < 2; i++) { /* refs/{heads,tags,...}/ */
                while (*p && *p != '/')
                        p++;
@@ -2296,8 +2298,7 @@ static void try_remove_empty_parents(char *refname)
                while (*p == '/')
                        p++;
        }
                while (*p == '/')
                        p++;
        }
-       for (q = p; *q; q++)
-               ;
+       q = buf.buf + buf.len;
        while (1) {
                while (q > p && *q != '/')
                        q--;
        while (1) {
                while (q > p && *q != '/')
                        q--;
@@ -2305,10 +2306,11 @@ static void try_remove_empty_parents(char *refname)
                        q--;
                if (q == p)
                        break;
                        q--;
                if (q == p)
                        break;
-               *q = '\0';
-               if (rmdir(git_path("%s", refname)))
+               strbuf_setlen(&buf, q - buf.buf);
+               if (rmdir(git_path("%s", buf.buf)))
                        break;
        }
                        break;
        }
+       strbuf_release(&buf);
 }
 
 /* make sure nobody touched the ref, and unlink */
 }
 
 /* make sure nobody touched the ref, and unlink */