aboutsummaryrefslogtreecommitdiffstats
path: root/fs/fuse/dir.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/fuse/dir.c')
-rw-r--r--fs/fuse/dir.c53
1 files changed, 26 insertions, 27 deletions
diff --git a/fs/fuse/dir.c b/fs/fuse/dir.c
index c9627c95482d..6ea42e98cb17 100644
--- a/fs/fuse/dir.c
+++ b/fs/fuse/dir.c
@@ -10,9 +10,9 @@
10 10
11#include <linux/pagemap.h> 11#include <linux/pagemap.h>
12#include <linux/file.h> 12#include <linux/file.h>
13#include <linux/gfp.h>
14#include <linux/sched.h> 13#include <linux/sched.h>
15#include <linux/namei.h> 14#include <linux/namei.h>
15#include <linux/slab.h>
16 16
17#if BITS_PER_LONG >= 64 17#if BITS_PER_LONG >= 64
18static inline void fuse_dentry_settime(struct dentry *entry, u64 time) 18static inline void fuse_dentry_settime(struct dentry *entry, u64 time)
@@ -165,7 +165,7 @@ static int fuse_dentry_revalidate(struct dentry *entry, struct nameidata *nd)
165 struct fuse_entry_out outarg; 165 struct fuse_entry_out outarg;
166 struct fuse_conn *fc; 166 struct fuse_conn *fc;
167 struct fuse_req *req; 167 struct fuse_req *req;
168 struct fuse_req *forget_req; 168 struct fuse_forget_link *forget;
169 struct dentry *parent; 169 struct dentry *parent;
170 u64 attr_version; 170 u64 attr_version;
171 171
@@ -178,8 +178,8 @@ static int fuse_dentry_revalidate(struct dentry *entry, struct nameidata *nd)
178 if (IS_ERR(req)) 178 if (IS_ERR(req))
179 return 0; 179 return 0;
180 180
181 forget_req = fuse_get_req(fc); 181 forget = fuse_alloc_forget();
182 if (IS_ERR(forget_req)) { 182 if (!forget) {
183 fuse_put_request(fc, req); 183 fuse_put_request(fc, req);
184 return 0; 184 return 0;
185 } 185 }
@@ -199,15 +199,14 @@ static int fuse_dentry_revalidate(struct dentry *entry, struct nameidata *nd)
199 if (!err) { 199 if (!err) {
200 struct fuse_inode *fi = get_fuse_inode(inode); 200 struct fuse_inode *fi = get_fuse_inode(inode);
201 if (outarg.nodeid != get_node_id(inode)) { 201 if (outarg.nodeid != get_node_id(inode)) {
202 fuse_send_forget(fc, forget_req, 202 fuse_queue_forget(fc, forget, outarg.nodeid, 1);
203 outarg.nodeid, 1);
204 return 0; 203 return 0;
205 } 204 }
206 spin_lock(&fc->lock); 205 spin_lock(&fc->lock);
207 fi->nlookup++; 206 fi->nlookup++;
208 spin_unlock(&fc->lock); 207 spin_unlock(&fc->lock);
209 } 208 }
210 fuse_put_request(fc, forget_req); 209 kfree(forget);
211 if (err || (outarg.attr.mode ^ inode->i_mode) & S_IFMT) 210 if (err || (outarg.attr.mode ^ inode->i_mode) & S_IFMT)
212 return 0; 211 return 0;
213 212
@@ -259,7 +258,7 @@ int fuse_lookup_name(struct super_block *sb, u64 nodeid, struct qstr *name,
259{ 258{
260 struct fuse_conn *fc = get_fuse_conn_super(sb); 259 struct fuse_conn *fc = get_fuse_conn_super(sb);
261 struct fuse_req *req; 260 struct fuse_req *req;
262 struct fuse_req *forget_req; 261 struct fuse_forget_link *forget;
263 u64 attr_version; 262 u64 attr_version;
264 int err; 263 int err;
265 264
@@ -273,9 +272,9 @@ int fuse_lookup_name(struct super_block *sb, u64 nodeid, struct qstr *name,
273 if (IS_ERR(req)) 272 if (IS_ERR(req))
274 goto out; 273 goto out;
275 274
276 forget_req = fuse_get_req(fc); 275 forget = fuse_alloc_forget();
277 err = PTR_ERR(forget_req); 276 err = -ENOMEM;
278 if (IS_ERR(forget_req)) { 277 if (!forget) {
279 fuse_put_request(fc, req); 278 fuse_put_request(fc, req);
280 goto out; 279 goto out;
281 } 280 }
@@ -301,13 +300,13 @@ int fuse_lookup_name(struct super_block *sb, u64 nodeid, struct qstr *name,
301 attr_version); 300 attr_version);
302 err = -ENOMEM; 301 err = -ENOMEM;
303 if (!*inode) { 302 if (!*inode) {
304 fuse_send_forget(fc, forget_req, outarg->nodeid, 1); 303 fuse_queue_forget(fc, forget, outarg->nodeid, 1);
305 goto out; 304 goto out;
306 } 305 }
307 err = 0; 306 err = 0;
308 307
309 out_put_forget: 308 out_put_forget:
310 fuse_put_request(fc, forget_req); 309 kfree(forget);
311 out: 310 out:
312 return err; 311 return err;
313} 312}
@@ -374,7 +373,7 @@ static int fuse_create_open(struct inode *dir, struct dentry *entry, int mode,
374 struct inode *inode; 373 struct inode *inode;
375 struct fuse_conn *fc = get_fuse_conn(dir); 374 struct fuse_conn *fc = get_fuse_conn(dir);
376 struct fuse_req *req; 375 struct fuse_req *req;
377 struct fuse_req *forget_req; 376 struct fuse_forget_link *forget;
378 struct fuse_create_in inarg; 377 struct fuse_create_in inarg;
379 struct fuse_open_out outopen; 378 struct fuse_open_out outopen;
380 struct fuse_entry_out outentry; 379 struct fuse_entry_out outentry;
@@ -388,9 +387,9 @@ static int fuse_create_open(struct inode *dir, struct dentry *entry, int mode,
388 if (flags & O_DIRECT) 387 if (flags & O_DIRECT)
389 return -EINVAL; 388 return -EINVAL;
390 389
391 forget_req = fuse_get_req(fc); 390 forget = fuse_alloc_forget();
392 if (IS_ERR(forget_req)) 391 if (!forget)
393 return PTR_ERR(forget_req); 392 return -ENOMEM;
394 393
395 req = fuse_get_req(fc); 394 req = fuse_get_req(fc);
396 err = PTR_ERR(req); 395 err = PTR_ERR(req);
@@ -448,10 +447,10 @@ static int fuse_create_open(struct inode *dir, struct dentry *entry, int mode,
448 if (!inode) { 447 if (!inode) {
449 flags &= ~(O_CREAT | O_EXCL | O_TRUNC); 448 flags &= ~(O_CREAT | O_EXCL | O_TRUNC);
450 fuse_sync_release(ff, flags); 449 fuse_sync_release(ff, flags);
451 fuse_send_forget(fc, forget_req, outentry.nodeid, 1); 450 fuse_queue_forget(fc, forget, outentry.nodeid, 1);
452 return -ENOMEM; 451 return -ENOMEM;
453 } 452 }
454 fuse_put_request(fc, forget_req); 453 kfree(forget);
455 d_instantiate(entry, inode); 454 d_instantiate(entry, inode);
456 fuse_change_entry_timeout(entry, &outentry); 455 fuse_change_entry_timeout(entry, &outentry);
457 fuse_invalidate_attr(dir); 456 fuse_invalidate_attr(dir);
@@ -469,7 +468,7 @@ static int fuse_create_open(struct inode *dir, struct dentry *entry, int mode,
469 out_put_request: 468 out_put_request:
470 fuse_put_request(fc, req); 469 fuse_put_request(fc, req);
471 out_put_forget_req: 470 out_put_forget_req:
472 fuse_put_request(fc, forget_req); 471 kfree(forget);
473 return err; 472 return err;
474} 473}
475 474
@@ -483,12 +482,12 @@ static int create_new_entry(struct fuse_conn *fc, struct fuse_req *req,
483 struct fuse_entry_out outarg; 482 struct fuse_entry_out outarg;
484 struct inode *inode; 483 struct inode *inode;
485 int err; 484 int err;
486 struct fuse_req *forget_req; 485 struct fuse_forget_link *forget;
487 486
488 forget_req = fuse_get_req(fc); 487 forget = fuse_alloc_forget();
489 if (IS_ERR(forget_req)) { 488 if (!forget) {
490 fuse_put_request(fc, req); 489 fuse_put_request(fc, req);
491 return PTR_ERR(forget_req); 490 return -ENOMEM;
492 } 491 }
493 492
494 memset(&outarg, 0, sizeof(outarg)); 493 memset(&outarg, 0, sizeof(outarg));
@@ -515,10 +514,10 @@ static int create_new_entry(struct fuse_conn *fc, struct fuse_req *req,
515 inode = fuse_iget(dir->i_sb, outarg.nodeid, outarg.generation, 514 inode = fuse_iget(dir->i_sb, outarg.nodeid, outarg.generation,
516 &outarg.attr, entry_attr_timeout(&outarg), 0); 515 &outarg.attr, entry_attr_timeout(&outarg), 0);
517 if (!inode) { 516 if (!inode) {
518 fuse_send_forget(fc, forget_req, outarg.nodeid, 1); 517 fuse_queue_forget(fc, forget, outarg.nodeid, 1);
519 return -ENOMEM; 518 return -ENOMEM;
520 } 519 }
521 fuse_put_request(fc, forget_req); 520 kfree(forget);
522 521
523 if (S_ISDIR(inode->i_mode)) { 522 if (S_ISDIR(inode->i_mode)) {
524 struct dentry *alias; 523 struct dentry *alias;
@@ -541,7 +540,7 @@ static int create_new_entry(struct fuse_conn *fc, struct fuse_req *req,
541 return 0; 540 return 0;
542 541
543 out_put_forget_req: 542 out_put_forget_req:
544 fuse_put_request(fc, forget_req); 543 kfree(forget);
545 return err; 544 return err;
546} 545}
547 546