This is the mail archive of the
glibc-bugs@sourceware.org
mailing list for the glibc project.
[Bug libc/11449] crypt/crypt_util.c: __init_des_r() needs memory barrier
- From: "prince.cse99 at gmail dot com" <sourceware-bugzilla at sourceware dot org>
- To: glibc-bugs at sources dot redhat dot com
- Date: Fri, 22 Jul 2011 22:28:16 +0000
- Subject: [Bug libc/11449] crypt/crypt_util.c: __init_des_r() needs memory barrier
- Auto-submitted: auto-generated
- References: <bug-11449-131@http.sourceware.org/bugzilla/>
http://sourceware.org/bugzilla/show_bug.cgi?id=11449
Abdullah Muzahid <prince.cse99 at gmail dot com> changed:
What |Removed |Added
----------------------------------------------------------------------------
Status|RESOLVED |REOPENED
CC| |prince.cse99 at gmail dot
| |com
Resolution|FIXED |
--- Comment #3 from Abdullah Muzahid <prince.cse99 at gmail dot com> 2011-07-22 22:28:12 UTC ---
Hi,
I am a phd student in University of Illinois in CS dept. Recently I have been
working on memory model related bugs in software. I was experimenting with this
bug. And I found out that the bug is not properly fixed. __init_des_r() uses
a double checked locking(DCL) pattern. To make DCL work, we need to use 2
barrier - one before setting small_tables_initialized flag and one after
reading it in line 365 (just before acquiring the lock). The fix puts the first
barrier but not the second one. Now consider the following scenario
Thread 1 Thread 2
eperm32tab[..] |= BITMASK[bit % 24]; if(small_tables_initialized == 0)
atomic_write_barrier();
small_tables_initialized = 1; sb[sg][inx ] = eperm32tab[...];
Now in Power-PC memory model, it is perfectly valid to execute read operations
to different addresses out of order as long as there is no barrier in between
them. Although thread 2 issues the instructions in order, it is possible that
the second read (...= experm32tab[...]) will execute before the first read of
the flag. This is shown here.
Thread 1 Thread 2
sb[sg][inx ] = eperm32tab[...];
eperm32tab[..] |= BITMASK[bit % 24];
atomic_write_barrier();
small_tables_initialized = 1;
if(small_tables_initialized == 0)
As a result, although the condition of the if statement for thread 2 becomes
true, it will end up using wrong value of eperm32tab[...]. So, you need to put
a read_barrier after the if statement (i.e at line 491 before clearmem
operation). More on DCL can be found here
http://www.cs.umd.edu/~pugh/java/memoryModel/DoubleCheckedLocking.html
Thanks.
-Abdullah Muzahid
PhD Student
CS, UIUC
--
Configure bugmail: http://sourceware.org/bugzilla/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
You are on the CC list for the bug.