{"thread":{"id":"44464","subject":"[PATCH] upload-pack: Optionally allow fetching any sha1","startedAt":"2016-11-11T16:32:14Z","lastAt":"2016-11-11T16:32:14Z","messageCount":1,"participants":["David Turner"],"isPatch":true,"patchVersion":1,"patchTotal":null},"messages":[{"id":"305791","messageId":"1478881918-11482-1-git-send-email-dturner@twosigma.com","threadId":"44464","inReplyTo":null,"subject":"[PATCH] upload-pack: Optionally allow fetching any sha1","fromName":"David Turner","fromEmail":"dturner@twosigma.com","sentAt":"2016-11-11T16:31:58Z","receivedAt":"2016-11-11T16:32:14Z","isPatch":true,"sender":{"key":"novalis@novalis.org","avatar":"https://avatars.githubusercontent.com/u/77003?v=4"},"body":"It seems a little silly to do a reachabilty check in the case where we\ntrust the user to access absolutely everything in the repository.\n\nAlso, it's racy in a distributed system -- perhaps one server\nadvertises a ref, but another has since had a force-push to that ref,\nand perhaps the two HTTP requests end up directed to these different\nservers.\n\nSigned-off-by: David Turner <dturner@twosigma.com>\n---\n\nThis one is on top of yesterday's patch, \"remote-curl: don't hang when\na server dies before any output\".\n\nThat's because I want my test to show that allowanysha1inhead allows a\nfetch to succeed where allowreachablesha1inhead would fail.  Prior to\nthe previous patch, the first fetch's failure would instead be a hang.\n\n t/t5551-http-fetch-smart.sh | 22 ++++++++++++++++++++++\n upload-pack.c               | 10 +++++++++-\n 2 files changed, 31 insertions(+), 1 deletion(-)\n\ndiff --git a/t/t5551-http-fetch-smart.sh b/t/t5551-http-fetch-smart.sh\nindex 43665ab..8d3db40 100755\n--- a/t/t5551-http-fetch-smart.sh\n+++ b/t/t5551-http-fetch-smart.sh\n@@ -306,6 +306,28 @@ test_expect_success 'test allowreachablesha1inwant with unreachable' '\n \ttest_must_fail git -C test_reachable.git fetch origin \"$(git rev-parse HEAD)\"\n '\n \n+test_expect_success 'test allowanysha1inwant with unreachable' '\n+\ttest_when_finished \"rm -rf test_reachable.git; git reset --hard $(git rev-parse HEAD)\" &&\n+\n+\t#create unreachable sha\n+\techo content >file2 &&\n+\tgit add file2 &&\n+\tgit commit -m two &&\n+\tgit push public HEAD:refs/heads/doomed &&\n+\tgit push public :refs/heads/doomed &&\n+\n+\tserver=\"$HTTPD_DOCUMENT_ROOT_PATH/repo.git\" &&\n+\tmaster_sha=$(git -C \"$server\" rev-parse refs/heads/master) &&\n+\tgit -C \"$server\" config uploadpack.allowreachablesha1inwant 1 &&\n+\n+\tgit init --bare test_reachable.git &&\n+\tgit -C test_reachable.git remote add origin \"$HTTPD_URL/smart/repo.git\" &&\n+\ttest_must_fail git -C test_reachable.git fetch origin \"$(git rev-parse HEAD)\" &&\n+\n+\tgit -C \"$server\" config uploadpack.allowanysha1inwant 1 &&\n+\tgit -C test_reachable.git fetch origin \"$(git rev-parse HEAD)\"\n+'\n+\n test_expect_success EXPENSIVE 'http can handle enormous ref negotiation' '\n \t(\n \t\tcd \"$HTTPD_DOCUMENT_ROOT_PATH/repo.git\" &&\ndiff --git a/upload-pack.c b/upload-pack.c\nindex e0db8b4..7597ba3 100644\n--- a/upload-pack.c\n+++ b/upload-pack.c\n@@ -46,6 +46,8 @@ static int no_progress, daemon_mode;\n #define ALLOW_TIP_SHA1\t01\n /* Allow request of a sha1 if it is reachable from a ref (possibly hidden ref). */\n #define ALLOW_REACHABLE_SHA1\t02\n+/* Allow request of any sha1. Implies ALLOW_TIP_SHA1 and ALLOW_REACHABLE_SHA1. */\n+#define ALLOW_ANY_SHA1\t07\n static unsigned int allow_unadvertised_object_request;\n static int shallow_nr;\n static struct object_array have_obj;\n@@ -825,7 +827,8 @@ static void receive_needs(void)\n \t\t\t    sha1_to_hex(sha1_buf));\n \t\tif (!(o->flags & WANTED)) {\n \t\t\to->flags |= WANTED;\n-\t\t\tif (!is_our_ref(o))\n+\t\t\tif (!((allow_unadvertised_object_request & ALLOW_ANY_SHA1) == ALLOW_ANY_SHA1\n+\t\t\t      || is_our_ref(o)))\n \t\t\t\thas_non_tip = 1;\n \t\t\tadd_object_array(o, NULL, &want_obj);\n \t\t}\n@@ -1008,6 +1011,11 @@ static int upload_pack_config(const char *var, const char *value, void *unused)\n \t\t\tallow_unadvertised_object_request |= ALLOW_REACHABLE_SHA1;\n \t\telse\n \t\t\tallow_unadvertised_object_request &= ~ALLOW_REACHABLE_SHA1;\n+\t} else if (!strcmp(\"uploadpack.allowanysha1inwant\", var)) {\n+\t\tif (git_config_bool(var, value))\n+\t\t\tallow_unadvertised_object_request |= ALLOW_ANY_SHA1;\n+\t\telse\n+\t\t\tallow_unadvertised_object_request &= ~ALLOW_ANY_SHA1;\n \t} else if (!strcmp(\"uploadpack.keepalive\", var)) {\n \t\tkeepalive = git_config_int(var, value);\n \t\tif (!keepalive)\n-- \n2.8.0.rc4.22.g8ae061a\n\n"}]}