diff options
author | David Vrabel <david.vrabel@citrix.com> | 2015-01-05 09:13:41 -0500 |
---|---|---|
committer | David Vrabel <david.vrabel@citrix.com> | 2015-01-28 09:03:10 -0500 |
commit | 853d0289340026b30f93fd0e768340221d4e605c (patch) | |
tree | 17d52ad1d7ae43007d8b664bbdba2a50db7dbb81 /drivers/xen | |
parent | d8ac3dd41aea245f65465449efc35dd3ac71e91d (diff) |
xen/grant-table: pre-populate kernel unmap ops for xen_gnttab_unmap_refs()
When unmapping grants, instead of converting the kernel map ops to
unmap ops on the fly, pre-populate the set of unmap ops.
This allows the grant unmap for the kernel mappings to be trivially
batched in the future.
Signed-off-by: David Vrabel <david.vrabel@citrix.com>
Reviewed-by: Stefano Stabellini <stefano.stabellini@eu.citrix.com>
Diffstat (limited to 'drivers/xen')
-rw-r--r-- | drivers/xen/gntdev.c | 20 | ||||
-rw-r--r-- | drivers/xen/grant-table.c | 4 |
2 files changed, 16 insertions, 8 deletions
diff --git a/drivers/xen/gntdev.c b/drivers/xen/gntdev.c index 073b4a19a8b0..6444172f2842 100644 --- a/drivers/xen/gntdev.c +++ b/drivers/xen/gntdev.c | |||
@@ -91,6 +91,7 @@ struct grant_map { | |||
91 | struct gnttab_map_grant_ref *map_ops; | 91 | struct gnttab_map_grant_ref *map_ops; |
92 | struct gnttab_unmap_grant_ref *unmap_ops; | 92 | struct gnttab_unmap_grant_ref *unmap_ops; |
93 | struct gnttab_map_grant_ref *kmap_ops; | 93 | struct gnttab_map_grant_ref *kmap_ops; |
94 | struct gnttab_unmap_grant_ref *kunmap_ops; | ||
94 | struct page **pages; | 95 | struct page **pages; |
95 | }; | 96 | }; |
96 | 97 | ||
@@ -124,6 +125,7 @@ static void gntdev_free_map(struct grant_map *map) | |||
124 | kfree(map->map_ops); | 125 | kfree(map->map_ops); |
125 | kfree(map->unmap_ops); | 126 | kfree(map->unmap_ops); |
126 | kfree(map->kmap_ops); | 127 | kfree(map->kmap_ops); |
128 | kfree(map->kunmap_ops); | ||
127 | kfree(map); | 129 | kfree(map); |
128 | } | 130 | } |
129 | 131 | ||
@@ -140,11 +142,13 @@ static struct grant_map *gntdev_alloc_map(struct gntdev_priv *priv, int count) | |||
140 | add->map_ops = kcalloc(count, sizeof(add->map_ops[0]), GFP_KERNEL); | 142 | add->map_ops = kcalloc(count, sizeof(add->map_ops[0]), GFP_KERNEL); |
141 | add->unmap_ops = kcalloc(count, sizeof(add->unmap_ops[0]), GFP_KERNEL); | 143 | add->unmap_ops = kcalloc(count, sizeof(add->unmap_ops[0]), GFP_KERNEL); |
142 | add->kmap_ops = kcalloc(count, sizeof(add->kmap_ops[0]), GFP_KERNEL); | 144 | add->kmap_ops = kcalloc(count, sizeof(add->kmap_ops[0]), GFP_KERNEL); |
145 | add->kunmap_ops = kcalloc(count, sizeof(add->kunmap_ops[0]), GFP_KERNEL); | ||
143 | add->pages = kcalloc(count, sizeof(add->pages[0]), GFP_KERNEL); | 146 | add->pages = kcalloc(count, sizeof(add->pages[0]), GFP_KERNEL); |
144 | if (NULL == add->grants || | 147 | if (NULL == add->grants || |
145 | NULL == add->map_ops || | 148 | NULL == add->map_ops || |
146 | NULL == add->unmap_ops || | 149 | NULL == add->unmap_ops || |
147 | NULL == add->kmap_ops || | 150 | NULL == add->kmap_ops || |
151 | NULL == add->kunmap_ops || | ||
148 | NULL == add->pages) | 152 | NULL == add->pages) |
149 | goto err; | 153 | goto err; |
150 | 154 | ||
@@ -155,6 +159,7 @@ static struct grant_map *gntdev_alloc_map(struct gntdev_priv *priv, int count) | |||
155 | add->map_ops[i].handle = -1; | 159 | add->map_ops[i].handle = -1; |
156 | add->unmap_ops[i].handle = -1; | 160 | add->unmap_ops[i].handle = -1; |
157 | add->kmap_ops[i].handle = -1; | 161 | add->kmap_ops[i].handle = -1; |
162 | add->kunmap_ops[i].handle = -1; | ||
158 | } | 163 | } |
159 | 164 | ||
160 | add->index = 0; | 165 | add->index = 0; |
@@ -280,6 +285,8 @@ static int map_grant_pages(struct grant_map *map) | |||
280 | map->flags | GNTMAP_host_map, | 285 | map->flags | GNTMAP_host_map, |
281 | map->grants[i].ref, | 286 | map->grants[i].ref, |
282 | map->grants[i].domid); | 287 | map->grants[i].domid); |
288 | gnttab_set_unmap_op(&map->kunmap_ops[i], address, | ||
289 | map->flags | GNTMAP_host_map, -1); | ||
283 | } | 290 | } |
284 | } | 291 | } |
285 | 292 | ||
@@ -290,13 +297,14 @@ static int map_grant_pages(struct grant_map *map) | |||
290 | return err; | 297 | return err; |
291 | 298 | ||
292 | for (i = 0; i < map->count; i++) { | 299 | for (i = 0; i < map->count; i++) { |
293 | if (map->map_ops[i].status) | 300 | if (map->map_ops[i].status) { |
294 | err = -EINVAL; | 301 | err = -EINVAL; |
295 | else { | 302 | continue; |
296 | BUG_ON(map->map_ops[i].handle == -1); | ||
297 | map->unmap_ops[i].handle = map->map_ops[i].handle; | ||
298 | pr_debug("map handle=%d\n", map->map_ops[i].handle); | ||
299 | } | 303 | } |
304 | |||
305 | map->unmap_ops[i].handle = map->map_ops[i].handle; | ||
306 | if (use_ptemod) | ||
307 | map->kunmap_ops[i].handle = map->kmap_ops[i].handle; | ||
300 | } | 308 | } |
301 | return err; | 309 | return err; |
302 | } | 310 | } |
@@ -316,7 +324,7 @@ static int __unmap_grant_pages(struct grant_map *map, int offset, int pages) | |||
316 | } | 324 | } |
317 | 325 | ||
318 | err = gnttab_unmap_refs(map->unmap_ops + offset, | 326 | err = gnttab_unmap_refs(map->unmap_ops + offset, |
319 | use_ptemod ? map->kmap_ops + offset : NULL, map->pages + offset, | 327 | use_ptemod ? map->kunmap_ops + offset : NULL, map->pages + offset, |
320 | pages); | 328 | pages); |
321 | if (err) | 329 | if (err) |
322 | return err; | 330 | return err; |
diff --git a/drivers/xen/grant-table.c b/drivers/xen/grant-table.c index 7786291ba229..999d7abdbcec 100644 --- a/drivers/xen/grant-table.c +++ b/drivers/xen/grant-table.c | |||
@@ -738,7 +738,7 @@ int gnttab_map_refs(struct gnttab_map_grant_ref *map_ops, | |||
738 | EXPORT_SYMBOL_GPL(gnttab_map_refs); | 738 | EXPORT_SYMBOL_GPL(gnttab_map_refs); |
739 | 739 | ||
740 | int gnttab_unmap_refs(struct gnttab_unmap_grant_ref *unmap_ops, | 740 | int gnttab_unmap_refs(struct gnttab_unmap_grant_ref *unmap_ops, |
741 | struct gnttab_map_grant_ref *kmap_ops, | 741 | struct gnttab_unmap_grant_ref *kunmap_ops, |
742 | struct page **pages, unsigned int count) | 742 | struct page **pages, unsigned int count) |
743 | { | 743 | { |
744 | int ret; | 744 | int ret; |
@@ -747,7 +747,7 @@ int gnttab_unmap_refs(struct gnttab_unmap_grant_ref *unmap_ops, | |||
747 | if (ret) | 747 | if (ret) |
748 | return ret; | 748 | return ret; |
749 | 749 | ||
750 | return clear_foreign_p2m_mapping(unmap_ops, kmap_ops, pages, count); | 750 | return clear_foreign_p2m_mapping(unmap_ops, kunmap_ops, pages, count); |
751 | } | 751 | } |
752 | EXPORT_SYMBOL_GPL(gnttab_unmap_refs); | 752 | EXPORT_SYMBOL_GPL(gnttab_unmap_refs); |
753 | 753 | ||