Read FILE* input with std::fgetc under MemorySanitizer (#5874)

With glibc and optimization, <stdio.h> turns getc_unlocked into an extern
inline function that reads the stdio buffer (fp->_IO_read_ptr) directly.
glibc, which is not instrumented, fills that buffer, so MemorySanitizer
treats the bytes as uninitialized and reports a false positive when the
parsers read from a FILE* (e.g., the fuzz harness FILE* leg, OSS-Fuzz
575915982). std::fgetc is an opaque call whose result MemorySanitizer treats
as initialized.

Select JSON_UNLOCKED_FILE_IO 0 when compiled with MemorySanitizer. This is a
regression from #5828 and not part of any release.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
This commit is contained in:
Niels Lohmann authored and GitHub committed 2026-10-21 10:22:50 +02:00
1 parent 4155e2938f
commit 08d7fbb0a1
3 files changed
+25 -4

No files matched your search

@@ -10,6 +10,9 @@ earlier, instead of locking the file once and reading it with the unlocked stdio
It does not change any result: values, exceptions, and the position of the file after parsing are the same either way.
Only the speed and the locking of the file differ (see the notes on locking below).
Builds with MemorySanitizer use `std::fgetc` automatically, because the inline `getc_unlocked` of glibc reads the stdio
buffer directly, which glibc (not instrumented) filled, and MemorySanitizer would report it as uninitialized.
## Default definition
The default value is `0`: the file is locked once and read with the unlocked stdio functions where they are available.