mirror of
https://github.com/xen-project/xen.git
synced 2026-10-28 02:01:24 +01:00
[TPM] back: Allocate pages for foreign mappings individually rather than contiguously.
Signed-off-by: Keir Fraser <keir@xensource.com>
This commit is contained in:
1 parent
10ac5cd887
commit
f58fdb8d02
3 files changed
+43
-16
No files matched your search
@@ -46,11 +46,10 @@ typedef struct tpmif_st {
|
||||
atomic_t refcnt;
|
||||
|
||||
struct backend_info *bi;
|
||||
unsigned long mmap_vstart;
|
||||
|
||||
grant_handle_t shmem_handle;
|
||||
grant_ref_t shmem_ref;
|
||||
struct page *pagerange;
|
||||
struct page **mmap_pages;
|
||||
|
||||
char devname[20];
|
||||
} tpmif_t;
|
||||
@@ -80,6 +79,9 @@ int vtpm_release_packets(tpmif_t * tpmif, int send_msgs);
|
||||
|
||||
extern int num_frontends;
|
||||
|
||||
#define MMAP_VADDR(t,_req) ((t)->mmap_vstart + ((_req) * PAGE_SIZE))
|
||||
static inline unsigned long idx_to_kaddr(tpmif_t *t, unsigned int idx)
|
||||
{
|
||||
return (unsigned long)pfn_to_kaddr(page_to_pfn(t->mmap_pages[idx]));
|
||||
}
|
||||
|
||||
#endif /* __TPMIF__BACKEND__COMMON_H__ */
|
||||
@@ -23,10 +23,11 @@ LIST_HEAD(tpmif_list);
|
||||
static tpmif_t *alloc_tpmif(domid_t domid, struct backend_info *bi)
|
||||
{
|
||||
tpmif_t *tpmif;
|
||||
int i;
|
||||
|
||||
tpmif = kmem_cache_alloc(tpmif_cachep, GFP_KERNEL);
|
||||
if (!tpmif)
|
||||
return ERR_PTR(-ENOMEM);
|
||||
goto out_of_memory;
|
||||
|
||||
memset(tpmif, 0, sizeof (*tpmif));
|
||||
tpmif->domid = domid;
|
||||
@@ -35,22 +36,46 @@ static tpmif_t *alloc_tpmif(domid_t domid, struct backend_info *bi)
|
||||
snprintf(tpmif->devname, sizeof(tpmif->devname), "tpmif%d", domid);
|
||||
atomic_set(&tpmif->refcnt, 1);
|
||||
|
||||
tpmif->pagerange = balloon_alloc_empty_page_range(TPMIF_TX_RING_SIZE);
|
||||
BUG_ON(tpmif->pagerange == NULL);
|
||||
tpmif->mmap_vstart = (unsigned long)pfn_to_kaddr(
|
||||
page_to_pfn(tpmif->pagerange));
|
||||
tpmif->mmap_pages = kmalloc(sizeof(tpmif->mmap_pages[0])
|
||||
* TPMIF_TX_RING_SIZE, GFP_KERNEL);
|
||||
if (tpmif->mmap_pages == NULL)
|
||||
goto out_of_memory;
|
||||
|
||||
for (i = 0; i < TPMIF_TX_RING_SIZE; i++) {
|
||||
tpmif->mmap_pages[i] = balloon_alloc_empty_page();
|
||||
if (tpmif->mmap_pages[i] == NULL) {
|
||||
while (--i >= 0)
|
||||
balloon_free_empty_page(tpmif->mmap_pages[i]);
|
||||
goto out_of_memory;
|
||||
}
|
||||
}
|
||||
|
||||
list_add(&tpmif->tpmif_list, &tpmif_list);
|
||||
num_frontends++;
|
||||
|
||||
return tpmif;
|
||||
|
||||
out_of_memory:
|
||||
if (tpmif != NULL) {
|
||||
kfree(tpmif->mmap_pages);
|
||||
kmem_cache_free(tpmif_cachep, tpmif);
|
||||
}
|
||||
printk("%s: out of memory\n", __FUNCTION__);
|
||||
return ERR_PTR(-ENOMEM);
|
||||
}
|
||||
|
||||
static void free_tpmif(tpmif_t * tpmif)
|
||||
{
|
||||
int i;
|
||||
|
||||
num_frontends--;
|
||||
|
||||
list_del(&tpmif->tpmif_list);
|
||||
balloon_dealloc_empty_page_range(tpmif->pagerange, TPMIF_TX_RING_SIZE);
|
||||
|
||||
for (i = 0; i < TPMIF_TX_RING_SIZE; i++)
|
||||
balloon_free_empty_page(tpmif->mmap_pages[i]);
|
||||
kfree(tpmif->mmap_pages);
|
||||
|
||||
kmem_cache_free(tpmif_cachep, tpmif);
|
||||
}
|
||||
|
||||
|
||||
@@ -253,7 +253,7 @@ int _packet_write(struct packet *pak,
|
||||
return 0;
|
||||
}
|
||||
|
||||
gnttab_set_map_op(&map_op, MMAP_VADDR(tpmif, i),
|
||||
gnttab_set_map_op(&map_op, idx_to_kaddr(tpmif, i),
|
||||
GNTMAP_host_map, tx->ref, tpmif->domid);
|
||||
|
||||
if (unlikely(HYPERVISOR_grant_table_op(GNTTABOP_map_grant_ref,
|
||||
@@ -270,7 +270,7 @@ int _packet_write(struct packet *pak,
|
||||
|
||||
tocopy = min_t(size_t, size - offset, PAGE_SIZE);
|
||||
|
||||
if (copy_from_buffer((void *)(MMAP_VADDR(tpmif, i) |
|
||||
if (copy_from_buffer((void *)(idx_to_kaddr(tpmif, i) |
|
||||
(tx->addr & ~PAGE_MASK)),
|
||||
&data[offset], tocopy, isuserbuffer)) {
|
||||
tpmif_put(tpmif);
|
||||
@@ -278,7 +278,7 @@ int _packet_write(struct packet *pak,
|
||||
}
|
||||
tx->size = tocopy;
|
||||
|
||||
gnttab_set_unmap_op(&unmap_op, MMAP_VADDR(tpmif, i),
|
||||
gnttab_set_unmap_op(&unmap_op, idx_to_kaddr(tpmif, i),
|
||||
GNTMAP_host_map, handle);
|
||||
|
||||
if (unlikely
|
||||
@@ -391,7 +391,7 @@ static int packet_read_shmem(struct packet *pak,
|
||||
|
||||
tx = &tpmif->tx->ring[i].req;
|
||||
|
||||
gnttab_set_map_op(&map_op, MMAP_VADDR(tpmif, i),
|
||||
gnttab_set_map_op(&map_op, idx_to_kaddr(tpmif, i),
|
||||
GNTMAP_host_map, tx->ref, tpmif->domid);
|
||||
|
||||
if (unlikely(HYPERVISOR_grant_table_op(GNTTABOP_map_grant_ref,
|
||||
@@ -414,10 +414,10 @@ static int packet_read_shmem(struct packet *pak,
|
||||
}
|
||||
|
||||
DPRINTK("Copying from mapped memory at %08lx\n",
|
||||
(unsigned long)(MMAP_VADDR(tpmif, i) |
|
||||
(unsigned long)(idx_to_kaddr(tpmif, i) |
|
||||
(tx->addr & ~PAGE_MASK)));
|
||||
|
||||
src = (void *)(MMAP_VADDR(tpmif, i) |
|
||||
src = (void *)(idx_to_kaddr(tpmif, i) |
|
||||
((tx->addr & ~PAGE_MASK) + pg_offset));
|
||||
if (copy_to_buffer(&buffer[offset],
|
||||
src, to_copy, isuserbuffer)) {
|
||||
@@ -428,7 +428,7 @@ static int packet_read_shmem(struct packet *pak,
|
||||
tpmif->domid, buffer[offset], buffer[offset + 1],
|
||||
buffer[offset + 2], buffer[offset + 3]);
|
||||
|
||||
gnttab_set_unmap_op(&unmap_op, MMAP_VADDR(tpmif, i),
|
||||
gnttab_set_unmap_op(&unmap_op, idx_to_kaddr(tpmif, i),
|
||||
GNTMAP_host_map, handle);
|
||||
|
||||
if (unlikely
|
||||
|
||||