worktree.c: make find_shared_symref() return struct worktree *
This gives the caller more information and they can answer things like, "is it the main worktree" or "is it the current worktree". The latter question is needed for the "checkout a rebase branch" case later. Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
Nguyễn Thái Ngọc Duy committed
Apr 22, 2016 at 20:01 UTC
d3b9ac07eb44974bb619d71fc6c81c9f2036b96c
5 files changed
+28
-23
branch.c
+7
-6
@@ -336,13 +336,14 @@ void remove_branch_state(void)
336
337
void die_if_checked_out(const char *branch)
338
{
339
- char *existing;
339
+ const struct worktree *wt;
340
341
- existing = find_shared_symref("HEAD", branch);
342
- if (existing) {
343
- skip_prefix(branch, "refs/heads/", &branch);
344
- die(_("'%s' is already checked out at '%s'"), branch, existing);
345
- }
341
+ wt = find_shared_symref("HEAD", branch);
342
+ if (!wt)
343
+ return;
344
+ skip_prefix(branch, "refs/heads/", &branch);
345
+ die(_("'%s' is already checked out at '%s'"),
346
+ branch, wt->path);
347
}
348
349
int replace_each_worktree_head_symref(const char *oldref, const char *newref)
builtin/branch.c
+4
-4
@@ -220,12 +220,12 @@ static int delete_branches(int argc, const char **argv, int force, int kinds,
220
name = mkpathdup(fmt, bname.buf);
221
222
if (kinds == FILTER_REFS_BRANCHES) {
223
- char *worktree = find_shared_symref("HEAD", name);
224
- if (worktree) {
223
+ const struct worktree *wt =
224
+ find_shared_symref("HEAD", name);
225
+ if (wt) {
226
error(_("Cannot delete branch '%s' "
227
"checked out at '%s'"),
227
- bname.buf, worktree);
228
- free(worktree);
228
+ bname.buf, wt->path);
229
ret = 1;
230
continue;
231
}
builtin/notes.c
+4
-4
@@ -847,15 +847,15 @@ static int merge(int argc, const char **argv, const char *prefix)
847
update_ref(msg.buf, default_notes_ref(), result_sha1, NULL,
848
0, UPDATE_REFS_DIE_ON_ERR);
849
else { /* Merge has unresolved conflicts */
850
- char *existing;
850
+ const struct worktree *wt;
851
/* Update .git/NOTES_MERGE_PARTIAL with partial merge result */
852
update_ref(msg.buf, "NOTES_MERGE_PARTIAL", result_sha1, NULL,
853
0, UPDATE_REFS_DIE_ON_ERR);
854
/* Store ref-to-be-updated into .git/NOTES_MERGE_REF */
855
- existing = find_shared_symref("NOTES_MERGE_REF", default_notes_ref());
856
- if (existing)
855
+ wt = find_shared_symref("NOTES_MERGE_REF", default_notes_ref());
856
+ if (wt)
857
die(_("A notes merge into %s is already in-progress at %s"),
858
- default_notes_ref(), existing);
858
+ default_notes_ref(), wt->path);
859
if (create_symref("NOTES_MERGE_REF", default_notes_ref(), NULL))
860
die("Failed to store link to current notes ref (%s)",
861
default_notes_ref());
worktree.c
+9
-5
@@ -191,14 +191,19 @@ const char *get_worktree_git_dir(const struct worktree *wt)
191
return git_common_path("worktrees/%s", wt->id);
192
}
193
194
-char *find_shared_symref(const char *symref, const char *target)
194
+const struct worktree *find_shared_symref(const char *symref,
195
+ const char *target)
196
{
196
- char *existing = NULL;
197
+ const struct worktree *existing = NULL;
198
struct strbuf path = STRBUF_INIT;
199
struct strbuf sb = STRBUF_INIT;
199
- struct worktree **worktrees = get_worktrees();
200
+ static struct worktree **worktrees;
201
int i = 0;
202
203
+ if (worktrees)
204
+ free_worktrees(worktrees);
205
+ worktrees = get_worktrees();
206
+
207
for (i = 0; worktrees[i]; i++) {
208
strbuf_reset(&path);
209
strbuf_reset(&sb);
@@ -211,14 +216,13 @@ char *find_shared_symref(const char *symref, const char *target)
216
}
217
218
if (!strcmp(sb.buf, target)) {
214
- existing = xstrdup(worktrees[i]->path);
219
+ existing = worktrees[i];
220
break;
221
}
222
}
223
224
strbuf_release(&path);
225
strbuf_release(&sb);
221
- free_worktrees(worktrees);
226
227
return existing;
228
}
worktree.h
+4
-4
@@ -35,10 +35,10 @@ extern void free_worktrees(struct worktree **);
35
36
/*
37
* Check if a per-worktree symref points to a ref in the main worktree
38
- * or any linked worktree, and return the path to the exising worktree
39
- * if it is. Returns NULL if there is no existing ref. The caller is
40
- * responsible for freeing the returned path.
38
+ * or any linked worktree, and return the worktree that holds the ref,
39
+ * or NULL otherwise. The result may be destroyed by the next call.
40
*/
42
-extern char *find_shared_symref(const char *symref, const char *target);
41
+extern const struct worktree *find_shared_symref(const char *symref,
42
+ const char *target);
43
44
#endif