aboutsummaryrefslogtreecommitdiffstats
path: root/builtin
diff options
context:
space:
mode:
authorToon Claes <toon@iotcl.com>2025-02-06 07:33:33 +0100
committerJunio C Hamano <gitster@pobox.com>2025-02-06 12:23:54 -0800
commit7a52a8c7d855d3ed779059af160248934ac2c6b0 (patch)
treeac459e99c5846ff6e2d77769d9e408de4c9e7190 /builtin
parentclone: add tags refspec earlier to fetch refspec (diff)
downloadgit-7a52a8c7d855d3ed779059af160248934ac2c6b0.tar.gz
git-7a52a8c7d855d3ed779059af160248934ac2c6b0.zip
clone: introduce struct clone_opts in builtin/clone.c
There is a lot of state stored in global variables in builtin/clone.c. In the long run we'd like to remove many of those. Introduce `struct clone_opts` in this file. This struct will be used to contain all details needed to perform the clone. The struct object can be thrown around to all the functions that need these details. The first field we're adding is `wants_head`. In some scenarios (specifically when both `--single-branch` and `--branch` are given) we are not interested in `HEAD` on the remote. The field `wants_head` in `struct clone_opts` will hold this information. We could have put `option_branch` and `option_single_branch` into that struct instead, but in a following commit we'll be using `wants_head` as well. Signed-off-by: Toon Claes <toon@iotcl.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
Diffstat (limited to 'builtin')
-rw-r--r--builtin/clone.c44
1 files changed, 29 insertions, 15 deletions
diff --git a/builtin/clone.c b/builtin/clone.c
index ef4af1f3e6..1d421c8f75 100644
--- a/builtin/clone.c
+++ b/builtin/clone.c
@@ -57,6 +57,13 @@
*
*/
+struct clone_opts {
+ int wants_head;
+};
+#define CLONE_OPTS_INIT { \
+ .wants_head = 1 /* default enabled */ \
+}
+
static int option_no_checkout, option_bare, option_mirror, option_single_branch = -1;
static int option_local = -1, option_no_hardlinks, option_shared;
static int option_tags = 1; /* default enabled */
@@ -429,23 +436,24 @@ static struct ref *find_remote_branch(const struct ref *refs, const char *branch
return ref;
}
-static struct ref *wanted_peer_refs(const struct ref *refs,
- struct refspec *refspec)
+static struct ref *wanted_peer_refs(struct clone_opts *opts,
+ const struct ref *refs,
+ struct refspec *refspec)
{
- struct ref *head = copy_ref(find_ref_by_name(refs, "HEAD"));
- struct ref *local_refs = head;
- struct ref **tail = local_refs ? &local_refs->next : &local_refs;
+ struct ref *local_refs = NULL;
+ struct ref **tail = &local_refs;
struct ref *to_free = NULL;
- if (option_single_branch) {
- if (!option_branch)
+ if (opts->wants_head) {
+ struct ref *head = copy_ref(find_ref_by_name(refs, "HEAD"));
+ if (head)
+ tail_link_ref(head, &tail);
+ if (option_single_branch)
refs = to_free = guess_remote_head(head, refs, 0);
- else {
- free_one_ref(head);
- local_refs = head = NULL;
- tail = &local_refs;
- refs = to_free = copy_ref(find_remote_branch(refs, option_branch));
- }
+ } else if (option_single_branch) {
+ local_refs = NULL;
+ tail = &local_refs;
+ refs = to_free = copy_ref(find_remote_branch(refs, option_branch));
}
for (size_t i = 0; i < refspec->nr; i++)
@@ -893,6 +901,8 @@ int cmd_clone(int argc,
struct string_list server_options = STRING_LIST_INIT_NODUP;
const char *bundle_uri = NULL;
+ struct clone_opts opts = CLONE_OPTS_INIT;
+
struct transport_ls_refs_options transport_ls_refs_options =
TRANSPORT_LS_REFS_OPTIONS_INIT;
@@ -1343,9 +1353,13 @@ int cmd_clone(int argc,
if (option_not.nr)
transport_set_option(transport, TRANS_OPT_DEEPEN_NOT,
(const char *)&option_not);
- if (option_single_branch)
+ if (option_single_branch) {
transport_set_option(transport, TRANS_OPT_FOLLOWTAGS, "1");
+ if (option_branch)
+ opts.wants_head = 0;
+ }
+
if (option_upload_pack)
transport_set_option(transport, TRANS_OPT_UPLOADPACK,
option_upload_pack);
@@ -1454,7 +1468,7 @@ int cmd_clone(int argc,
}
if (refs)
- mapped_refs = wanted_peer_refs(refs, &remote->fetch);
+ mapped_refs = wanted_peer_refs(&opts, refs, &remote->fetch);
if (mapped_refs) {
/*