aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/xen/gntdev.c
diff options
context:
space:
mode:
authorDaniel De Graaf <dgdegra@tycho.nsa.gov>2011-03-09 18:07:34 -0500
committerKonrad Rzeszutek Wilk <konrad.wilk@oracle.com>2011-03-16 10:05:36 -0400
commitca47ceaa2c407bbddd395c1807b616042365bd65 (patch)
tree0af54829ad78f6f43cc090299384c294f7739603 /drivers/xen/gntdev.c
parentb6f3067985f12d514187059fb10fe3c877f87cb2 (diff)
xen-gntdev: Use ballooned pages for grant mappings
Grant mappings cause the PFN<->MFN mapping to be lost on the pages used for the mapping. Instead of leaking memory, use pages that have already been ballooned out and so have no valid mapping. This removes the need for the bad-page leak workaround as pages are repopulated by the balloon driver. Acked-by: Ian Campbell <ian.campbell@citrix.com> Signed-off-by: Daniel De Graaf <dgdegra@tycho.nsa.gov> Signed-off-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
Diffstat (limited to 'drivers/xen/gntdev.c')
-rw-r--r--drivers/xen/gntdev.c38
1 files changed, 5 insertions, 33 deletions
diff --git a/drivers/xen/gntdev.c b/drivers/xen/gntdev.c
index d96d311b858e..017ce600fbc6 100644
--- a/drivers/xen/gntdev.c
+++ b/drivers/xen/gntdev.c
@@ -36,6 +36,7 @@
36 36
37#include <xen/xen.h> 37#include <xen/xen.h>
38#include <xen/grant_table.h> 38#include <xen/grant_table.h>
39#include <xen/balloon.h>
39#include <xen/gntdev.h> 40#include <xen/gntdev.h>
40#include <xen/events.h> 41#include <xen/events.h>
41#include <asm/xen/hypervisor.h> 42#include <asm/xen/hypervisor.h>
@@ -122,10 +123,10 @@ static struct grant_map *gntdev_alloc_map(struct gntdev_priv *priv, int count)
122 NULL == add->pages) 123 NULL == add->pages)
123 goto err; 124 goto err;
124 125
126 if (alloc_xenballooned_pages(count, add->pages))
127 goto err;
128
125 for (i = 0; i < count; i++) { 129 for (i = 0; i < count; i++) {
126 add->pages[i] = alloc_page(GFP_KERNEL | __GFP_HIGHMEM);
127 if (add->pages[i] == NULL)
128 goto err;
129 add->map_ops[i].handle = -1; 130 add->map_ops[i].handle = -1;
130 add->unmap_ops[i].handle = -1; 131 add->unmap_ops[i].handle = -1;
131 } 132 }
@@ -137,11 +138,6 @@ static struct grant_map *gntdev_alloc_map(struct gntdev_priv *priv, int count)
137 return add; 138 return add;
138 139
139err: 140err:
140 if (add->pages)
141 for (i = 0; i < count; i++) {
142 if (add->pages[i])
143 __free_page(add->pages[i]);
144 }
145 kfree(add->pages); 141 kfree(add->pages);
146 kfree(add->grants); 142 kfree(add->grants);
147 kfree(add->map_ops); 143 kfree(add->map_ops);
@@ -184,8 +180,6 @@ static struct grant_map *gntdev_find_map_index(struct gntdev_priv *priv,
184 180
185static void gntdev_put_map(struct grant_map *map) 181static void gntdev_put_map(struct grant_map *map)
186{ 182{
187 int i;
188
189 if (!map) 183 if (!map)
190 return; 184 return;
191 185
@@ -202,29 +196,7 @@ static void gntdev_put_map(struct grant_map *map)
202 if (!use_ptemod) 196 if (!use_ptemod)
203 unmap_grant_pages(map, 0, map->count); 197 unmap_grant_pages(map, 0, map->count);
204 198
205 for (i = 0; i < map->count; i++) { 199 free_xenballooned_pages(map->count, map->pages);
206 uint32_t check, *tmp;
207 if (!map->pages[i])
208 continue;
209 /* XXX When unmapping in an HVM domain, Xen will
210 * sometimes end up mapping the GFN to an invalid MFN.
211 * In this case, writes will be discarded and reads will
212 * return all 0xFF bytes. Leak these unusable GFNs
213 * until Xen supports fixing their p2m mapping.
214 *
215 * Confirmed present in Xen 4.1-RC3 with HVM source
216 */
217 tmp = kmap(map->pages[i]);
218 *tmp = 0xdeaddead;
219 mb();
220 check = *tmp;
221 kunmap(map->pages[i]);
222 if (check == 0xdeaddead)
223 __free_page(map->pages[i]);
224 else
225 pr_debug("Discard page %d=%ld\n", i,
226 page_to_pfn(map->pages[i]));
227 }
228 } 200 }
229 kfree(map->pages); 201 kfree(map->pages);
230 kfree(map->grants); 202 kfree(map->grants);