* [PATCH 0/2] Enable STRICT_MODULE_RWX
@ 2026-06-06 13:21 haoran.jiang
2026-06-06 13:21 ` [PATCH 1/2] LoongArch: Move fixmap page tables to BSS segment haoran.jiang
` (2 more replies)
0 siblings, 3 replies; 4+ messages in thread
From: haoran.jiang @ 2026-06-06 13:21 UTC (permalink / raw)
To: loongarch
Cc: linux-kernel, chenhuacai, kernel, akpm, jbohac, kees, yangtiezhu,
Haoran Jiang
From: Haoran Jiang <jianghaoran@kylinos.cn>
Enable STRICT_MODULE_RWX on LoongArch and
Move fixmap page tables to BSS segment.
Haoran Jiang (2):
LoongArch: Move fixmap page tables to BSS segment
LoongArch: Enable STRICT_MODULE_RWX for stricter modules memory
permissions
arch/loongarch/Kconfig | 2 +
arch/loongarch/include/asm/fixmap.h | 2 +
arch/loongarch/kernel/inst.c | 29 +++++++++++-
arch/loongarch/kernel/setup.c | 1 +
arch/loongarch/mm/init.c | 71 ++++++++++++++++++++++++++---
5 files changed, 98 insertions(+), 7 deletions(-)
--
2.25.1
^ permalink raw reply [flat|nested] 4+ messages in thread
* [PATCH 1/2] LoongArch: Move fixmap page tables to BSS segment
2026-06-06 13:21 [PATCH 0/2] Enable STRICT_MODULE_RWX haoran.jiang
@ 2026-06-06 13:21 ` haoran.jiang
2026-06-06 13:21 ` [PATCH 2/2] LoongArch: Enable STRICT_MODULE_RWX for stricter modules memory permissions haoran.jiang
2026-06-06 14:04 ` [PATCH 0/2] Enable STRICT_MODULE_RWX Huacai Chen
2 siblings, 0 replies; 4+ messages in thread
From: haoran.jiang @ 2026-06-06 13:21 UTC (permalink / raw)
To: loongarch
Cc: linux-kernel, chenhuacai, kernel, akpm, jbohac, kees, yangtiezhu,
Haoran Jiang
From: Haoran Jiang <jianghaoran@kylinos.cn>
__set_fixmap() is not only used during initialization
but may also be invoked after the kernel is up.
Before this change, fixmap page tables resided in memblock.
After the change, they are placed in the BSS segment.
Thus, the fixmap becomes usable both during early boot and
after kernel startup.
Signed-off-by: Haoran Jiang <jianghaoran@kylinos.cn>
---
arch/loongarch/include/asm/fixmap.h | 1 +
arch/loongarch/kernel/setup.c | 1 +
arch/loongarch/mm/init.c | 71 ++++++++++++++++++++++++++---
3 files changed, 67 insertions(+), 6 deletions(-)
diff --git a/arch/loongarch/include/asm/fixmap.h b/arch/loongarch/include/asm/fixmap.h
index dce2da6ba787..5a9b04c720bf 100644
--- a/arch/loongarch/include/asm/fixmap.h
+++ b/arch/loongarch/include/asm/fixmap.h
@@ -31,6 +31,7 @@ enum fixed_addresses {
extern void __set_fixmap(enum fixed_addresses idx,
phys_addr_t phys, pgprot_t flags);
+void __init early_fixmap_init(void);
#include <asm-generic/fixmap.h>
diff --git a/arch/loongarch/kernel/setup.c b/arch/loongarch/kernel/setup.c
index 839b23edee87..2724d67a96cc 100644
--- a/arch/loongarch/kernel/setup.c
+++ b/arch/loongarch/kernel/setup.c
@@ -599,6 +599,7 @@ void __init setup_arch(char **cmdline_p)
fdt_setup();
memblock_init();
pagetable_init();
+ early_fixmap_init();
bootcmdline_init(cmdline_p);
parse_early_param();
reserve_initrd_mem();
diff --git a/arch/loongarch/mm/init.c b/arch/loongarch/mm/init.c
index 031b39eb081c..4046d31f0266 100644
--- a/arch/loongarch/mm/init.c
+++ b/arch/loongarch/mm/init.c
@@ -36,6 +36,69 @@
#include <asm/pgalloc.h>
#include <asm/tlb.h>
+#define SPAN_NR_ENTRIES(vstart, vend, shift) \
+ ((((vend) - 1) >> (shift)) - ((vstart) >> (shift)) + 1)
+
+#define NR_BM_PTE_TABLES \
+ SPAN_NR_ENTRIES(FIXADDR_START, FIXADDR_TOP, PMD_SHIFT)
+
+#define __BM_TABLE_IDX(addr, shift) \
+ (((addr) >> (shift)) - (FIXADDR_START >> (shift)))
+
+#define BM_PTE_TABLE_IDX(addr) __BM_TABLE_IDX(addr, PMD_SHIFT)
+
+static pte_t bm_pte[NR_BM_PTE_TABLES][PTRS_PER_PTE] __page_aligned_bss;
+static pmd_t bm_pmd[PTRS_PER_PMD] __page_aligned_bss __maybe_unused;
+static pud_t bm_pud[PTRS_PER_PUD] __page_aligned_bss __maybe_unused;
+
+static inline pte_t *fixmap_pte(unsigned long addr)
+{
+ return &bm_pte[BM_PTE_TABLE_IDX(addr)][pte_index(addr)];
+}
+
+void __init early_fixmap_init(void)
+{
+ unsigned long addr = FIXADDR_START;
+ unsigned long end = FIXADDR_TOP;
+
+ pgd_t *pgd = pgd_offset_k(addr);
+ p4d_t *p4d = p4d_offset(pgd, addr);
+ pud_t *pud;
+ pmd_t *pmd;
+
+ unsigned long next;
+
+ if (p4d_none(p4dp_get(p4d))) {
+ pud = bm_pud;
+ p4d_populate(&init_mm, p4d, pud);
+#ifndef __PAGETABLE_PUD_FOLDED
+ pud_init(pud);
+#endif
+}
+
+ pud = pud_offset(p4d, addr);
+ if (pud_none(pudp_get(pud))) {
+ pmd = bm_pmd;
+ pud_populate(&init_mm, pud, pmd);
+#ifndef __PAGETABLE_PMD_FOLDED
+ pmd_init(pmd);
+#endif
+}
+
+ pmd = pmd_offset(pud, addr);
+ do {
+ next = pmd_addr_end(addr, end);
+ if (!pmd_present(pmdp_get(pmd))) {
+ pte_t *pte;
+
+ pte = bm_pte[BM_PTE_TABLE_IDX(addr)];
+ pmd_populate_kernel(&init_mm, pmd, pte);
+ kernel_pte_init(pte);
+ }
+ } while (pmd++, addr = next, addr != end);
+
+}
+
int __ref page_is_ram(unsigned long pfn)
{
unsigned long addr = PFN_PHYS(pfn);
@@ -203,7 +266,7 @@ pte_t * __init populate_kernel_pte(unsigned long addr)
return pte_offset_kernel(pmd, addr);
}
-void __init __set_fixmap(enum fixed_addresses idx,
+void __set_fixmap(enum fixed_addresses idx,
phys_addr_t phys, pgprot_t flags)
{
unsigned long addr = __fix_to_virt(idx);
@@ -211,11 +274,7 @@ void __init __set_fixmap(enum fixed_addresses idx,
BUG_ON(idx <= FIX_HOLE || idx >= __end_of_fixed_addresses);
- ptep = populate_kernel_pte(addr);
- if (!pte_none(ptep_get(ptep))) {
- pte_ERROR(*ptep);
- return;
- }
+ ptep = fixmap_pte(addr);
if (pgprot_val(flags))
set_pte(ptep, pfn_pte(phys >> PAGE_SHIFT, flags));
--
2.25.1
^ permalink raw reply [flat|nested] 4+ messages in thread
* [PATCH 2/2] LoongArch: Enable STRICT_MODULE_RWX for stricter modules memory permissions
2026-06-06 13:21 [PATCH 0/2] Enable STRICT_MODULE_RWX haoran.jiang
2026-06-06 13:21 ` [PATCH 1/2] LoongArch: Move fixmap page tables to BSS segment haoran.jiang
@ 2026-06-06 13:21 ` haoran.jiang
2026-06-06 14:04 ` [PATCH 0/2] Enable STRICT_MODULE_RWX Huacai Chen
2 siblings, 0 replies; 4+ messages in thread
From: haoran.jiang @ 2026-06-06 13:21 UTC (permalink / raw)
To: loongarch
Cc: linux-kernel, chenhuacai, kernel, akpm, jbohac, kees, yangtiezhu,
Haoran Jiang
From: Haoran Jiang <jianghaoran@kylinos.cn>
Enable STRICT_MODULE_RWX to enforce strict memory permissions
on modules,making the code region non-writable, the data region
non-executable, and the read-only data region both non-writable
and non-executable.Add patch_map interface to temporarily map
read-only code sections via fixmap, enabling runtime code patching
while preserving memory protection after modifications
Signed-off-by: Haoran Jiang <jianghaoran@kylinos.cn>
---
arch/loongarch/Kconfig | 2 ++
arch/loongarch/include/asm/fixmap.h | 1 +
arch/loongarch/kernel/inst.c | 29 ++++++++++++++++++++++++++++-
3 files changed, 31 insertions(+), 1 deletion(-)
diff --git a/arch/loongarch/Kconfig b/arch/loongarch/Kconfig
index 606597da46b8..40d748a13c50 100644
--- a/arch/loongarch/Kconfig
+++ b/arch/loongarch/Kconfig
@@ -27,6 +27,7 @@ config LOONGARCH
select ARCH_HAS_PTE_SPECIAL if 64BIT
select ARCH_HAS_SET_MEMORY
select ARCH_HAS_SET_DIRECT_MAP
+ select ARCH_HAS_STRICT_MODULE_RWX
select ARCH_HAS_TICK_BROADCAST if GENERIC_CLOCKEVENTS_BROADCAST
select ARCH_HAS_UBSAN
select ARCH_HAS_VDSO_ARCH_DATA
@@ -197,6 +198,7 @@ config LOONGARCH
select NUMA_MEMBLKS if NUMA
select OF
select OF_EARLY_FLATTREE
+ select ARCH_OPTIONAL_KERNEL_RWX
select PCI
select PCI_DOMAINS_GENERIC
select PCI_ECAM if ACPI
diff --git a/arch/loongarch/include/asm/fixmap.h b/arch/loongarch/include/asm/fixmap.h
index 5a9b04c720bf..7d174eafdc21 100644
--- a/arch/loongarch/include/asm/fixmap.h
+++ b/arch/loongarch/include/asm/fixmap.h
@@ -22,6 +22,7 @@ enum fixed_addresses {
FIX_KMAP_END = FIX_KMAP_BEGIN + (KM_MAX_IDX * NR_CPUS) - 1,
#endif
FIX_EARLYCON_MEM_BASE,
+ FIX_TEXT_POKE0,
__end_of_fixed_addresses
};
diff --git a/arch/loongarch/kernel/inst.c b/arch/loongarch/kernel/inst.c
index 0b9228b7c13a..7c4f60a7e892 100644
--- a/arch/loongarch/kernel/inst.c
+++ b/arch/loongarch/kernel/inst.c
@@ -9,9 +9,33 @@
#include <asm/cacheflush.h>
#include <asm/inst.h>
+#include <linux/kprobes.h>
static DEFINE_RAW_SPINLOCK(patch_lock);
+static void __kprobes *patch_map(void *addr, const unsigned int fixmap)
+{
+ phys_addr_t phys;
+
+ if ((unsigned long)addr < vm_map_base) {
+ return addr;
+ } else if (IS_ENABLED(CONFIG_STRICT_MODULE_RWX)) {
+ struct page *page = vmalloc_to_page(addr);
+
+ BUG_ON(!page);
+ phys = page_to_phys(page) + offset_in_page(addr);
+ } else {
+ return addr;
+ }
+
+ return (void *)set_fixmap_offset(fixmap, phys);
+}
+
+static void __kprobes patch_unmap(int fixmap)
+{
+ clear_fixmap(fixmap);
+}
+
void simu_pc(struct pt_regs *regs, union loongarch_instruction insn)
{
unsigned long pc = regs->csr_era;
@@ -208,12 +232,15 @@ int larch_insn_write(void *addr, u32 insn)
{
int ret;
unsigned long flags = 0;
+ void *waddr = addr;
if ((unsigned long)addr & 3)
return -EINVAL;
raw_spin_lock_irqsave(&patch_lock, flags);
- ret = copy_to_kernel_nofault(addr, &insn, LOONGARCH_INSN_SIZE);
+ waddr = patch_map(addr, FIX_TEXT_POKE0);
+ ret = copy_to_kernel_nofault(waddr, &insn, LOONGARCH_INSN_SIZE);
+ patch_unmap(FIX_TEXT_POKE0);
raw_spin_unlock_irqrestore(&patch_lock, flags);
return ret;
--
2.25.1
^ permalink raw reply [flat|nested] 4+ messages in thread
* Re: [PATCH 0/2] Enable STRICT_MODULE_RWX
2026-06-06 13:21 [PATCH 0/2] Enable STRICT_MODULE_RWX haoran.jiang
2026-06-06 13:21 ` [PATCH 1/2] LoongArch: Move fixmap page tables to BSS segment haoran.jiang
2026-06-06 13:21 ` [PATCH 2/2] LoongArch: Enable STRICT_MODULE_RWX for stricter modules memory permissions haoran.jiang
@ 2026-06-06 14:04 ` Huacai Chen
2 siblings, 0 replies; 4+ messages in thread
From: Huacai Chen @ 2026-06-06 14:04 UTC (permalink / raw)
To: haoran.jiang
Cc: loongarch, linux-kernel, kernel, akpm, jbohac, kees, yangtiezhu,
Haoran Jiang
Hi, Haoran,
On Sat, Jun 6, 2026 at 9:21 PM <haoran.jiang@linux.dev> wrote:
>
> From: Haoran Jiang <jianghaoran@kylinos.cn>
>
> Enable STRICT_MODULE_RWX on LoongArch and
> Move fixmap page tables to BSS segment.
As discussed before, we don't need to change fixmap, we can just use
set_memory() API, similar as done in larch_insn_text_copy().
Huacai
>
> Haoran Jiang (2):
> LoongArch: Move fixmap page tables to BSS segment
> LoongArch: Enable STRICT_MODULE_RWX for stricter modules memory
> permissions
>
> arch/loongarch/Kconfig | 2 +
> arch/loongarch/include/asm/fixmap.h | 2 +
> arch/loongarch/kernel/inst.c | 29 +++++++++++-
> arch/loongarch/kernel/setup.c | 1 +
> arch/loongarch/mm/init.c | 71 ++++++++++++++++++++++++++---
> 5 files changed, 98 insertions(+), 7 deletions(-)
>
> --
> 2.25.1
>
>
^ permalink raw reply [flat|nested] 4+ messages in thread
end of thread, other threads:[~2026-06-06 14:04 UTC | newest]
Thread overview: 4+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2026-06-06 13:21 [PATCH 0/2] Enable STRICT_MODULE_RWX haoran.jiang
2026-06-06 13:21 ` [PATCH 1/2] LoongArch: Move fixmap page tables to BSS segment haoran.jiang
2026-06-06 13:21 ` [PATCH 2/2] LoongArch: Enable STRICT_MODULE_RWX for stricter modules memory permissions haoran.jiang
2026-06-06 14:04 ` [PATCH 0/2] Enable STRICT_MODULE_RWX Huacai Chen
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox
Powered by JetHome