Commit Diff


commit - f2522b43139cc1a41a4a75d9eff84ee40be408da
commit + 9d092b607a25f4598557792be5ec35f02c3ae966
blob - 442af15efbc4f16171083fe27bd80d7d836631af
blob + e1552d6b8595ba8240fe007659929e6180225ef4
--- iri.c
+++ iri.c
@@ -272,9 +272,13 @@ path_clean(char *path)
 	}
 
 	/* 3. eliminate each inner .. along with the preceding non-.. */
-	for (i = strstr(path, "../"); i != NULL; i = strstr(path, ".."))
+	for (i = strstr(path, "../"); i != NULL; i = strstr(path, "..")) {
+		/* break if we've found a trailing .. */
+		if (i[2] == '\0')
+			break;
 		if (!path_elide_dotdot(path, i, 3))
 			return 0;
+	}
 
 	/* 4. eliminate trailing ..*/
 	if ((i = strstr(path, "..")) != NULL)
blob - 785305d049d2d46348dc1fe7d627117c645413cc
blob + 6595f92dc5ec0c201cab30c116bbdf6745e2ebaf
--- regress/iri_test.c
+++ regress/iri_test.c
@@ -194,6 +194,10 @@ main(void)
 	    PASS,
             IRI("gemini", "omarpolo.com", "", "foo", "", ""),
 	    "Trim initial slashes (pt. 2)");
+	TEST("http://a/b/c/../..",
+	    PASS,
+	    IRI("http", "a", "", "", "", ""),
+	    "avoid infinite loops (see v1.6.1)");
 
 	/* query */
 	TEST("foo://example.com/foo/?gne",