This is the mail archive of the
libc-alpha@sourceware.org
mailing list for the glibc project.
[PATCH] Make fmtmsg() function to multithread-safe
- From: Peng Haitao <penght at cn dot fujitsu dot com>
- To: libc-alpha at sourceware dot org
- Cc: Ulrich Drepper <drepper at gmail dot com>
- Date: Tue, 21 Feb 2012 17:19:06 +0800
- Subject: [PATCH] Make fmtmsg() function to multithread-safe
fmtmsg() uses a static variables severity_list which is not protected. It is
not safe in multithread circumstance.
When call fmtmsg() and addseverity() simultaneously in multithread circumstance,
the following case will cause unsafe. The case has two threads: A and B.
a. thread B call addseverity(5, "TEST_FMTMSG")
b. thread A call fmtmsg(classification, NULL, 5, NULL, NULL, NULL), when search
severity, but not output error message
code: if (severity == severity_rec->severity)
c. thread B call addseverity(5, NULL)
d. thread A output error message to the given severity
Signed-off-by: Peng Haitao <penght@cn.fujitsu.com>
---
ChangeLog | 4 ++++
stdlib/fmtmsg.c | 12 ++++++++++--
2 files changed, 14 insertions(+), 2 deletions(-)
diff --git a/ChangeLog b/ChangeLog
index 5c3e98c..11153cb 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,7 @@
+2012-02-21 Peng Haitao <penght@cn.fujitsu.com>
+
+ * stdlib/fmtmsg.c: Add lock to protect static variable.
+
2012-02-20 Joseph Myers <joseph@codesourcery.com>
* sysdeps/i386/fpu/libm-test-ulps: Resort with gen-libm-test.pl -n
diff --git a/stdlib/fmtmsg.c b/stdlib/fmtmsg.c
index 9203317..c0dc1ac 100644
--- a/stdlib/fmtmsg.c
+++ b/stdlib/fmtmsg.c
@@ -105,6 +105,7 @@ fmtmsg (long int classification, const char *label, int severity,
__libc_once_define (static, once);
int result = MM_OK;
struct severity_info *severity_rec;
+ const char *pstring;
/* Make sure everything is initialized. */
__libc_once (once, init);
@@ -124,11 +125,18 @@ fmtmsg (long int classification, const char *label, int severity,
return MM_NOTOK;
}
+ __libc_lock_lock (lock);
+
for (severity_rec = severity_list; severity_rec != NULL;
severity_rec = severity_rec->next)
if (severity == severity_rec->severity)
+ {
+ pstring = severity_rec->string;
/* Bingo. */
break;
+ }
+
+ __libc_lock_unlock (lock);
/* If we don't know anything about the severity level return an error. */
if (severity_rec == NULL)
@@ -156,7 +164,7 @@ fmtmsg (long int classification, const char *label, int severity,
do_label ? label : "",
do_label && (do_severity | do_text | do_action | do_tag)
? ": " : "",
- do_severity ? severity_rec->string : "",
+ do_severity ? pstring : "",
do_severity && (do_text | do_action | do_tag)
? ": " : "",
do_text ? text : "",
@@ -181,7 +189,7 @@ fmtmsg (long int classification, const char *label, int severity,
do_label ? label : "",
do_label && (do_severity | do_text | do_action | do_tag)
? ": " : "",
- do_severity ? severity_rec->string : "",
+ do_severity ? pstring : "",
do_severity && (do_text | do_action | do_tag) ? ": " : "",
do_text ? text : "",
do_text && (do_action | do_tag) ? "\n" : "",
--
1.7.1
--
Best Regards,
Peng