From: "lilinchao@oschina.cn" <lilinchao@oschina.cn>
To: "Li Linchao via GitGitGadget" <gitgitgadget@gmail.com>,
git <git@vger.kernel.org>
Cc: "Junio C Hamano" <gitster@pobox.com>,
"Derrick Stolee" <stolee@gmail.com>,
dscho <johannes.schindelin@gmx.de>,
"Jonathan Tan" <jonathantanmy@google.com>
Subject: Re: [PATCH v6] builtin/clone.c: add --reject-shallow option
Date: Sat, 13 Mar 2021 02:25:44 +0800 [thread overview]
Message-ID: <5e9d62c6836011eb9c540026b95c99cc@oschina.cn> (raw)
In-Reply-To: pull.865.v6.git.1614878345754.gitgitgadget@gmail.com
PING.
Seems that this patch have been forgotten by everyone.
--------------
>From: lilinchao <lilinchao@oschina.cn>
>
>In some scenarios, users may want more history than the repository
>offered for cloning, which happens to be a shallow repository, can
>give them. But because users don't know it is a shallow repository
>until they download it to local, users should have the option to
>refuse to clone this kind of repository, and may want to exit the
>process immediately without creating any unnecessary files.
>
>Althought there is an option '--depth=x' for users to decide how
>deep history they can fetch, but as the unshallow cloning's depth
>is INFINITY, we can't know exactly the minimun 'x' value that can
>satisfy the minimum integrity, so we can't pass 'x' value to --depth,
>and expect this can obtain a complete history of a repository.
>
>In other scenarios, if we have an API that allow us to import external
>repository, and then perform various operations on the repo.
>But if the imported is a shallow one(which is actually possible), it
>will affect the subsequent operations. So we can choose to refuse to
>clone, and let's just import a normal repository.
>
>This patch offers a new option '--reject-shallow' that can reject to
>clone a shallow repository.
>
>Signed-off-by: lilinchao <lilinchao@oschina.cn>
>---
> builtin/clone.c: add --reject-shallow option
>
> Changes since v1:
>
> * Rename --no-shallow to --reject-shallow
> * Enable to reject a non-local clone
> * Enable --[no-]reject-shallow from CLI override configuration.
> * Add more testcases.
> * Reword commit messages and relative documentation.
>
> Changes since v3:
>
> * Add support to reject clone shallow repo over https protocol
> * Add testcase to reject clone shallow repo over https:// transport
> * Reword commit messages and relative documentation according
> suggestions from Junio.
>
> Changes since v5:
>
> * camelcase config variable
> * warning client that source repo is shallow
> * better support ssh:// and git:// protocol v1, v2
>
> Signed-off-by: lilinchao lilinchao@oschina.cn
>
>Published-As: https://github.com/gitgitgadget/git/releases/tag/pr-865%2FCactusinhand%2Fgit-clone-options-v6
>Fetch-It-Via: git fetch https://github.com/gitgitgadget/git pr-865/Cactusinhand/git-clone-options-v6
>Pull-Request: https://github.com/gitgitgadget/git/pull/865
>
>Range-diff vs v5:
>
> 1: 3f765e49e4a7 ! 1: 953122588ca8 builtin/clone.c: add --reject-shallow option
> @@ Documentation/config/clone.txt: clone.defaultRemoteName::
> `origin`, and can be overridden by passing the `--origin` command-line
> option to linkgit:git-clone[1].
> +
> -+clone.rejectshallow::
> ++clone.rejectShallow::
> + Reject to clone a repository if it is a shallow one, can be overridden by
> + passing option `--reject-shallow` in command line. See linkgit:git-clone[1]
>
> @@ Documentation/git-clone.txt: objects from the source repository into a pack in t
> No checkout of HEAD is performed after the clone is complete.
>
> +--[no-]reject-shallow::
> -+ Fail if the source repository is a shallow repository. The
> -+ 'clone.rejectshallow' configuration variable can be used to
> ++ Fail if the source repository is a shallow repository.
> ++ The 'clone.rejectShallow' configuration variable can be used to
> + give the default.
> +
> --bare::
> @@ builtin/clone.c: static int git_clone_config(const char *k, const char *v, void
> free(remote_name);
> remote_name = xstrdup(v);
> }
> -+ if (!strcmp(k, "clone.rejectshallow")) {
> ++ if (!strcmp(k, "clone.rejectshallow"))
> + config_shallow = git_config_bool(k, v);
> -+ }
> ++
> return git_default_config(k, v, cb);
> }
>
> @@ builtin/clone.c: int cmd_clone(int argc, const char **argv, const char *prefix)
> + * If option_shallow is specified from CLI option,
> + * ignore config_shallow from git_clone_config.
> + */
> -+ if (config_shallow != -1) {
> ++ if (config_shallow != -1)
> + reject_shallow = config_shallow;
> -+ }
> -+ if (option_shallow != -1) {
> ++
> ++ if (option_shallow != -1)
> + reject_shallow = option_shallow;
> -+ }
> ++
> /*
> * apply the remote name provided by --origin only after this second
> * call to git_config, to ensure it overrides all config-based values.
> @@ builtin/clone.c: int cmd_clone(int argc, const char **argv, const char *prefix)
> if (!access(mkpath("%s/shallow", path), F_OK)) {
> + if (reject_shallow)
> + die("source repository is shallow, reject to clone.");
> ++ else
> ++ warning("source repository is shallow.");
> if (option_local > 0)
> warning(_("source repository is shallow, ignoring --local"));
> is_local = 0;
> @@ fetch-pack.c: static struct ref *do_fetch_pack(struct fetch_pack_args *args,
>
> if (args->stateless_rpc)
> packet_flush(fd[1]);
> -+
> -+ if (!args->deepen && args->remote_shallow)
> -+ die("source repository is shallow, reject to clone.");
> +
> if (args->deepen)
> setup_alternate_shallow(&shallow_lock, &alternate_shallow_file,
> NULL);
> +- else if (si->nr_ours || si->nr_theirs)
> ++ else if (si->nr_ours || si->nr_theirs) {
> ++ if (args->remote_shallow)
> ++ die("source repository is shallow, reject to clone.");
> ++ else
> ++ warning("source repository is shallow.");
> + alternate_shallow_file = setup_temporary_shallow(si->shallow);
> +- else
> ++ } else
> + alternate_shallow_file = NULL;
> + if (get_pack(args, fd, pack_lockfiles, NULL, sought, nr_sought,
> + &gitmodules_oids))
> @@ fetch-pack.c: static void receive_shallow_info(struct fetch_pack_args *args,
> - * shallow. In v0, remote refs that reach these objects are
> * rejected (unless --update-shallow is set); do the same.
> */
> -+ if (args->remote_shallow)
> -+ die("source repository is shallow, reject to clone.");
> prepare_shallow_info(si, shallows);
> - if (si->nr_ours || si->nr_theirs)
> +- if (si->nr_ours || si->nr_theirs)
> ++ if (si->nr_ours || si->nr_theirs) {
> ++ if (args->remote_shallow)
> ++ die("source repository is shallow, reject to clone.");
> ++ else
> ++ warning("source repository is shallow.");
> alternate_shallow_file =
> + setup_temporary_shallow(si->shallow);
> +- else
> ++ } else
> + alternate_shallow_file = NULL;
> + } else {
> + alternate_shallow_file = NULL;
>
> ## fetch-pack.h ##
> @@ fetch-pack.h: struct fetch_pack_args {
> @@ t/t5611-clone-config.sh: test_expect_success 'clone -c remote.<remote>.fetch=<re
> test_commit attributes .gitattributes "" &&
> rm -rf child &&
>
> - ## transport-helper.c ##
> -@@ transport-helper.c: static const char *boolean_options[] = {
> - TRANS_OPT_THIN,
> - TRANS_OPT_KEEP,
> - TRANS_OPT_FOLLOWTAGS,
> -- TRANS_OPT_DEEPEN_RELATIVE
> -+ TRANS_OPT_DEEPEN_RELATIVE,
> -+ TRANS_OPT_REJECT_SHALLOW
> - };
> -
> - static int strbuf_set_helper_option(struct helper_data *data,
> -
> ## transport.c ##
> @@ transport.c: static int set_git_option(struct git_transport_options *opts,
> list_objects_filter_die_if_populated(&opts->filter_options);
> @@ transport.h: void transport_check_allowed(const char *type);
> /* Aggressively fetch annotated tags if possible */
> #define TRANS_OPT_FOLLOWTAGS "followtags"
>
> -+/* reject shallow repo transport */
> ++/* Reject shallow repo transport */
> +#define TRANS_OPT_REJECT_SHALLOW "rejectshallow"
> +
> /* Accept refs that may update .git/shallow without --depth */
>
>
> Documentation/config/clone.txt | 4 +++
> Documentation/git-clone.txt | 7 ++++-
> builtin/clone.c | 24 +++++++++++++++++
> fetch-pack.c | 17 +++++++++---
> fetch-pack.h | 1 +
> t/t5606-clone-options.sh | 47 ++++++++++++++++++++++++++++++++++
> t/t5611-clone-config.sh | 32 +++++++++++++++++++++++
> transport.c | 4 +++
> transport.h | 4 +++
> 9 files changed, 135 insertions(+), 5 deletions(-)
>
>diff --git a/Documentation/config/clone.txt b/Documentation/config/clone.txt
>index 47de36a5fedf..7bcfbd18a52a 100644
>--- a/Documentation/config/clone.txt
>+++ b/Documentation/config/clone.txt
>@@ -2,3 +2,7 @@ clone.defaultRemoteName::
> The name of the remote to create when cloning a repository. Defaults to
> `origin`, and can be overridden by passing the `--origin` command-line
> option to linkgit:git-clone[1].
>+
>+clone.rejectShallow::
>+ Reject to clone a repository if it is a shallow one, can be overridden by
>+ passing option `--reject-shallow` in command line. See linkgit:git-clone[1]
>diff --git a/Documentation/git-clone.txt b/Documentation/git-clone.txt
>index 02d9c19cec75..0adc98fa7eee 100644
>--- a/Documentation/git-clone.txt
>+++ b/Documentation/git-clone.txt
>@@ -15,7 +15,7 @@ SYNOPSIS
> [--dissociate] [--separate-git-dir <git dir>]
> [--depth <depth>] [--[no-]single-branch] [--no-tags]
> [--recurse-submodules[=<pathspec>]] [--[no-]shallow-submodules]
>- [--[no-]remote-submodules] [--jobs <n>] [--sparse]
>+ [--[no-]remote-submodules] [--jobs <n>] [--sparse] [--[no-]reject-shallow]
> [--filter=<filter>] [--] <repository>
> [<directory>]
>
>@@ -149,6 +149,11 @@ objects from the source repository into a pack in the cloned repository.
> --no-checkout::
> No checkout of HEAD is performed after the clone is complete.
>
>+--[no-]reject-shallow::
>+ Fail if the source repository is a shallow repository.
>+ The 'clone.rejectShallow' configuration variable can be used to
>+ give the default.
>+
> --bare::
> Make a 'bare' Git repository. That is, instead of
> creating `<directory>` and placing the administrative
>diff --git a/builtin/clone.c b/builtin/clone.c
>index 51e844a2de0a..5c64837e8f7b 100644
>--- a/builtin/clone.c
>+++ b/builtin/clone.c
>@@ -50,6 +50,8 @@ static int option_no_checkout, option_bare, option_mirror, option_single_branch
> static int option_local = -1, option_no_hardlinks, option_shared;
> static int option_no_tags;
> static int option_shallow_submodules;
>+static int option_shallow = -1; /* unspecified */
>+static int config_shallow = -1; /* unspecified */
> static int deepen;
> static char *option_template, *option_depth, *option_since;
> static char *option_origin = NULL;
>@@ -90,6 +92,8 @@ static struct option builtin_clone_options[] = {
> OPT__VERBOSITY(&option_verbosity),
> OPT_BOOL(0, "progress", &option_progress,
> N_("force progress reporting")),
>+ OPT_BOOL(0, "reject-shallow", &option_shallow,
>+ N_("don't clone shallow repository")),
> OPT_BOOL('n', "no-checkout", &option_no_checkout,
> N_("don't create a checkout")),
> OPT_BOOL(0, "bare", &option_bare, N_("create a bare repository")),
>@@ -858,6 +862,9 @@ static int git_clone_config(const char *k, const char *v, void *cb)
> free(remote_name);
> remote_name = xstrdup(v);
> }
>+ if (!strcmp(k, "clone.rejectshallow"))
>+ config_shallow = git_config_bool(k, v);
>+
> return git_default_config(k, v, cb);
> }
>
>@@ -963,6 +970,7 @@ static int path_exists(const char *path)
> int cmd_clone(int argc, const char **argv, const char *prefix)
> {
> int is_bundle = 0, is_local;
>+ int reject_shallow = 0;
> const char *repo_name, *repo, *work_tree, *git_dir;
> char *path, *dir, *display_repo = NULL;
> int dest_exists, real_dest_exists = 0;
>@@ -1156,6 +1164,16 @@ int cmd_clone(int argc, const char **argv, const char *prefix)
> */
> git_config(git_clone_config, NULL);
>
>+ /*
>+ * If option_shallow is specified from CLI option,
>+ * ignore config_shallow from git_clone_config.
>+ */
>+ if (config_shallow != -1)
>+ reject_shallow = config_shallow;
>+
>+ if (option_shallow != -1)
>+ reject_shallow = option_shallow;
>+
> /*
> * apply the remote name provided by --origin only after this second
> * call to git_config, to ensure it overrides all config-based values.
>@@ -1216,6 +1234,10 @@ int cmd_clone(int argc, const char **argv, const char *prefix)
> if (filter_options.choice)
> warning(_("--filter is ignored in local clones; use file:// instead."));
> if (!access(mkpath("%s/shallow", path), F_OK)) {
>+ if (reject_shallow)
>+ die("source repository is shallow, reject to clone.");
>+ else
>+ warning("source repository is shallow.");
> if (option_local > 0)
> warning(_("source repository is shallow, ignoring --local"));
> is_local = 0;
>@@ -1227,6 +1249,8 @@ int cmd_clone(int argc, const char **argv, const char *prefix)
>
> transport_set_option(transport, TRANS_OPT_KEEP, "yes");
>
>+ if (reject_shallow)
>+ transport_set_option(transport, TRANS_OPT_REJECT_SHALLOW, "1");
> if (option_depth)
> transport_set_option(transport, TRANS_OPT_DEPTH,
> option_depth);
>diff --git a/fetch-pack.c b/fetch-pack.c
>index 0cb59acc4866..860ff45d46e7 100644
>--- a/fetch-pack.c
>+++ b/fetch-pack.c
>@@ -1126,12 +1126,17 @@ static struct ref *do_fetch_pack(struct fetch_pack_args *args,
>
> if (args->stateless_rpc)
> packet_flush(fd[1]);
>+
> if (args->deepen)
> setup_alternate_shallow(&shallow_lock, &alternate_shallow_file,
> NULL);
>- else if (si->nr_ours || si->nr_theirs)
>+ else if (si->nr_ours || si->nr_theirs) {
>+ if (args->remote_shallow)
>+ die("source repository is shallow, reject to clone.");
>+ else
>+ warning("source repository is shallow.");
> alternate_shallow_file = setup_temporary_shallow(si->shallow);
>- else
>+ } else
> alternate_shallow_file = NULL;
> if (get_pack(args, fd, pack_lockfiles, NULL, sought, nr_sought,
> &gitmodules_oids))
>@@ -1498,10 +1503,14 @@ static void receive_shallow_info(struct fetch_pack_args *args,
> * rejected (unless --update-shallow is set); do the same.
> */
> prepare_shallow_info(si, shallows);
>- if (si->nr_ours || si->nr_theirs)
>+ if (si->nr_ours || si->nr_theirs) {
>+ if (args->remote_shallow)
>+ die("source repository is shallow, reject to clone.");
>+ else
>+ warning("source repository is shallow.");
> alternate_shallow_file =
> setup_temporary_shallow(si->shallow);
>- else
>+ } else
> alternate_shallow_file = NULL;
> } else {
> alternate_shallow_file = NULL;
>diff --git a/fetch-pack.h b/fetch-pack.h
>index 736a3dae467a..6e4f8f0d738c 100644
>--- a/fetch-pack.h
>+++ b/fetch-pack.h
>@@ -39,6 +39,7 @@ struct fetch_pack_args {
> unsigned self_contained_and_connected:1;
> unsigned cloning:1;
> unsigned update_shallow:1;
>+ unsigned remote_shallow:1;
> unsigned deepen:1;
>
> /*
>diff --git a/t/t5606-clone-options.sh b/t/t5606-clone-options.sh
>index 52e5789fb050..6170d0513227 100755
>--- a/t/t5606-clone-options.sh
>+++ b/t/t5606-clone-options.sh
>@@ -5,6 +5,8 @@ GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME=main
> export GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME
>
> . ./test-lib.sh
>+. "$TEST_DIRECTORY"/lib-httpd.sh
>+start_httpd
>
> test_expect_success 'setup' '
>
>@@ -45,6 +47,51 @@ test_expect_success 'disallows --bare with --separate-git-dir' '
>
> '
>
>+test_expect_success 'fail to clone http shallow repository' '
>+ git clone --depth=1 --no-local parent shallow-repo &&
>+ git clone --bare --no-local shallow-repo "$HTTPD_DOCUMENT_ROOT_PATH/repo.git" &&
>+ test_must_fail git clone --reject-shallow $HTTPD_URL/smart/repo.git out 2>err &&
>+ test_i18ngrep -e "source repository is shallow, reject to clone." err
>+
>+'
>+
>+test_expect_success 'fail to clone shallow repository' '
>+ rm -rf shallow-repo &&
>+ git clone --depth=1 --no-local parent shallow-repo &&
>+ test_must_fail git clone --reject-shallow shallow-repo out 2>err &&
>+ test_i18ngrep -e "source repository is shallow, reject to clone." err
>+
>+'
>+
>+test_expect_success 'fail to clone non-local shallow repository' '
>+ rm -rf shallow-repo &&
>+ git clone --depth=1 --no-local parent shallow-repo &&
>+ test_must_fail git clone --reject-shallow --no-local shallow-repo out 2>err &&
>+ test_i18ngrep -e "source repository is shallow, reject to clone." err
>+
>+'
>+
>+test_expect_success 'clone shallow repository with --no-reject-shallow' '
>+ rm -rf shallow-repo &&
>+ git clone --depth=1 --no-local parent shallow-repo &&
>+ git clone --no-reject-shallow --no-local shallow-repo clone-repo
>+
>+'
>+
>+test_expect_success 'clone normal repository with --reject-shallow' '
>+ rm -rf clone-repo &&
>+ git clone --no-local parent normal-repo &&
>+ git clone --reject-shallow --no-local normal-repo clone-repo
>+
>+'
>+
>+test_expect_success 'unspecified any configs or options' '
>+ rm -rf shallow-repo clone-repo &&
>+ git clone --depth=1 --no-local parent shallow-repo &&
>+ git clone shallow-repo clone-repo
>+
>+'
>+
> test_expect_success 'uses "origin" for default remote name' '
>
> git clone parent clone-default-origin &&
>diff --git a/t/t5611-clone-config.sh b/t/t5611-clone-config.sh
>index 9f555b87ecdf..da10d3f10352 100755
>--- a/t/t5611-clone-config.sh
>+++ b/t/t5611-clone-config.sh
>@@ -95,6 +95,38 @@ test_expect_success 'clone -c remote.<remote>.fetch=<refspec> --origin=<name>' '
> test_cmp expect actual
> '
>
>+test_expect_success 'clone.rejectshallow=true should fail to clone' '
>+ rm -rf child &&
>+ git clone --depth=1 --no-local . child &&
>+ test_must_fail git -c clone.rejectshallow=true clone --no-local child out 2>err &&
>+ test_i18ngrep -e "source repository is shallow, reject to clone." err
>+'
>+
>+test_expect_success 'clone.rejectshallow=false should succeed' '
>+ rm -rf child out &&
>+ git clone --depth=1 --no-local . child &&
>+ git -c clone.rejectshallow=false clone --no-local child out
>+'
>+
>+test_expect_success 'clone.rejectshallow=true should succeed with normal repo' '
>+ rm -rf child out &&
>+ git clone --no-local . child &&
>+ git -c clone.rejectshallow=true clone --no-local child out
>+'
>+
>+test_expect_success 'option --reject-shallow override clone.rejectshallow' '
>+ rm -rf child out &&
>+ git clone --depth=1 --no-local . child &&
>+ test_must_fail git -c clone.rejectshallow=false clone --reject-shallow --no-local child out 2>err &&
>+ test_i18ngrep -e "source repository is shallow, reject to clone." err
>+'
>+
>+test_expect_success 'option --no-reject-shallow override clone.rejectshallow' '
>+ rm -rf child out &&
>+ git clone --depth=1 --no-local . child &&
>+ git -c clone.rejectshallow=true clone --no-reject-shallow --no-local child out
>+'
>+
> test_expect_success MINGW 'clone -c core.hideDotFiles' '
> test_commit attributes .gitattributes "" &&
> rm -rf child &&
>diff --git a/transport.c b/transport.c
>index b13fab5dc3b1..34fe01221ee0 100644
>--- a/transport.c
>+++ b/transport.c
>@@ -236,6 +236,9 @@ static int set_git_option(struct git_transport_options *opts,
> list_objects_filter_die_if_populated(&opts->filter_options);
> parse_list_objects_filter(&opts->filter_options, value);
> return 0;
>+ } else if (!strcmp(name, TRANS_OPT_REJECT_SHALLOW)) {
>+ opts->reject_shallow = !!value;
>+ return 0;
> }
> return 1;
> }
>@@ -370,6 +373,7 @@ static int fetch_refs_via_pack(struct transport *transport,
> args.stateless_rpc = transport->stateless_rpc;
> args.server_options = transport->server_options;
> args.negotiation_tips = data->options.negotiation_tips;
>+ args.remote_shallow = transport->smart_options->reject_shallow;
>
> if (!data->got_remote_heads) {
> int i;
>diff --git a/transport.h b/transport.h
>index 24e15799e714..4d5db0a7f22b 100644
>--- a/transport.h
>+++ b/transport.h
>@@ -14,6 +14,7 @@ struct git_transport_options {
> unsigned check_self_contained_and_connected : 1;
> unsigned self_contained_and_connected : 1;
> unsigned update_shallow : 1;
>+ unsigned reject_shallow : 1;
> unsigned deepen_relative : 1;
>
> /* see documentation of corresponding flag in fetch-pack.h */
>@@ -194,6 +195,9 @@ void transport_check_allowed(const char *type);
> /* Aggressively fetch annotated tags if possible */
> #define TRANS_OPT_FOLLOWTAGS "followtags"
>
>+/* Reject shallow repo transport */
>+#define TRANS_OPT_REJECT_SHALLOW "rejectshallow"
>+
> /* Accept refs that may update .git/shallow without --depth */
> #define TRANS_OPT_UPDATE_SHALLOW "updateshallow"
>
>
>base-commit: f01623b2c9d14207e497b21ebc6b3ec4afaf4b46
>--
>gitgitgadget
>
next prev parent reply other threads:[~2021-03-12 18:26 UTC|newest]
Thread overview: 48+ messages / expand[flat|nested] mbox.gz Atom feed top
2021-02-04 3:31 [PATCH] builtin/clone.c: add --no-shallow option Li Linchao via GitGitGadget
2021-02-04 5:50 ` Junio C Hamano
2021-02-04 10:32 ` lilinchao
2021-02-04 18:36 ` Junio C Hamano
2021-02-04 14:00 ` Johannes Schindelin
2021-02-04 18:24 ` Junio C Hamano
2021-02-08 8:31 ` [PATCH v2 0/2] " Li Linchao via GitGitGadget
2021-02-08 8:31 ` [PATCH v2 1/2] " lilinchao via GitGitGadget
2021-02-08 8:31 ` [PATCH v2 2/2] builtin/clone.c: add --reject-shallow option lilinchao via GitGitGadget
2021-02-08 13:33 ` [PATCH v2 0/2] builtin/clone.c: add --no-shallow option Derrick Stolee
[not found] ` <32bb0d006a1211ebb94254a05087d89a835@gmail.com>
2021-02-08 13:48 ` lilinchao
2021-02-08 14:12 ` [PATCH v3] builtin/clone.c: add --reject-shallow option Li Linchao via GitGitGadget
2021-02-09 20:32 ` Junio C Hamano
[not found] ` <026bd8966b1611eb975aa4badb2c2b1190694@pobox.com>
2021-02-10 9:07 ` lilinchao
2021-02-10 16:27 ` Junio C Hamano
[not found] ` <eaa219a86bbc11ebb6c7a4badb2c2b1165032@pobox.com>
2021-02-20 10:40 ` lilinchao
2021-02-21 7:05 ` [PATCH v4] " Li Linchao via GitGitGadget
2021-02-22 18:12 ` Junio C Hamano
2021-03-01 22:03 ` Jonathan Tan
2021-03-01 22:34 ` Junio C Hamano
2021-03-02 8:44 ` lilinchao
2021-03-03 23:59 ` Junio C Hamano
2021-03-04 1:53 ` Jonathan Tan
[not found] ` <8f3c00de753911eb93d3d4ae5278bc1270191@pobox.com>
2021-02-28 17:58 ` lilinchao
2021-02-28 18:06 ` [PATCH v5] " Li Linchao via GitGitGadget
2021-03-01 7:11 ` lilinchao
2021-03-01 22:40 ` Johannes Schindelin
2021-03-04 6:26 ` lilinchao
2021-03-03 23:21 ` Junio C Hamano
2021-03-04 5:50 ` lilinchao
2021-03-04 17:19 ` [PATCH v6] " Li Linchao via GitGitGadget
2021-03-12 18:25 ` lilinchao [this message]
2021-03-25 11:09 ` [PATCH v7] " Li Linchao via GitGitGadget
2021-03-25 20:31 ` Junio C Hamano
2021-03-25 22:57 ` Junio C Hamano
[not found] ` <19c9dc128da911ebacc7d4ae5278bc1233465@pobox.com>
2021-03-26 3:34 ` lilinchao
[not found] ` <7a71c96c8dbd11eb8bb0d4ae5278bc1296681@pobox.com>
2021-03-26 3:49 ` lilinchao
2021-03-29 10:19 ` [PATCH v8] " Li Linchao via GitGitGadget
2021-03-29 21:36 ` Junio C Hamano
2021-03-30 9:54 ` Johannes Schindelin
2021-03-30 17:46 ` Junio C Hamano
2021-03-31 13:30 ` Johannes Schindelin
[not found] ` <f8b2582c913d11ebaddbd4ae5278bc1214940@gmx.de>
2021-03-31 11:03 ` lilinchao
2021-03-31 15:51 ` [PATCH v9] " lilinchao via GitGitGadget
2021-03-31 19:14 ` Junio C Hamano
2021-03-31 22:24 ` Johannes Schindelin
2021-03-31 22:37 ` Junio C Hamano
2021-04-01 10:46 ` [PATCH v10] " Li Linchao via GitGitGadget
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
List information: http://vger.kernel.org/majordomo-info.html
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=5e9d62c6836011eb9c540026b95c99cc@oschina.cn \
--to=lilinchao@oschina.cn \
--cc=git@vger.kernel.org \
--cc=gitgitgadget@gmail.com \
--cc=gitster@pobox.com \
--cc=johannes.schindelin@gmx.de \
--cc=jonathantanmy@google.com \
--cc=stolee@gmail.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
Code repositories for project(s) associated with this public inbox
https://80x24.org/mirrors/git.git
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).