Fix NULL file pointer dereferences in vlen disk operations#6385
Conversation
When reading corrupted HDF5 files, the file pointer passed to the disk-based vlen type operations (H5T__vlen_disk_read, H5T__vlen_disk_write, H5T__vlen_disk_isnull, H5T__vlen_disk_setnull, H5T__vlen_disk_delete) and H5T__vlen_set_loc can be NULL. The existing assert(file) causes a crash in debug builds, while release builds proceed to dereference the NULL pointer in H5VL_blob_put / H5VL_blob_get / H5VL_blob_specific, causing a SEGV. Replace assert(file) with proper NULL checks and HGOTO_ERROR so that the error is propagated through the normal HDF5 error handling mechanism. Found by OSS-Fuzz via the matio project fuzzer (ClusterFuzz testcase 5366895365914624).
|
Please do not merge this yet. The comment in #6377 also applies here. |
|
The issue occurs with corrupted HDF5 files on fuzzing. It is not possible to detect / prevent the error outside hdf5, i.e. as consumer of hdf5 lib. |
|
Hi @tbeu, I just wanted to clarify a bit. What @bmribler is saying is that we currently believe it would be more appropriate to fix this at a higher level rather than converting these |
| H5VL_file_cont_info_t cont_info = {H5VL_CONTAINER_INFO_VERSION, 0, 0, 0}; | ||
| H5VL_file_get_args_t vol_cb_args; /* Arguments to VOL callback */ | ||
|
|
||
| assert(file); |
There was a problem hiding this comment.
For example, it may make sense to leave this as an assert() and instead add a regular error check to H5T_set_loc() in H5T.c when the loc param is H5T_LOC_DISK. Even better would be to figure out where the file pointer initially gets set to NULL and fix the issue there.
|
Closing in favor of a fix at the decode level (validating vlen.type in H5O__dtype_decode_helper). See replacement PR. |
…_set_loc H5O__dtype_decode_helper() reads vlen.type from the file without validation. With corrupted HDF5 files (e.g. from fuzzing), this field can have an invalid value that is neither H5T_VLEN_SEQUENCE nor H5T_VLEN_STRING, which later triggers assert(0) in H5T__vlen_set_loc() (debug builds) or a NULL pointer dereference / SEGV in release builds. Fix by: 1. Adding a validation check in H5O__dtype_decode_helper() immediately after reading the vlen.type field, returning an error if the value is invalid. 2. Adding a NULL file pointer check in H5T_set_loc() before calling H5T__vlen_set_loc() when loc == H5T_LOC_DISK, so the low-level assert(file) invariant is never violated. This fixes the root cause at the decode level where the bad value enters the system, as requested in review of HDFGroup#6378 and HDFGroup#6385. Closes HDFGroup#6378 Closes HDFGroup#6385 Found by OSS-Fuzz via the matio fuzzer (ClusterFuzz testcase 5366895365914624).
…_set_loc H5O__dtype_decode_helper() reads vlen.type from the file without validation. With corrupted HDF5 files (e.g. from fuzzing), this field can have an invalid value that is neither H5T_VLEN_SEQUENCE nor H5T_VLEN_STRING, which later triggers assert(0) in H5T__vlen_set_loc() (debug builds) or a NULL pointer dereference / SEGV in release builds. Fix by: 1. Adding a validation check in H5O__dtype_decode_helper() immediately after reading the vlen.type field, returning an error if the value is invalid. 2. Adding a NULL file pointer check in H5T_set_loc() before calling H5T__vlen_set_loc() when loc == H5T_LOC_DISK, so the low-level assert(file) invariant is never violated. This fixes the root cause at the decode level where the bad value enters the system, as requested in review of HDFGroup#6378 and HDFGroup#6385. Closes HDFGroup#6378 Closes HDFGroup#6385 Found by OSS-Fuzz via the matio fuzzer (ClusterFuzz testcase 5366895365914624).
…_set_loc H5O__dtype_decode_helper() reads vlen.type from the file without validation. With corrupted HDF5 files (e.g. from fuzzing), this field can have an invalid value that is neither H5T_VLEN_SEQUENCE nor H5T_VLEN_STRING, which later triggers assert(0) in H5T__vlen_set_loc() (debug builds) or a NULL pointer dereference / SEGV in release builds. Fix by: 1. Adding a validation check in H5O__dtype_decode_helper() immediately after reading the vlen.type field, returning an error if the value is invalid. 2. Adding a NULL file pointer check in H5T_set_loc() before calling H5T__vlen_set_loc() when loc == H5T_LOC_DISK, so the low-level assert(file) invariant is never violated. This fixes the root cause at the decode level where the bad value enters the system, as requested in review of HDFGroup#6378 and HDFGroup#6385. Closes HDFGroup#6378 Closes HDFGroup#6385 Found by OSS-Fuzz via the matio fuzzer (ClusterFuzz testcase 5366895365914624).
…_set_loc H5O__dtype_decode_helper() reads vlen.type from the file without validation. With corrupted HDF5 files (e.g. from fuzzing), this field can have an invalid value that is neither H5T_VLEN_SEQUENCE nor H5T_VLEN_STRING, which later triggers assert(0) in H5T__vlen_set_loc() (debug builds) or a NULL pointer dereference / SEGV in release builds. Fix by: 1. Adding a validation check in H5O__dtype_decode_helper() immediately after reading the vlen.type field, returning an error if the value is invalid. 2. Adding a NULL file pointer check in H5T_set_loc() before calling H5T__vlen_set_loc() when loc == H5T_LOC_DISK, so the low-level assert(file) invariant is never violated. This fixes the root cause at the decode level where the bad value enters the system, as requested in review of HDFGroup#6378 and HDFGroup#6385. Closes HDFGroup#6378 Closes HDFGroup#6385 Found by OSS-Fuzz via the matio fuzzer (ClusterFuzz testcase 5366895365914624).
…_set_loc (#6395) H5O__dtype_decode_helper() reads vlen.type from the file without validation. With corrupted HDF5 files (e.g. from fuzzing), this field can have an invalid value that is neither H5T_VLEN_SEQUENCE nor H5T_VLEN_STRING, which later triggers assert(0) in H5T__vlen_set_loc() (debug builds) or a NULL pointer dereference / SEGV in release builds. Fix by: 1. Adding a validation check in H5O__dtype_decode_helper() immediately after reading the vlen.type field, returning an error if the value is invalid. 2. Adding a NULL file pointer check in H5T_set_loc() before calling H5T__vlen_set_loc() when loc == H5T_LOC_DISK, so the low-level assert(file) invariant is never violated. This fixes the root cause at the decode level where the bad value enters the system, as requested in review of #6378 and #6385. Found by OSS-Fuzz via the matio fuzzer (ClusterFuzz testcase 5366895365914624).
…_set_loc (HDFGroup#6395) H5O__dtype_decode_helper() reads vlen.type from the file without validation. With corrupted HDF5 files (e.g. from fuzzing), this field can have an invalid value that is neither H5T_VLEN_SEQUENCE nor H5T_VLEN_STRING, which later triggers assert(0) in H5T__vlen_set_loc() (debug builds) or a NULL pointer dereference / SEGV in release builds. Fix by: 1. Adding a validation check in H5O__dtype_decode_helper() immediately after reading the vlen.type field, returning an error if the value is invalid. 2. Adding a NULL file pointer check in H5T_set_loc() before calling H5T__vlen_set_loc() when loc == H5T_LOC_DISK, so the low-level assert(file) invariant is never violated. This fixes the root cause at the decode level where the bad value enters the system, as requested in review of HDFGroup#6378 and HDFGroup#6385. Found by OSS-Fuzz via the matio fuzzer (ClusterFuzz testcase 5366895365914624).
When reading corrupted HDF5 files, the file pointer passed to the disk-based vlen type operations (
H5T__vlen_disk_read,H5T__vlen_disk_write,H5T__vlen_disk_isnull,H5T__vlen_disk_setnull,H5T__vlen_disk_delete) andH5T__vlen_set_loccan be NULL. The existingassert(file)causes a crash in debug builds, while release builds proceed to dereference the NULL pointer inH5VL_blob_put/H5VL_blob_get/H5VL_blob_specific, causing a SEGV.Changes
Replace
assert(file)with proper NULL checks andHGOTO_ERRORso that the error is propagated through the normal HDF5 error handling mechanism.ASAN report (from OSS-Fuzz)
https://issues.oss-fuzz.com/issues?q=5366895365914624