* [PATCH 0/2] ARM: Support initrd loading
@ 2013-09-16 15:20 Julien Grall
2013-09-16 15:20 ` [PATCH 1/2] xen/arm: Add support to load initrd in dom0 Julien Grall
2013-09-16 15:20 ` [PATCH 2/2] xen/dts: Support Linux initrd DT bindings Julien Grall
0 siblings, 2 replies; 10+ messages in thread
From: Julien Grall @ 2013-09-16 15:20 UTC (permalink / raw)
To: xen-devel
Cc: patches, Julien Grall, ian.campbell, andre.przywara,
stefano.stabellini
Hi,
This small patch series adds support to load initrd in dom0 for ARM.
It depends on the patch series "Allow Xen to boot with a raw device tree"
(http://www.gossamer-threads.com/lists/xen/devel/297786) and the patch
"xen: arm: rework placement of fdt in initial dom0 memory map"
(http://www.gossamer-threads.com/lists/xen/devel/297844).
Cheers,
Julien Grall (2):
xen/arm: Add support to load initrd in dom0
xen/dts: Support Linux initrd DT bindings
xen/arch/arm/domain_build.c | 98 ++++++++++++++++++++++++++++++++++++++-----
xen/arch/arm/kernel.c | 20 +++++----
xen/arch/arm/kernel.h | 2 +
xen/common/device_tree.c | 25 +++++++++++
4 files changed, 127 insertions(+), 18 deletions(-)
--
1.7.10.4
^ permalink raw reply [flat|nested] 10+ messages in thread
* [PATCH 1/2] xen/arm: Add support to load initrd in dom0
2013-09-16 15:20 [PATCH 0/2] ARM: Support initrd loading Julien Grall
@ 2013-09-16 15:20 ` Julien Grall
2013-09-25 15:15 ` Ian Campbell
2013-09-16 15:20 ` [PATCH 2/2] xen/dts: Support Linux initrd DT bindings Julien Grall
1 sibling, 1 reply; 10+ messages in thread
From: Julien Grall @ 2013-09-16 15:20 UTC (permalink / raw)
To: xen-devel
Cc: patches, Julien Grall, ian.campbell, andre.przywara,
stefano.stabellini
Signed-off-by: Julien Grall <julien.grall@linaro.org>
---
xen/arch/arm/domain_build.c | 98 ++++++++++++++++++++++++++++++++++++++-----
xen/arch/arm/kernel.c | 20 +++++----
xen/arch/arm/kernel.h | 2 +
3 files changed, 102 insertions(+), 18 deletions(-)
diff --git a/xen/arch/arm/domain_build.c b/xen/arch/arm/domain_build.c
index f569e31..f3bb262 100644
--- a/xen/arch/arm/domain_build.c
+++ b/xen/arch/arm/domain_build.c
@@ -163,12 +163,16 @@ static int write_properties(struct domain *d, struct kernel_info *kinfo,
*
* * remember xen,dom0-bootargs if we don't already have
* bootargs (from module #1, above).
- * * remove bootargs, xen,dom0-bootargs and xen,xen-bootargs.
+ * * remove bootargs, xen,dom0-bootargs, xen,xen-bootargs,
+ * linux,initrd-start and linux,initrd-end.
*/
if ( dt_node_path_is_equal(np, "/chosen") )
{
- if ( dt_property_name_is_equal(pp, "xen,xen-bootargs") )
+ if ( dt_property_name_is_equal(pp, "xen,xen-bootargs") ||
+ dt_property_name_is_equal(pp, "linux,initrd-start") ||
+ dt_property_name_is_equal(pp, "linux,initrd-end") )
continue;
+
if ( dt_property_name_is_equal(pp, "xen,dom0-bootargs") )
{
had_dom0_bootargs = 1;
@@ -214,12 +218,22 @@ static int write_properties(struct domain *d, struct kernel_info *kinfo,
strlen(bootargs) + 1);
if ( res )
return res;
- }
- /*
- * XXX should populate /chosen/linux,initrd-{start,end} here if we
- * have module[2]
- */
+ /*
+ * If the bootloader provides an initrd, we must create a placeholder
+ * for the initrd properties. The values will be replaced later.
+ */
+ if ( early_info.modules.module[MOD_INITRD].size )
+ {
+ res = fdt_property_cell(kinfo->fdt, "linux,initrd-start", 0);
+ if ( res )
+ return res;
+
+ res = fdt_property_cell(kinfo->fdt, "linux,initrd-end", 0);
+ if ( res )
+ return res;
+ }
+ }
return 0;
}
@@ -779,6 +793,7 @@ static int prepare_dtb(struct domain *d, struct kernel_info *kinfo)
int new_size;
int ret;
paddr_t end;
+ paddr_t initrd_len;
ASSERT(dt_host && (dt_host->sibling == NULL));
@@ -806,7 +821,8 @@ static int prepare_dtb(struct domain *d, struct kernel_info *kinfo)
goto err;
/* Actual new size */
- new_size = fdt_totalsize(kinfo->fdt);
+ initrd_len = early_info.modules.module[MOD_INITRD].size;
+ new_size = fdt_totalsize(kinfo->fdt) + initrd_len;
/*
* DTB must be loaded such that it does not conflict with the
@@ -815,15 +831,20 @@ static int prepare_dtb(struct domain *d, struct kernel_info *kinfo)
* the recommendation in Documentation/arm64/booting.txt is below
* 512MB. Place at 128MB, (or, if we have less RAM, as high as
* possible) in order to satisfy both.
+ * If the bootloader provides an initrd, it will be loaded just
+ * after the DTB.
*/
end = kinfo->mem.bank[0].start + kinfo->mem.bank[0].size;
end = MIN(kinfo->mem.bank[0].start + (128<<20) + new_size, end);
- kinfo->dtb_paddr = end - fdt_totalsize(kinfo->fdt);
+ kinfo->initrd_paddr = end - initrd_len;
+ kinfo->initrd_paddr &= ~((1 << 20) - 1);
+
+ kinfo->dtb_paddr = kinfo->initrd_paddr - fdt_totalsize(kinfo->fdt);
/* Align the address to 2Mb. Linux only requires 4 byte alignment */
kinfo->dtb_paddr &= ~((2 << 20) - 1);
- if ( fdt_totalsize(kinfo->fdt) > end )
+ if ( new_size > (end - kinfo->mem.bank[0].size) )
{
printk(XENLOG_ERR "Not enough memory in the first bank for "
"the device tree.");
@@ -854,6 +875,61 @@ static void dtb_load(struct kernel_info *kinfo)
xfree(kinfo->fdt);
}
+static void initrd_load(struct kernel_info *kinfo)
+{
+ paddr_t load_addr = kinfo->initrd_paddr;
+ paddr_t paddr = early_info.modules.module[MOD_INITRD].start;
+ paddr_t len = early_info.modules.module[MOD_INITRD].size;
+ unsigned long offs;
+ int node;
+ int res;
+
+ if ( !len )
+ return;
+
+ printk("Loading dom0 initrd from %"PRIpaddr" to 0x%"PRIpaddr"-0x%"PRIpaddr"\n",
+ paddr, load_addr, load_addr + len);
+
+ /* Fix up linux,initrd-start and linux,initrd-end in /chosen */
+ node = fdt_path_offset(kinfo->fdt, "/chosen");
+ if ( node < 0 )
+ panic("Cannot find the /chosen node");
+
+ res = fdt_setprop_inplace_cell(kinfo->fdt, node, "linux,initrd-start",
+ load_addr);
+ if ( res )
+ panic("Cannot fix up \"linux,initrd-start\" property\n");
+
+ res = fdt_setprop_inplace_cell(kinfo->fdt, node, "linux,initrd-end",
+ load_addr + len);
+ if ( res )
+ panic("Cannot fix up \"linux,initrd-end\" property\n");
+
+ for ( offs = 0; offs < len; )
+ {
+ int rc;
+ paddr_t s, l, ma;
+ void *dst;
+
+ s = offs & ~PAGE_MASK;
+ l = min(PAGE_SIZE - s, len);
+
+ rc = gvirt_to_maddr(load_addr + offs, &ma);
+ if ( rc )
+ {
+ panic("\nUnable to translate guest address\n");
+ return;
+ }
+
+ dst = map_domain_page(ma>>PAGE_SHIFT);
+
+ copy_from_paddr(dst + s, paddr + offs, l, BUFFERABLE);
+
+ unmap_domain_page(dst);
+ offs += l;
+ }
+}
+
int construct_dom0(struct domain *d)
{
struct kernel_info kinfo = {};
@@ -890,6 +966,8 @@ int construct_dom0(struct domain *d)
p2m_load_VTTBR(d);
kernel_load(&kinfo);
+ /* initrd_load will fix up the fdt, so call it before dtb_load */
+ initrd_load(&kinfo);
dtb_load(&kinfo);
discard_initial_modules();
diff --git a/xen/arch/arm/kernel.c b/xen/arch/arm/kernel.c
index e4c0981..84356a1 100644
--- a/xen/arch/arm/kernel.c
+++ b/xen/arch/arm/kernel.c
@@ -71,15 +71,22 @@ static void kernel_zimage_check_overlap(struct kernel_info *info)
{
paddr_t zimage_start = info->zimage.load_addr;
paddr_t zimage_end = info->zimage.load_addr + info->zimage.len;
- paddr_t dtb_start = info->dtb_paddr;
- paddr_t dtb_end = info->dtb_paddr + fdt_totalsize(info->fdt);
+ paddr_t start = info->dtb_paddr;
+ paddr_t end;
- if ( (dtb_start > zimage_end) || (dtb_end < zimage_start) )
+ end = info->initrd_paddr + early_info.modules.module[MOD_INITRD].size;
+
+ /*
+ * In the dom0 memory, the initrd will be just after the DTB. So we
+ * only need to check if the zImage range will overlap the
+ * DTB-initrd range.
+ */
+ if ( (start > zimage_end) || (end < zimage_start) )
return;
panic(XENLOG_ERR "The kernel(0x%"PRIpaddr"-0x%"PRIpaddr
- ") is overlapping the DTB(0x%"PRIpaddr"-0x%"PRIpaddr")\n",
- zimage_start, zimage_end, dtb_start, dtb_end);
+ ") is overlapping the DTB-initrd(0x%"PRIpaddr"-0x%"PRIpaddr")\n",
+ zimage_start, zimage_end, start, end);
}
static void kernel_zimage_load(struct kernel_info *info)
@@ -328,9 +335,6 @@ int kernel_prepare(struct kernel_info *info)
paddr_t start, size;
- if ( early_info.modules.nr_mods > MOD_INITRD )
- panic("Cannot handle dom0 initrd yet\n");
-
if ( early_info.modules.nr_mods < MOD_KERNEL )
{
printk("No boot modules found, trying flash\n");
diff --git a/xen/arch/arm/kernel.h b/xen/arch/arm/kernel.h
index c900e74..debf590 100644
--- a/xen/arch/arm/kernel.h
+++ b/xen/arch/arm/kernel.h
@@ -21,6 +21,8 @@ struct kernel_info {
paddr_t dtb_paddr;
paddr_t entry;
+ paddr_t initrd_paddr;
+
void *kernel_img;
unsigned kernel_order;
--
1.7.10.4
^ permalink raw reply related [flat|nested] 10+ messages in thread
* [PATCH 2/2] xen/dts: Support Linux initrd DT bindings
2013-09-16 15:20 [PATCH 0/2] ARM: Support initrd loading Julien Grall
2013-09-16 15:20 ` [PATCH 1/2] xen/arm: Add support to load initrd in dom0 Julien Grall
@ 2013-09-16 15:20 ` Julien Grall
2013-09-25 15:16 ` Ian Campbell
1 sibling, 1 reply; 10+ messages in thread
From: Julien Grall @ 2013-09-16 15:20 UTC (permalink / raw)
To: xen-devel
Cc: patches, Julien Grall, ian.campbell, andre.przywara,
stefano.stabellini
Linux uses the property linux,initrd-start and linux,initrd-end to know where
the initrd lives in memory.
Signed-off-by: Julien Grall <julien.grall@linaro.org>
---
xen/common/device_tree.c | 25 +++++++++++++++++++++++++
1 file changed, 25 insertions(+)
diff --git a/xen/common/device_tree.c b/xen/common/device_tree.c
index 9a16650..906f9f9 100644
--- a/xen/common/device_tree.c
+++ b/xen/common/device_tree.c
@@ -382,6 +382,29 @@ static void __init process_multiboot_node(const void *fdt, int node,
early_info.modules.nr_mods = nr;
}
+static void __init process_chosen_node(const void *fdt, int node,
+ const char *name,
+ u32 address_cells, u32 size_cells)
+{
+ struct dt_mb_module *mod = &early_info.modules.module[MOD_INITRD];
+ u32 start, end;
+
+ dt_printk("Checking for initrd in /chosen\n");
+
+ start = device_tree_get_u32(fdt, node, "linux,initrd-start", 0);
+ end = device_tree_get_u32(fdt, node, "linux,initrd-end", 0);
+
+ if ( !start || !end || (start >= end) )
+ return;
+
+ dt_printk("Initrd 0x%x-0x%x\n", start, end);
+
+ mod->start = start;
+ mod->size = end - start;
+
+ early_info.modules.nr_mods = MAX(MOD_INITRD, early_info.modules.nr_mods);
+}
+
static int __init early_scan_node(const void *fdt,
int node, const char *name, int depth,
u32 address_cells, u32 size_cells,
@@ -391,6 +414,8 @@ static int __init early_scan_node(const void *fdt,
process_memory_node(fdt, node, name, address_cells, size_cells);
else if ( device_tree_node_compatible(fdt, node, "xen,multiboot-module" ) )
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);
return 0;
}
--
1.7.10.4
^ permalink raw reply related [flat|nested] 10+ messages in thread
* Re: [PATCH 1/2] xen/arm: Add support to load initrd in dom0
2013-09-16 15:20 ` [PATCH 1/2] xen/arm: Add support to load initrd in dom0 Julien Grall
@ 2013-09-25 15:15 ` Ian Campbell
2013-09-25 15:23 ` Julien Grall
0 siblings, 1 reply; 10+ messages in thread
From: Ian Campbell @ 2013-09-25 15:15 UTC (permalink / raw)
To: Julien Grall; +Cc: stefano.stabellini, andre.przywara, patches, xen-devel
On Mon, 2013-09-16 at 16:20 +0100, Julien Grall wrote:
> @@ -806,7 +821,8 @@ static int prepare_dtb(struct domain *d, struct kernel_info *kinfo)
> goto err;
>
> /* Actual new size */
> - new_size = fdt_totalsize(kinfo->fdt);
> + initrd_len = early_info.modules.module[MOD_INITRD].size;
I think you need to check nr_modules here and in write_properties (which
I already trimmed by mistake.
.size may not be initialised otherwise. (in reality it's probably
in .bss not sure I want to rely on that though)
> + new_size = fdt_totalsize(kinfo->fdt) + initrd_len;
>
> /*
> * DTB must be loaded such that it does not conflict with the
> @@ -815,15 +831,20 @@ static int prepare_dtb(struct domain *d, struct kernel_info *kinfo)
> * the recommendation in Documentation/arm64/booting.txt is below
> * 512MB. Place at 128MB, (or, if we have less RAM, as high as
> * possible) in order to satisfy both.
> + * If the bootloader provides an initrd, it will be loaded just
> + * after the DTB.
> */
> end = kinfo->mem.bank[0].start + kinfo->mem.bank[0].size;
> end = MIN(kinfo->mem.bank[0].start + (128<<20) + new_size, end);
>
> - kinfo->dtb_paddr = end - fdt_totalsize(kinfo->fdt);
> + kinfo->initrd_paddr = end - initrd_len;
> + kinfo->initrd_paddr &= ~((1 << 20) - 1);
1MB aligned, why not 2 like most things?
> + kinfo->dtb_paddr = kinfo->initrd_paddr - fdt_totalsize(kinfo->fdt);
> /* Align the address to 2Mb. Linux only requires 4 byte alignment */
> kinfo->dtb_paddr &= ~((2 << 20) - 1);
>
> - if ( fdt_totalsize(kinfo->fdt) > end )
> + if ( new_size > (end - kinfo->mem.bank[0].size) )
> {
> printk(XENLOG_ERR "Not enough memory in the first bank for "
> "the device tree.");
> @@ -854,6 +875,61 @@ static void dtb_load(struct kernel_info *kinfo)
> xfree(kinfo->fdt);
> }
>
> +static void initrd_load(struct kernel_info *kinfo)
> +{
> + paddr_t load_addr = kinfo->initrd_paddr;
> + paddr_t paddr = early_info.modules.module[MOD_INITRD].start;
> + paddr_t len = early_info.modules.module[MOD_INITRD].size;
> + unsigned long offs;
> + int node;
> + int res;
> +
> + if ( !len )
> + return;
> +
> + printk("Loading dom0 initrd from %"PRIpaddr" to 0x%"PRIpaddr"-0x%"PRIpaddr"\n",
> + paddr, load_addr, load_addr + len);
> +
> + /* Fix up linux,initrd-start and linux,initrd-end in /chosen */
> + node = fdt_path_offset(kinfo->fdt, "/chosen");
> + if ( node < 0 )
> + panic("Cannot find the /chosen node");
> +
> + res = fdt_setprop_inplace_cell(kinfo->fdt, node, "linux,initrd-start",
> + load_addr);
> + if ( res )
> + panic("Cannot fix up \"linux,initrd-start\" property\n");
> +
> + res = fdt_setprop_inplace_cell(kinfo->fdt, node, "linux,initrd-end",
> + load_addr + len);
> + if ( res )
> + panic("Cannot fix up \"linux,initrd-end\" property\n");
> +
> + for ( offs = 0; offs < len; )
Can you refactor kernel_zimage_load into a more generic function which
can be used here?
^ permalink raw reply [flat|nested] 10+ messages in thread
* Re: [PATCH 2/2] xen/dts: Support Linux initrd DT bindings
2013-09-16 15:20 ` [PATCH 2/2] xen/dts: Support Linux initrd DT bindings Julien Grall
@ 2013-09-25 15:16 ` Ian Campbell
0 siblings, 0 replies; 10+ messages in thread
From: Ian Campbell @ 2013-09-25 15:16 UTC (permalink / raw)
To: Julien Grall; +Cc: stefano.stabellini, andre.przywara, patches, xen-devel
On Mon, 2013-09-16 at 16:20 +0100, Julien Grall wrote:
> Linux uses the property linux,initrd-start and linux,initrd-end to know where
> the initrd lives in memory.
>
> Signed-off-by: Julien Grall <julien.grall@linaro.org>
Acked-by: Ian Campbell <ian.campbell@citrix.com>
> ---
> xen/common/device_tree.c | 25 +++++++++++++++++++++++++
> 1 file changed, 25 insertions(+)
>
> diff --git a/xen/common/device_tree.c b/xen/common/device_tree.c
> index 9a16650..906f9f9 100644
> --- a/xen/common/device_tree.c
> +++ b/xen/common/device_tree.c
> @@ -382,6 +382,29 @@ static void __init process_multiboot_node(const void *fdt, int node,
> early_info.modules.nr_mods = nr;
> }
>
> +static void __init process_chosen_node(const void *fdt, int node,
> + const char *name,
> + u32 address_cells, u32 size_cells)
> +{
> + struct dt_mb_module *mod = &early_info.modules.module[MOD_INITRD];
> + u32 start, end;
> +
> + dt_printk("Checking for initrd in /chosen\n");
> +
> + start = device_tree_get_u32(fdt, node, "linux,initrd-start", 0);
> + end = device_tree_get_u32(fdt, node, "linux,initrd-end", 0);
> +
> + if ( !start || !end || (start >= end) )
> + return;
> +
> + dt_printk("Initrd 0x%x-0x%x\n", start, end);
> +
> + mod->start = start;
> + mod->size = end - start;
> +
> + early_info.modules.nr_mods = MAX(MOD_INITRD, early_info.modules.nr_mods);
> +}
> +
> static int __init early_scan_node(const void *fdt,
> int node, const char *name, int depth,
> u32 address_cells, u32 size_cells,
> @@ -391,6 +414,8 @@ static int __init early_scan_node(const void *fdt,
> process_memory_node(fdt, node, name, address_cells, size_cells);
> else if ( device_tree_node_compatible(fdt, node, "xen,multiboot-module" ) )
> 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);
>
> return 0;
> }
^ permalink raw reply [flat|nested] 10+ messages in thread
* Re: [PATCH 1/2] xen/arm: Add support to load initrd in dom0
2013-09-25 15:15 ` Ian Campbell
@ 2013-09-25 15:23 ` Julien Grall
2013-09-25 15:30 ` Ian Campbell
0 siblings, 1 reply; 10+ messages in thread
From: Julien Grall @ 2013-09-25 15:23 UTC (permalink / raw)
To: Ian Campbell; +Cc: stefano.stabellini, andre.przywara, patches, xen-devel
On 09/25/2013 04:15 PM, Ian Campbell wrote:
> On Mon, 2013-09-16 at 16:20 +0100, Julien Grall wrote:
>> @@ -806,7 +821,8 @@ static int prepare_dtb(struct domain *d, struct kernel_info *kinfo)
>> goto err;
>>
>> /* Actual new size */
>> - new_size = fdt_totalsize(kinfo->fdt);
>> + initrd_len = early_info.modules.module[MOD_INITRD].size;
>
> I think you need to check nr_modules here and in write_properties (which
> I already trimmed by mistake.
>
Even if we check nr_modules, we can't assume MOD_INITRD is the last
modules in the array, so it's possible to have nr_modules greater than
MOD_INITRD but the module is not set. That's why I only choose to rely
on size.
> .size may not be initialised otherwise. (in reality it's probably
> in .bss not sure I want to rely on that though)
It's in .bss, on common/device_tree.c we already rely that this
structure is zeroed (nr_modules is never initialized to 0).
>
>> + new_size = fdt_totalsize(kinfo->fdt) + initrd_len;
>>
>> /*
>> * DTB must be loaded such that it does not conflict with the
>> @@ -815,15 +831,20 @@ static int prepare_dtb(struct domain *d, struct kernel_info *kinfo)
>> * the recommendation in Documentation/arm64/booting.txt is below
>> * 512MB. Place at 128MB, (or, if we have less RAM, as high as
>> * possible) in order to satisfy both.
>> + * If the bootloader provides an initrd, it will be loaded just
>> + * after the DTB.
>> */
>> end = kinfo->mem.bank[0].start + kinfo->mem.bank[0].size;
>> end = MIN(kinfo->mem.bank[0].start + (128<<20) + new_size, end);
>>
>> - kinfo->dtb_paddr = end - fdt_totalsize(kinfo->fdt);
>> + kinfo->initrd_paddr = end - initrd_len;
>> + kinfo->initrd_paddr &= ~((1 << 20) - 1);
>
> 1MB aligned, why not 2 like most things?
A mistake, I will fix it in the next patch series.
>
>> + kinfo->dtb_paddr = kinfo->initrd_paddr - fdt_totalsize(kinfo->fdt);
>> /* Align the address to 2Mb. Linux only requires 4 byte alignment */
>> kinfo->dtb_paddr &= ~((2 << 20) - 1);
>>
>> - if ( fdt_totalsize(kinfo->fdt) > end )
>> + if ( new_size > (end - kinfo->mem.bank[0].size) )
>> {
>> printk(XENLOG_ERR "Not enough memory in the first bank for "
>> "the device tree.");
>> @@ -854,6 +875,61 @@ static void dtb_load(struct kernel_info *kinfo)
>> xfree(kinfo->fdt);
>> }
>>
>> +static void initrd_load(struct kernel_info *kinfo)
>> +{
>> + paddr_t load_addr = kinfo->initrd_paddr;
>> + paddr_t paddr = early_info.modules.module[MOD_INITRD].start;
>> + paddr_t len = early_info.modules.module[MOD_INITRD].size;
>> + unsigned long offs;
>> + int node;
>> + int res;
>> +
>> + if ( !len )
>> + return;
>> +
>> + printk("Loading dom0 initrd from %"PRIpaddr" to 0x%"PRIpaddr"-0x%"PRIpaddr"\n",
>> + paddr, load_addr, load_addr + len);
>> +
>> + /* Fix up linux,initrd-start and linux,initrd-end in /chosen */
>> + node = fdt_path_offset(kinfo->fdt, "/chosen");
>> + if ( node < 0 )
>> + panic("Cannot find the /chosen node");
>> +
>> + res = fdt_setprop_inplace_cell(kinfo->fdt, node, "linux,initrd-start",
>> + load_addr);
>> + if ( res )
>> + panic("Cannot fix up \"linux,initrd-start\" property\n");
>> +
>> + res = fdt_setprop_inplace_cell(kinfo->fdt, node, "linux,initrd-end",
>> + load_addr + len);
>> + if ( res )
>> + panic("Cannot fix up \"linux,initrd-end\" property\n");
>> +
>> + for ( offs = 0; offs < len; )
>
> Can you refactor kernel_zimage_load into a more generic function which
> can be used here?
I will do.
--
Julien Grall
^ permalink raw reply [flat|nested] 10+ messages in thread
* Re: [PATCH 1/2] xen/arm: Add support to load initrd in dom0
2013-09-25 15:23 ` Julien Grall
@ 2013-09-25 15:30 ` Ian Campbell
2013-09-25 15:36 ` Julien Grall
0 siblings, 1 reply; 10+ messages in thread
From: Ian Campbell @ 2013-09-25 15:30 UTC (permalink / raw)
To: Julien Grall; +Cc: stefano.stabellini, andre.przywara, patches, xen-devel
On Wed, 2013-09-25 at 16:23 +0100, Julien Grall wrote:
> On 09/25/2013 04:15 PM, Ian Campbell wrote:
> > On Mon, 2013-09-16 at 16:20 +0100, Julien Grall wrote:
> >> @@ -806,7 +821,8 @@ static int prepare_dtb(struct domain *d, struct kernel_info *kinfo)
> >> goto err;
> >>
> >> /* Actual new size */
> >> - new_size = fdt_totalsize(kinfo->fdt);
> >> + initrd_len = early_info.modules.module[MOD_INITRD].size;
> >
> > I think you need to check nr_modules here and in write_properties (which
> > I already trimmed by mistake.
> >
>
> Even if we check nr_modules, we can't assume MOD_INITRD is the last
> modules in the array, so it's possible to have nr_modules greater than
> MOD_INITRD but the module is not set. That's why I only choose to rely
> on size.
Hrm that's true.
> > .size may not be initialised otherwise. (in reality it's probably
> > in .bss not sure I want to rely on that though)
>
> It's in .bss, on common/device_tree.c we already rely that this
> structure is zeroed (nr_modules is never initialized to 0).
OK, I guess its fine then.
>
>
> >
> >> + new_size = fdt_totalsize(kinfo->fdt) + initrd_len;
> >>
> >> /*
> >> * DTB must be loaded such that it does not conflict with the
> >> @@ -815,15 +831,20 @@ static int prepare_dtb(struct domain *d, struct kernel_info *kinfo)
> >> * the recommendation in Documentation/arm64/booting.txt is below
> >> * 512MB. Place at 128MB, (or, if we have less RAM, as high as
> >> * possible) in order to satisfy both.
> >> + * If the bootloader provides an initrd, it will be loaded just
> >> + * after the DTB.
> >> */
> >> end = kinfo->mem.bank[0].start + kinfo->mem.bank[0].size;
> >> end = MIN(kinfo->mem.bank[0].start + (128<<20) + new_size, end);
> >>
> >> - kinfo->dtb_paddr = end - fdt_totalsize(kinfo->fdt);
> >> + kinfo->initrd_paddr = end - initrd_len;
> >> + kinfo->initrd_paddr &= ~((1 << 20) - 1);
> >
> > 1MB aligned, why not 2 like most things?
>
> A mistake, I will fix it in the next patch series.
Actually, this extra alignment makes me think that maybe new_size needs
to account for the slop too? Does it?
Otherwise start + 128M + new_size doesn't make it such that
{dtb,initrd}_paddr are actually above 128M?
Ian.
^ permalink raw reply [flat|nested] 10+ messages in thread
* Re: [PATCH 1/2] xen/arm: Add support to load initrd in dom0
2013-09-25 15:30 ` Ian Campbell
@ 2013-09-25 15:36 ` Julien Grall
2013-09-25 15:44 ` Ian Campbell
0 siblings, 1 reply; 10+ messages in thread
From: Julien Grall @ 2013-09-25 15:36 UTC (permalink / raw)
To: Ian Campbell; +Cc: stefano.stabellini, andre.przywara, patches, xen-devel
On 09/25/2013 04:30 PM, Ian Campbell wrote:
> On Wed, 2013-09-25 at 16:23 +0100, Julien Grall wrote:
>> On 09/25/2013 04:15 PM, Ian Campbell wrote:
>>> On Mon, 2013-09-16 at 16:20 +0100, Julien Grall wrote:
>>>> @@ -806,7 +821,8 @@ static int prepare_dtb(struct domain *d, struct kernel_info *kinfo)
>>>> goto err;
>>>>
>>>> /* Actual new size */
>>>> - new_size = fdt_totalsize(kinfo->fdt);
>>>> + initrd_len = early_info.modules.module[MOD_INITRD].size;
>>>
>>> I think you need to check nr_modules here and in write_properties (which
>>> I already trimmed by mistake.
>>>
>>
>> Even if we check nr_modules, we can't assume MOD_INITRD is the last
>> modules in the array, so it's possible to have nr_modules greater than
>> MOD_INITRD but the module is not set. That's why I only choose to rely
>> on size.
>
> Hrm that's true.
>
>>> .size may not be initialised otherwise. (in reality it's probably
>>> in .bss not sure I want to rely on that though)
>>
>> It's in .bss, on common/device_tree.c we already rely that this
>> structure is zeroed (nr_modules is never initialized to 0).
>
> OK, I guess its fine then.
>
>>
>>
>>>
>>>> + new_size = fdt_totalsize(kinfo->fdt) + initrd_len;
>>>>
>>>> /*
>>>> * DTB must be loaded such that it does not conflict with the
>>>> @@ -815,15 +831,20 @@ static int prepare_dtb(struct domain *d, struct kernel_info *kinfo)
>>>> * the recommendation in Documentation/arm64/booting.txt is below
>>>> * 512MB. Place at 128MB, (or, if we have less RAM, as high as
>>>> * possible) in order to satisfy both.
>>>> + * If the bootloader provides an initrd, it will be loaded just
>>>> + * after the DTB.
>>>> */
>>>> end = kinfo->mem.bank[0].start + kinfo->mem.bank[0].size;
>>>> end = MIN(kinfo->mem.bank[0].start + (128<<20) + new_size, end);
>>>>
>>>> - kinfo->dtb_paddr = end - fdt_totalsize(kinfo->fdt);
>>>> + kinfo->initrd_paddr = end - initrd_len;
>>>> + kinfo->initrd_paddr &= ~((1 << 20) - 1);
>>>
>>> 1MB aligned, why not 2 like most things?
>>
>> A mistake, I will fix it in the next patch series.
>
> Actually, this extra alignment makes me think that maybe new_size needs
> to account for the slop too? Does it?
> Otherwise start + 128M + new_size doesn't make it such that
> {dtb,initrd}_paddr are actually above 128M?
>
Right, what about?
#define ALIGN_2MB(size) ((len) + ((1 << 20 - 1)) & (~((1 << 20) - 1))
new_size = ALIGN_2MB(dtb_size) + ALIGN_2MB(initrd_size)
--
Julien Grall
^ permalink raw reply [flat|nested] 10+ messages in thread
* Re: [PATCH 1/2] xen/arm: Add support to load initrd in dom0
2013-09-25 15:36 ` Julien Grall
@ 2013-09-25 15:44 ` Ian Campbell
2013-09-25 15:48 ` Julien Grall
0 siblings, 1 reply; 10+ messages in thread
From: Ian Campbell @ 2013-09-25 15:44 UTC (permalink / raw)
To: Julien Grall; +Cc: patches, xen-devel, andre.przywara, stefano.stabellini
On Wed, 2013-09-25 at 16:36 +0100, Julien Grall wrote:
> Right, what about?
>
> #define ALIGN_2MB(size) ((len) + ((1 << 20 - 1)) & (~((1 << 20) - 1))
> new_size = ALIGN_2MB(dtb_size) + ALIGN_2MB(initrd_size)
Hard to believe we don't have an ALIGN or ROUNDUP macro already in a
common header! How about we move the one from device_tree.c somewhere
more generic?
We could also add #define MB(x) ((x)<<20) alongside the existing GB(x)?
^ permalink raw reply [flat|nested] 10+ messages in thread
* Re: [PATCH 1/2] xen/arm: Add support to load initrd in dom0
2013-09-25 15:44 ` Ian Campbell
@ 2013-09-25 15:48 ` Julien Grall
0 siblings, 0 replies; 10+ messages in thread
From: Julien Grall @ 2013-09-25 15:48 UTC (permalink / raw)
To: Ian Campbell; +Cc: patches, xen-devel, andre.przywara, stefano.stabellini
On 09/25/2013 04:44 PM, Ian Campbell wrote:
> On Wed, 2013-09-25 at 16:36 +0100, Julien Grall wrote:
>
>> Right, what about?
>>
>> #define ALIGN_2MB(size) ((len) + ((1 << 20 - 1)) & (~((1 << 20) - 1))
>> new_size = ALIGN_2MB(dtb_size) + ALIGN_2MB(initrd_size)
>
> Hard to believe we don't have an ALIGN or ROUNDUP macro already in a
> common header! How about we move the one from device_tree.c somewhere
> more generic?
>
> We could also add #define MB(x) ((x)<<20) alongside the existing GB(x)?
>
I will send a patch for the both macro and update this patch.
--
Julien Grall
^ permalink raw reply [flat|nested] 10+ messages in thread
end of thread, other threads:[~2013-09-25 15:48 UTC | newest]
Thread overview: 10+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2013-09-16 15:20 [PATCH 0/2] ARM: Support initrd loading Julien Grall
2013-09-16 15:20 ` [PATCH 1/2] xen/arm: Add support to load initrd in dom0 Julien Grall
2013-09-25 15:15 ` Ian Campbell
2013-09-25 15:23 ` Julien Grall
2013-09-25 15:30 ` Ian Campbell
2013-09-25 15:36 ` Julien Grall
2013-09-25 15:44 ` Ian Campbell
2013-09-25 15:48 ` Julien Grall
2013-09-16 15:20 ` [PATCH 2/2] xen/dts: Support Linux initrd DT bindings Julien Grall
2013-09-25 15:16 ` Ian Campbell
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).