git/list[1] front-page[2] threads[3] people[4] search[5] about
 

Re: upload-pack is slow with lots of refs

From
Johannes Sixt <j6t@kdbg.org>
Date
Oct 8, 2012, 15:05 UTC
Message-ID
<5072EBD1.40500@kdbg.org>
In-Reply-To
<CAJo=hJsYVdWeG0ZyqexEXNfOq_k1XDR_gGP+fy_z==LvdnWJTQ@mail.gmail.com>
Am 05.10.2012 18:57, schrieb Shawn Pearce:
Show 12 quoted lines
> On Thu, Oct 4, 2012 at 11:24 PM, Johannes Sixt <j.sixt@viscovery.net> wrote:
>> Upload-pack can just start
>> advertising refs in the "v1" way and announce a "v2" capability and listen
>> for response in parallel. A v2 capable client can start sending "wants" or
>> some other signal as soon as it sees the "v2" capability. Upload-pack,
>> which was listening for responses in parallel, can interrupt its
>> advertisements and continue with v2 protocol from here.
>>
>> This sounds so simple (not the implementation, of course) - I must be
>> missing something.
> 
> Smart HTTP is not bidirectional. The client can't cut off the server.

Smart HTTP does not need it: you already posted a better solution (I'm refering to "&v=2").

> Its also more complex to code the server to listen for a stop command
> from the client at the same time the server is blasting out useless
> references to the client.

At least the server side does not seem to be that complex. See below. Of course, the server blasted out some refs, but I'm confident that in practice the client will be able to signal v2 capability after a few packets of advertisements. You can switch on TCP_NODELAY for the first line with the capabilities to ensure it goes out on the wire ASAP.

diff --git a/upload-pack.c b/upload-pack.c
index 2e90ccb..c29ae04 100644
--- a/upload-pack.c
+++ b/upload-pack.c
@@ -720,11 +720,20 @@ static void receive_needs(void)
 	free(shallows.objects);
 }
 
+static int client_spoke(void)
+{
+	struct pollfd pfd;
+	pfd.fd = 0;
+	pfd.events = POLLIN;
+	return poll(&pfd, 1, 0) > 0 &&
+		(pfd.revents & (POLLIN|POLLHUP));
+}
+
 static int send_ref(const char *refname, const unsigned char *sha1, int flag, void *cb_data)
 {
 	static const char *capabilities = "multi_ack thin-pack side-band"
 		" side-band-64k ofs-delta shallow no-progress"
-		" include-tag multi_ack_detailed";
+		" include-tag multi_ack_detailed version2";
 	struct object *o = lookup_unknown_object(sha1);
 	const char *refname_nons = strip_namespace(refname);
 
@@ -752,7 +761,8 @@ static int send_ref(const char *refname, const unsigned char *sha1, int flag, vo
 		if (o)
 			packet_write(1, "%s %s^{}\n", sha1_to_hex(o->sha1), refname_nons);
 	}
-	return 0;
+
+	return client_spoke();
 }
 
 static int mark_our_ref(const char *refname, const unsigned char *sha1, int flag, void *cb_data)
@@ -771,8 +781,14 @@ static void upload_pack(void)
 {
 	if (advertise_refs || !stateless_rpc) {
 		reset_timeout();
-		head_ref_namespaced(send_ref, NULL);
-		for_each_namespaced_ref(send_ref, NULL);
+		if (head_ref_namespaced(send_ref, NULL) ||
+		    for_each_namespaced_ref(send_ref, NULL)) {
+			/*
+			 * TODO: continue with protocol version 2
+			 * optimization: do not send refs
+			 * that were already sent
+			 */
+		}
 		packet_flush(1);
 	} else {
 		head_ref_namespaced(mark_our_ref, NULL);
Previous: Shawn PearceNext: Shawn Pearce
Message 12 of 24 in “upload-pack is slow with lots of refs”
  1. Ævar Arnfjörð BjarmasonOct 3, 2012
  2. Nguyen Thai Ngoc DuyOct 3, 2012
  3. Jeff KingOct 3, 2012
  4. Junio C HamanoOct 3, 2012
  5. Jeff KingOct 3, 2012
  6. Shawn PearceOct 3, 2012
  7. Jeff KingOct 3, 2012
  8. Sascha CunzOct 4, 2012
  9. Jeff KingOct 5, 2012
  10. Johannes SixtOct 5, 2012
  11. Shawn PearceOct 5, 2012
  12. Johannes SixtOct 8, 2012
  13. Shawn PearceOct 9, 2012
  14. Johannes SixtOct 9, 2012
  15. Johannes SixtOct 9, 2012
  16. Ævar Arnfjörð BjarmasonOct 3, 2012
  17. Jeff KingOct 3, 2012
  18. Ævar Arnfjörð BjarmasonOct 3, 2012
  19. Jeff KingOct 3, 2012
  20. Ævar Arnfjörð BjarmasonOct 3, 2012
  21. Ævar Arnfjörð BjarmasonOct 3, 2012
  22. Jeff KingOct 3, 2012
  23. Ævar Arnfjörð BjarmasonOct 3, 2012
  24. Junio C HamanoOct 3, 2012

Read the whole thread, see it on lore, or plain text.

$ cat FOOTERMessages come from the public archive at lore.kernel.org/git, fetched every hour. The front page is chosen and written each morning by an AI editor and can be wrong; the threads themselves are the record. About and API. For agents: an MCP server at https://gitlist.dev/mcp, and any thread, story or person page as Markdown by adding .md to its URL (or sending Accept: text/markdown). Details in /llms.txt.