diff options
author | Yan, Zheng <zyan@redhat.com> | 2014-09-16 05:50:45 -0400 |
---|---|---|
committer | Sage Weil <sage@redhat.com> | 2014-10-14 15:56:48 -0400 |
commit | e4339d28f640a7c0d92903bcf389a2dfa281270d (patch) | |
tree | 428c172af1081d29613732cdcf7801f958be358f /net/ceph | |
parent | 0abb43dcacb52145aa265f82c914375d59dfe2da (diff) |
libceph: reference counting pagelist
this allow pagelist to present data that may be sent multiple times.
Signed-off-by: Yan, Zheng <zyan@redhat.com>
Reviewed-by: Sage Weil <sage@redhat.com>
Diffstat (limited to 'net/ceph')
-rw-r--r-- | net/ceph/messenger.c | 4 | ||||
-rw-r--r-- | net/ceph/pagelist.c | 7 |
2 files changed, 6 insertions, 5 deletions
diff --git a/net/ceph/messenger.c b/net/ceph/messenger.c index e7d94113f2d6..9764c771cfb1 100644 --- a/net/ceph/messenger.c +++ b/net/ceph/messenger.c | |||
@@ -3071,10 +3071,8 @@ static void ceph_msg_data_destroy(struct ceph_msg_data *data) | |||
3071 | return; | 3071 | return; |
3072 | 3072 | ||
3073 | WARN_ON(!list_empty(&data->links)); | 3073 | WARN_ON(!list_empty(&data->links)); |
3074 | if (data->type == CEPH_MSG_DATA_PAGELIST) { | 3074 | if (data->type == CEPH_MSG_DATA_PAGELIST) |
3075 | ceph_pagelist_release(data->pagelist); | 3075 | ceph_pagelist_release(data->pagelist); |
3076 | kfree(data->pagelist); | ||
3077 | } | ||
3078 | kmem_cache_free(ceph_msg_data_cache, data); | 3076 | kmem_cache_free(ceph_msg_data_cache, data); |
3079 | } | 3077 | } |
3080 | 3078 | ||
diff --git a/net/ceph/pagelist.c b/net/ceph/pagelist.c index 92866bebb65f..c7c220a736e5 100644 --- a/net/ceph/pagelist.c +++ b/net/ceph/pagelist.c | |||
@@ -1,5 +1,6 @@ | |||
1 | #include <linux/module.h> | 1 | #include <linux/module.h> |
2 | #include <linux/gfp.h> | 2 | #include <linux/gfp.h> |
3 | #include <linux/slab.h> | ||
3 | #include <linux/pagemap.h> | 4 | #include <linux/pagemap.h> |
4 | #include <linux/highmem.h> | 5 | #include <linux/highmem.h> |
5 | #include <linux/ceph/pagelist.h> | 6 | #include <linux/ceph/pagelist.h> |
@@ -13,8 +14,10 @@ static void ceph_pagelist_unmap_tail(struct ceph_pagelist *pl) | |||
13 | } | 14 | } |
14 | } | 15 | } |
15 | 16 | ||
16 | int ceph_pagelist_release(struct ceph_pagelist *pl) | 17 | void ceph_pagelist_release(struct ceph_pagelist *pl) |
17 | { | 18 | { |
19 | if (!atomic_dec_and_test(&pl->refcnt)) | ||
20 | return; | ||
18 | ceph_pagelist_unmap_tail(pl); | 21 | ceph_pagelist_unmap_tail(pl); |
19 | while (!list_empty(&pl->head)) { | 22 | while (!list_empty(&pl->head)) { |
20 | struct page *page = list_first_entry(&pl->head, struct page, | 23 | struct page *page = list_first_entry(&pl->head, struct page, |
@@ -23,7 +26,7 @@ int ceph_pagelist_release(struct ceph_pagelist *pl) | |||
23 | __free_page(page); | 26 | __free_page(page); |
24 | } | 27 | } |
25 | ceph_pagelist_free_reserve(pl); | 28 | ceph_pagelist_free_reserve(pl); |
26 | return 0; | 29 | kfree(pl); |
27 | } | 30 | } |
28 | EXPORT_SYMBOL(ceph_pagelist_release); | 31 | EXPORT_SYMBOL(ceph_pagelist_release); |
29 | 32 | ||