]> git.ipfire.org Git - thirdparty/curl.git/commitdiff
file: support GETing directories again
authorLuke Granger-Brown <git@lukegb.com>
Sat, 3 Apr 2021 19:12:48 +0000 (19:12 +0000)
committerDaniel Stenberg <daniel@haxx.se>
Mon, 5 Apr 2021 10:22:07 +0000 (12:22 +0200)
After 957bc1881e686f9714c4e6a01bf33535091f0e21, we no longer compute an
expected_size for directories. This has the upshot that when we compare
even an empty Range with the available size, we fail.

This brings back the previous behaviour, which was to succeed, but with
empty content. This also removes the "Accept-ranges: bytes" header,
which is nonsensical on directories.

Adds test 3016
Fixes #6845
Closes #6846

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

index dd8a1fd12ac36f1cc0c6edbe910a46cbca95b599..1d174e519e19eaa569ed933aece6dafadf067662 100644 (file)
@@ -417,12 +417,12 @@ static CURLcode file_do(struct Curl_easy *data, bool *done)
       result = Curl_client_write(data, CLIENTWRITE_HEADER, header, 0);
       if(result)
         return result;
-    }
 
-    result = Curl_client_write(data, CLIENTWRITE_HEADER,
-                               (char *)"Accept-ranges: bytes\r\n", 0);
-    if(result)
-      return result;
+      result = Curl_client_write(data, CLIENTWRITE_HEADER,
+                                 (char *)"Accept-ranges: bytes\r\n", 0);
+      if(result != CURLE_OK)
+        return result;
+    }
 
     filetime = (time_t)statbuf.st_mtime;
     result = Curl_gmtime(filetime, &buffer);
@@ -464,18 +464,23 @@ static CURLcode file_do(struct Curl_easy *data, bool *done)
     data->state.resume_from += (curl_off_t)statbuf.st_size;
   }
 
-  if(data->state.resume_from <= expected_size)
-    expected_size -= data->state.resume_from;
-  else {
-    failf(data, "failed to resume file:// transfer");
-    return CURLE_BAD_DOWNLOAD_RESUME;
+  if(data->state.resume_from > 0) {
+    /* We check explicitly if we have a start offset, because
+     * expected_size may be -1 if we don't know how large the file is,
+     * in which case we should not adjust it. */
+    if(data->state.resume_from <= expected_size)
+      expected_size -= data->state.resume_from;
+    else {
+      failf(data, "failed to resume file:// transfer");
+      return CURLE_BAD_DOWNLOAD_RESUME;
+    }
   }
 
   /* A high water mark has been specified so we obey... */
   if(data->req.maxdownload > 0)
     expected_size = data->req.maxdownload;
 
-  if(!fstated || (expected_size == 0))
+  if(!fstated || (expected_size <= 0))
     size_known = FALSE;
   else
     size_known = TRUE;
@@ -484,7 +489,7 @@ static CURLcode file_do(struct Curl_easy *data, bool *done)
      this is both more efficient than the former call to download() and
      it avoids problems with select() and recv() on file descriptors
      in Winsock */
-  if(fstated)
+  if(size_known)
     Curl_pgrsSetDownloadSize(data, expected_size);
 
   if(data->state.resume_from) {
index ea52683d2254ae90081b203fb2f5387767feef7f..6ae2a249b4f8463dc421ee60e4cd8af975540f5c 100644 (file)
@@ -229,4 +229,5 @@ test2080 test2081 \
 test2100 \
 \
 test3000 test3001 test3002 test3003 test3004 test3005 test3006 test3007 \
-test3008 test3009 test3010 test3011 test3012 test3013 test3014 test3015
+test3008 test3009 test3010 test3011 test3012 test3013 test3014 test3015 \
+test3016
diff --git a/tests/data/test3016 b/tests/data/test3016
new file mode 100644 (file)
index 0000000..b645074
--- /dev/null
@@ -0,0 +1,34 @@
+<testcase>
+<info>
+<keywords>
+HTTP
+HTTP GET
+FILE
+</keywords>
+</info>
+
+#
+# Client-side
+<client>
+<server>
+file
+</server>
+<name>
+GET a directory using file://
+</name>
+<!-- doesn't work on win32, see #6379 -->
+<features>
+!win32
+</features>
+<command>
+file://%PWD/
+</command>
+</client>
+
+#
+# Verify data after the test has been "shot"
+<verify>
+<errorcode>
+0
+</errorcode>
+</verify>