aboutsummaryrefslogtreecommitdiffstats
path: root/lib/fuse_lowlevel.c
diff options
context:
space:
mode:
authorMiklos Szeredi <miklos@szeredi.hu>2008-11-27 18:31:18 +0000
committerMiklos Szeredi <miklos@szeredi.hu>2008-11-27 18:31:18 +0000
commite9191d5550e36bde10781e4aa84a3fc4be17f609 (patch)
tree586ebdb2730f163a670292d6c1f0ca25d8db8dad /lib/fuse_lowlevel.c
parent5c094ac0150ebfef6a2c9c2c9d1c545a90ff4e96 (diff)
downloadandroid_external_fuse-e9191d5550e36bde10781e4aa84a3fc4be17f609.tar.gz
android_external_fuse-e9191d5550e36bde10781e4aa84a3fc4be17f609.tar.bz2
android_external_fuse-e9191d5550e36bde10781e4aa84a3fc4be17f609.zip
lowlevel lib: fix deadlock if fuse_reply_* is called from theinterrupt handling function. Reported by Tero Marttila
Diffstat (limited to 'lib/fuse_lowlevel.c')
-rw-r--r--lib/fuse_lowlevel.c16
1 files changed, 10 insertions, 6 deletions
diff --git a/lib/fuse_lowlevel.c b/lib/fuse_lowlevel.c
index df88f26..99fbfe3 100644
--- a/lib/fuse_lowlevel.c
+++ b/lib/fuse_lowlevel.c
@@ -139,12 +139,9 @@ static void free_req(fuse_req_t req)
int ctr;
struct fuse_ll *f = req->f;
- pthread_mutex_lock(&req->lock);
+ pthread_mutex_lock(&f->lock);
req->u.ni.func = NULL;
req->u.ni.data = NULL;
- pthread_mutex_unlock(&req->lock);
-
- pthread_mutex_lock(&f->lock);
list_del_req(req);
ctr = --req->ctr;
pthread_mutex_unlock(&f->lock);
@@ -920,6 +917,9 @@ static int find_interrupted(struct fuse_ll *f, struct fuse_req *req)
for (curr = f->list.next; curr != &f->list; curr = curr->next) {
if (curr->unique == req->u.i.unique) {
+ fuse_interrupt_func_t func;
+ void *data;
+
curr->ctr++;
pthread_mutex_unlock(&f->lock);
@@ -927,9 +927,11 @@ static int find_interrupted(struct fuse_ll *f, struct fuse_req *req)
pthread_mutex_lock(&curr->lock);
pthread_mutex_lock(&f->lock);
curr->interrupted = 1;
+ func = curr->u.ni.func;
+ data = curr->u.ni.data;
pthread_mutex_unlock(&f->lock);
- if (curr->u.ni.func)
- curr->u.ni.func(curr, curr->u.ni.data);
+ if (func)
+ func(curr, data);
pthread_mutex_unlock(&curr->lock);
pthread_mutex_lock(&f->lock);
@@ -1120,8 +1122,10 @@ void fuse_req_interrupt_func(fuse_req_t req, fuse_interrupt_func_t func,
void *data)
{
pthread_mutex_lock(&req->lock);
+ pthread_mutex_lock(&req->f->lock);
req->u.ni.func = func;
req->u.ni.data = data;
+ pthread_mutex_unlock(&req->f->lock);
if (req->interrupted && func)
func(req, data);
pthread_mutex_unlock(&req->lock);