You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@pinot.apache.org by si...@apache.org on 2022/01/09 23:31:31 UTC

[pinot] branch master updated: Prevent partial path traversal in untar. (#7985)

This is an automated email from the ASF dual-hosted git repository.

siddteotia pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/pinot.git


The following commit(s) were added to refs/heads/master by this push:
     new 7030260  Prevent partial path traversal in untar. (#7985)
7030260 is described below

commit 7030260b9e6ac38a3caded34cb47c56d0ddf61e4
Author: Mayank Shrivastava <ma...@apache.org>
AuthorDate: Sun Jan 9 15:31:06 2022 -0800

    Prevent partial path traversal in untar. (#7985)
    
    The `File.getCanonicalPath` method  transforms the path into a canonical form preventing such attack types as `..` in path
    segments. If the result of `outputDir.getCanonicalPath()` is not slash terminated it allows for partial path
    traversal.
    
    Consider `"/usr/outnot".startsWith("/usr/out")`. The check is bypassed although it is not the
    out directory. The terminating slash may be removed in various places. On Linux `println(new
    File("/var/"))` returns /var, but `println(new File("/var", "/"))` - `/var/`, however `println(new
    File("/var", "/").getCanonicalPath())` - `/var`
---
 .../org/apache/pinot/common/utils/TarGzCompressionUtils.java | 12 +++++++++++-
 1 file changed, 11 insertions(+), 1 deletion(-)

diff --git a/pinot-common/src/main/java/org/apache/pinot/common/utils/TarGzCompressionUtils.java b/pinot-common/src/main/java/org/apache/pinot/common/utils/TarGzCompressionUtils.java
index e82d6eb..8e5d590 100644
--- a/pinot-common/src/main/java/org/apache/pinot/common/utils/TarGzCompressionUtils.java
+++ b/pinot-common/src/main/java/org/apache/pinot/common/utils/TarGzCompressionUtils.java
@@ -124,6 +124,10 @@ public class TarGzCompressionUtils {
   public static List<File> untar(InputStream inputStream, File outputDir)
       throws IOException {
     String outputDirCanonicalPath = outputDir.getCanonicalPath();
+    // Prevent partial path traversal
+    if (!outputDirCanonicalPath.endsWith(File.separator)) {
+      outputDirCanonicalPath += File.separator;
+    }
     List<File> untarredFiles = new ArrayList<>();
     try (InputStream bufferedIn = new BufferedInputStream(inputStream);
         InputStream gzipIn = new GzipCompressorInputStream(bufferedIn);
@@ -146,7 +150,13 @@ public class TarGzCompressionUtils {
           }
         } else {
           File parentFile = outputFile.getParentFile();
-          if (!parentFile.getCanonicalPath().startsWith(outputDirCanonicalPath)) {
+          String parentFileCanonicalPath = parentFile.getCanonicalPath();
+
+          // Ensure parentFile's canonical path is separator terminated, since outputDirCanonicalPath is.
+          if (!parentFileCanonicalPath.endsWith(File.separator)) {
+            parentFileCanonicalPath += File.separator;
+          }
+          if (!parentFileCanonicalPath.startsWith(outputDirCanonicalPath)) {
             throw new IOException(String
                 .format("Trying to create directory: %s outside of the output directory: %s", parentFile, outputDir));
           }

---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@pinot.apache.org
For additional commands, e-mail: commits-help@pinot.apache.org