From: Tim Kientzle Date: Mon, 4 May 2026 03:12:42 +0000 (-0700) Subject: rar5: convert remaining per-entry data errors to ARCHIVE_FAILED X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=2bb18c06702948ac4aad8a8a1bdcaeec303088bd;p=thirdparty%2Flibarchive.git rar5: convert remaining per-entry data errors to ARCHIVE_FAILED Follow-up to 9fa772ab. An audit of the rar5 reader found many more ARCHIVE_FATAL returns in data-decode paths that should be ARCHIVE_FAILED so the caller can move on to the next entry after a corrupt one: apply_filters Unsupported filter type parse_tables Truncated huffman tables, decode failures (8 sites) parse_block_header Unsupported header size, block checksum error do_uncompress_block Decode code length / distance slot failures Distance pointer overflow decode_number / decode_code_length failures merge_block Block size == 0 during merge do_uncompress_file Invalid window size declaration verify_checksums CRC32 / BLAKE2 mismatch Programmer assertions, ENOMEM, true I/O errors, and propagation of copy_string's window-buf-NULL FATAL return are intentionally kept as ARCHIVE_FATAL because they are not recoverable per-entry conditions. --- diff --git a/libarchive/archive_read_support_format_rar5.c b/libarchive/archive_read_support_format_rar5.c index 9b263110c..6e5656b8f 100644 --- a/libarchive/archive_read_support_format_rar5.c +++ b/libarchive/archive_read_support_format_rar5.c @@ -700,7 +700,7 @@ static int run_filter(struct archive_read* a, struct filter_info* flt) { ARCHIVE_ERRNO_FILE_FORMAT, "Unsupported filter type: 0x%x", (unsigned int)flt->type); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } if(ret != ARCHIVE_OK) { @@ -2748,7 +2748,7 @@ static int parse_tables(struct archive_read* a, struct rar5* rar, archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT, "Truncated data in huffman tables"); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } value = (p[i] & nibble_mask) >> nibble_shift; @@ -2794,7 +2794,7 @@ static int parse_tables(struct archive_read* a, struct rar5* rar, if(ret != ARCHIVE_OK) { archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT, "Decoding huffman tables failed"); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } for(i = 0; i < HUFF_TABLE_SIZE;) { @@ -2805,7 +2805,7 @@ static int parse_tables(struct archive_read* a, struct rar5* rar, archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT, "Decoding huffman tables failed"); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } if(num < 16) { @@ -2839,7 +2839,7 @@ static int parse_tables(struct archive_read* a, struct rar5* rar, ARCHIVE_ERRNO_FILE_FORMAT, "Unexpected error when decoding " "huffman tables"); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } } else { /* other codes: fill with zeroes `n` times */ @@ -2867,7 +2867,7 @@ static int parse_tables(struct archive_read* a, struct rar5* rar, if(ret != ARCHIVE_OK) { archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT, "Failed to create literal table"); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } idx += HUFF_NC; @@ -2876,7 +2876,7 @@ static int parse_tables(struct archive_read* a, struct rar5* rar, if(ret != ARCHIVE_OK) { archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT, "Failed to create distance table"); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } idx += HUFF_DC; @@ -2885,7 +2885,7 @@ static int parse_tables(struct archive_read* a, struct rar5* rar, if(ret != ARCHIVE_OK) { archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT, "Failed to create lower bits of distances table"); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } idx += HUFF_LDC; @@ -2894,7 +2894,7 @@ static int parse_tables(struct archive_read* a, struct rar5* rar, if(ret != ARCHIVE_OK) { archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT, "Failed to create repeating distances table"); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } return ARCHIVE_OK; @@ -2912,7 +2912,7 @@ static int parse_block_header(struct archive_read* a, const uint8_t* p, archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT, "Unsupported block header size (was %d, max is 2)", bf_byte_count(hdr)); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } /* This should probably use bit reader interface in order to be more @@ -2956,7 +2956,7 @@ static int parse_block_header(struct archive_read* a, const uint8_t* p, "Block checksum error: got 0x%x, expected 0x%x", hdr->block_cksum, calculated_cksum); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; #endif } @@ -3203,7 +3203,7 @@ static int do_uncompress_block(struct archive_read* a, const uint8_t* p) { ARCHIVE_ERRNO_PROGRAMMER, "Failed to decode the code length"); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } if(ARCHIVE_OK != decode_number(a, &rar->cstate.dd, p, @@ -3213,7 +3213,7 @@ static int do_uncompress_block(struct archive_read* a, const uint8_t* p) { ARCHIVE_ERRNO_PROGRAMMER, "Failed to decode the distance slot"); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } if(dist_slot < 4) { @@ -3258,7 +3258,7 @@ static int do_uncompress_block(struct archive_read* a, const uint8_t* p) { "Failed to decode the " "distance slot"); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } if(dist >= INT_MAX - low_dist - 1) { @@ -3268,7 +3268,7 @@ static int do_uncompress_block(struct archive_read* a, const uint8_t* p) { ARCHIVE_ERRNO_FILE_FORMAT, "Distance pointer " "overflow"); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } dist += low_dist; @@ -3334,12 +3334,12 @@ static int do_uncompress_block(struct archive_read* a, const uint8_t* p) { if(ARCHIVE_OK != decode_number(a, &rar->cstate.rd, p, &len_slot)) { - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } len = decode_code_length(a, rar, p, len_slot); if (len == -1) { - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } rar->cstate.last_len = len; @@ -3528,7 +3528,7 @@ static int merge_block(struct archive_read* a, ssize_t block_size, archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT, "Encountered block size == 0 during block merge"); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } if(!read_ahead(a, cur_block_size, &lp)) @@ -3876,7 +3876,7 @@ static int do_uncompress_file(struct archive_read* a) { "Invalid window size declaration in this file"); /* This should never happen in valid files. */ - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; } if(rar->cstate.all_filters_applied == 1) { @@ -4131,7 +4131,7 @@ static int verify_checksums(struct archive_read* a) { archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT, "Checksum error: CRC32"); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; #endif } else { DEBUG_CODE { @@ -4166,7 +4166,7 @@ static int verify_checksums(struct archive_read* a) { ARCHIVE_ERRNO_FILE_FORMAT, "Checksum error: BLAKE2"); - return ARCHIVE_FATAL; + return ARCHIVE_FAILED; #endif } }