Prevent arbitrary file writes with malicious resource names. (#3484)

* refactor: rename sanitize function

* fix: expose getDir

* fix: safe handling of untrusted resource names

 - fixes: GHSA-2hqv-2xv4-5h5w

* test: sample file for GHSA-2hqv-2xv4-5h5w

* refactor: avoid detection of absolute files for resource check

* chore: enable info mode on gradle

* test: skip test on windows

* chore: debug windows handling

* fix: normalize entry with file separators

* fix: normalize filepath after cleansing

* chore: Android paths are not OS specific

* refactor: use java.nio for path traversal checking

* chore: align path separator on Windows for Zip files

* chore: rework towards basic directory traversal

* chore: remove '--info' on build.yml
This commit is contained in:
Connor Tumbleson 2024-01-02 06:11:03 -05:00 committed by Connor Tumbleson
parent fedae0b6de
commit 087f89ebc0
No known key found for this signature in database
GPG Key ID: BC12D5F3264560C1
2 changed files with 15 additions and 0 deletions

View File

@ -25,6 +25,7 @@ import brut.androlib.res.data.value.ResFileValue;
import brut.directory.DirUtil; import brut.directory.DirUtil;
import brut.directory.Directory; import brut.directory.Directory;
import brut.directory.DirectoryException; import brut.directory.DirectoryException;
import brut.util.BrutIO;
import java.io.*; import java.io.*;
import java.util.Map; import java.util.Map;
@ -47,6 +48,13 @@ public class ResFileDecoder {
String outResName = res.getFilePath(); String outResName = res.getFilePath();
String typeName = res.getResSpec().getType().getName(); String typeName = res.getResSpec().getType().getName();
if (BrutIO.detectPossibleDirectoryTraversal(outResName)) {
outResName = inFileName;
LOGGER.warning(String.format(
"Potentially malicious file path: %s, using instead %s", res.getFilePath(), outResName
));
}
String ext = null; String ext = null;
String outFileName; String outFileName;
int extPos = inFileName.lastIndexOf("."); int extPos = inFileName.lastIndexOf(".");

View File

@ -94,6 +94,13 @@ public class BrutIO {
return canonicalEntryPath.substring(canonicalDirPath.length()); return canonicalEntryPath.substring(canonicalDirPath.length());
} }
public static boolean detectPossibleDirectoryTraversal(String entry) {
if (OSDetection.isWindows()) {
return entry.contains("..\\") || entry.contains("\\..");
}
return entry.contains("../") || entry.contains("/..");
}
public static String normalizePath(String path) { public static String normalizePath(String path) {
char separator = File.separatorChar; char separator = File.separatorChar;