aboutsummaryrefslogtreecommitdiffstats
path: root/fs/fuse
diff options
context:
space:
mode:
authorSteven Whitehouse <swhiteho@redhat.com>2006-04-21 12:52:36 -0400
committerSteven Whitehouse <swhiteho@redhat.com>2006-04-21 12:52:36 -0400
commita748422ee45725e04e1d3792fa19dfa90ddfd116 (patch)
tree978e12895468baaa9f7ab2747b9f7d50beaf1717 /fs/fuse
parentc63e31c2cc1ec67372920b5e1aff8204d04dd172 (diff)
parentf4ffaa452e71495a06376f12f772342bc57051fc (diff)
Merge branch 'master'
Diffstat (limited to 'fs/fuse')
-rw-r--r--fs/fuse/dev.c286
-rw-r--r--fs/fuse/dir.c118
-rw-r--r--fs/fuse/file.c66
-rw-r--r--fs/fuse/fuse_i.h72
-rw-r--r--fs/fuse/inode.c158
5 files changed, 326 insertions, 374 deletions
diff --git a/fs/fuse/dev.c b/fs/fuse/dev.c
index 23d1f52eb1b8..cc750c68fe70 100644
--- a/fs/fuse/dev.c
+++ b/fs/fuse/dev.c
@@ -1,6 +1,6 @@
1/* 1/*
2 FUSE: Filesystem in Userspace 2 FUSE: Filesystem in Userspace
3 Copyright (C) 2001-2005 Miklos Szeredi <miklos@szeredi.hu> 3 Copyright (C) 2001-2006 Miklos Szeredi <miklos@szeredi.hu>
4 4
5 This program can be distributed under the terms of the GNU GPL. 5 This program can be distributed under the terms of the GNU GPL.
6 See the file COPYING. 6 See the file COPYING.
@@ -23,13 +23,11 @@ static kmem_cache_t *fuse_req_cachep;
23 23
24static struct fuse_conn *fuse_get_conn(struct file *file) 24static struct fuse_conn *fuse_get_conn(struct file *file)
25{ 25{
26 struct fuse_conn *fc; 26 /*
27 spin_lock(&fuse_lock); 27 * Lockless access is OK, because file->private data is set
28 fc = file->private_data; 28 * once during mount and is valid until the file is released.
29 if (fc && !fc->connected) 29 */
30 fc = NULL; 30 return file->private_data;
31 spin_unlock(&fuse_lock);
32 return fc;
33} 31}
34 32
35static void fuse_request_init(struct fuse_req *req) 33static void fuse_request_init(struct fuse_req *req)
@@ -74,10 +72,8 @@ static void restore_sigs(sigset_t *oldset)
74 */ 72 */
75void fuse_reset_request(struct fuse_req *req) 73void fuse_reset_request(struct fuse_req *req)
76{ 74{
77 int preallocated = req->preallocated;
78 BUG_ON(atomic_read(&req->count) != 1); 75 BUG_ON(atomic_read(&req->count) != 1);
79 fuse_request_init(req); 76 fuse_request_init(req);
80 req->preallocated = preallocated;
81} 77}
82 78
83static void __fuse_get_request(struct fuse_req *req) 79static void __fuse_get_request(struct fuse_req *req)
@@ -92,80 +88,54 @@ static void __fuse_put_request(struct fuse_req *req)
92 atomic_dec(&req->count); 88 atomic_dec(&req->count);
93} 89}
94 90
95static struct fuse_req *do_get_request(struct fuse_conn *fc) 91struct fuse_req *fuse_get_req(struct fuse_conn *fc)
96{ 92{
97 struct fuse_req *req; 93 struct fuse_req *req;
98
99 spin_lock(&fuse_lock);
100 BUG_ON(list_empty(&fc->unused_list));
101 req = list_entry(fc->unused_list.next, struct fuse_req, list);
102 list_del_init(&req->list);
103 spin_unlock(&fuse_lock);
104 fuse_request_init(req);
105 req->preallocated = 1;
106 req->in.h.uid = current->fsuid;
107 req->in.h.gid = current->fsgid;
108 req->in.h.pid = current->pid;
109 return req;
110}
111
112/* This can return NULL, but only in case it's interrupted by a SIGKILL */
113struct fuse_req *fuse_get_request(struct fuse_conn *fc)
114{
115 int intr;
116 sigset_t oldset; 94 sigset_t oldset;
95 int intr;
96 int err;
117 97
118 atomic_inc(&fc->num_waiting); 98 atomic_inc(&fc->num_waiting);
119 block_sigs(&oldset); 99 block_sigs(&oldset);
120 intr = down_interruptible(&fc->outstanding_sem); 100 intr = wait_event_interruptible(fc->blocked_waitq, !fc->blocked);
121 restore_sigs(&oldset); 101 restore_sigs(&oldset);
122 if (intr) { 102 err = -EINTR;
123 atomic_dec(&fc->num_waiting); 103 if (intr)
124 return NULL; 104 goto out;
125 }
126 return do_get_request(fc);
127}
128 105
129/* Must be called with fuse_lock held */ 106 req = fuse_request_alloc();
130static void fuse_putback_request(struct fuse_conn *fc, struct fuse_req *req) 107 err = -ENOMEM;
131{ 108 if (!req)
132 if (req->preallocated) { 109 goto out;
133 atomic_dec(&fc->num_waiting);
134 list_add(&req->list, &fc->unused_list);
135 } else
136 fuse_request_free(req);
137 110
138 /* If we are in debt decrease that first */ 111 req->in.h.uid = current->fsuid;
139 if (fc->outstanding_debt) 112 req->in.h.gid = current->fsgid;
140 fc->outstanding_debt--; 113 req->in.h.pid = current->pid;
141 else 114 req->waiting = 1;
142 up(&fc->outstanding_sem); 115 return req;
116
117 out:
118 atomic_dec(&fc->num_waiting);
119 return ERR_PTR(err);
143} 120}
144 121
145void fuse_put_request(struct fuse_conn *fc, struct fuse_req *req) 122void fuse_put_request(struct fuse_conn *fc, struct fuse_req *req)
146{ 123{
147 if (atomic_dec_and_test(&req->count)) { 124 if (atomic_dec_and_test(&req->count)) {
148 spin_lock(&fuse_lock); 125 if (req->waiting)
149 fuse_putback_request(fc, req); 126 atomic_dec(&fc->num_waiting);
150 spin_unlock(&fuse_lock); 127 fuse_request_free(req);
151 } 128 }
152} 129}
153 130
154static void fuse_put_request_locked(struct fuse_conn *fc, struct fuse_req *req) 131void fuse_remove_background(struct fuse_conn *fc, struct fuse_req *req)
155{
156 if (atomic_dec_and_test(&req->count))
157 fuse_putback_request(fc, req);
158}
159
160void fuse_release_background(struct fuse_req *req)
161{ 132{
162 iput(req->inode); 133 list_del_init(&req->bg_entry);
163 iput(req->inode2); 134 if (fc->num_background == FUSE_MAX_BACKGROUND) {
164 if (req->file) 135 fc->blocked = 0;
165 fput(req->file); 136 wake_up_all(&fc->blocked_waitq);
166 spin_lock(&fuse_lock); 137 }
167 list_del(&req->bg_entry); 138 fc->num_background--;
168 spin_unlock(&fuse_lock);
169} 139}
170 140
171/* 141/*
@@ -184,28 +154,38 @@ void fuse_release_background(struct fuse_req *req)
184 * interrupted and put in the background, it will return with an error 154 * interrupted and put in the background, it will return with an error
185 * and hence never be reset and reused. 155 * and hence never be reset and reused.
186 * 156 *
187 * Called with fuse_lock, unlocks it 157 * Called with fc->lock, unlocks it
188 */ 158 */
189static void request_end(struct fuse_conn *fc, struct fuse_req *req) 159static void request_end(struct fuse_conn *fc, struct fuse_req *req)
190{ 160{
191 list_del(&req->list); 161 list_del(&req->list);
192 req->state = FUSE_REQ_FINISHED; 162 req->state = FUSE_REQ_FINISHED;
193 if (!req->background) { 163 if (!req->background) {
164 spin_unlock(&fc->lock);
194 wake_up(&req->waitq); 165 wake_up(&req->waitq);
195 fuse_put_request_locked(fc, req); 166 fuse_put_request(fc, req);
196 spin_unlock(&fuse_lock);
197 } else { 167 } else {
168 struct inode *inode = req->inode;
169 struct inode *inode2 = req->inode2;
170 struct file *file = req->file;
198 void (*end) (struct fuse_conn *, struct fuse_req *) = req->end; 171 void (*end) (struct fuse_conn *, struct fuse_req *) = req->end;
199 req->end = NULL; 172 req->end = NULL;
200 spin_unlock(&fuse_lock); 173 req->inode = NULL;
201 down_read(&fc->sbput_sem); 174 req->inode2 = NULL;
202 if (fc->mounted) 175 req->file = NULL;
203 fuse_release_background(req); 176 if (!list_empty(&req->bg_entry))
204 up_read(&fc->sbput_sem); 177 fuse_remove_background(fc, req);
178 spin_unlock(&fc->lock);
179
205 if (end) 180 if (end)
206 end(fc, req); 181 end(fc, req);
207 else 182 else
208 fuse_put_request(fc, req); 183 fuse_put_request(fc, req);
184
185 if (file)
186 fput(file);
187 iput(inode);
188 iput(inode2);
209 } 189 }
210} 190}
211 191
@@ -242,6 +222,9 @@ static void background_request(struct fuse_conn *fc, struct fuse_req *req)
242{ 222{
243 req->background = 1; 223 req->background = 1;
244 list_add(&req->bg_entry, &fc->background); 224 list_add(&req->bg_entry, &fc->background);
225 fc->num_background++;
226 if (fc->num_background == FUSE_MAX_BACKGROUND)
227 fc->blocked = 1;
245 if (req->inode) 228 if (req->inode)
246 req->inode = igrab(req->inode); 229 req->inode = igrab(req->inode);
247 if (req->inode2) 230 if (req->inode2)
@@ -250,16 +233,16 @@ static void background_request(struct fuse_conn *fc, struct fuse_req *req)
250 get_file(req->file); 233 get_file(req->file);
251} 234}
252 235
253/* Called with fuse_lock held. Releases, and then reacquires it. */ 236/* Called with fc->lock held. Releases, and then reacquires it. */
254static void request_wait_answer(struct fuse_conn *fc, struct fuse_req *req) 237static void request_wait_answer(struct fuse_conn *fc, struct fuse_req *req)
255{ 238{
256 sigset_t oldset; 239 sigset_t oldset;
257 240
258 spin_unlock(&fuse_lock); 241 spin_unlock(&fc->lock);
259 block_sigs(&oldset); 242 block_sigs(&oldset);
260 wait_event_interruptible(req->waitq, req->state == FUSE_REQ_FINISHED); 243 wait_event_interruptible(req->waitq, req->state == FUSE_REQ_FINISHED);
261 restore_sigs(&oldset); 244 restore_sigs(&oldset);
262 spin_lock(&fuse_lock); 245 spin_lock(&fc->lock);
263 if (req->state == FUSE_REQ_FINISHED && !req->interrupted) 246 if (req->state == FUSE_REQ_FINISHED && !req->interrupted)
264 return; 247 return;
265 248
@@ -273,9 +256,9 @@ static void request_wait_answer(struct fuse_conn *fc, struct fuse_req *req)
273 locked state, there mustn't be any filesystem 256 locked state, there mustn't be any filesystem
274 operation (e.g. page fault), since that could lead 257 operation (e.g. page fault), since that could lead
275 to deadlock */ 258 to deadlock */
276 spin_unlock(&fuse_lock); 259 spin_unlock(&fc->lock);
277 wait_event(req->waitq, !req->locked); 260 wait_event(req->waitq, !req->locked);
278 spin_lock(&fuse_lock); 261 spin_lock(&fc->lock);
279 } 262 }
280 if (req->state == FUSE_REQ_PENDING) { 263 if (req->state == FUSE_REQ_PENDING) {
281 list_del(&req->list); 264 list_del(&req->list);
@@ -304,19 +287,14 @@ static void queue_request(struct fuse_conn *fc, struct fuse_req *req)
304 req->in.h.unique = fc->reqctr; 287 req->in.h.unique = fc->reqctr;
305 req->in.h.len = sizeof(struct fuse_in_header) + 288 req->in.h.len = sizeof(struct fuse_in_header) +
306 len_args(req->in.numargs, (struct fuse_arg *) req->in.args); 289 len_args(req->in.numargs, (struct fuse_arg *) req->in.args);
307 if (!req->preallocated) {
308 /* If request is not preallocated (either FORGET or
309 RELEASE), then still decrease outstanding_sem, so
310 user can't open infinite number of files while not
311 processing the RELEASE requests. However for
312 efficiency do it without blocking, so if down()
313 would block, just increase the debt instead */
314 if (down_trylock(&fc->outstanding_sem))
315 fc->outstanding_debt++;
316 }
317 list_add_tail(&req->list, &fc->pending); 290 list_add_tail(&req->list, &fc->pending);
318 req->state = FUSE_REQ_PENDING; 291 req->state = FUSE_REQ_PENDING;
292 if (!req->waiting) {
293 req->waiting = 1;
294 atomic_inc(&fc->num_waiting);
295 }
319 wake_up(&fc->waitq); 296 wake_up(&fc->waitq);
297 kill_fasync(&fc->fasync, SIGIO, POLL_IN);
320} 298}
321 299
322/* 300/*
@@ -325,7 +303,7 @@ static void queue_request(struct fuse_conn *fc, struct fuse_req *req)
325void request_send(struct fuse_conn *fc, struct fuse_req *req) 303void request_send(struct fuse_conn *fc, struct fuse_req *req)
326{ 304{
327 req->isreply = 1; 305 req->isreply = 1;
328 spin_lock(&fuse_lock); 306 spin_lock(&fc->lock);
329 if (!fc->connected) 307 if (!fc->connected)
330 req->out.h.error = -ENOTCONN; 308 req->out.h.error = -ENOTCONN;
331 else if (fc->conn_error) 309 else if (fc->conn_error)
@@ -338,15 +316,16 @@ void request_send(struct fuse_conn *fc, struct fuse_req *req)
338 316
339 request_wait_answer(fc, req); 317 request_wait_answer(fc, req);
340 } 318 }
341 spin_unlock(&fuse_lock); 319 spin_unlock(&fc->lock);
342} 320}
343 321
344static void request_send_nowait(struct fuse_conn *fc, struct fuse_req *req) 322static void request_send_nowait(struct fuse_conn *fc, struct fuse_req *req)
345{ 323{
346 spin_lock(&fuse_lock); 324 spin_lock(&fc->lock);
325 background_request(fc, req);
347 if (fc->connected) { 326 if (fc->connected) {
348 queue_request(fc, req); 327 queue_request(fc, req);
349 spin_unlock(&fuse_lock); 328 spin_unlock(&fc->lock);
350 } else { 329 } else {
351 req->out.h.error = -ENOTCONN; 330 req->out.h.error = -ENOTCONN;
352 request_end(fc, req); 331 request_end(fc, req);
@@ -362,9 +341,6 @@ void request_send_noreply(struct fuse_conn *fc, struct fuse_req *req)
362void request_send_background(struct fuse_conn *fc, struct fuse_req *req) 341void request_send_background(struct fuse_conn *fc, struct fuse_req *req)
363{ 342{
364 req->isreply = 1; 343 req->isreply = 1;
365 spin_lock(&fuse_lock);
366 background_request(fc, req);
367 spin_unlock(&fuse_lock);
368 request_send_nowait(fc, req); 344 request_send_nowait(fc, req);
369} 345}
370 346
@@ -373,16 +349,16 @@ void request_send_background(struct fuse_conn *fc, struct fuse_req *req)
373 * anything that could cause a page-fault. If the request was already 349 * anything that could cause a page-fault. If the request was already
374 * interrupted bail out. 350 * interrupted bail out.
375 */ 351 */
376static int lock_request(struct fuse_req *req) 352static int lock_request(struct fuse_conn *fc, struct fuse_req *req)
377{ 353{
378 int err = 0; 354 int err = 0;
379 if (req) { 355 if (req) {
380 spin_lock(&fuse_lock); 356 spin_lock(&fc->lock);
381 if (req->interrupted) 357 if (req->interrupted)
382 err = -ENOENT; 358 err = -ENOENT;
383 else 359 else
384 req->locked = 1; 360 req->locked = 1;
385 spin_unlock(&fuse_lock); 361 spin_unlock(&fc->lock);
386 } 362 }
387 return err; 363 return err;
388} 364}
@@ -392,18 +368,19 @@ static int lock_request(struct fuse_req *req)
392 * requester thread is currently waiting for it to be unlocked, so 368 * requester thread is currently waiting for it to be unlocked, so
393 * wake it up. 369 * wake it up.
394 */ 370 */
395static void unlock_request(struct fuse_req *req) 371static void unlock_request(struct fuse_conn *fc, struct fuse_req *req)
396{ 372{
397 if (req) { 373 if (req) {
398 spin_lock(&fuse_lock); 374 spin_lock(&fc->lock);
399 req->locked = 0; 375 req->locked = 0;
400 if (req->interrupted) 376 if (req->interrupted)
401 wake_up(&req->waitq); 377 wake_up(&req->waitq);
402 spin_unlock(&fuse_lock); 378 spin_unlock(&fc->lock);
403 } 379 }
404} 380}
405 381
406struct fuse_copy_state { 382struct fuse_copy_state {
383 struct fuse_conn *fc;
407 int write; 384 int write;
408 struct fuse_req *req; 385 struct fuse_req *req;
409 const struct iovec *iov; 386 const struct iovec *iov;
@@ -416,11 +393,12 @@ struct fuse_copy_state {
416 unsigned len; 393 unsigned len;
417}; 394};
418 395
419static void fuse_copy_init(struct fuse_copy_state *cs, int write, 396static void fuse_copy_init(struct fuse_copy_state *cs, struct fuse_conn *fc,
420 struct fuse_req *req, const struct iovec *iov, 397 int write, struct fuse_req *req,
421 unsigned long nr_segs) 398 const struct iovec *iov, unsigned long nr_segs)
422{ 399{
423 memset(cs, 0, sizeof(*cs)); 400 memset(cs, 0, sizeof(*cs));
401 cs->fc = fc;
424 cs->write = write; 402 cs->write = write;
425 cs->req = req; 403 cs->req = req;
426 cs->iov = iov; 404 cs->iov = iov;
@@ -450,7 +428,7 @@ static int fuse_copy_fill(struct fuse_copy_state *cs)
450 unsigned long offset; 428 unsigned long offset;
451 int err; 429 int err;
452 430
453 unlock_request(cs->req); 431 unlock_request(cs->fc, cs->req);
454 fuse_copy_finish(cs); 432 fuse_copy_finish(cs);
455 if (!cs->seglen) { 433 if (!cs->seglen) {
456 BUG_ON(!cs->nr_segs); 434 BUG_ON(!cs->nr_segs);
@@ -473,7 +451,7 @@ static int fuse_copy_fill(struct fuse_copy_state *cs)
473 cs->seglen -= cs->len; 451 cs->seglen -= cs->len;
474 cs->addr += cs->len; 452 cs->addr += cs->len;
475 453
476 return lock_request(cs->req); 454 return lock_request(cs->fc, cs->req);
477} 455}
478 456
479/* Do as much copy to/from userspace buffer as we can */ 457/* Do as much copy to/from userspace buffer as we can */
@@ -585,9 +563,9 @@ static void request_wait(struct fuse_conn *fc)
585 if (signal_pending(current)) 563 if (signal_pending(current))
586 break; 564 break;
587 565
588 spin_unlock(&fuse_lock); 566 spin_unlock(&fc->lock);
589 schedule(); 567 schedule();
590 spin_lock(&fuse_lock); 568 spin_lock(&fc->lock);
591 } 569 }
592 set_current_state(TASK_RUNNING); 570 set_current_state(TASK_RUNNING);
593 remove_wait_queue(&fc->waitq, &wait); 571 remove_wait_queue(&fc->waitq, &wait);
@@ -606,18 +584,21 @@ static ssize_t fuse_dev_readv(struct file *file, const struct iovec *iov,
606 unsigned long nr_segs, loff_t *off) 584 unsigned long nr_segs, loff_t *off)
607{ 585{
608 int err; 586 int err;
609 struct fuse_conn *fc;
610 struct fuse_req *req; 587 struct fuse_req *req;
611 struct fuse_in *in; 588 struct fuse_in *in;
612 struct fuse_copy_state cs; 589 struct fuse_copy_state cs;
613 unsigned reqsize; 590 unsigned reqsize;
591 struct fuse_conn *fc = fuse_get_conn(file);
592 if (!fc)
593 return -EPERM;
614 594
615 restart: 595 restart:
616 spin_lock(&fuse_lock); 596 spin_lock(&fc->lock);
617 fc = file->private_data; 597 err = -EAGAIN;
618 err = -EPERM; 598 if ((file->f_flags & O_NONBLOCK) && fc->connected &&
619 if (!fc) 599 list_empty(&fc->pending))
620 goto err_unlock; 600 goto err_unlock;
601
621 request_wait(fc); 602 request_wait(fc);
622 err = -ENODEV; 603 err = -ENODEV;
623 if (!fc->connected) 604 if (!fc->connected)
@@ -641,14 +622,14 @@ static ssize_t fuse_dev_readv(struct file *file, const struct iovec *iov,
641 request_end(fc, req); 622 request_end(fc, req);
642 goto restart; 623 goto restart;
643 } 624 }
644 spin_unlock(&fuse_lock); 625 spin_unlock(&fc->lock);
645 fuse_copy_init(&cs, 1, req, iov, nr_segs); 626 fuse_copy_init(&cs, fc, 1, req, iov, nr_segs);
646 err = fuse_copy_one(&cs, &in->h, sizeof(in->h)); 627 err = fuse_copy_one(&cs, &in->h, sizeof(in->h));
647 if (!err) 628 if (!err)
648 err = fuse_copy_args(&cs, in->numargs, in->argpages, 629 err = fuse_copy_args(&cs, in->numargs, in->argpages,
649 (struct fuse_arg *) in->args, 0); 630 (struct fuse_arg *) in->args, 0);
650 fuse_copy_finish(&cs); 631 fuse_copy_finish(&cs);
651 spin_lock(&fuse_lock); 632 spin_lock(&fc->lock);
652 req->locked = 0; 633 req->locked = 0;
653 if (!err && req->interrupted) 634 if (!err && req->interrupted)
654 err = -ENOENT; 635 err = -ENOENT;
@@ -663,12 +644,12 @@ static ssize_t fuse_dev_readv(struct file *file, const struct iovec *iov,
663 else { 644 else {
664 req->state = FUSE_REQ_SENT; 645 req->state = FUSE_REQ_SENT;
665 list_move_tail(&req->list, &fc->processing); 646 list_move_tail(&req->list, &fc->processing);
666 spin_unlock(&fuse_lock); 647 spin_unlock(&fc->lock);
667 } 648 }
668 return reqsize; 649 return reqsize;
669 650
670 err_unlock: 651 err_unlock:
671 spin_unlock(&fuse_lock); 652 spin_unlock(&fc->lock);
672 return err; 653 return err;
673} 654}
674 655
@@ -735,9 +716,9 @@ static ssize_t fuse_dev_writev(struct file *file, const struct iovec *iov,
735 struct fuse_copy_state cs; 716 struct fuse_copy_state cs;
736 struct fuse_conn *fc = fuse_get_conn(file); 717 struct fuse_conn *fc = fuse_get_conn(file);
737 if (!fc) 718 if (!fc)
738 return -ENODEV; 719 return -EPERM;
739 720
740 fuse_copy_init(&cs, 0, NULL, iov, nr_segs); 721 fuse_copy_init(&cs, fc, 0, NULL, iov, nr_segs);
741 if (nbytes < sizeof(struct fuse_out_header)) 722 if (nbytes < sizeof(struct fuse_out_header))
742 return -EINVAL; 723 return -EINVAL;
743 724
@@ -749,7 +730,7 @@ static ssize_t fuse_dev_writev(struct file *file, const struct iovec *iov,
749 oh.len != nbytes) 730 oh.len != nbytes)
750 goto err_finish; 731 goto err_finish;
751 732
752 spin_lock(&fuse_lock); 733 spin_lock(&fc->lock);
753 err = -ENOENT; 734 err = -ENOENT;
754 if (!fc->connected) 735 if (!fc->connected)
755 goto err_unlock; 736 goto err_unlock;
@@ -760,9 +741,9 @@ static ssize_t fuse_dev_writev(struct file *file, const struct iovec *iov,
760 goto err_unlock; 741 goto err_unlock;
761 742
762 if (req->interrupted) { 743 if (req->interrupted) {
763 spin_unlock(&fuse_lock); 744 spin_unlock(&fc->lock);
764 fuse_copy_finish(&cs); 745 fuse_copy_finish(&cs);
765 spin_lock(&fuse_lock); 746 spin_lock(&fc->lock);
766 request_end(fc, req); 747 request_end(fc, req);
767 return -ENOENT; 748 return -ENOENT;
768 } 749 }
@@ -770,12 +751,12 @@ static ssize_t fuse_dev_writev(struct file *file, const struct iovec *iov,
770 req->out.h = oh; 751 req->out.h = oh;
771 req->locked = 1; 752 req->locked = 1;
772 cs.req = req; 753 cs.req = req;
773 spin_unlock(&fuse_lock); 754 spin_unlock(&fc->lock);
774 755
775 err = copy_out_args(&cs, &req->out, nbytes); 756 err = copy_out_args(&cs, &req->out, nbytes);
776 fuse_copy_finish(&cs); 757 fuse_copy_finish(&cs);
777 758
778 spin_lock(&fuse_lock); 759 spin_lock(&fc->lock);
779 req->locked = 0; 760 req->locked = 0;
780 if (!err) { 761 if (!err) {
781 if (req->interrupted) 762 if (req->interrupted)
@@ -787,7 +768,7 @@ static ssize_t fuse_dev_writev(struct file *file, const struct iovec *iov,
787 return err ? err : nbytes; 768 return err ? err : nbytes;
788 769
789 err_unlock: 770 err_unlock:
790 spin_unlock(&fuse_lock); 771 spin_unlock(&fc->lock);
791 err_finish: 772 err_finish:
792 fuse_copy_finish(&cs); 773 fuse_copy_finish(&cs);
793 return err; 774 return err;
@@ -804,18 +785,19 @@ static ssize_t fuse_dev_write(struct file *file, const char __user *buf,
804 785
805static unsigned fuse_dev_poll(struct file *file, poll_table *wait) 786static unsigned fuse_dev_poll(struct file *file, poll_table *wait)
806{ 787{
807 struct fuse_conn *fc = fuse_get_conn(file);
808 unsigned mask = POLLOUT | POLLWRNORM; 788 unsigned mask = POLLOUT | POLLWRNORM;
809 789 struct fuse_conn *fc = fuse_get_conn(file);
810 if (!fc) 790 if (!fc)
811 return -ENODEV; 791 return POLLERR;
812 792
813 poll_wait(file, &fc->waitq, wait); 793 poll_wait(file, &fc->waitq, wait);
814 794
815 spin_lock(&fuse_lock); 795 spin_lock(&fc->lock);
816 if (!list_empty(&fc->pending)) 796 if (!fc->connected)
817 mask |= POLLIN | POLLRDNORM; 797 mask = POLLERR;
818 spin_unlock(&fuse_lock); 798 else if (!list_empty(&fc->pending))
799 mask |= POLLIN | POLLRDNORM;
800 spin_unlock(&fc->lock);
819 801
820 return mask; 802 return mask;
821} 803}
@@ -823,7 +805,7 @@ static unsigned fuse_dev_poll(struct file *file, poll_table *wait)
823/* 805/*
824 * Abort all requests on the given list (pending or processing) 806 * Abort all requests on the given list (pending or processing)
825 * 807 *
826 * This function releases and reacquires fuse_lock 808 * This function releases and reacquires fc->lock
827 */ 809 */
828static void end_requests(struct fuse_conn *fc, struct list_head *head) 810static void end_requests(struct fuse_conn *fc, struct list_head *head)
829{ 811{
@@ -832,7 +814,7 @@ static void end_requests(struct fuse_conn *fc, struct list_head *head)
832 req = list_entry(head->next, struct fuse_req, list); 814 req = list_entry(head->next, struct fuse_req, list);
833 req->out.h.error = -ECONNABORTED; 815 req->out.h.error = -ECONNABORTED;
834 request_end(fc, req); 816 request_end(fc, req);
835 spin_lock(&fuse_lock); 817 spin_lock(&fc->lock);
836 } 818 }
837} 819}
838 820
@@ -863,10 +845,10 @@ static void end_io_requests(struct fuse_conn *fc)
863 req->end = NULL; 845 req->end = NULL;
864 /* The end function will consume this reference */ 846 /* The end function will consume this reference */
865 __fuse_get_request(req); 847 __fuse_get_request(req);
866 spin_unlock(&fuse_lock); 848 spin_unlock(&fc->lock);
867 wait_event(req->waitq, !req->locked); 849 wait_event(req->waitq, !req->locked);
868 end(fc, req); 850 end(fc, req);
869 spin_lock(&fuse_lock); 851 spin_lock(&fc->lock);
870 } 852 }
871 } 853 }
872} 854}
@@ -893,35 +875,44 @@ static void end_io_requests(struct fuse_conn *fc)
893 */ 875 */
894void fuse_abort_conn(struct fuse_conn *fc) 876void fuse_abort_conn(struct fuse_conn *fc)
895{ 877{
896 spin_lock(&fuse_lock); 878 spin_lock(&fc->lock);
897 if (fc->connected) { 879 if (fc->connected) {
898 fc->connected = 0; 880 fc->connected = 0;
899 end_io_requests(fc); 881 end_io_requests(fc);
900 end_requests(fc, &fc->pending); 882 end_requests(fc, &fc->pending);
901 end_requests(fc, &fc->processing); 883 end_requests(fc, &fc->processing);
902 wake_up_all(&fc->waitq); 884 wake_up_all(&fc->waitq);
885 kill_fasync(&fc->fasync, SIGIO, POLL_IN);
903 } 886 }
904 spin_unlock(&fuse_lock); 887 spin_unlock(&fc->lock);
905} 888}
906 889
907static int fuse_dev_release(struct inode *inode, struct file *file) 890static int fuse_dev_release(struct inode *inode, struct file *file)
908{ 891{
909 struct fuse_conn *fc; 892 struct fuse_conn *fc = fuse_get_conn(file);
910
911 spin_lock(&fuse_lock);
912 fc = file->private_data;
913 if (fc) { 893 if (fc) {
894 spin_lock(&fc->lock);
914 fc->connected = 0; 895 fc->connected = 0;
915 end_requests(fc, &fc->pending); 896 end_requests(fc, &fc->pending);
916 end_requests(fc, &fc->processing); 897 end_requests(fc, &fc->processing);
917 } 898 spin_unlock(&fc->lock);
918 spin_unlock(&fuse_lock); 899 fasync_helper(-1, file, 0, &fc->fasync);
919 if (fc)
920 kobject_put(&fc->kobj); 900 kobject_put(&fc->kobj);
901 }
921 902
922 return 0; 903 return 0;
923} 904}
924 905
906static int fuse_dev_fasync(int fd, struct file *file, int on)
907{
908 struct fuse_conn *fc = fuse_get_conn(file);
909 if (!fc)
910 return -EPERM;
911
912 /* No locking - fasync_helper does its own locking */
913 return fasync_helper(fd, file, on, &fc->fasync);
914}
915
925const struct file_operations fuse_dev_operations = { 916const struct file_operations fuse_dev_operations = {
926 .owner = THIS_MODULE, 917 .owner = THIS_MODULE,
927 .llseek = no_llseek, 918 .llseek = no_llseek,
@@ -931,6 +922,7 @@ const struct file_operations fuse_dev_operations = {
931 .writev = fuse_dev_writev, 922 .writev = fuse_dev_writev,
932 .poll = fuse_dev_poll, 923 .poll = fuse_dev_poll,
933 .release = fuse_dev_release, 924 .release = fuse_dev_release,
925 .fasync = fuse_dev_fasync,
934}; 926};
935 927
936static struct miscdevice fuse_miscdevice = { 928static struct miscdevice fuse_miscdevice = {
diff --git a/fs/fuse/dir.c b/fs/fuse/dir.c
index 256355b80256..8d7546e832e8 100644
--- a/fs/fuse/dir.c
+++ b/fs/fuse/dir.c
@@ -117,8 +117,8 @@ static int fuse_dentry_revalidate(struct dentry *entry, struct nameidata *nd)
117 return 0; 117 return 0;
118 118
119 fc = get_fuse_conn(inode); 119 fc = get_fuse_conn(inode);
120 req = fuse_get_request(fc); 120 req = fuse_get_req(fc);
121 if (!req) 121 if (IS_ERR(req))
122 return 0; 122 return 0;
123 123
124 fuse_lookup_init(req, entry->d_parent->d_inode, entry, &outarg); 124 fuse_lookup_init(req, entry->d_parent->d_inode, entry, &outarg);
@@ -188,9 +188,9 @@ static struct dentry *fuse_lookup(struct inode *dir, struct dentry *entry,
188 if (entry->d_name.len > FUSE_NAME_MAX) 188 if (entry->d_name.len > FUSE_NAME_MAX)
189 return ERR_PTR(-ENAMETOOLONG); 189 return ERR_PTR(-ENAMETOOLONG);
190 190
191 req = fuse_get_request(fc); 191 req = fuse_get_req(fc);
192 if (!req) 192 if (IS_ERR(req))
193 return ERR_PTR(-EINTR); 193 return ERR_PTR(PTR_ERR(req));
194 194
195 fuse_lookup_init(req, dir, entry, &outarg); 195 fuse_lookup_init(req, dir, entry, &outarg);
196 request_send(fc, req); 196 request_send(fc, req);
@@ -244,15 +244,14 @@ static int fuse_create_open(struct inode *dir, struct dentry *entry, int mode,
244 struct file *file; 244 struct file *file;
245 int flags = nd->intent.open.flags - 1; 245 int flags = nd->intent.open.flags - 1;
246 246
247 err = -ENOSYS;
248 if (fc->no_create) 247 if (fc->no_create)
249 goto out; 248 return -ENOSYS;
250 249
251 err = -EINTR; 250 req = fuse_get_req(fc);
252 req = fuse_get_request(fc); 251 if (IS_ERR(req))
253 if (!req) 252 return PTR_ERR(req);
254 goto out;
255 253
254 err = -ENOMEM;
256 ff = fuse_file_alloc(); 255 ff = fuse_file_alloc();
257 if (!ff) 256 if (!ff)
258 goto out_put_request; 257 goto out_put_request;
@@ -314,7 +313,6 @@ static int fuse_create_open(struct inode *dir, struct dentry *entry, int mode,
314 fuse_file_free(ff); 313 fuse_file_free(ff);
315 out_put_request: 314 out_put_request:
316 fuse_put_request(fc, req); 315 fuse_put_request(fc, req);
317 out:
318 return err; 316 return err;
319} 317}
320 318
@@ -375,9 +373,9 @@ static int fuse_mknod(struct inode *dir, struct dentry *entry, int mode,
375{ 373{
376 struct fuse_mknod_in inarg; 374 struct fuse_mknod_in inarg;
377 struct fuse_conn *fc = get_fuse_conn(dir); 375 struct fuse_conn *fc = get_fuse_conn(dir);
378 struct fuse_req *req = fuse_get_request(fc); 376 struct fuse_req *req = fuse_get_req(fc);
379 if (!req) 377 if (IS_ERR(req))
380 return -EINTR; 378 return PTR_ERR(req);
381 379
382 memset(&inarg, 0, sizeof(inarg)); 380 memset(&inarg, 0, sizeof(inarg));
383 inarg.mode = mode; 381 inarg.mode = mode;
@@ -407,9 +405,9 @@ static int fuse_mkdir(struct inode *dir, struct dentry *entry, int mode)
407{ 405{
408 struct fuse_mkdir_in inarg; 406 struct fuse_mkdir_in inarg;
409 struct fuse_conn *fc = get_fuse_conn(dir); 407 struct fuse_conn *fc = get_fuse_conn(dir);
410 struct fuse_req *req = fuse_get_request(fc); 408 struct fuse_req *req = fuse_get_req(fc);
411 if (!req) 409 if (IS_ERR(req))
412 return -EINTR; 410 return PTR_ERR(req);
413 411
414 memset(&inarg, 0, sizeof(inarg)); 412 memset(&inarg, 0, sizeof(inarg));
415 inarg.mode = mode; 413 inarg.mode = mode;
@@ -427,9 +425,9 @@ static int fuse_symlink(struct inode *dir, struct dentry *entry,
427{ 425{
428 struct fuse_conn *fc = get_fuse_conn(dir); 426 struct fuse_conn *fc = get_fuse_conn(dir);
429 unsigned len = strlen(link) + 1; 427 unsigned len = strlen(link) + 1;
430 struct fuse_req *req = fuse_get_request(fc); 428 struct fuse_req *req = fuse_get_req(fc);
431 if (!req) 429 if (IS_ERR(req))
432 return -EINTR; 430 return PTR_ERR(req);
433 431
434 req->in.h.opcode = FUSE_SYMLINK; 432 req->in.h.opcode = FUSE_SYMLINK;
435 req->in.numargs = 2; 433 req->in.numargs = 2;
@@ -444,9 +442,9 @@ static int fuse_unlink(struct inode *dir, struct dentry *entry)
444{ 442{
445 int err; 443 int err;
446 struct fuse_conn *fc = get_fuse_conn(dir); 444 struct fuse_conn *fc = get_fuse_conn(dir);
447 struct fuse_req *req = fuse_get_request(fc); 445 struct fuse_req *req = fuse_get_req(fc);
448 if (!req) 446 if (IS_ERR(req))
449 return -EINTR; 447 return PTR_ERR(req);
450 448
451 req->in.h.opcode = FUSE_UNLINK; 449 req->in.h.opcode = FUSE_UNLINK;
452 req->in.h.nodeid = get_node_id(dir); 450 req->in.h.nodeid = get_node_id(dir);
@@ -476,9 +474,9 @@ static int fuse_rmdir(struct inode *dir, struct dentry *entry)
476{ 474{
477 int err; 475 int err;
478 struct fuse_conn *fc = get_fuse_conn(dir); 476 struct fuse_conn *fc = get_fuse_conn(dir);
479 struct fuse_req *req = fuse_get_request(fc); 477 struct fuse_req *req = fuse_get_req(fc);
480 if (!req) 478 if (IS_ERR(req))
481 return -EINTR; 479 return PTR_ERR(req);
482 480
483 req->in.h.opcode = FUSE_RMDIR; 481 req->in.h.opcode = FUSE_RMDIR;
484 req->in.h.nodeid = get_node_id(dir); 482 req->in.h.nodeid = get_node_id(dir);
@@ -504,9 +502,9 @@ static int fuse_rename(struct inode *olddir, struct dentry *oldent,
504 int err; 502 int err;
505 struct fuse_rename_in inarg; 503 struct fuse_rename_in inarg;
506 struct fuse_conn *fc = get_fuse_conn(olddir); 504 struct fuse_conn *fc = get_fuse_conn(olddir);
507 struct fuse_req *req = fuse_get_request(fc); 505 struct fuse_req *req = fuse_get_req(fc);
508 if (!req) 506 if (IS_ERR(req))
509 return -EINTR; 507 return PTR_ERR(req);
510 508
511 memset(&inarg, 0, sizeof(inarg)); 509 memset(&inarg, 0, sizeof(inarg));
512 inarg.newdir = get_node_id(newdir); 510 inarg.newdir = get_node_id(newdir);
@@ -553,9 +551,9 @@ static int fuse_link(struct dentry *entry, struct inode *newdir,
553 struct fuse_link_in inarg; 551 struct fuse_link_in inarg;
554 struct inode *inode = entry->d_inode; 552 struct inode *inode = entry->d_inode;
555 struct fuse_conn *fc = get_fuse_conn(inode); 553 struct fuse_conn *fc = get_fuse_conn(inode);
556 struct fuse_req *req = fuse_get_request(fc); 554 struct fuse_req *req = fuse_get_req(fc);
557 if (!req) 555 if (IS_ERR(req))
558 return -EINTR; 556 return PTR_ERR(req);
559 557
560 memset(&inarg, 0, sizeof(inarg)); 558 memset(&inarg, 0, sizeof(inarg));
561 inarg.oldnodeid = get_node_id(inode); 559 inarg.oldnodeid = get_node_id(inode);
@@ -583,9 +581,9 @@ int fuse_do_getattr(struct inode *inode)
583 int err; 581 int err;
584 struct fuse_attr_out arg; 582 struct fuse_attr_out arg;
585 struct fuse_conn *fc = get_fuse_conn(inode); 583 struct fuse_conn *fc = get_fuse_conn(inode);
586 struct fuse_req *req = fuse_get_request(fc); 584 struct fuse_req *req = fuse_get_req(fc);
587 if (!req) 585 if (IS_ERR(req))
588 return -EINTR; 586 return PTR_ERR(req);
589 587
590 req->in.h.opcode = FUSE_GETATTR; 588 req->in.h.opcode = FUSE_GETATTR;
591 req->in.h.nodeid = get_node_id(inode); 589 req->in.h.nodeid = get_node_id(inode);
@@ -673,9 +671,9 @@ static int fuse_access(struct inode *inode, int mask)
673 if (fc->no_access) 671 if (fc->no_access)
674 return 0; 672 return 0;
675 673
676 req = fuse_get_request(fc); 674 req = fuse_get_req(fc);
677 if (!req) 675 if (IS_ERR(req))
678 return -EINTR; 676 return PTR_ERR(req);
679 677
680 memset(&inarg, 0, sizeof(inarg)); 678 memset(&inarg, 0, sizeof(inarg));
681 inarg.mask = mask; 679 inarg.mask = mask;
@@ -780,9 +778,9 @@ static int fuse_readdir(struct file *file, void *dstbuf, filldir_t filldir)
780 if (is_bad_inode(inode)) 778 if (is_bad_inode(inode))
781 return -EIO; 779 return -EIO;
782 780
783 req = fuse_get_request(fc); 781 req = fuse_get_req(fc);
784 if (!req) 782 if (IS_ERR(req))
785 return -EINTR; 783 return PTR_ERR(req);
786 784
787 page = alloc_page(GFP_KERNEL); 785 page = alloc_page(GFP_KERNEL);
788 if (!page) { 786 if (!page) {
@@ -809,11 +807,11 @@ static char *read_link(struct dentry *dentry)
809{ 807{
810 struct inode *inode = dentry->d_inode; 808 struct inode *inode = dentry->d_inode;
811 struct fuse_conn *fc = get_fuse_conn(inode); 809 struct fuse_conn *fc = get_fuse_conn(inode);
812 struct fuse_req *req = fuse_get_request(fc); 810 struct fuse_req *req = fuse_get_req(fc);
813 char *link; 811 char *link;
814 812
815 if (!req) 813 if (IS_ERR(req))
816 return ERR_PTR(-EINTR); 814 return ERR_PTR(PTR_ERR(req));
817 815
818 link = (char *) __get_free_page(GFP_KERNEL); 816 link = (char *) __get_free_page(GFP_KERNEL);
819 if (!link) { 817 if (!link) {
@@ -933,9 +931,9 @@ static int fuse_setattr(struct dentry *entry, struct iattr *attr)
933 } 931 }
934 } 932 }
935 933
936 req = fuse_get_request(fc); 934 req = fuse_get_req(fc);
937 if (!req) 935 if (IS_ERR(req))
938 return -EINTR; 936 return PTR_ERR(req);
939 937
940 memset(&inarg, 0, sizeof(inarg)); 938 memset(&inarg, 0, sizeof(inarg));
941 iattr_to_fattr(attr, &inarg); 939 iattr_to_fattr(attr, &inarg);
@@ -995,9 +993,9 @@ static int fuse_setxattr(struct dentry *entry, const char *name,
995 if (fc->no_setxattr) 993 if (fc->no_setxattr)
996 return -EOPNOTSUPP; 994 return -EOPNOTSUPP;
997 995
998 req = fuse_get_request(fc); 996 req = fuse_get_req(fc);
999 if (!req) 997 if (IS_ERR(req))
1000 return -EINTR; 998 return PTR_ERR(req);
1001 999
1002 memset(&inarg, 0, sizeof(inarg)); 1000 memset(&inarg, 0, sizeof(inarg));
1003 inarg.size = size; 1001 inarg.size = size;
@@ -1035,9 +1033,9 @@ static ssize_t fuse_getxattr(struct dentry *entry, const char *name,
1035 if (fc->no_getxattr) 1033 if (fc->no_getxattr)
1036 return -EOPNOTSUPP; 1034 return -EOPNOTSUPP;
1037 1035
1038 req = fuse_get_request(fc); 1036 req = fuse_get_req(fc);
1039 if (!req) 1037 if (IS_ERR(req))
1040 return -EINTR; 1038 return PTR_ERR(req);
1041 1039
1042 memset(&inarg, 0, sizeof(inarg)); 1040 memset(&inarg, 0, sizeof(inarg));
1043 inarg.size = size; 1041 inarg.size = size;
@@ -1085,9 +1083,9 @@ static ssize_t fuse_listxattr(struct dentry *entry, char *list, size_t size)
1085 if (fc->no_listxattr) 1083 if (fc->no_listxattr)
1086 return -EOPNOTSUPP; 1084 return -EOPNOTSUPP;
1087 1085
1088 req = fuse_get_request(fc); 1086 req = fuse_get_req(fc);
1089 if (!req) 1087 if (IS_ERR(req))
1090 return -EINTR; 1088 return PTR_ERR(req);
1091 1089
1092 memset(&inarg, 0, sizeof(inarg)); 1090 memset(&inarg, 0, sizeof(inarg));
1093 inarg.size = size; 1091 inarg.size = size;
@@ -1131,9 +1129,9 @@ static int fuse_removexattr(struct dentry *entry, const char *name)
1131 if (fc->no_removexattr) 1129 if (fc->no_removexattr)
1132 return -EOPNOTSUPP; 1130 return -EOPNOTSUPP;
1133 1131
1134 req = fuse_get_request(fc); 1132 req = fuse_get_req(fc);
1135 if (!req) 1133 if (IS_ERR(req))
1136 return -EINTR; 1134 return PTR_ERR(req);
1137 1135
1138 req->in.h.opcode = FUSE_REMOVEXATTR; 1136 req->in.h.opcode = FUSE_REMOVEXATTR;
1139 req->in.h.nodeid = get_node_id(inode); 1137 req->in.h.nodeid = get_node_id(inode);
diff --git a/fs/fuse/file.c b/fs/fuse/file.c
index 975f2697e866..fc342cf7c2cc 100644
--- a/fs/fuse/file.c
+++ b/fs/fuse/file.c
@@ -1,6 +1,6 @@
1/* 1/*
2 FUSE: Filesystem in Userspace 2 FUSE: Filesystem in Userspace
3 Copyright (C) 2001-2005 Miklos Szeredi <miklos@szeredi.hu> 3 Copyright (C) 2001-2006 Miklos Szeredi <miklos@szeredi.hu>
4 4
5 This program can be distributed under the terms of the GNU GPL. 5 This program can be distributed under the terms of the GNU GPL.
6 See the file COPYING. 6 See the file COPYING.
@@ -22,9 +22,9 @@ static int fuse_send_open(struct inode *inode, struct file *file, int isdir,
22 struct fuse_req *req; 22 struct fuse_req *req;
23 int err; 23 int err;
24 24
25 req = fuse_get_request(fc); 25 req = fuse_get_req(fc);
26 if (!req) 26 if (IS_ERR(req))
27 return -EINTR; 27 return PTR_ERR(req);
28 28
29 memset(&inarg, 0, sizeof(inarg)); 29 memset(&inarg, 0, sizeof(inarg));
30 inarg.flags = file->f_flags & ~(O_CREAT | O_EXCL | O_NOCTTY | O_TRUNC); 30 inarg.flags = file->f_flags & ~(O_CREAT | O_EXCL | O_NOCTTY | O_TRUNC);
@@ -184,9 +184,9 @@ static int fuse_flush(struct file *file)
184 if (fc->no_flush) 184 if (fc->no_flush)
185 return 0; 185 return 0;
186 186
187 req = fuse_get_request(fc); 187 req = fuse_get_req(fc);
188 if (!req) 188 if (IS_ERR(req))
189 return -EINTR; 189 return PTR_ERR(req);
190 190
191 memset(&inarg, 0, sizeof(inarg)); 191 memset(&inarg, 0, sizeof(inarg));
192 inarg.fh = ff->fh; 192 inarg.fh = ff->fh;
@@ -223,9 +223,9 @@ int fuse_fsync_common(struct file *file, struct dentry *de, int datasync,
223 if ((!isdir && fc->no_fsync) || (isdir && fc->no_fsyncdir)) 223 if ((!isdir && fc->no_fsync) || (isdir && fc->no_fsyncdir))
224 return 0; 224 return 0;
225 225
226 req = fuse_get_request(fc); 226 req = fuse_get_req(fc);
227 if (!req) 227 if (IS_ERR(req))
228 return -EINTR; 228 return PTR_ERR(req);
229 229
230 memset(&inarg, 0, sizeof(inarg)); 230 memset(&inarg, 0, sizeof(inarg));
231 inarg.fh = ff->fh; 231 inarg.fh = ff->fh;
@@ -297,9 +297,9 @@ static int fuse_readpage(struct file *file, struct page *page)
297 if (is_bad_inode(inode)) 297 if (is_bad_inode(inode))
298 goto out; 298 goto out;
299 299
300 err = -EINTR; 300 req = fuse_get_req(fc);
301 req = fuse_get_request(fc); 301 err = PTR_ERR(req);
302 if (!req) 302 if (IS_ERR(req))
303 goto out; 303 goto out;
304 304
305 req->out.page_zeroing = 1; 305 req->out.page_zeroing = 1;
@@ -368,10 +368,10 @@ static int fuse_readpages_fill(void *_data, struct page *page)
368 (req->num_pages + 1) * PAGE_CACHE_SIZE > fc->max_read || 368 (req->num_pages + 1) * PAGE_CACHE_SIZE > fc->max_read ||
369 req->pages[req->num_pages - 1]->index + 1 != page->index)) { 369 req->pages[req->num_pages - 1]->index + 1 != page->index)) {
370 fuse_send_readpages(req, data->file, inode); 370 fuse_send_readpages(req, data->file, inode);
371 data->req = req = fuse_get_request(fc); 371 data->req = req = fuse_get_req(fc);
372 if (!req) { 372 if (IS_ERR(req)) {
373 unlock_page(page); 373 unlock_page(page);
374 return -EINTR; 374 return PTR_ERR(req);
375 } 375 }
376 } 376 }
377 req->pages[req->num_pages] = page; 377 req->pages[req->num_pages] = page;
@@ -392,13 +392,17 @@ static int fuse_readpages(struct file *file, struct address_space *mapping,
392 392
393 data.file = file; 393 data.file = file;
394 data.inode = inode; 394 data.inode = inode;
395 data.req = fuse_get_request(fc); 395 data.req = fuse_get_req(fc);
396 if (!data.req) 396 if (IS_ERR(data.req))
397 return -EINTR; 397 return PTR_ERR(data.req);
398 398
399 err = read_cache_pages(mapping, pages, fuse_readpages_fill, &data); 399 err = read_cache_pages(mapping, pages, fuse_readpages_fill, &data);
400 if (!err) 400 if (!err) {
401 fuse_send_readpages(data.req, file, inode); 401 if (data.req->num_pages)
402 fuse_send_readpages(data.req, file, inode);
403 else
404 fuse_put_request(fc, data.req);
405 }
402 return err; 406 return err;
403} 407}
404 408
@@ -451,9 +455,9 @@ static int fuse_commit_write(struct file *file, struct page *page,
451 if (is_bad_inode(inode)) 455 if (is_bad_inode(inode))
452 return -EIO; 456 return -EIO;
453 457
454 req = fuse_get_request(fc); 458 req = fuse_get_req(fc);
455 if (!req) 459 if (IS_ERR(req))
456 return -EINTR; 460 return PTR_ERR(req);
457 461
458 req->num_pages = 1; 462 req->num_pages = 1;
459 req->pages[0] = page; 463 req->pages[0] = page;
@@ -528,9 +532,9 @@ static ssize_t fuse_direct_io(struct file *file, const char __user *buf,
528 if (is_bad_inode(inode)) 532 if (is_bad_inode(inode))
529 return -EIO; 533 return -EIO;
530 534
531 req = fuse_get_request(fc); 535 req = fuse_get_req(fc);
532 if (!req) 536 if (IS_ERR(req))
533 return -EINTR; 537 return PTR_ERR(req);
534 538
535 while (count) { 539 while (count) {
536 size_t nres; 540 size_t nres;
@@ -561,8 +565,12 @@ static ssize_t fuse_direct_io(struct file *file, const char __user *buf,
561 buf += nres; 565 buf += nres;
562 if (nres != nbytes) 566 if (nres != nbytes)
563 break; 567 break;
564 if (count) 568 if (count) {
565 fuse_reset_request(req); 569 fuse_put_request(fc, req);
570 req = fuse_get_req(fc);
571 if (IS_ERR(req))
572 break;
573 }
566 } 574 }
567 fuse_put_request(fc, req); 575 fuse_put_request(fc, req);
568 if (res > 0) { 576 if (res > 0) {
diff --git a/fs/fuse/fuse_i.h b/fs/fuse/fuse_i.h
index a16a04fcf41e..59661c481d9d 100644
--- a/fs/fuse/fuse_i.h
+++ b/fs/fuse/fuse_i.h
@@ -1,6 +1,6 @@
1/* 1/*
2 FUSE: Filesystem in Userspace 2 FUSE: Filesystem in Userspace
3 Copyright (C) 2001-2005 Miklos Szeredi <miklos@szeredi.hu> 3 Copyright (C) 2001-2006 Miklos Szeredi <miklos@szeredi.hu>
4 4
5 This program can be distributed under the terms of the GNU GPL. 5 This program can be distributed under the terms of the GNU GPL.
6 See the file COPYING. 6 See the file COPYING.
@@ -18,8 +18,8 @@
18/** Max number of pages that can be used in a single read request */ 18/** Max number of pages that can be used in a single read request */
19#define FUSE_MAX_PAGES_PER_REQ 32 19#define FUSE_MAX_PAGES_PER_REQ 32
20 20
21/** If more requests are outstanding, then the operation will block */ 21/** Maximum number of outstanding background requests */
22#define FUSE_MAX_OUTSTANDING 10 22#define FUSE_MAX_BACKGROUND 10
23 23
24/** It could be as large as PATH_MAX, but would that have any uses? */ 24/** It could be as large as PATH_MAX, but would that have any uses? */
25#define FUSE_NAME_MAX 1024 25#define FUSE_NAME_MAX 1024
@@ -131,8 +131,8 @@ struct fuse_conn;
131 * A request to the client 131 * A request to the client
132 */ 132 */
133struct fuse_req { 133struct fuse_req {
134 /** This can be on either unused_list, pending processing or 134 /** This can be on either pending processing or io lists in
135 io lists in fuse_conn */ 135 fuse_conn */
136 struct list_head list; 136 struct list_head list;
137 137
138 /** Entry on the background list */ 138 /** Entry on the background list */
@@ -144,15 +144,12 @@ struct fuse_req {
144 /* 144 /*
145 * The following bitfields are either set once before the 145 * The following bitfields are either set once before the
146 * request is queued or setting/clearing them is protected by 146 * request is queued or setting/clearing them is protected by
147 * fuse_lock 147 * fuse_conn->lock
148 */ 148 */
149 149
150 /** True if the request has reply */ 150 /** True if the request has reply */
151 unsigned isreply:1; 151 unsigned isreply:1;
152 152
153 /** The request is preallocated */
154 unsigned preallocated:1;
155
156 /** The request was interrupted */ 153 /** The request was interrupted */
157 unsigned interrupted:1; 154 unsigned interrupted:1;
158 155
@@ -162,6 +159,9 @@ struct fuse_req {
162 /** Data is being copied to/from the request */ 159 /** Data is being copied to/from the request */
163 unsigned locked:1; 160 unsigned locked:1;
164 161
162 /** Request is counted as "waiting" */
163 unsigned waiting:1;
164
165 /** State of the request */ 165 /** State of the request */
166 enum fuse_req_state state; 166 enum fuse_req_state state;
167 167
@@ -213,6 +213,9 @@ struct fuse_req {
213 * unmounted. 213 * unmounted.
214 */ 214 */
215struct fuse_conn { 215struct fuse_conn {
216 /** Lock protecting accessess to members of this structure */
217 spinlock_t lock;
218
216 /** The user id for this mount */ 219 /** The user id for this mount */
217 uid_t user_id; 220 uid_t user_id;
218 221
@@ -244,25 +247,20 @@ struct fuse_conn {
244 interrupted request) */ 247 interrupted request) */
245 struct list_head background; 248 struct list_head background;
246 249
247 /** Controls the maximum number of outstanding requests */ 250 /** Number of requests currently in the background */
248 struct semaphore outstanding_sem; 251 unsigned num_background;
249 252
250 /** This counts the number of outstanding requests if 253 /** Flag indicating if connection is blocked. This will be
251 outstanding_sem would go negative */ 254 the case before the INIT reply is received, and if there
252 unsigned outstanding_debt; 255 are too many outstading backgrounds requests */
256 int blocked;
253 257
254 /** RW semaphore for exclusion with fuse_put_super() */ 258 /** waitq for blocked connection */
255 struct rw_semaphore sbput_sem; 259 wait_queue_head_t blocked_waitq;
256
257 /** The list of unused requests */
258 struct list_head unused_list;
259 260
260 /** The next unique request id */ 261 /** The next unique request id */
261 u64 reqctr; 262 u64 reqctr;
262 263
263 /** Mount is active */
264 unsigned mounted;
265
266 /** Connection established, cleared on umount, connection 264 /** Connection established, cleared on umount, connection
267 abort and device release */ 265 abort and device release */
268 unsigned connected; 266 unsigned connected;
@@ -318,6 +316,9 @@ struct fuse_conn {
318 316
319 /** kobject */ 317 /** kobject */
320 struct kobject kobj; 318 struct kobject kobj;
319
320 /** O_ASYNC requests */
321 struct fasync_struct *fasync;
321}; 322};
322 323
323static inline struct fuse_conn *get_fuse_conn_super(struct super_block *sb) 324static inline struct fuse_conn *get_fuse_conn_super(struct super_block *sb)
@@ -349,21 +350,6 @@ static inline u64 get_node_id(struct inode *inode)
349extern const struct file_operations fuse_dev_operations; 350extern const struct file_operations fuse_dev_operations;
350 351
351/** 352/**
352 * This is the single global spinlock which protects FUSE's structures
353 *
354 * The following data is protected by this lock:
355 *
356 * - the private_data field of the device file
357 * - the s_fs_info field of the super block
358 * - unused_list, pending, processing lists in fuse_conn
359 * - background list in fuse_conn
360 * - the unique request ID counter reqctr in fuse_conn
361 * - the sb (super_block) field in fuse_conn
362 * - the file (device file) field in fuse_conn
363 */
364extern spinlock_t fuse_lock;
365
366/**
367 * Get a filled in inode 353 * Get a filled in inode
368 */ 354 */
369struct inode *fuse_iget(struct super_block *sb, unsigned long nodeid, 355struct inode *fuse_iget(struct super_block *sb, unsigned long nodeid,
@@ -461,11 +447,11 @@ void fuse_reset_request(struct fuse_req *req);
461/** 447/**
462 * Reserve a preallocated request 448 * Reserve a preallocated request
463 */ 449 */
464struct fuse_req *fuse_get_request(struct fuse_conn *fc); 450struct fuse_req *fuse_get_req(struct fuse_conn *fc);
465 451
466/** 452/**
467 * Decrement reference count of a request. If count goes to zero put 453 * Decrement reference count of a request. If count goes to zero free
468 * on unused list (preallocated) or free request (not preallocated). 454 * the request.
469 */ 455 */
470void fuse_put_request(struct fuse_conn *fc, struct fuse_req *req); 456void fuse_put_request(struct fuse_conn *fc, struct fuse_req *req);
471 457
@@ -485,11 +471,11 @@ void request_send_noreply(struct fuse_conn *fc, struct fuse_req *req);
485void request_send_background(struct fuse_conn *fc, struct fuse_req *req); 471void request_send_background(struct fuse_conn *fc, struct fuse_req *req);
486 472
487/** 473/**
488 * Release inodes and file associated with background request 474 * Remove request from the the background list
489 */ 475 */
490void fuse_release_background(struct fuse_req *req); 476void fuse_remove_background(struct fuse_conn *fc, struct fuse_req *req);
491 477
492/* Abort all requests */ 478/** Abort all requests */
493void fuse_abort_conn(struct fuse_conn *fc); 479void fuse_abort_conn(struct fuse_conn *fc);
494 480
495/** 481/**
diff --git a/fs/fuse/inode.c b/fs/fuse/inode.c
index 879e6fba9480..43a6fc0db8a7 100644
--- a/fs/fuse/inode.c
+++ b/fs/fuse/inode.c
@@ -1,6 +1,6 @@
1/* 1/*
2 FUSE: Filesystem in Userspace 2 FUSE: Filesystem in Userspace
3 Copyright (C) 2001-2005 Miklos Szeredi <miklos@szeredi.hu> 3 Copyright (C) 2001-2006 Miklos Szeredi <miklos@szeredi.hu>
4 4
5 This program can be distributed under the terms of the GNU GPL. 5 This program can be distributed under the terms of the GNU GPL.
6 See the file COPYING. 6 See the file COPYING.
@@ -22,7 +22,6 @@ MODULE_AUTHOR("Miklos Szeredi <miklos@szeredi.hu>");
22MODULE_DESCRIPTION("Filesystem in Userspace"); 22MODULE_DESCRIPTION("Filesystem in Userspace");
23MODULE_LICENSE("GPL"); 23MODULE_LICENSE("GPL");
24 24
25spinlock_t fuse_lock;
26static kmem_cache_t *fuse_inode_cachep; 25static kmem_cache_t *fuse_inode_cachep;
27static struct subsystem connections_subsys; 26static struct subsystem connections_subsys;
28 27
@@ -205,17 +204,28 @@ static void fuse_put_super(struct super_block *sb)
205{ 204{
206 struct fuse_conn *fc = get_fuse_conn_super(sb); 205 struct fuse_conn *fc = get_fuse_conn_super(sb);
207 206
208 down_write(&fc->sbput_sem); 207 spin_lock(&fc->lock);
209 while (!list_empty(&fc->background))
210 fuse_release_background(list_entry(fc->background.next,
211 struct fuse_req, bg_entry));
212
213 spin_lock(&fuse_lock);
214 fc->mounted = 0;
215 fc->connected = 0; 208 fc->connected = 0;
216 spin_unlock(&fuse_lock); 209 while (!list_empty(&fc->background)) {
217 up_write(&fc->sbput_sem); 210 struct fuse_req *req = list_entry(fc->background.next,
211 struct fuse_req, bg_entry);
212 struct inode *inode = req->inode;
213 struct inode *inode2 = req->inode2;
214
215 /* File would hold a reference to vfsmount */
216 BUG_ON(req->file);
217 req->inode = NULL;
218 req->inode2 = NULL;
219 fuse_remove_background(fc, req);
220
221 spin_unlock(&fc->lock);
222 iput(inode);
223 iput(inode2);
224 spin_lock(&fc->lock);
225 }
226 spin_unlock(&fc->lock);
218 /* Flush all readers on this fs */ 227 /* Flush all readers on this fs */
228 kill_fasync(&fc->fasync, SIGIO, POLL_IN);
219 wake_up_all(&fc->waitq); 229 wake_up_all(&fc->waitq);
220 kobject_del(&fc->kobj); 230 kobject_del(&fc->kobj);
221 kobject_put(&fc->kobj); 231 kobject_put(&fc->kobj);
@@ -242,9 +252,9 @@ static int fuse_statfs(struct super_block *sb, struct kstatfs *buf)
242 struct fuse_statfs_out outarg; 252 struct fuse_statfs_out outarg;
243 int err; 253 int err;
244 254
245 req = fuse_get_request(fc); 255 req = fuse_get_req(fc);
246 if (!req) 256 if (IS_ERR(req))
247 return -EINTR; 257 return PTR_ERR(req);
248 258
249 memset(&outarg, 0, sizeof(outarg)); 259 memset(&outarg, 0, sizeof(outarg));
250 req->in.numargs = 0; 260 req->in.numargs = 0;
@@ -369,15 +379,7 @@ static int fuse_show_options(struct seq_file *m, struct vfsmount *mnt)
369 379
370static void fuse_conn_release(struct kobject *kobj) 380static void fuse_conn_release(struct kobject *kobj)
371{ 381{
372 struct fuse_conn *fc = get_fuse_conn_kobj(kobj); 382 kfree(get_fuse_conn_kobj(kobj));
373
374 while (!list_empty(&fc->unused_list)) {
375 struct fuse_req *req;
376 req = list_entry(fc->unused_list.next, struct fuse_req, list);
377 list_del(&req->list);
378 fuse_request_free(req);
379 }
380 kfree(fc);
381} 383}
382 384
383static struct fuse_conn *new_conn(void) 385static struct fuse_conn *new_conn(void)
@@ -386,64 +388,24 @@ static struct fuse_conn *new_conn(void)
386 388
387 fc = kzalloc(sizeof(*fc), GFP_KERNEL); 389 fc = kzalloc(sizeof(*fc), GFP_KERNEL);
388 if (fc) { 390 if (fc) {
389 int i; 391 spin_lock_init(&fc->lock);
390 init_waitqueue_head(&fc->waitq); 392 init_waitqueue_head(&fc->waitq);
393 init_waitqueue_head(&fc->blocked_waitq);
391 INIT_LIST_HEAD(&fc->pending); 394 INIT_LIST_HEAD(&fc->pending);
392 INIT_LIST_HEAD(&fc->processing); 395 INIT_LIST_HEAD(&fc->processing);
393 INIT_LIST_HEAD(&fc->io); 396 INIT_LIST_HEAD(&fc->io);
394 INIT_LIST_HEAD(&fc->unused_list);
395 INIT_LIST_HEAD(&fc->background); 397 INIT_LIST_HEAD(&fc->background);
396 sema_init(&fc->outstanding_sem, 1); /* One for INIT */
397 init_rwsem(&fc->sbput_sem);
398 kobj_set_kset_s(fc, connections_subsys); 398 kobj_set_kset_s(fc, connections_subsys);
399 kobject_init(&fc->kobj); 399 kobject_init(&fc->kobj);
400 atomic_set(&fc->num_waiting, 0); 400 atomic_set(&fc->num_waiting, 0);
401 for (i = 0; i < FUSE_MAX_OUTSTANDING; i++) {
402 struct fuse_req *req = fuse_request_alloc();
403 if (!req) {
404 kobject_put(&fc->kobj);
405 return NULL;
406 }
407 list_add(&req->list, &fc->unused_list);
408 }
409 fc->bdi.ra_pages = (VM_MAX_READAHEAD * 1024) / PAGE_CACHE_SIZE; 401 fc->bdi.ra_pages = (VM_MAX_READAHEAD * 1024) / PAGE_CACHE_SIZE;
410 fc->bdi.unplug_io_fn = default_unplug_io_fn; 402 fc->bdi.unplug_io_fn = default_unplug_io_fn;
411 fc->reqctr = 0; 403 fc->reqctr = 0;
404 fc->blocked = 1;
412 } 405 }
413 return fc; 406 return fc;
414} 407}
415 408
416static struct fuse_conn *get_conn(struct file *file, struct super_block *sb)
417{
418 struct fuse_conn *fc;
419 int err;
420
421 err = -EINVAL;
422 if (file->f_op != &fuse_dev_operations)
423 goto out_err;
424
425 err = -ENOMEM;
426 fc = new_conn();
427 if (!fc)
428 goto out_err;
429
430 spin_lock(&fuse_lock);
431 err = -EINVAL;
432 if (file->private_data)
433 goto out_unlock;
434
435 kobject_get(&fc->kobj);
436 file->private_data = fc;
437 spin_unlock(&fuse_lock);
438 return fc;
439
440 out_unlock:
441 spin_unlock(&fuse_lock);
442 kobject_put(&fc->kobj);
443 out_err:
444 return ERR_PTR(err);
445}
446
447static struct inode *get_root_inode(struct super_block *sb, unsigned mode) 409static struct inode *get_root_inode(struct super_block *sb, unsigned mode)
448{ 410{
449 struct fuse_attr attr; 411 struct fuse_attr attr;
@@ -467,7 +429,6 @@ static struct super_operations fuse_super_operations = {
467 429
468static void process_init_reply(struct fuse_conn *fc, struct fuse_req *req) 430static void process_init_reply(struct fuse_conn *fc, struct fuse_req *req)
469{ 431{
470 int i;
471 struct fuse_init_out *arg = &req->misc.init_out; 432 struct fuse_init_out *arg = &req->misc.init_out;
472 433
473 if (req->out.h.error || arg->major != FUSE_KERNEL_VERSION) 434 if (req->out.h.error || arg->major != FUSE_KERNEL_VERSION)
@@ -486,22 +447,13 @@ static void process_init_reply(struct fuse_conn *fc, struct fuse_req *req)
486 fc->minor = arg->minor; 447 fc->minor = arg->minor;
487 fc->max_write = arg->minor < 5 ? 4096 : arg->max_write; 448 fc->max_write = arg->minor < 5 ? 4096 : arg->max_write;
488 } 449 }
489
490 /* After INIT reply is received other requests can go
491 out. So do (FUSE_MAX_OUTSTANDING - 1) number of
492 up()s on outstanding_sem. The last up() is done in
493 fuse_putback_request() */
494 for (i = 1; i < FUSE_MAX_OUTSTANDING; i++)
495 up(&fc->outstanding_sem);
496
497 fuse_put_request(fc, req); 450 fuse_put_request(fc, req);
451 fc->blocked = 0;
452 wake_up_all(&fc->blocked_waitq);
498} 453}
499 454
500static void fuse_send_init(struct fuse_conn *fc) 455static void fuse_send_init(struct fuse_conn *fc, struct fuse_req *req)
501{ 456{
502 /* This is called from fuse_read_super() so there's guaranteed
503 to be exactly one request available */
504 struct fuse_req *req = fuse_get_request(fc);
505 struct fuse_init_in *arg = &req->misc.init_in; 457 struct fuse_init_in *arg = &req->misc.init_in;
506 458
507 arg->major = FUSE_KERNEL_VERSION; 459 arg->major = FUSE_KERNEL_VERSION;
@@ -525,12 +477,9 @@ static void fuse_send_init(struct fuse_conn *fc)
525 477
526static unsigned long long conn_id(void) 478static unsigned long long conn_id(void)
527{ 479{
480 /* BKL is held for ->get_sb() */
528 static unsigned long long ctr = 1; 481 static unsigned long long ctr = 1;
529 unsigned long long val; 482 return ctr++;
530 spin_lock(&fuse_lock);
531 val = ctr++;
532 spin_unlock(&fuse_lock);
533 return val;
534} 483}
535 484
536static int fuse_fill_super(struct super_block *sb, void *data, int silent) 485static int fuse_fill_super(struct super_block *sb, void *data, int silent)
@@ -540,6 +489,7 @@ static int fuse_fill_super(struct super_block *sb, void *data, int silent)
540 struct fuse_mount_data d; 489 struct fuse_mount_data d;
541 struct file *file; 490 struct file *file;
542 struct dentry *root_dentry; 491 struct dentry *root_dentry;
492 struct fuse_req *init_req;
543 int err; 493 int err;
544 494
545 if (!parse_fuse_opt((char *) data, &d)) 495 if (!parse_fuse_opt((char *) data, &d))
@@ -555,10 +505,17 @@ static int fuse_fill_super(struct super_block *sb, void *data, int silent)
555 if (!file) 505 if (!file)
556 return -EINVAL; 506 return -EINVAL;
557 507
558 fc = get_conn(file, sb); 508 if (file->f_op != &fuse_dev_operations)
559 fput(file); 509 return -EINVAL;
560 if (IS_ERR(fc)) 510
561 return PTR_ERR(fc); 511 /* Setting file->private_data can't race with other mount()
512 instances, since BKL is held for ->get_sb() */
513 if (file->private_data)
514 return -EINVAL;
515
516 fc = new_conn();
517 if (!fc)
518 return -ENOMEM;
562 519
563 fc->flags = d.flags; 520 fc->flags = d.flags;
564 fc->user_id = d.user_id; 521 fc->user_id = d.user_id;
@@ -579,27 +536,39 @@ static int fuse_fill_super(struct super_block *sb, void *data, int silent)
579 goto err; 536 goto err;
580 } 537 }
581 538
539 init_req = fuse_request_alloc();
540 if (!init_req)
541 goto err_put_root;
542
582 err = kobject_set_name(&fc->kobj, "%llu", conn_id()); 543 err = kobject_set_name(&fc->kobj, "%llu", conn_id());
583 if (err) 544 if (err)
584 goto err_put_root; 545 goto err_free_req;
585 546
586 err = kobject_add(&fc->kobj); 547 err = kobject_add(&fc->kobj);
587 if (err) 548 if (err)
588 goto err_put_root; 549 goto err_free_req;
589 550
590 sb->s_root = root_dentry; 551 sb->s_root = root_dentry;
591 spin_lock(&fuse_lock);
592 fc->mounted = 1;
593 fc->connected = 1; 552 fc->connected = 1;
594 spin_unlock(&fuse_lock); 553 kobject_get(&fc->kobj);
554 file->private_data = fc;
555 /*
556 * atomic_dec_and_test() in fput() provides the necessary
557 * memory barrier for file->private_data to be visible on all
558 * CPUs after this
559 */
560 fput(file);
595 561
596 fuse_send_init(fc); 562 fuse_send_init(fc, init_req);
597 563
598 return 0; 564 return 0;
599 565
566 err_free_req:
567 fuse_request_free(init_req);
600 err_put_root: 568 err_put_root:
601 dput(root_dentry); 569 dput(root_dentry);
602 err: 570 err:
571 fput(file);
603 kobject_put(&fc->kobj); 572 kobject_put(&fc->kobj);
604 return err; 573 return err;
605} 574}
@@ -753,7 +722,6 @@ static int __init fuse_init(void)
753 printk("fuse init (API version %i.%i)\n", 722 printk("fuse init (API version %i.%i)\n",
754 FUSE_KERNEL_VERSION, FUSE_KERNEL_MINOR_VERSION); 723 FUSE_KERNEL_VERSION, FUSE_KERNEL_MINOR_VERSION);
755 724
756 spin_lock_init(&fuse_lock);
757 res = fuse_fs_init(); 725 res = fuse_fs_init();
758 if (res) 726 if (res)
759 goto err; 727 goto err;