Date: Wed, 18 Jul 2001 14:12:43 -0400 From: "Louis-Philippe Gagnon" <louisphilippe@macadamian.com> To: <freebsd-hackers@FreeBSD.ORG> Cc: "Stephane Lussier" <stephane@macadamian.com> Subject: flock/pthread bug? Message-ID: <1f9c01c10fb5$3d4ba770$2964a8c0@macadamian.com>
next in thread | raw e-mail | index | archive | help
Hi,
I've been looking for a way to get inter-process synchronization between multithreaded processes. (I need synchronized access to
an area of shared memory between multiple instances of the same process)
Since I was using SysV shared memory, I had first thought of using SysV semaphores for synchronization; however, the functions
semop, semctl (etc) don't seem to be pthread-aware, so that if a semop() call blocks, the entire process is blocked instead of
only the calling thread.
I then looked at the pthread mutexes, but it looks like the FreeBSD implementation doesn't support PTHREAD_PROCESS_SHARED (at
least in 4.3-release; has this changed in -stable or -current?)
Then I found out about the flock() function; the man page mentions a different implementation for threaded and non-threaded
libraries, so I though this would work with pthreads.
This does not appear to be the case. If one program locks a file with flock(LOCK_EX), the next program that tries to lock will be
suspended completely, instead of only the calling thread.
Given this program :
#include <pthread.h>
#include <fcntl.h>
#include <stdio.h>
#include <sys/file.h>
void *printf_thread(void *p)
{
while(1)
printf("#");
}
void main(void)
{
pthread_t t;
int fd;
fd = open("lockfile",O_WRONLY|O_CREAT, 0666);
pthread_create(&t,NULL,printf_thread,NULL);
flock(fd,LOCK_EX);
pthread_join(t,NULL);
}
(program opens a file, launches a thread (which calls printf() endlessly), locks the file and waits for ^C)
The first instance launched will print an infinity of #'s from its printf_thread
The second instance (launced from the sae directory, to use the same lock file) will not print anything until the first intance is
killed. Since the printf_thread is launched before the flock() call, I expected it to keep running while the main thread blocks;
instead, both threads apear to be blocked.
(I tried on Linux (RH6.1), the program behaves as I expected)
I tried another test before this one (don't have the source anymore, I overwrote the same file), which used only one instance of
the program, with 2 threads trying to lock the file
I expected something like this :
thread 1 locks the file
thread 2 tries to lock the file, blocks
thread 1 unlocks the file
thread 2 gets file lock and unblocks
Instead I got
thread 1 locks the file
thread 2 tries to lock the file, whole process blocks
(thread 1 is blocked, can't unlock the file : deadlock)
So :
-Is flock() supposed to block the whole process?
-Is my test program wrong?
-Does this look like a bug in libc_r?
-Is there a better (working) way of getting interprocess synchronization in multithreaded programs?
Thanks.
Louis-Philippe Gagnon
ps. should I submit problem reports immediately in cases like this, or wait for people's opinions first?
To Unsubscribe: send mail to majordomo@FreeBSD.org
with "unsubscribe freebsd-hackers" in the body of the message
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?1f9c01c10fb5$3d4ba770$2964a8c0>
