xen/arm: introduce domain on Static Allocation

Static Allocation refers to system or sub-system(domains) for which memory
areas are pre-defined by configuration using physical address ranges.

Those pre-defined memory, -- Static Memory, as parts of RAM reserved in the
beginning, shall never go to heap allocator or boot allocator for any use.

Memory can be statically allocated to a domain using the property "xen,static-
mem" defined in the domain configuration. The number of cells for the address
and the size must be defined using respectively the properties
"#xen,static-mem-address-cells" and "#xen,static-mem-size-cells".

The property 'memory' is still needed and should match the amount of memory
given to the guest. Currently, it either comes from static memory or lets Xen
allocate from heap. *Mixing* is not supported.

The static memory will be mapped in the guest at the usual guest memory
addresses (GUEST_RAM0_BASE, GUEST_RAM1_BASE) defined by
xen/include/public/arch-arm.h.

This patch introduces this new `xen,static-mem` feature, and also documents
and parses this new attribute at boot time.

This patch also introduces a new field "bool xen_domain" in "struct membank"
to tell whether the memory bank is reserved as the whole hardware resource,
or bind to a xen domain node, through "xen,static-mem"

Signed-off-by: Penny Zheng <penny.zheng@arm.com>
Reviewed-by: Stefano Stabellini <sstabellini@kernel.org>
This commit is contained in:
Penny Zheng authored and Stefano Stabellini committed 2021-09-13 14:10:14 -07:00
1 parent 904ba3ce2e
commit 41c031ff43
3 files changed
+71 -2

No files matched your search

+42
View File
@@ -268,3 +268,45 @@ The DTB fragment is loaded at 0xc000000 in the example above. It should
follow the convention explained in docs/misc/arm/passthrough.txt. The
DTB fragment will be added to the guest device tree, so that the guest
kernel will be able to discover the device.
Static Allocation
=============
Static Allocation refers to system or sub-system(domains) for which memory
areas are pre-defined by configuration using physical address ranges.
Memory can be statically allocated to a domain using the property "xen,static-
mem" defined in the domain configuration. The number of cells for the address
and the size must be defined using respectively the properties
"#xen,static-mem-address-cells" and "#xen,static-mem-size-cells".
The property 'memory' is still needed and should match the amount of memory
given to the guest. Currently, it either comes from static memory or lets Xen
allocate from heap. *Mixing* is not supported.
The static memory will be mapped in the guest at the usual guest memory
addresses (GUEST_RAM0_BASE, GUEST_RAM1_BASE) defined by
xen/include/public/arch-arm.h.
Below is an example on how to specify the static memory region in the
device-tree:
/ {
chosen {
domU1 {
compatible = "xen,domain";
#address-cells = <0x2>;
#size-cells = <0x2>;
cpus = <2>;
memory = <0x0 0x80000>;
#xen,static-mem-address-cells = <0x1>;
#xen,static-mem-size-cells = <0x1>;
xen,static-mem = <0x30000000 0x20000000>;
...
};
};
};
This will reserve a 512MB region starting at the host physical address
0x30000000 to be exclusively used by DomU1.
+28 -2
View File
@@ -66,7 +66,7 @@ void __init device_tree_get_reg(const __be32 **cell, u32 address_cells,
static int __init device_tree_get_meminfo(const void *fdt, int node,
const char *prop_name,
u32 address_cells, u32 size_cells,
void *data)
void *data, bool xen_domain)
{
const struct fdt_property *prop;
unsigned int i, banks;
@@ -97,6 +97,7 @@ static int __init device_tree_get_meminfo(const void *fdt, int node,
continue;
mem->bank[mem->nr_banks].start = start;
mem->bank[mem->nr_banks].size = size;
mem->bank[mem->nr_banks].xen_domain = xen_domain;
mem->nr_banks++;
}
@@ -185,7 +186,8 @@ static int __init process_memory_node(const void *fdt, int node,
u32 address_cells, u32 size_cells,
void *data)
{
return device_tree_get_meminfo(fdt, node, "reg", address_cells, size_cells, data);
return device_tree_get_meminfo(fdt, node, "reg", address_cells, size_cells,
data, false);
}
static int __init process_reserved_memory_node(const void *fdt, int node,
@@ -339,6 +341,28 @@ static void __init process_chosen_node(const void *fdt, int node,
add_boot_module(BOOTMOD_RAMDISK, start, end-start, false);
}
static int __init process_domain_node(const void *fdt, int node,
const char *name,
u32 address_cells, u32 size_cells)
{
const struct fdt_property *prop;
printk("Checking for \"xen,static-mem\" in domain node\n");
prop = fdt_get_property(fdt, node, "xen,static-mem", NULL);
if ( !prop )
/* No "xen,static-mem" present. */
return 0;
address_cells = device_tree_get_u32(fdt, node,
"#xen,static-mem-address-cells", 0);
size_cells = device_tree_get_u32(fdt, node,
"#xen,static-mem-size-cells", 0);
return device_tree_get_meminfo(fdt, node, "xen,static-mem", address_cells,
size_cells, &bootinfo.reserved_mem, true);
}
static int __init early_scan_node(const void *fdt,
int node, const char *name, int depth,
u32 address_cells, u32 size_cells,
@@ -357,6 +381,8 @@ static int __init early_scan_node(const void *fdt,
process_multiboot_node(fdt, node, name, address_cells, size_cells);
else if ( depth == 1 && device_tree_node_matches(fdt, node, "chosen") )
process_chosen_node(fdt, node, name, address_cells, size_cells);
else if ( depth == 2 && device_tree_node_compatible(fdt, node, "xen,domain") )
rc = process_domain_node(fdt, node, name, address_cells, size_cells);
if ( rc < 0 )
printk("fdt: node `%s': parsing failed\n", name);
+1
View File
@@ -24,6 +24,7 @@ typedef enum {
struct membank {
paddr_t start;
paddr_t size;
bool xen_domain; /* whether the memory bank is bound to a Xen domain. */
};
struct meminfo {
Reference in new issue
Block a user
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.