aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/interfaces/libpq/fe-connect.c42
-rw-r--r--src/interfaces/libpq/t/001_uri.pl18
2 files changed, 54 insertions, 6 deletions
diff --git a/src/interfaces/libpq/fe-connect.c b/src/interfaces/libpq/fe-connect.c
index 64787bea511..61c025ff3bf 100644
--- a/src/interfaces/libpq/fe-connect.c
+++ b/src/interfaces/libpq/fe-connect.c
@@ -6763,9 +6763,9 @@ conninfo_uri_parse_params(char *params,
static char *
conninfo_uri_decode(const char *str, PQExpBuffer errorMessage)
{
- char *buf;
- char *p;
- const char *q = str;
+ char *buf; /* result */
+ char *p; /* output location */
+ const char *q = str; /* input location */
buf = malloc(strlen(str) + 1);
if (buf == NULL)
@@ -6775,13 +6775,23 @@ conninfo_uri_decode(const char *str, PQExpBuffer errorMessage)
}
p = buf;
+ /* skip leading whitespaces */
+ for (const char *s = q; *s == ' '; s++)
+ {
+ q++;
+ continue;
+ }
+
for (;;)
{
if (*q != '%')
{
- /* copy and check for NUL terminator */
- if (!(*(p++) = *(q++)))
- break;
+ /* if found a whitespace or NUL, the string ends */
+ if (*q == ' ' || *q == '\0')
+ goto end;
+
+ /* copy character */
+ *(p++) = *(q++);
}
else
{
@@ -6817,6 +6827,26 @@ conninfo_uri_decode(const char *str, PQExpBuffer errorMessage)
}
}
+end:
+
+ /* skip trailing whitespaces */
+ for (const char *s = q; *s == ' '; s++)
+ {
+ q++;
+ continue;
+ }
+
+ /* Not at the end of the string yet? Fail. */
+ if (*q != '\0')
+ {
+ libpq_append_error(errorMessage, "trailing data found: \"%s\"", str);
+ free(buf);
+ return NULL;
+ }
+
+ /* Copy NUL terminator */
+ *p = '\0';
+
return buf;
}
diff --git a/src/interfaces/libpq/t/001_uri.pl b/src/interfaces/libpq/t/001_uri.pl
index 49ea5377e03..27cf67ae800 100644
--- a/src/interfaces/libpq/t/001_uri.pl
+++ b/src/interfaces/libpq/t/001_uri.pl
@@ -86,6 +86,24 @@ my @tests = (
q{user='uri-user' host='host' (inet)},
q{},
],
+ [
+ # Leading and trailing spaces, works.
+ q{postgresql://host? user = uri-user & port = 12345 },
+ q{user='uri-user' host='host' port='12345' (inet)},
+ q{},
+ ],
+ [
+ # Trailing data in parameter.
+ q{postgresql://host? user user = uri & port = 12345 12 },
+ q{},
+ q{libpq_uri_regress: trailing data found: " user user "},
+ ],
+ [
+ # Trailing data in value.
+ q{postgresql://host? user = uri-user & port = 12345 12 },
+ q{},
+ q{libpq_uri_regress: trailing data found: " 12345 12 "},
+ ],
[ q{postgresql://host?}, q{host='host' (inet)}, q{}, ],
[
q{postgresql://[::1]:12345/db},