提交 83f3c251 编写于 作者: A Avi Kivity

memory: add address_space_destroy()

Since address spaces can be created dynamically by device hotplug, they
can also be destroyed dynamically.
Signed-off-by: NAvi Kivity <avi@redhat.com>
上级 b90600ee
......@@ -3234,6 +3234,16 @@ void address_space_init_dispatch(AddressSpace *as)
memory_listener_register(&d->listener, as);
}
void address_space_destroy_dispatch(AddressSpace *as)
{
AddressSpaceDispatch *d = as->dispatch;
memory_listener_unregister(&d->listener);
destroy_l2_mapping(&d->phys_map, P_L2_LEVELS - 1);
g_free(d);
as->dispatch = NULL;
}
static void memory_map_init(void)
{
system_memory = g_malloc(sizeof(*system_memory));
......
......@@ -41,6 +41,7 @@ struct AddressSpaceDispatch {
};
void address_space_init_dispatch(AddressSpace *as);
void address_space_destroy_dispatch(AddressSpace *as);
ram_addr_t qemu_ram_alloc_from_ptr(ram_addr_t size, void *host,
MemoryRegion *mr);
......
......@@ -564,8 +564,10 @@ static FlatView generate_memory_topology(MemoryRegion *mr)
flatview_init(&view);
render_memory_region(&view, mr, int128_zero(),
addrrange_make(int128_zero(), int128_2_64()), false);
if (mr) {
render_memory_region(&view, mr, int128_zero(),
addrrange_make(int128_zero(), int128_2_64()), false);
}
flatview_simplify(&view);
return view;
......@@ -1542,6 +1544,18 @@ void address_space_init(AddressSpace *as, MemoryRegion *root)
address_space_init_dispatch(as);
}
void address_space_destroy(AddressSpace *as)
{
/* Flush out anything from MemoryListeners listening in on this */
memory_region_transaction_begin();
as->root = NULL;
memory_region_transaction_commit();
QTAILQ_REMOVE(&address_spaces, as, address_spaces_link);
address_space_destroy_dispatch(as);
flatview_destroy(as->current_map);
g_free(as->current_map);
}
uint64_t io_mem_read(MemoryRegion *mr, target_phys_addr_t addr, unsigned size)
{
return memory_region_dispatch_read(mr, addr, size);
......
......@@ -804,6 +804,18 @@ void mtree_info(fprintf_function mon_printf, void *f);
*/
void address_space_init(AddressSpace *as, MemoryRegion *root);
/**
* address_space_destroy: destroy an address space
*
* Releases all resources associated with an address space. After an address space
* is destroyed, its root memory region (given by address_space_init()) may be destroyed
* as well.
*
* @as: address space to be destroyed
*/
void address_space_destroy(AddressSpace *as);
/**
* address_space_rw: read from or write to an address space.
*
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册