From f98d82d9fcedbd5b3311f1631108acd6f74f5a74 Mon Sep 17 00:00:00 2001 From: Arjun Shankar Date: Fri, 14 Mar 2025 18:13:47 +0100 Subject: [PATCH] Fix a race condition in a threaded fopen test (RHEL-83007) Resolves: RHEL-83007 --- glibc-RHEL-83007.patch | 62 ++++++++++++++++++++++++++++++++++++++++++ glibc.spec | 6 +++- 2 files changed, 67 insertions(+), 1 deletion(-) create mode 100644 glibc-RHEL-83007.patch diff --git a/glibc-RHEL-83007.patch b/glibc-RHEL-83007.patch new file mode 100644 index 0000000..8ae0eae --- /dev/null +++ b/glibc-RHEL-83007.patch @@ -0,0 +1,62 @@ +commit 10af00f7a135c85796a9c4c75228358b8898da5c +Author: Siddhesh Poyarekar +Date: Fri Mar 14 10:18:21 2025 -0400 + + tst-fopen-threaded: Only check EOF for failing read + + The fread race checker looks for EOF in every thread, which is incorrect + since threads calling fread successfully could lag behind and read the + EOF condition, resulting in multiple threads thinking that they + encountered an EOF. + + Only look for EOF condition if fread fails to read a char. Also drop + the clearerr() since it could mask the failure of another reader, thus + hiding a test failure. + + Finally, also check for error in the stream for completeness. + + Signed-off-by: Siddhesh Poyarekar + Reviewed-by: Florian Weimer + +diff --git a/sysdeps/pthread/tst-fopen-threaded.c b/sysdeps/pthread/tst-fopen-threaded.c +index 5c792c93e3711621..ade58ad19eb209d1 100644 +--- a/sysdeps/pthread/tst-fopen-threaded.c ++++ b/sysdeps/pthread/tst-fopen-threaded.c +@@ -64,19 +64,27 @@ threadReadRoutine (void *argv) + /* Wait for all threads to be ready to read. */ + xpthread_barrier_wait (&barrier); + +- ret = +- fread (&read_buffer, sizeof (char), sizeof (read_buffer), my_data->fd); +- if (feof (my_data->fd) != 0) ++ ret = fread (&read_buffer, 1, sizeof (read_buffer), my_data->fd); ++ /* If no data is returned (we read only 1 byte, so there's no short read ++ situation here), look for EOF flag and record it in MY_DATA. The EOF flag ++ is not cleared because that could result in a test failure being masked ++ when two threads fail to read and one of them clears error/EOF flags ++ before the second one has the chance to observe it. ++ ++ Successful readers could still see the EOF if they fall behind the failing ++ read when calling feof(), which could result in a false test failure. To ++ avoid this race, we only make the failing reader check for EOF or ++ error. */ ++ if (ret == 0) + { +- clearerr (my_data->fd); +- my_data->eof = true; ++ if (feof (my_data->fd) != 0) ++ my_data->eof = true; ++ else ++ FAIL_EXIT1 ("fread failed (ferror: %d): %m", ferror (my_data->fd)); + } + else +- { +- TEST_COMPARE (ret, 1); +- /* Save the read value. */ +- my_data->value = read_buffer; +- } ++ /* Save the read value. */ ++ my_data->value = read_buffer; + TEST_COMPARE (ferror (my_data->fd), 0); + return NULL; + } diff --git a/glibc.spec b/glibc.spec index 8519255..ff9f52c 100644 --- a/glibc.spec +++ b/glibc.spec @@ -157,7 +157,7 @@ end \ Summary: The GNU libc libraries Name: glibc Version: %{glibcversion} -Release: 179%{?dist} +Release: 180%{?dist} # In general, GPLv2+ is used by programs, LGPLv2+ is used for # libraries. @@ -1152,6 +1152,7 @@ Patch844: glibc-RHEL-28119.patch Patch845: glibc-RHEL-61561.patch Patch846: glibc-RHEL-83527-1.patch Patch847: glibc-RHEL-83527-2.patch +Patch848: glibc-RHEL-83007.patch ############################################################################## # Continued list of core "glibc" package information: @@ -3145,6 +3146,9 @@ update_gconv_modules_cache () %endif %changelog +* Fri Mar 14 2025 Arjun Shankar - 2.34-180 +- Fix a race condition in a threaded fopen test (RHEL-83007) + * Fri Mar 14 2025 Arjun Shankar - 2.34-179 - assert: Add test for CVE-2025-0395 (RHEL-83527)