* [PATCH v2 0/8] remove size limit on XIP kernel
@ 2024-06-07 20:22 Nam Cao
2024-06-07 20:22 ` [PATCH v2 1/8] riscv: cleanup XIP_FIXUP macro Nam Cao
` (8 more replies)
0 siblings, 9 replies; 11+ messages in thread
From: Nam Cao @ 2024-06-07 20:22 UTC (permalink / raw)
To: Alexandre Ghiti, Paul Walmsley, Palmer Dabbelt, Albert Ou,
linux-riscv, linux-kernel
Hi,
For XIP kernel, the writable data section is always at offset specified in
XIP_OFFSET, which is hard-coded to 32MB.
Unfortunately, this means the read-only section (placed before the
writable section) is restricted in size. This causes build failure if the
kernel gets too large.
This series remove the use of XIP_OFFSET one by one, then remove this
macro entirely at the end, with the goal of lifting this size restriction.
Also some cleanup and documentation along the way.
This series depends on
https://lore.kernel.org/linux-riscv/20240508191917.2892064-1-namcao@linutronix.de/
v2: address all Alex's comments (thanks Alex!). This includes the addition of a
new patch (riscv: don't export va_kernel_pa_offset in vmcoreinfo for XIP kernel),
which fix a build failure if CONFIG_VMCORE_INFO=y
Best regards,
Nam
Nam Cao (8):
riscv: cleanup XIP_FIXUP macro
riscv: don't export va_kernel_pa_offset in vmcoreinfo for XIP kernel
riscv: replace misleading va_kernel_pa_offset on XIP kernel
riscv: drop the use of XIP_OFFSET in XIP_FIXUP_OFFSET
riscv: drop the use of XIP_OFFSET in XIP_FIXUP_FLASH_OFFSET
riscv: drop the use of XIP_OFFSET in kernel_mapping_va_to_pa()
riscv: drop the use of XIP_OFFSET in create_kernel_page_table()
riscv: remove limit on the size of read-only section for XIP kernel
arch/riscv/include/asm/page.h | 29 ++++++++++++++++++++--------
arch/riscv/include/asm/pgtable.h | 18 +++++++----------
arch/riscv/include/asm/set_memory.h | 2 +-
arch/riscv/include/asm/xip_fixup.h | 30 +++++++++++++++++++++++------
arch/riscv/kernel/vmcore_info.c | 7 +++++++
arch/riscv/kernel/vmlinux-xip.lds.S | 5 +++--
arch/riscv/mm/init.c | 13 ++++++++-----
7 files changed, 71 insertions(+), 33 deletions(-)
--
2.39.2
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply [flat|nested] 11+ messages in thread
* [PATCH v2 1/8] riscv: cleanup XIP_FIXUP macro
2024-06-07 20:22 [PATCH v2 0/8] remove size limit on XIP kernel Nam Cao
@ 2024-06-07 20:22 ` Nam Cao
2024-06-07 20:22 ` [PATCH v2 2/8] riscv: don't export va_kernel_pa_offset in vmcoreinfo for XIP kernel Nam Cao
` (7 subsequent siblings)
8 siblings, 0 replies; 11+ messages in thread
From: Nam Cao @ 2024-06-07 20:22 UTC (permalink / raw)
To: Alexandre Ghiti, Paul Walmsley, Palmer Dabbelt, Albert Ou,
linux-riscv, linux-kernel
The XIP_FIXUP macro is used to fix addresses early during boot before MMU:
generated code "thinks" the data section is in ROM while it is actually in
RAM. So this macro corrects the addresses in the data section.
This macro determines if the address needs to be fixed by checking if it is
within the range starting from ROM address up to the size of (2 *
XIP_OFFSET).
This means if the kernel size is bigger than (2 * XIP_OFFSET), some
addresses would not be fixed up.
XIP kernel can still work if the above scenario does not happen. But this
macro is obviously incorrect.
Rewrite this macro to only fix up addresses within the data section.
Signed-off-by: Nam Cao <namcao@linutronix.de>
Reviewed-by: Alexandre Ghiti <alexghiti@rivosinc.com>
---
arch/riscv/include/asm/pgtable.h | 11 +++++++----
1 file changed, 7 insertions(+), 4 deletions(-)
diff --git a/arch/riscv/include/asm/pgtable.h b/arch/riscv/include/asm/pgtable.h
index aad8b8ca51f1..1bc103aa9b74 100644
--- a/arch/riscv/include/asm/pgtable.h
+++ b/arch/riscv/include/asm/pgtable.h
@@ -142,11 +142,14 @@
#ifdef CONFIG_XIP_KERNEL
#define XIP_FIXUP(addr) ({ \
+ extern char _sdata[], _start[], _end[]; \
+ uintptr_t __rom_start_data = CONFIG_XIP_PHYS_ADDR \
+ + (uintptr_t)&_sdata - (uintptr_t)&_start; \
+ uintptr_t __rom_end_data = CONFIG_XIP_PHYS_ADDR \
+ + (uintptr_t)&_end - (uintptr_t)&_start; \
uintptr_t __a = (uintptr_t)(addr); \
- (__a >= CONFIG_XIP_PHYS_ADDR && \
- __a < CONFIG_XIP_PHYS_ADDR + XIP_OFFSET * 2) ? \
- __a - CONFIG_XIP_PHYS_ADDR + CONFIG_PHYS_RAM_BASE - XIP_OFFSET :\
- __a; \
+ (__a >= __rom_start_data && __a < __rom_end_data) ? \
+ __a - __rom_start_data + CONFIG_PHYS_RAM_BASE : __a; \
})
#else
#define XIP_FIXUP(addr) (addr)
--
2.39.2
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply related [flat|nested] 11+ messages in thread
* [PATCH v2 2/8] riscv: don't export va_kernel_pa_offset in vmcoreinfo for XIP kernel
2024-06-07 20:22 [PATCH v2 0/8] remove size limit on XIP kernel Nam Cao
2024-06-07 20:22 ` [PATCH v2 1/8] riscv: cleanup XIP_FIXUP macro Nam Cao
@ 2024-06-07 20:22 ` Nam Cao
2024-06-21 10:27 ` Alexandre Ghiti
2024-06-07 20:22 ` [PATCH v2 3/8] riscv: replace misleading va_kernel_pa_offset on " Nam Cao
` (6 subsequent siblings)
8 siblings, 1 reply; 11+ messages in thread
From: Nam Cao @ 2024-06-07 20:22 UTC (permalink / raw)
To: Alexandre Ghiti, Paul Walmsley, Palmer Dabbelt, Albert Ou,
linux-riscv, linux-kernel
The crash utility uses va_kernel_pa_offset to translate virtual addresses.
This is incorrect in the case of XIP kernel, because va_kernel_pa_offset is
not the virtual-physical address offset (yes, the name is misleading; this
variable will be removed for XIP in a following commit).
Stop exporting this variable for XIP kernel. The replacement is to be
determined, note it as a TODO for now.
Signed-off-by: Nam Cao <namcao@linutronix.de>
---
arch/riscv/kernel/vmcore_info.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/arch/riscv/kernel/vmcore_info.c b/arch/riscv/kernel/vmcore_info.c
index 6d7a22522d63..d5e448aa90e7 100644
--- a/arch/riscv/kernel/vmcore_info.c
+++ b/arch/riscv/kernel/vmcore_info.c
@@ -19,6 +19,13 @@ void arch_crash_save_vmcoreinfo(void)
#endif
#endif
vmcoreinfo_append_str("NUMBER(KERNEL_LINK_ADDR)=0x%lx\n", KERNEL_LINK_ADDR);
+#ifdef CONFIG_XIP_KERNEL
+ /* TODO: Communicate with crash-utility developers on the information to
+ * export. The XIP case is more complicated, because the virtual-physical
+ * address offset depends on whether the address is in ROM or in RAM.
+ */
+#else
vmcoreinfo_append_str("NUMBER(va_kernel_pa_offset)=0x%lx\n",
kernel_map.va_kernel_pa_offset);
+#endif
}
--
2.39.2
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply related [flat|nested] 11+ messages in thread
* [PATCH v2 3/8] riscv: replace misleading va_kernel_pa_offset on XIP kernel
2024-06-07 20:22 [PATCH v2 0/8] remove size limit on XIP kernel Nam Cao
2024-06-07 20:22 ` [PATCH v2 1/8] riscv: cleanup XIP_FIXUP macro Nam Cao
2024-06-07 20:22 ` [PATCH v2 2/8] riscv: don't export va_kernel_pa_offset in vmcoreinfo for XIP kernel Nam Cao
@ 2024-06-07 20:22 ` Nam Cao
2024-06-07 20:22 ` [PATCH v2 4/8] riscv: drop the use of XIP_OFFSET in XIP_FIXUP_OFFSET Nam Cao
` (5 subsequent siblings)
8 siblings, 0 replies; 11+ messages in thread
From: Nam Cao @ 2024-06-07 20:22 UTC (permalink / raw)
To: Alexandre Ghiti, Paul Walmsley, Palmer Dabbelt, Albert Ou,
linux-riscv, linux-kernel
On XIP kernel, the name "va_kernel_pa_offset" is misleading: unlike
"normal" kernel, it is not the virtual-physical address offset of kernel
mapping, it is the offset of kernel mapping's first virtual address to
first physical address in DRAM, which is not meaningful because the
kernel's first physical address is not in DRAM.
For XIP kernel, there are 2 different offsets because the read-only part of
the kernel resides in ROM while the rest is in RAM. The offset to ROM is in
kernel_map.va_kernel_xip_pa_offset, while the offset to RAM is not stored
anywhere: it is calculated on-the-fly.
Remove this confusing "va_kernel_pa_offset" and add
"va_kernel_xip_data_pa_offset" as its replacement. This new variable is the
offset of virtual mapping of the kernel's data portion to the corresponding
physical addresses.
With the introduction of this new variable, also rename
va_kernel_xip_pa_offset -> va_kernel_xip_text_pa_offset to make it clear
that this one is about the .text section.
Signed-off-by: Nam Cao <namcao@linutronix.de>
Reviewed-by: Alexandre Ghiti <alexghiti@rivosinc.com>
---
arch/riscv/include/asm/page.h | 29 +++++++++++++++++++++--------
arch/riscv/mm/init.c | 6 ++++--
2 files changed, 25 insertions(+), 10 deletions(-)
diff --git a/arch/riscv/include/asm/page.h b/arch/riscv/include/asm/page.h
index 115ac98b8d72..b1fcf0d733c4 100644
--- a/arch/riscv/include/asm/page.h
+++ b/arch/riscv/include/asm/page.h
@@ -112,11 +112,13 @@ struct kernel_mapping {
/* Offset between linear mapping virtual address and kernel load address */
unsigned long va_pa_offset;
/* Offset between kernel mapping virtual address and kernel load address */
- unsigned long va_kernel_pa_offset;
- unsigned long va_kernel_xip_pa_offset;
#ifdef CONFIG_XIP_KERNEL
+ unsigned long va_kernel_xip_text_pa_offset;
+ unsigned long va_kernel_xip_data_pa_offset;
uintptr_t xiprom;
uintptr_t xiprom_sz;
+#else
+ unsigned long va_kernel_pa_offset;
#endif
};
@@ -134,12 +136,18 @@ extern phys_addr_t phys_ram_base;
#else
void *linear_mapping_pa_to_va(unsigned long x);
#endif
+
+#ifdef CONFIG_XIP_KERNEL
#define kernel_mapping_pa_to_va(y) ({ \
unsigned long _y = (unsigned long)(y); \
- (IS_ENABLED(CONFIG_XIP_KERNEL) && _y < phys_ram_base) ? \
- (void *)(_y + kernel_map.va_kernel_xip_pa_offset) : \
- (void *)(_y + kernel_map.va_kernel_pa_offset + XIP_OFFSET); \
+ (_y < phys_ram_base) ? \
+ (void *)(_y + kernel_map.va_kernel_xip_text_pa_offset) : \
+ (void *)(_y + kernel_map.va_kernel_xip_data_pa_offset); \
})
+#else
+#define kernel_mapping_pa_to_va(y) ((void *)((unsigned long)(y) + kernel_map.va_kernel_pa_offset))
+#endif
+
#define __pa_to_va_nodebug(x) linear_mapping_pa_to_va(x)
#ifndef CONFIG_DEBUG_VIRTUAL
@@ -147,12 +155,17 @@ void *linear_mapping_pa_to_va(unsigned long x);
#else
phys_addr_t linear_mapping_va_to_pa(unsigned long x);
#endif
+
+#ifdef CONFIG_XIP_KERNEL
#define kernel_mapping_va_to_pa(y) ({ \
unsigned long _y = (unsigned long)(y); \
- (IS_ENABLED(CONFIG_XIP_KERNEL) && _y < kernel_map.virt_addr + XIP_OFFSET) ? \
- (_y - kernel_map.va_kernel_xip_pa_offset) : \
- (_y - kernel_map.va_kernel_pa_offset - XIP_OFFSET); \
+ (_y < kernel_map.virt_addr + XIP_OFFSET) ? \
+ (_y - kernel_map.va_kernel_xip_text_pa_offset) : \
+ (_y - kernel_map.va_kernel_xip_data_pa_offset); \
})
+#else
+#define kernel_mapping_va_to_pa(y) ((unsigned long)(y) - kernel_map.va_kernel_pa_offset)
+#endif
#define __va_to_pa_nodebug(x) ({ \
unsigned long _x = x; \
diff --git a/arch/riscv/mm/init.c b/arch/riscv/mm/init.c
index 28f9c37443c8..313459329d16 100644
--- a/arch/riscv/mm/init.c
+++ b/arch/riscv/mm/init.c
@@ -1092,11 +1092,14 @@ asmlinkage void __init setup_vm(uintptr_t dtb_pa)
kernel_map.phys_addr = (uintptr_t)CONFIG_PHYS_RAM_BASE;
kernel_map.size = (uintptr_t)(&_end) - (uintptr_t)(&_start);
- kernel_map.va_kernel_xip_pa_offset = kernel_map.virt_addr - kernel_map.xiprom;
+ kernel_map.va_kernel_xip_text_pa_offset = kernel_map.virt_addr - kernel_map.xiprom;
+ kernel_map.va_kernel_xip_data_pa_offset = kernel_map.virt_addr - kernel_map.phys_addr
+ + (uintptr_t)&_sdata - (uintptr_t)&_start;
#else
kernel_map.page_offset = _AC(CONFIG_PAGE_OFFSET, UL);
kernel_map.phys_addr = (uintptr_t)(&_start);
kernel_map.size = (uintptr_t)(&_end) - kernel_map.phys_addr;
+ kernel_map.va_kernel_pa_offset = kernel_map.virt_addr - kernel_map.phys_addr;
#endif
#if defined(CONFIG_64BIT) && !defined(CONFIG_XIP_KERNEL)
@@ -1118,7 +1121,6 @@ asmlinkage void __init setup_vm(uintptr_t dtb_pa)
*/
kernel_map.va_pa_offset = IS_ENABLED(CONFIG_64BIT) ?
0UL : PAGE_OFFSET - kernel_map.phys_addr;
- kernel_map.va_kernel_pa_offset = kernel_map.virt_addr - kernel_map.phys_addr;
/*
* The default maximal physical memory size is KERN_VIRT_SIZE for 32-bit
--
2.39.2
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply related [flat|nested] 11+ messages in thread
* [PATCH v2 4/8] riscv: drop the use of XIP_OFFSET in XIP_FIXUP_OFFSET
2024-06-07 20:22 [PATCH v2 0/8] remove size limit on XIP kernel Nam Cao
` (2 preceding siblings ...)
2024-06-07 20:22 ` [PATCH v2 3/8] riscv: replace misleading va_kernel_pa_offset on " Nam Cao
@ 2024-06-07 20:22 ` Nam Cao
2024-06-07 20:22 ` [PATCH v2 5/8] riscv: drop the use of XIP_OFFSET in XIP_FIXUP_FLASH_OFFSET Nam Cao
` (4 subsequent siblings)
8 siblings, 0 replies; 11+ messages in thread
From: Nam Cao @ 2024-06-07 20:22 UTC (permalink / raw)
To: Alexandre Ghiti, Paul Walmsley, Palmer Dabbelt, Albert Ou,
linux-riscv, linux-kernel
XIP_OFFSET is the hard-coded offset of writable data section within the
kernel.
By hard-coding this value, the read-only section of the kernel (which is
placed before the writable data section) is restricted in size.
As a preparation to remove this hard-coded macro XIP_OFFSET entirely, stop
using XIP_OFFSET in XIP_FIXUP_OFFSET. Instead, use CONFIG_PHYS_RAM_BASE and
_sdata to do the same thing.
While at it, also add a description for XIP_FIXUP_OFFSET.
Signed-off-by: Nam Cao <namcao@linutronix.de>
Reviewed-by: Alexandre Ghiti <alexghiti@rivosinc.com>
---
arch/riscv/include/asm/xip_fixup.h | 14 ++++++++++++--
1 file changed, 12 insertions(+), 2 deletions(-)
diff --git a/arch/riscv/include/asm/xip_fixup.h b/arch/riscv/include/asm/xip_fixup.h
index b65bf6306f69..9ed2cfae09e0 100644
--- a/arch/riscv/include/asm/xip_fixup.h
+++ b/arch/riscv/include/asm/xip_fixup.h
@@ -9,8 +9,19 @@
#ifdef CONFIG_XIP_KERNEL
.macro XIP_FIXUP_OFFSET reg
- REG_L t0, _xip_fixup
+ /* Fix-up address in Flash into address in RAM early during boot before
+ * MMU is up. Because generated code "thinks" data is in Flash, but it
+ * is actually in RAM (actually data is also in Flash, but Flash is
+ * read-only, thus we need to use the data residing in RAM).
+ *
+ * The start of data in Flash is _sdata and the start of data in RAM is
+ * CONFIG_PHYS_RAM_BASE. So this fix-up essentially does this:
+ * reg += CONFIG_PHYS_RAM_BASE - _start
+ */
+ li t0, CONFIG_PHYS_RAM_BASE
add \reg, \reg, t0
+ la t0, _sdata
+ sub \reg, \reg, t0
.endm
.macro XIP_FIXUP_FLASH_OFFSET reg
la t0, __data_loc
@@ -19,7 +30,6 @@
add \reg, \reg, t0
.endm
-_xip_fixup: .dword CONFIG_PHYS_RAM_BASE - CONFIG_XIP_PHYS_ADDR - XIP_OFFSET
_xip_phys_offset: .dword CONFIG_XIP_PHYS_ADDR + XIP_OFFSET
#else
.macro XIP_FIXUP_OFFSET reg
--
2.39.2
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply related [flat|nested] 11+ messages in thread
* [PATCH v2 5/8] riscv: drop the use of XIP_OFFSET in XIP_FIXUP_FLASH_OFFSET
2024-06-07 20:22 [PATCH v2 0/8] remove size limit on XIP kernel Nam Cao
` (3 preceding siblings ...)
2024-06-07 20:22 ` [PATCH v2 4/8] riscv: drop the use of XIP_OFFSET in XIP_FIXUP_OFFSET Nam Cao
@ 2024-06-07 20:22 ` Nam Cao
2024-06-07 20:22 ` [PATCH v2 6/8] riscv: drop the use of XIP_OFFSET in kernel_mapping_va_to_pa() Nam Cao
` (3 subsequent siblings)
8 siblings, 0 replies; 11+ messages in thread
From: Nam Cao @ 2024-06-07 20:22 UTC (permalink / raw)
To: Alexandre Ghiti, Paul Walmsley, Palmer Dabbelt, Albert Ou,
linux-riscv, linux-kernel
XIP_OFFSET is the hard-coded offset of writable data section within the
kernel.
By hard-coding this value, the read-only section of the kernel (which is
placed before the writable data section) is restricted in size.
As a preparation to remove this hard-coded macro XIP_OFFSET entirely, stop
using XIP_OFFSET in XIP_FIXUP_FLASH_OFFSET. Instead, use __data_loc and
_sdata to do the same thing.
While at it, also add a description for XIP_FIXUP_FLASH_OFFSET.
Signed-off-by: Nam Cao <namcao@linutronix.de>
Reviewed-by: Alexandre Ghiti <alexghiti@rivosinc.com>
---
arch/riscv/include/asm/xip_fixup.h | 16 ++++++++++++----
1 file changed, 12 insertions(+), 4 deletions(-)
diff --git a/arch/riscv/include/asm/xip_fixup.h b/arch/riscv/include/asm/xip_fixup.h
index 9ed2cfae09e0..f3d56299bc22 100644
--- a/arch/riscv/include/asm/xip_fixup.h
+++ b/arch/riscv/include/asm/xip_fixup.h
@@ -24,13 +24,21 @@
sub \reg, \reg, t0
.endm
.macro XIP_FIXUP_FLASH_OFFSET reg
+ /* In linker script, at the transition from read-only section to
+ * writable section, the VMA is increased while LMA remains the same.
+ * (See in linker script how _sdata, __data_loc and LOAD_OFFSET is
+ * changed)
+ *
+ * Consequently, early during boot before MMU is up, the generated code
+ * reads the "writable" section at wrong addresses, because VMA is used
+ * by compiler to generate code, but the data is located in Flash using
+ * LMA.
+ */
+ la t0, _sdata
+ sub \reg, \reg, t0
la t0, __data_loc
- REG_L t1, _xip_phys_offset
- sub \reg, \reg, t1
add \reg, \reg, t0
.endm
-
-_xip_phys_offset: .dword CONFIG_XIP_PHYS_ADDR + XIP_OFFSET
#else
.macro XIP_FIXUP_OFFSET reg
.endm
--
2.39.2
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply related [flat|nested] 11+ messages in thread
* [PATCH v2 6/8] riscv: drop the use of XIP_OFFSET in kernel_mapping_va_to_pa()
2024-06-07 20:22 [PATCH v2 0/8] remove size limit on XIP kernel Nam Cao
` (4 preceding siblings ...)
2024-06-07 20:22 ` [PATCH v2 5/8] riscv: drop the use of XIP_OFFSET in XIP_FIXUP_FLASH_OFFSET Nam Cao
@ 2024-06-07 20:22 ` Nam Cao
2024-06-07 20:22 ` [PATCH v2 7/8] riscv: drop the use of XIP_OFFSET in create_kernel_page_table() Nam Cao
` (2 subsequent siblings)
8 siblings, 0 replies; 11+ messages in thread
From: Nam Cao @ 2024-06-07 20:22 UTC (permalink / raw)
To: Alexandre Ghiti, Paul Walmsley, Palmer Dabbelt, Albert Ou,
linux-riscv, linux-kernel
XIP_OFFSET is the hard-coded offset of writable data section within the
kernel.
By hard-coding this value, the read-only section of the kernel (which is
placed before the writable data section) is restricted in size.
As a preparation to remove this hard-coded macro XIP_OFFSET entirely,
remove the use of XIP_OFFSET in kernel_mapping_va_to_pa(). The macro
XIP_OFFSET is used in this case to check if the virtual address is mapped
to Flash or to RAM. The same check can be done with kernel_map.xiprom_sz.
Signed-off-by: Nam Cao <namcao@linutronix.de>
Reviewed-by: Alexandre Ghiti <alexghiti@rivosinc.com>
---
arch/riscv/include/asm/page.h | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/arch/riscv/include/asm/page.h b/arch/riscv/include/asm/page.h
index b1fcf0d733c4..cda4a917f90a 100644
--- a/arch/riscv/include/asm/page.h
+++ b/arch/riscv/include/asm/page.h
@@ -159,7 +159,7 @@ phys_addr_t linear_mapping_va_to_pa(unsigned long x);
#ifdef CONFIG_XIP_KERNEL
#define kernel_mapping_va_to_pa(y) ({ \
unsigned long _y = (unsigned long)(y); \
- (_y < kernel_map.virt_addr + XIP_OFFSET) ? \
+ (_y < kernel_map.virt_addr + kernel_map.xiprom_sz) ? \
(_y - kernel_map.va_kernel_xip_text_pa_offset) : \
(_y - kernel_map.va_kernel_xip_data_pa_offset); \
})
--
2.39.2
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply related [flat|nested] 11+ messages in thread
* [PATCH v2 7/8] riscv: drop the use of XIP_OFFSET in create_kernel_page_table()
2024-06-07 20:22 [PATCH v2 0/8] remove size limit on XIP kernel Nam Cao
` (5 preceding siblings ...)
2024-06-07 20:22 ` [PATCH v2 6/8] riscv: drop the use of XIP_OFFSET in kernel_mapping_va_to_pa() Nam Cao
@ 2024-06-07 20:22 ` Nam Cao
2024-06-07 20:22 ` [PATCH v2 8/8] riscv: remove limit on the size of read-only section for XIP kernel Nam Cao
2024-09-14 8:13 ` [PATCH v2 0/8] remove size limit on " patchwork-bot+linux-riscv
8 siblings, 0 replies; 11+ messages in thread
From: Nam Cao @ 2024-06-07 20:22 UTC (permalink / raw)
To: Alexandre Ghiti, Paul Walmsley, Palmer Dabbelt, Albert Ou,
linux-riscv, linux-kernel
XIP_OFFSET is the hard-coded offset of writable data section within the
kernel.
By hard-coding this value, the read-only section of the kernel (which is
placed before the writable data section) is restricted in size.
As a preparation to remove this hard-coded value entirely, stop using
XIP_OFFSET in create_kernel_page_table(). Instead use _sdata and _start to
do the same thing.
Signed-off-by: Nam Cao <namcao@linutronix.de>
Reviewed-by: Alexandre Ghiti <alexghiti@rivosinc.com>
---
arch/riscv/mm/init.c | 7 ++++---
1 file changed, 4 insertions(+), 3 deletions(-)
diff --git a/arch/riscv/mm/init.c b/arch/riscv/mm/init.c
index 313459329d16..b7b6affd4b79 100644
--- a/arch/riscv/mm/init.c
+++ b/arch/riscv/mm/init.c
@@ -911,7 +911,7 @@ static void __init relocate_kernel(void)
static void __init create_kernel_page_table(pgd_t *pgdir,
__always_unused bool early)
{
- uintptr_t va, end_va;
+ uintptr_t va, start_va, end_va;
/* Map the flash resident part */
end_va = kernel_map.virt_addr + kernel_map.xiprom_sz;
@@ -921,10 +921,11 @@ static void __init create_kernel_page_table(pgd_t *pgdir,
PMD_SIZE, PAGE_KERNEL_EXEC);
/* Map the data in RAM */
+ start_va = kernel_map.virt_addr + (uintptr_t)&_sdata - (uintptr_t)&_start;
end_va = kernel_map.virt_addr + kernel_map.size;
- for (va = kernel_map.virt_addr + XIP_OFFSET; va < end_va; va += PMD_SIZE)
+ for (va = start_va; va < end_va; va += PMD_SIZE)
create_pgd_mapping(pgdir, va,
- kernel_map.phys_addr + (va - (kernel_map.virt_addr + XIP_OFFSET)),
+ kernel_map.phys_addr + (va - start_va),
PMD_SIZE, PAGE_KERNEL);
}
#else
--
2.39.2
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply related [flat|nested] 11+ messages in thread
* [PATCH v2 8/8] riscv: remove limit on the size of read-only section for XIP kernel
2024-06-07 20:22 [PATCH v2 0/8] remove size limit on XIP kernel Nam Cao
` (6 preceding siblings ...)
2024-06-07 20:22 ` [PATCH v2 7/8] riscv: drop the use of XIP_OFFSET in create_kernel_page_table() Nam Cao
@ 2024-06-07 20:22 ` Nam Cao
2024-09-14 8:13 ` [PATCH v2 0/8] remove size limit on " patchwork-bot+linux-riscv
8 siblings, 0 replies; 11+ messages in thread
From: Nam Cao @ 2024-06-07 20:22 UTC (permalink / raw)
To: Alexandre Ghiti, Paul Walmsley, Palmer Dabbelt, Albert Ou,
linux-riscv, linux-kernel
XIP_OFFSET is the hard-coded offset of writable data section within the
kernel.
By hard-coding this value, the read-only section of the kernel (which is
placed before the writable data section) is restricted in size. This causes
build failures if the kernel gets too big [1].
Remove this limit.
Reported-by: kernel test robot <lkp@intel.com>
Closes: https://lore.kernel.org/oe-kbuild-all/202404211031.J6l2AfJk-lkp@intel.com [1]
Signed-off-by: Nam Cao <namcao@linutronix.de>
Reviewed-by: Alexandre Ghiti <alexghiti@rivosinc.com>
---
arch/riscv/include/asm/pgtable.h | 7 -------
arch/riscv/include/asm/set_memory.h | 2 +-
arch/riscv/kernel/vmlinux-xip.lds.S | 5 +++--
3 files changed, 4 insertions(+), 10 deletions(-)
diff --git a/arch/riscv/include/asm/pgtable.h b/arch/riscv/include/asm/pgtable.h
index 1bc103aa9b74..bf4afffe0c53 100644
--- a/arch/riscv/include/asm/pgtable.h
+++ b/arch/riscv/include/asm/pgtable.h
@@ -107,13 +107,6 @@
#endif
-#ifdef CONFIG_XIP_KERNEL
-#define XIP_OFFSET SZ_32M
-#define XIP_OFFSET_MASK (SZ_32M - 1)
-#else
-#define XIP_OFFSET 0
-#endif
-
#ifndef __ASSEMBLY__
#include <asm/page.h>
diff --git a/arch/riscv/include/asm/set_memory.h b/arch/riscv/include/asm/set_memory.h
index ec11001c3fe0..ab92fc84e1fc 100644
--- a/arch/riscv/include/asm/set_memory.h
+++ b/arch/riscv/include/asm/set_memory.h
@@ -46,7 +46,7 @@ bool kernel_page_present(struct page *page);
#endif /* __ASSEMBLY__ */
-#ifdef CONFIG_STRICT_KERNEL_RWX
+#if defined(CONFIG_STRICT_KERNEL_RWX) || defined(CONFIG_XIP_KERNEL)
#ifdef CONFIG_64BIT
#define SECTION_ALIGN (1 << 21)
#else
diff --git a/arch/riscv/kernel/vmlinux-xip.lds.S b/arch/riscv/kernel/vmlinux-xip.lds.S
index 8c3daa1b0531..a7611789bad5 100644
--- a/arch/riscv/kernel/vmlinux-xip.lds.S
+++ b/arch/riscv/kernel/vmlinux-xip.lds.S
@@ -14,6 +14,7 @@
#include <asm/page.h>
#include <asm/cache.h>
#include <asm/thread_info.h>
+#include <asm/set_memory.h>
OUTPUT_ARCH(riscv)
ENTRY(_start)
@@ -65,10 +66,10 @@ SECTIONS
* From this point, stuff is considered writable and will be copied to RAM
*/
__data_loc = ALIGN(PAGE_SIZE); /* location in file */
- . = KERNEL_LINK_ADDR + XIP_OFFSET; /* location in memory */
+ . = ALIGN(SECTION_ALIGN); /* location in memory */
#undef LOAD_OFFSET
-#define LOAD_OFFSET (KERNEL_LINK_ADDR + XIP_OFFSET - (__data_loc & XIP_OFFSET_MASK))
+#define LOAD_OFFSET (KERNEL_LINK_ADDR + _sdata - __data_loc)
_sdata = .; /* Start of data section */
_data = .;
--
2.39.2
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply related [flat|nested] 11+ messages in thread
* Re: [PATCH v2 2/8] riscv: don't export va_kernel_pa_offset in vmcoreinfo for XIP kernel
2024-06-07 20:22 ` [PATCH v2 2/8] riscv: don't export va_kernel_pa_offset in vmcoreinfo for XIP kernel Nam Cao
@ 2024-06-21 10:27 ` Alexandre Ghiti
0 siblings, 0 replies; 11+ messages in thread
From: Alexandre Ghiti @ 2024-06-21 10:27 UTC (permalink / raw)
To: Nam Cao, Alexandre Ghiti, Paul Walmsley, Palmer Dabbelt,
Albert Ou, linux-riscv, linux-kernel
Hi Nam,
On 07/06/2024 22:22, Nam Cao wrote:
> The crash utility uses va_kernel_pa_offset to translate virtual addresses.
> This is incorrect in the case of XIP kernel, because va_kernel_pa_offset is
> not the virtual-physical address offset (yes, the name is misleading; this
> variable will be removed for XIP in a following commit).
>
> Stop exporting this variable for XIP kernel. The replacement is to be
> determined, note it as a TODO for now.
>
> Signed-off-by: Nam Cao <namcao@linutronix.de>
> ---
> arch/riscv/kernel/vmcore_info.c | 7 +++++++
> 1 file changed, 7 insertions(+)
>
> diff --git a/arch/riscv/kernel/vmcore_info.c b/arch/riscv/kernel/vmcore_info.c
> index 6d7a22522d63..d5e448aa90e7 100644
> --- a/arch/riscv/kernel/vmcore_info.c
> +++ b/arch/riscv/kernel/vmcore_info.c
> @@ -19,6 +19,13 @@ void arch_crash_save_vmcoreinfo(void)
> #endif
> #endif
> vmcoreinfo_append_str("NUMBER(KERNEL_LINK_ADDR)=0x%lx\n", KERNEL_LINK_ADDR);
> +#ifdef CONFIG_XIP_KERNEL
> + /* TODO: Communicate with crash-utility developers on the information to
> + * export. The XIP case is more complicated, because the virtual-physical
> + * address offset depends on whether the address is in ROM or in RAM.
> + */
> +#else
> vmcoreinfo_append_str("NUMBER(va_kernel_pa_offset)=0x%lx\n",
> kernel_map.va_kernel_pa_offset);
> +#endif
> }
So that will regress crash on XIP kernels, but on the other hand this
was wrong in the first place. And not sure anyone ever used crash on a
XIP platform.
At least people will know that using va_kernel_pa_offset was wrong, so:
Reviewed-by: Alexandre Ghiti <alexghiti@rivosinc.com>
Thanks for all your changes in v2,
Alex
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [PATCH v2 0/8] remove size limit on XIP kernel
2024-06-07 20:22 [PATCH v2 0/8] remove size limit on XIP kernel Nam Cao
` (7 preceding siblings ...)
2024-06-07 20:22 ` [PATCH v2 8/8] riscv: remove limit on the size of read-only section for XIP kernel Nam Cao
@ 2024-09-14 8:13 ` patchwork-bot+linux-riscv
8 siblings, 0 replies; 11+ messages in thread
From: patchwork-bot+linux-riscv @ 2024-09-14 8:13 UTC (permalink / raw)
To: Nam Cao; +Cc: linux-riscv, alexghiti, paul.walmsley, palmer, aou, linux-kernel
Hello:
This series was applied to riscv/linux.git (for-next)
by Palmer Dabbelt <palmer@rivosinc.com>:
On Fri, 7 Jun 2024 22:22:05 +0200 you wrote:
> Hi,
>
> For XIP kernel, the writable data section is always at offset specified in
> XIP_OFFSET, which is hard-coded to 32MB.
>
> Unfortunately, this means the read-only section (placed before the
> writable section) is restricted in size. This causes build failure if the
> kernel gets too large.
>
> [...]
Here is the summary with links:
- [v2,1/8] riscv: cleanup XIP_FIXUP macro
https://git.kernel.org/riscv/c/aa3457f22f00
- [v2,2/8] riscv: don't export va_kernel_pa_offset in vmcoreinfo for XIP kernel
https://git.kernel.org/riscv/c/f2df5b4fdd74
- [v2,3/8] riscv: replace misleading va_kernel_pa_offset on XIP kernel
https://git.kernel.org/riscv/c/5cf089672119
- [v2,4/8] riscv: drop the use of XIP_OFFSET in XIP_FIXUP_OFFSET
https://git.kernel.org/riscv/c/e4eac34feda4
- [v2,5/8] riscv: drop the use of XIP_OFFSET in XIP_FIXUP_FLASH_OFFSET
https://git.kernel.org/riscv/c/23311f57ee13
- [v2,6/8] riscv: drop the use of XIP_OFFSET in kernel_mapping_va_to_pa()
https://git.kernel.org/riscv/c/75fdf791dff0
- [v2,7/8] riscv: drop the use of XIP_OFFSET in create_kernel_page_table()
https://git.kernel.org/riscv/c/a7cfb999433a
- [v2,8/8] riscv: remove limit on the size of read-only section for XIP kernel
https://git.kernel.org/riscv/c/b635a84bde6f
You are awesome, thank you!
--
Deet-doot-dot, I am a bot.
https://korg.docs.kernel.org/patchwork/pwbot.html
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply [flat|nested] 11+ messages in thread
end of thread, other threads:[~2024-09-14 8:13 UTC | newest]
Thread overview: 11+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2024-06-07 20:22 [PATCH v2 0/8] remove size limit on XIP kernel Nam Cao
2024-06-07 20:22 ` [PATCH v2 1/8] riscv: cleanup XIP_FIXUP macro Nam Cao
2024-06-07 20:22 ` [PATCH v2 2/8] riscv: don't export va_kernel_pa_offset in vmcoreinfo for XIP kernel Nam Cao
2024-06-21 10:27 ` Alexandre Ghiti
2024-06-07 20:22 ` [PATCH v2 3/8] riscv: replace misleading va_kernel_pa_offset on " Nam Cao
2024-06-07 20:22 ` [PATCH v2 4/8] riscv: drop the use of XIP_OFFSET in XIP_FIXUP_OFFSET Nam Cao
2024-06-07 20:22 ` [PATCH v2 5/8] riscv: drop the use of XIP_OFFSET in XIP_FIXUP_FLASH_OFFSET Nam Cao
2024-06-07 20:22 ` [PATCH v2 6/8] riscv: drop the use of XIP_OFFSET in kernel_mapping_va_to_pa() Nam Cao
2024-06-07 20:22 ` [PATCH v2 7/8] riscv: drop the use of XIP_OFFSET in create_kernel_page_table() Nam Cao
2024-06-07 20:22 ` [PATCH v2 8/8] riscv: remove limit on the size of read-only section for XIP kernel Nam Cao
2024-09-14 8:13 ` [PATCH v2 0/8] remove size limit on " patchwork-bot+linux-riscv
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox