]> git.ipfire.org Git - thirdparty/libarchive.git/commitdiff
Fix issue 119.
authorMichihiro NAKAJIMA <ggcueroad@gmail.com>
Tue, 7 Dec 2010 06:40:51 +0000 (01:40 -0500)
committerMichihiro NAKAJIMA <ggcueroad@gmail.com>
Tue, 7 Dec 2010 06:40:51 +0000 (01:40 -0500)
Change the file location check that a file location does not exceed
volume block. New one is that a file content does not exceed volume
block(end of an ISO image). It is better than previous check even
if the issue did not happen.

While reading an ISO image generated by an older version of mkisofs
utility, a file location indicates the end the ISO image if its file
size is zero and it is the last file of all files of the ISO image,
so it is possible that the location value is the same as the number
of the total block of the ISO image.

SVN-Revision: 2820

libarchive/archive_read_support_format_iso9660.c

index 0c640c88e86741227dc72aa47ceb9e9b34acd016..bec81f4497524c973aa1b0ffc4110cfa06649e6e 100644 (file)
@@ -1677,6 +1677,7 @@ parse_file_info(struct archive_read *a, struct file_info *parent,
        const unsigned char *rr_start, *rr_end;
        const unsigned char *p;
        size_t dr_len;
+       uint64_t fsize;
        int32_t location;
        int flags;
 
@@ -1685,6 +1686,7 @@ parse_file_info(struct archive_read *a, struct file_info *parent,
        dr_len = (size_t)isodirrec[DR_length_offset];
        name_len = (size_t)isodirrec[DR_name_len_offset];
        location = archive_le32dec(isodirrec + DR_extent_offset);
+       fsize = toi(isodirrec + DR_size_offset, DR_size_size);
        /* Sanity check that dr_len needs at least 34. */
        if (dr_len < 34) {
                archive_set_error(&a->archive, ARCHIVE_ERRNO_MISC,
@@ -1703,7 +1705,9 @@ parse_file_info(struct archive_read *a, struct file_info *parent,
         * link or file size is zero. As far as I know latest mkisofs
         * do that.
         */
-       if (location >= iso9660->volume_block) {
+       if (location > 0 &&
+           (location + ((fsize + iso9660->logical_block_size -1)
+              / iso9660->logical_block_size)) > iso9660->volume_block) {
                archive_set_error(&a->archive, ARCHIVE_ERRNO_MISC,
                    "Invalid location of extent of file");
                return (NULL);
@@ -1719,7 +1723,7 @@ parse_file_info(struct archive_read *a, struct file_info *parent,
        memset(file, 0, sizeof(*file));
        file->parent = parent;
        file->offset = iso9660->logical_block_size * (uint64_t)location;
-       file->size = toi(isodirrec + DR_size_offset, DR_size_size);
+       file->size = fsize;
        file->mtime = isodate7(isodirrec + DR_date_offset);
        file->ctime = file->atime = file->mtime;