]> wimlib.net Git - wimlib/commitdiff
Ignore dentries with null characters in name
authorEric Biggers <ebiggers3@gmail.com>
Fri, 3 Jun 2016 00:53:29 +0000 (19:53 -0500)
committerEric Biggers <ebiggers3@gmail.com>
Sat, 4 Jun 2016 16:16:48 +0000 (11:16 -0500)
src/dentry.c

index 4501525dcd0d70a2b121d00a6e64d60ba31fdd99..a8bf41ca6073a2b85fe1d00cbc3f970bd20feedc 100644 (file)
@@ -1532,7 +1532,6 @@ err_free_dentry:
        return ret;
 }
 
-/* Is the dentry named "." or ".." ?  */
 static bool
 dentry_is_dot_or_dotdot(const struct wim_dentry *dentry)
 {
@@ -1549,6 +1548,43 @@ dentry_is_dot_or_dotdot(const struct wim_dentry *dentry)
        return false;
 }
 
+static bool
+dentry_has_embedded_null(const struct wim_dentry *dentry)
+{
+       for (unsigned i = 0; i < dentry->d_name_nbytes / 2; i++)
+               if (dentry->d_name[i] == cpu_to_le16('\0'))
+                       return true;
+       return false;
+}
+
+static bool
+should_ignore_dentry(struct wim_dentry *dir, const struct wim_dentry *dentry)
+{
+       /* All dentries except the root must be named.  */
+       if (!dentry_has_long_name(dentry)) {
+               WARNING("Ignoring unnamed dentry in "
+                       "directory \"%"TS"\"", dentry_full_path(dir));
+               return true;
+       }
+
+       /* Don't allow files named "." or "..".  */
+       if (dentry_is_dot_or_dotdot(dentry)) {
+               WARNING("Ignoring file named \".\" or \"..\" in "
+                       "directory \"%"TS"\"", dentry_full_path(dir));
+               return true;
+       }
+
+       /* Don't allow filenames with embedded null characters.  */
+       if (dentry_has_embedded_null(dentry)) {
+               WARNING("Ignoring file with embedded null character in "
+                       "filename in directory \"%"TS"\"",
+                       dentry_full_path(dir));
+               return true;
+       }
+
+       return false;
+}
+
 static int
 read_dentry_tree_recursive(const u8 * restrict buf, size_t buf_len,
                           struct wim_dentry * restrict dir, unsigned depth)
@@ -1575,18 +1611,8 @@ read_dentry_tree_recursive(const u8 * restrict buf, size_t buf_len,
                if (child == NULL)
                        return 0;
 
-               /* All dentries except the root should be named.  */
-               if (unlikely(!dentry_has_long_name(child))) {
-                       WARNING("Ignoring unnamed dentry in "
-                               "directory \"%"TS"\"", dentry_full_path(dir));
-                       free_dentry(child);
-                       continue;
-               }
-
-               /* Don't allow files named "." or "..".  */
-               if (unlikely(dentry_is_dot_or_dotdot(child))) {
-                       WARNING("Ignoring file named \".\" or \"..\"; "
-                               "potentially malicious archive!!!");
+               /* Ignore dentries with bad filenames.  */
+               if (unlikely(should_ignore_dentry(dir, child))) {
                        free_dentry(child);
                        continue;
                }