]> wimlib.net Git - wimlib/blobdiff - src/metadata_resource.c
mount_image.c: add fallback definitions of RENAME_* constants
[wimlib] / src / metadata_resource.c
index c0467ef69c8877799ce4866e195a02ec1e2081d1..71d3d6d03802f49262865b2ad0916538426e079f 100644 (file)
@@ -3,7 +3,7 @@
  */
 
 /*
- * Copyright (C) 2012, 2013 Eric Biggers
+ * Copyright 2012-2023 Eric Biggers
  *
  * This file is free software; you can redistribute it and/or modify it under
  * the terms of the GNU Lesser General Public License as published by the Free
@@ -16,7 +16,7 @@
  * details.
  *
  * You should have received a copy of the GNU Lesser General Public License
- * along with this file; if not, see http://www.gnu.org/licenses/.
+ * along with this file; if not, see https://www.gnu.org/licenses/.
  */
 
 #ifdef HAVE_CONFIG_H
@@ -73,27 +73,36 @@ read_metadata_resource(struct wim_image_metadata *imd)
        const struct blob_descriptor *metadata_blob;
        void *buf;
        int ret;
+       u8 hash[SHA1_HASH_SIZE];
        struct wim_security_data *sd;
        struct wim_dentry *root;
 
        metadata_blob = imd->metadata_blob;
 
+       /*
+        * Prevent huge memory allocations when processing fuzzed files.  The
+        * case of metadata resources is tough, since a metadata resource can
+        * legitimately decompress to many times the size of the WIM file
+        * itself, e.g. in the case of an image containing many empty files with
+        * similar long filenames.  Arbitrarily choose 512x as a generous limit.
+        */
+       if (metadata_blob->blob_location == BLOB_IN_WIM &&
+           metadata_blob->rdesc->wim->file_size > 0 &&
+           metadata_blob->size / 512 > metadata_blob->rdesc->wim->file_size)
+               return WIMLIB_ERR_INVALID_METADATA_RESOURCE;
+
        /* Read the metadata resource into memory.  (It may be compressed.)  */
        ret = read_blob_into_alloc_buf(metadata_blob, &buf);
        if (ret)
                return ret;
 
        /* Checksum the metadata resource.  */
-       if (!metadata_blob->dont_check_metadata_hash) {
-               u8 hash[SHA1_HASH_SIZE];
-
-               sha1_buffer(buf, metadata_blob->size, hash);
-               if (!hashes_equal(metadata_blob->hash, hash)) {
-                       ERROR("Metadata resource is corrupted "
-                             "(invalid SHA-1 message digest)!");
-                       ret = WIMLIB_ERR_INVALID_METADATA_RESOURCE;
-                       goto out_free_buf;
-               }
+       sha1(buf, metadata_blob->size, hash);
+       if (!hashes_equal(metadata_blob->hash, hash)) {
+               ERROR("Metadata resource is corrupted "
+                     "(invalid SHA-1 message digest)!");
+               ret = WIMLIB_ERR_INVALID_METADATA_RESOURCE;
+               goto out_free_buf;
        }
 
        /* Parse the metadata resource.
@@ -245,9 +254,6 @@ write_metadata_resource(WIMStruct *wim, int image, int write_resource_flags)
                                             imd->metadata_blob->hash,
                                             write_resource_flags);
 
-       /* Original checksum was overridden; set a flag so it isn't used.  */
-       imd->metadata_blob->dont_check_metadata_hash = 1;
-
        FREE(buf);
        return ret;
 }