All of lore.kernel.org
 help / color / mirror / Atom feed
From: "Torsten Bögershausen" <tboegi@web.de>
To: git@vger.kernel.org
Cc: tboegi@web.de, lists@hcf.yourweb.de
Subject: [PATCH v2 1/3] connect.c: allow ssh://user@[2001:db8::1]/repo.git
Date: Sat, 21 Feb 2015 16:52:48 +0100	[thread overview]
Message-ID: <54E8A9D0.30108@web.de> (raw)

The ssh:// syntax was added in 2386d65822c91, it accepted
ssh://user@2001:db8::1/repo.git, which is now legacy.

Over the years the parser was improved to support [] and port numbers,
but the combination of ssh://user@[2001:db8::1]:222/repo.git did
never work.

The only only way to use a user name, a literall IPV6 address and a port
number was ssh://[user@2001:db8::1]:222/repo.git

(Thanks to Christian Taube <lists@hcf.yourweb.de> for reporting this long
standing issue)

New users would use ssh://user@[2001:db8::1]:222/repo.git,
so change the parser to handle it correctly.

Support the old legacy URL's as well, to be backwards compatible,
and avoid regressions for users which upgrade an existing installation
to a later Git version.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---

Thanks for the reviews
I hope the intention of being backward compatible is a little bit clearer now,
as well as the intention to accept URL's conforming to the RFC


 connect.c        | 63 ++++++++++++++++++++++++++++++++++----------------------
 t/t5601-clone.sh |  2 +-
 2 files changed, 39 insertions(+), 26 deletions(-)

diff --git a/connect.c b/connect.c
index d47d0ec..b608976 100644
--- a/connect.c
+++ b/connect.c
@@ -274,28 +274,44 @@ static enum protocol get_protocol(const char *name)
 	die("I don't handle protocol '%s'", name);
 }
 
+static char *host_end(char **hoststart, int removebrackets)
+{
+	char *host = *hoststart;
+	char *end;
+	char *start = strstr(host, "@[");
+	if (start)
+		start++; /* Jump over '@' */
+	else
+		start = host;
+	if (start[0] == '[') {
+		end = strchr(start + 1, ']');
+		if (end) {
+			if (removebrackets) {
+				*end = 0;
+				memmove(start, start + 1, end - start);
+				end++;
+			}
+		} else
+			end = host;
+	} else
+		end = host;
+	return end;
+}
+
 #define STR_(s)	# s
 #define STR(s)	STR_(s)
 
 static void get_host_and_port(char **host, const char **port)
 {
 	char *colon, *end;
-
-	if (*host[0] == '[') {
-		end = strchr(*host + 1, ']');
-		if (end) {
-			*end = 0;
-			end++;
-			(*host)++;
-		} else
-			end = *host;
-	} else
-		end = *host;
+	end = host_end(host, 1);
 	colon = strchr(end, ':');
-
 	if (colon) {
-		*colon = 0;
-		*port = colon + 1;
+		long portnr = strtol(colon + 1, &end, 10);
+		if (end != colon + 1 && *end == '\0' && 0 <= portnr && portnr < 65536) {
+			*colon = 0;
+			*port = colon + 1;
+		}
 	}
 }
 
@@ -547,13 +563,16 @@ static struct child_process *git_proxy_connect(int fd[2], char *host)
 	return proxy;
 }
 
-static const char *get_port_numeric(const char *p)
+static char *get_port(char *host)
 {
 	char *end;
+	char *p = strchr(host, ':');
+
 	if (p) {
 		long port = strtol(p + 1, &end, 10);
 		if (end != p + 1 && *end == '\0' && 0 <= port && port < 65536) {
-			return p;
+			*p = '\0';
+			return p+1;
 		}
 	}
 
@@ -595,14 +614,7 @@ static enum protocol parse_connect_url(const char *url_orig, char **ret_host,
 	 * Don't do destructive transforms as protocol code does
 	 * '[]' unwrapping in get_host_and_port()
 	 */
-	if (host[0] == '[') {
-		end = strchr(host + 1, ']');
-		if (end) {
-			end++;
-		} else
-			end = host;
-	} else
-		end = host;
+	end = host_end(&host, 0);
 
 	if (protocol == PROTO_LOCAL)
 		path = end;
@@ -705,7 +717,8 @@ struct child_process *git_connect(int fd[2], const char *url,
 			char *ssh_host = hostandport;
 			const char *port = NULL;
 			get_host_and_port(&ssh_host, &port);
-			port = get_port_numeric(port);
+			if (!port)
+				port = get_port(ssh_host);
 
 			if (!ssh) ssh = "ssh";
 
diff --git a/t/t5601-clone.sh b/t/t5601-clone.sh
index e4f10c0..f901b8a 100755
--- a/t/t5601-clone.sh
+++ b/t/t5601-clone.sh
@@ -326,7 +326,7 @@ test_expect_success !MINGW,!CYGWIN 'clone local path foo:bar' '
 
 test_expect_success 'bracketed hostnames are still ssh' '
 	git clone "[myhost:123]:src" ssh-bracket-clone &&
-	expect_ssh myhost:123 src
+	expect_ssh myhost '-p 123' src
 '
 
 counter=0
-- 
2.2.0.rc1.790.ge19fcd2

             reply	other threads:[~2015-02-21 15:52 UTC|newest]

Thread overview: 4+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2015-02-21 15:52 Torsten Bögershausen [this message]
2015-02-22 17:57 ` [PATCH v2 1/3] connect.c: allow ssh://user@[2001:db8::1]/repo.git Torsten Bögershausen
2015-02-22 19:37 ` Junio C Hamano
2015-02-23  0:23   ` brian m. carlson

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

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=54E8A9D0.30108@web.de \
    --to=tboegi@web.de \
    --cc=git@vger.kernel.org \
    --cc=lists@hcf.yourweb.de \
    /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.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.