]> granicus.if.org Git - curl/commitdiff
FTP: URL decode path for dir listing in nocwd mode
authorDaniel Stenberg <daniel@haxx.se>
Tue, 10 Oct 2017 10:02:11 +0000 (12:02 +0200)
committerDaniel Stenberg <daniel@haxx.se>
Tue, 10 Oct 2017 13:02:38 +0000 (15:02 +0200)
Reported-by: Zenju on github
Test 244 added to verify
Fixes #1974
Closes #1976

lib/ftp.c
tests/data/Makefile.inc
tests/data/test244 [new file with mode: 0644]

index d7be88136fb48860c51c8fe2b12fcfc43c21a023..0c9df7890da88b01cdd80b1adf93f14e099f4d20 100644 (file)
--- a/lib/ftp.c
+++ b/lib/ftp.c
@@ -1457,25 +1457,22 @@ static CURLcode ftp_state_list(struct connectdata *conn)
      then just do LIST (in that case: nothing to do here)
   */
   char *cmd, *lstArg, *slashPos;
+  const char *inpath = data->state.path;
 
   lstArg = NULL;
   if((data->set.ftp_filemethod == FTPFILE_NOCWD) &&
-     data->state.path &&
-     data->state.path[0] &&
-     strchr(data->state.path, '/')) {
-
-    lstArg = strdup(data->state.path);
-    if(!lstArg)
-      return CURLE_OUT_OF_MEMORY;
+     inpath && inpath[0] && strchr(inpath, '/')) {
+    size_t n = strlen(inpath);
 
     /* Check if path does not end with /, as then we cut off the file part */
-    if(lstArg[strlen(lstArg) - 1] != '/') {
-
+    if(inpath[n - 1] != '/') {
       /* chop off the file part if format is dir/dir/file */
-      slashPos = strrchr(lstArg, '/');
-      if(slashPos)
-        *(slashPos + 1) = '\0';
+      slashPos = strrchr(inpath, '/');
+      n = slashPos - inpath;
     }
+    result = Curl_urldecode(data, inpath, n, &lstArg, NULL, FALSE);
+    if(result)
+      return result;
   }
 
   cmd = aprintf("%s%s%s",
index caf7314de3262416d72f31190640b5e711bb7644..c84ea79e7a7143fc0a2ae3883df8afbb42f9b416 100644 (file)
@@ -47,7 +47,7 @@ test208 test209 test210 test211 test212 test213 test214 test215 test216 \
 test217 test218 test219 test220 test221 test222 test223 test224 test225 \
 test226 test227 test228 test229         test231         test233 test234 \
 test235 test236 test237 test238 test239 test240 test241 test242 test243 \
-        test245 test246 test247 test248 test249 test250 test251 test252 \
+test244 test245 test246 test247 test248 test249 test250 test251 test252 \
 test253 test254 test255 test256 test257 test258 test259 test260 test261 \
 test262 test263 test264 test265 test266 test267 test268 test269 test270 \
 test271 test272 test273 test274 test275 test276 test277 test278 test279 \
diff --git a/tests/data/test244 b/tests/data/test244
new file mode 100644 (file)
index 0000000..8ce4b63
--- /dev/null
@@ -0,0 +1,54 @@
+<testcase>
+<info>
+<keywords>
+FTP
+PASV
+CWD
+--ftp-method
+nocwd
+</keywords>
+</info>
+#
+# Server-side
+<reply>
+<data mode="text">
+total 20
+drwxr-xr-x   8 98       98           512 Oct 22 13:06 .
+drwxr-xr-x   8 98       98           512 Oct 22 13:06 ..
+drwxr-xr-x   2 98       98           512 May  2  1996 .NeXT
+-r--r--r--   1 0        1             35 Jul 16  1996 README
+lrwxrwxrwx   1 0        1              7 Dec  9  1999 bin -> usr/bin
+dr-xr-xr-x   2 0        1            512 Oct  1  1997 dev
+drwxrwxrwx   2 98       98           512 May 29 16:04 download.html
+dr-xr-xr-x   2 0        1            512 Nov 30  1995 etc
+drwxrwxrwx   2 98       1            512 Oct 30 14:33 pub
+dr-xr-xr-x   5 0        1            512 Oct  1  1997 usr
+</data>
+</reply>
+
+# Client-side
+<client>
+<server>
+ftp
+</server>
+ <name>
+FTP dir listing with nocwd and URL encoded path
+ </name>
+ <command>
+--ftp-method nocwd ftp://%HOSTIP:%FTPPORT/fir%23t/th%69rd/244/
+</command>
+</client>
+
+# Verify data after the test has been "shot"
+<verify>
+<protocol>
+USER anonymous\r
+PASS ftp@example.com\r
+PWD\r
+EPSV\r
+TYPE A\r
+LIST fir#t/third/244/\r
+QUIT\r
+</protocol>
+</verify>
+</testcase>