lua-lsm: support loadable API producers - #26
Open
chenzongyao200127 wants to merge 150 commits into
Open
Conversation
This reverts commit 97169cd.
The folling is main instructions: export PATH="$(brew --prefix make)/libexec/gnubin:$PATH" export PATH="$(brew --prefix llvm)/bin:$PATH" export PATH="$(brew --prefix lld)/bin:$PATH" # Eliminate compile errors of scripts/mod/file2alias.c export HOSTCFLAGS="-D_UUID_T -D__GETHOSTUUID_H" # Maybe the symlink is missed on macOS #ln -s ../../../scripts/syscall.tbl arch/arm64/tools/syscall_64.tbl #ln -s qcom,sm8550-dispcc.h include/dt-bindings/clock/qcom,sm8650-dispcc.h #make ARCH=arm64 LLVM=1 #make LLVM=1 menuconfig #make LLVM=1 -j8 Signed-off-by: Tianjia Zhang <tianjia.zhang@linux.alibaba.com>
When developing a dedicated LSM module, we need to operate on the file object within the LSM function, such as retrieving the path. However, in `security_file_alloc()`, the passed-in `filp` is only a valid pointer; the content of `filp` is completely uninitialized and entirely random, which confuses the LSM function. Therefore, it is necessary to call `security_file_alloc()` only after the main fields of the `filp` object have been initialized. This patch only moves the call to `security_file_alloc()` to the end of the `init_file()` function. Signed-off-by: Tianjia Zhang <tianjia.zhang@linux.alibaba.com>
Standard C provides basic library functions for jumping between functions. They were introduced to support the upcoming Lua language interpreter, which uses the setjmp/longjmp functions to implement exception handling. Signed-off-by: Tianjia Zhang <tianjia.zhang@linux.alibaba.com>
Standard C provides basic library functions for jumping between functions. They were introduced to support the upcoming Lua language interpreter, which uses the setjmp/longjmp functions to implement exception handling. Signed-off-by: Tianjia Zhang <tianjia.zhang@linux.alibaba.com>
Lua is an extension programming language designed to support general procedural programming with data description facilities. It also offers good support for object-oriented programming, functional programming, and data-driven programming. Lua is intended to be used as a powerful, light-weight scripting language for any program that needs one. Lua is implemented as a library, written in clean C (that is, in the common subset of ANSI C and C++). Lua is embedded in the kernel. Leveraging Lua's simplicity and powerful metaprogramming capabilities, it allows the use of scripting languages to develop complex security access control policies. The reason for choosing version 5.1 is that Lua has been mature enough since version 5.1, and secondly, LuaJIT may be introduced in the future for JIT acceleration. Currently, LuaJIT is compatible with version 5.1. Signed-off-by: Tianjia Zhang <tianjia.zhang@linux.alibaba.com>
queue.h and tree.h are borrowed from freebsd
d342ae67192f ("uath: add support for GCMP-128 encryption")
bitmap.h is borrowed from bitops of latest netbsd.
Signed-off-by: Tianjia Zhang <tianjia.zhang@linux.alibaba.com>
Fixes for queue and tree
Signed-off-by: Tianjia Zhang <tianjia.zhang@linux.alibaba.com>
Signed-off-by: Tianjia Zhang <tianjia.zhang@linux.alibaba.com> Co-developed-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Signed-off-by: Tianjia Zhang <tianjia.zhang@linux.alibaba.com>
Signed-off-by: Tianjia Zhang <tianjia.zhang@linux.alibaba.com>
Signed-off-by: Tianjia Zhang <tianjia.zhang@linux.alibaba.com>
Signed-off-by: Tianjia Zhang <tianjia.zhang@linux.alibaba.com>
Signed-off-by: Tianjia Zhang <tianjia.zhang@linux.alibaba.com>
This module leverages Lua's metaprogramming capabilities to develop complex access control logic and policies in Lua. Let us using a programmatic approach close to natural language, significantly lowers the barrier to entry for developing LSM access control. This module has the following notable features: * Supports developing LSM policies as mini-programs or LSM plugins. Multiple mini-programs or LSM plugins can be loaded simultaneously, and dynamic, on-demand uninstallation is supported. * Each mini-program runs in a secure sandbox environment. Script errors will not trigger kernel panics, and mini-programs are isolated from each other, ensuring no impact. * Mini-programs interact with the kernel through a specific, limited API, ensuring kernel security. * The LSM module features deep integration with the Lua language, enabling the most natural way to share data and set kernel object attributes. Signed-off-by: Tianjia Zhang <tianjia.zhang@linux.alibaba.com> Co-developed-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
The reason is that the modules_lock is held for a period of time during module registration. A softirq occurs within this critical section, and the softirq handler reenters the LSM function, causing a deadlock. This issue can be resolved by disabling softirq while holding the modules_lock lock during module registration. Some logs are as follows: [28031.294632] rcu: INFO: rcu_preempt self-detected stall on CPU [28031.294801] rcu: 2-...!: (886811 ticks this GP) idle=ea9c/1/0x4000000000000000 softirq=243287/243287 fqs=0 [28031.295043] rcu: (t=887418 jiffies g=263373 q=454 ncpus=4) [28031.295183] rcu: rcu_preempt kthread starved for 887418 jiffies! g263373 f0x0 RCU_GP_WAIT_FQS(5) ->state=0x0 ->cpu=2 [28031.295524] rcu: Unless rcu_preempt kthread gets sufficient CPU time, OOM is now expected behavior. [28031.295872] rcu: RCU grace-period kthread stack dump: [28031.296001] task:rcu_preempt state:R running task stack:0 pid:15 tgid:15 ppid:2 task_flags:0x208040 flags:0x00000010 [28031.296319] Call trace: [28031.296381] __switch_to+0x194/0x2b4 (T) [28031.296484] __schedule+0x5b4/0x980 [28031.296572] schedule+0x54/0xf8 [28031.296652] schedule_timeout+0x88/0xf8 [28031.296750] rcu_gp_fqs_loop+0x1c4/0x6b0 [28031.296851] rcu_gp_kthread+0x60/0x134 [28031.296946] kthread+0x140/0x254 [28031.297030] ret_from_fork+0x10/0x20 [28031.297123] Sending NMI from CPU 2 to CPUs 1: [28031.297242] NMI backtrace for cpu 1 [28031.297247] CPU: 1 UID: 0 PID: 81146 Comm: sh Not tainted 6.17.0-rc3+ #511 PREEMPT [28031.297249] Hardware name: QEMU QEMU Virtual Machine, BIOS edk2-stable202408-prebuilt.qemu.org 08/13/2024 [28031.297250] pstate: 01400005 (nzcv daif +PAN -UAO -TCO +DIT -SSBS BTYPE=--) [28031.297250] pc : queued_read_lock_slowpath+0x80/0x14c [28031.297253] lr : _raw_read_lock_bh+0x64/0x68 [28031.297254] sp : ffff800088ee39e0 [28031.297254] x29: ffff800088ee39e0 x28: 0000000000002e2e x27: 0000000000000501 [28031.297256] x26: 0000000000000030 x25: 2f2f2f2f2f2f2f2f x24: 61c8864680b583eb [28031.297257] x23: fefefefefefefeff x22: 0000000000000000 x21: ffff0000c2671138 [28031.297257] x20: 0000000000000081 x19: 00001643fef959e4 x18: 0000000000000000 [28031.297258] x17: 0000000000000000 x16: 0000000000000000 x15: 0000000000000000 [28031.297259] x14: 0000000000000000 x13: 0000000000000000 x12: 8080808080808000 [28031.297259] x11: 000000000000002e x10: 0000000000000018 x9 : 0000000000000000 [28031.297260] x8 : 00000000000008ff x7 : 0000000000000000 x6 : 0000000000000000 [28031.297261] x5 : 0000000000000000 x4 : 0000000000000000 x3 : ffff800088ee3c98 [28031.297261] x2 : 0000000000000000 x1 : 0000000000013cee x0 : ffff8000818ae3c8 [28031.297262] Call trace: [28031.297262] queued_read_lock_slowpath+0x80/0x14c (P) [28031.297264] _raw_read_lock_bh+0x64/0x68 [28031.297265] lua_lsm_inode_permission+0x54/0x35c [28031.297268] security_inode_permission+0x54/0xb0 [28031.297269] inode_permission+0x64/0x170 [28031.297270] link_path_walk+0xb4/0x388 [28031.297272] path_lookupat+0x68/0x120 [28031.297272] filename_lookup+0xe0/0x1e0 [28031.297273] vfs_statx+0x7c/0x1a0 [28031.297276] vfs_fstatat+0xb4/0xe0 [28031.297277] __arm64_sys_newfstatat+0x68/0xa8 [28031.297278] invoke_syscall+0x40/0xf8 [28031.297280] el0_svc_common+0xa8/0xd8 [28031.297281] do_el0_svc+0x1c/0x28 [28031.297282] el0_svc+0x38/0x8c [28031.297283] el0t_64_sync_handler+0x84/0x12c [28031.297284] el0t_64_sync+0x198/0x19c [28031.298239] CPU: 2 UID: 0 PID: 81145 Comm: cat Not tainted 6.17.0-rc3+ #511 PREEMPT [28031.303082] Hardware name: QEMU QEMU Virtual Machine, BIOS edk2-stable202408-prebuilt.qemu.org 08/13/2024 [28031.303326] pstate: 01400005 (nzcv daif +PAN -UAO -TCO +DIT -SSBS BTYPE=--) [28031.303504] pc : queued_read_lock_slowpath+0x80/0x14c [28031.303634] lr : _raw_read_lock_bh+0x64/0x68 [28031.303743] sp : ffff8000818ebe00 [28031.303828] x29: ffff8000818ebe00 x28: 0000000000000200 x27: 000000000000000a [28031.304011] x26: ffff800081788000 x25: ffff8000800fa104 x24: 0000000000000001 [28031.304192] x23: 0000000000000000 x22: 000000000000000a x21: 0000000000000000 [28031.304374] x20: ffff000008774600 x19: 00001643fef8ae04 x18: 0000000000000000 [28031.304556] x17: ffff80007e099000 x16: ffff8000818e8000 x15: 0000000000000000 [28031.304739] x14: 0000000000000004 x13: ffff0000ff6187a8 x12: 0000000000000002 [28031.304922] x11: ffff0000c2288a18 x10: 0000000000000018 x9 : 0000000000000000 [28031.305104] x8 : 00000000000008ff x7 : 7fffffffffffffff x6 : 00003d0900007d00 [28031.305285] x5 : ffff800081874120 x4 : 0000000000000008 x3 : ffff80008a153710 [28031.305470] x2 : 00000000000404d4 x1 : 00000000000138ce x0 : ffff8000818ae3c8 [28031.305651] Call trace: [28031.305714] queued_read_lock_slowpath+0x80/0x14c (P) [28031.305844] _raw_read_lock_bh+0x64/0x68 [28031.305945] lua_lsm_cred_free+0x54/0x2bc [28031.306048] security_cred_free+0x5c/0x90 [28031.306151] put_cred_rcu+0x28/0x15c [28031.306244] rcu_core+0x2c0/0x5e0 [28031.306330] rcu_core_si+0x10/0x1c [28031.306418] handle_softirqs+0xdc/0x200 [28031.306517] __do_softirq+0x14/0x20 [28031.306686] ____do_softirq+0x10/0x1c [28031.306782] call_on_irq_stack+0x30/0x48 [28031.306884] do_softirq_own_stack+0x1c/0x28 [28031.306993] __irq_exit_rcu+0x54/0xf8 [28031.307087] irq_exit_rcu+0x10/0x1c [28031.307176] el1_interrupt+0x38/0x54 [28031.307269] el1h_64_irq_handler+0x18/0x24 [28031.307375] el1h_64_irq+0x6c/0x70 [28031.307463] lua_module_register+0x550/0x588 (P) [28031.307582] register_write+0x78/0xac [28031.307676] vfs_write+0x160/0x3bc [28031.307764] ksys_write+0x70/0xe4 [28031.307849] __arm64_sys_write+0x1c/0x28 [28031.307950] invoke_syscall+0x40/0xf8 [28031.308044] el0_svc_common+0xa8/0xd8 [28031.308138] do_el0_svc+0x1c/0x28 [28031.308225] el0_svc+0x38/0x8c [28031.308311] el0t_64_sync_handler+0x84/0x12c [28031.308422] el0t_64_sync+0x198/0x19c
When interrupts are disabled, file system operations triggered by memory
allocation may cause a potential deadlock.
The log is as follows:
[ 37.041540] =====================================================
[ 37.041790] WARNING: SOFTIRQ-safe -> SOFTIRQ-unsafe lock order detected
[ 37.042170] 6.17.0-rc3+ #515 Tainted: G W
[ 37.042492] -----------------------------------------------------
[ 37.042953] cat/1610 [HC0[0]:SC0[2]:HE1:SE0] is trying to acquire:
[ 37.043316] ffff800081f2b9f8 (fs_reclaim){+.+.}-{0:0}, at: __kmalloc_noprof+0xb0/0x4d4
[ 37.043783]
[ 37.043783] and this task is already holding:
[ 37.044121] ffff0000c177e138 (&dict->lock){+.-.}-{3:3}, at: kvcache_incr+0x68/0x21c
[ 37.044569] which would create a new lock dependency:
[ 37.044861] (&dict->lock){+.-.}-{3:3} -> (fs_reclaim){+.+.}-{0:0}
[ 37.045222]
[ 37.045222] but this new dependency connects a SOFTIRQ-irq-safe lock:
[ 37.045685] (&dict->lock){+.-.}-{3:3}
[ 37.045687]
[ 37.045687] ... which became SOFTIRQ-irq-safe at:
[ 37.046273] lock_acquire+0x118/0x26c
[ 37.046479] _raw_write_lock+0x4c/0x88
[ 37.046736] kvcache_dict_free+0x24/0x104
[ 37.046950] lua_lsm_inode_free_security_rcu+0x1d4/0x274
[ 37.047231] inode_free_by_rcu+0x54/0x9c
[ 37.047442] rcu_core+0x474/0xa50
[ 37.047623] rcu_core_si+0x10/0x1c
[ 37.047805] handle_softirqs+0x178/0x42c
[ 37.048018] __do_softirq+0x14/0x20
[ 37.048205] ____do_softirq+0x10/0x1c
[ 37.048404] call_on_irq_stack+0x30/0x48
[ 37.048614] do_softirq_own_stack+0x1c/0x28
[ 37.048838] __irq_exit_rcu+0xd4/0x194
[ 37.049039] irq_exit_rcu+0x10/0x34
[ 37.049226] el1_interrupt+0x38/0x54
[ 37.049418] el1h_64_irq_handler+0x18/0x24
[ 37.049636] el1h_64_irq+0x6c/0x70
[ 37.049818] do_idle+0xe8/0x26c
[ 37.049994] cpu_startup_entry+0x34/0x38
[ 37.050206] kernel_init+0x0/0x128
[ 37.050389] start_kernel+0x304/0x3c0
[ 37.050659] __primary_switched+0x88/0x90
[ 37.050881]
[ 37.050881] to a SOFTIRQ-irq-unsafe lock:
[ 37.051169] (fs_reclaim){+.+.}-{0:0}
[ 37.051171]
[ 37.051171] ... which became SOFTIRQ-irq-unsafe at:
[ 37.051699] ...
[ 37.051704] lock_acquire+0x118/0x26c
[ 37.051997] fs_reclaim_acquire+0x64/0xd0
[ 37.052215] mem_cgroup_css_alloc+0xdc/0x6e4
[ 37.052436] cgroup_init_subsys+0x7c/0x1d0
[ 37.052642] cgroup_init+0x2d8/0x490
[ 37.052822] start_kernel+0x2f4/0x3c0
[ 37.053006] __primary_switched+0x88/0x90
[ 37.053210]
[ 37.053210] other info that might help us debug this:
[ 37.053210]
[ 37.053598] Possible interrupt unsafe locking scenario:
[ 37.053598]
[ 37.053929] CPU0 CPU1
[ 37.054152] ---- ----
[ 37.054372] lock(fs_reclaim);
[ 37.054649] local_irq_disable();
[ 37.055469] lock(&dict->lock);
[ 37.055751] lock(fs_reclaim);
[ 37.056024] <Interrupt>
[ 37.056151] lock(&dict->lock);
[ 37.056316]
[ 37.056316] *** DEADLOCK ***
[ 37.056316]
[ 37.056602] 2 locks held by cat/1610:
[ 37.056779] #0: ffff800081fdaf18 (modules_lock){++.-}-{3:3}, at: lua_lsm_file_permission+0x58/0x36c
[ 37.057221] openanolis#1: ffff0000c177e138 (&dict->lock){+.-.}-{3:3}, at: kvcache_incr+0x68/0x21c
[ 37.057611]
[ 37.057611] the dependencies between SOFTIRQ-irq-safe lock and the holding lock:
[ 37.058091] -> (&dict->lock){+.-.}-{3:3} {
[ 37.058303] HARDIRQ-ON-W at:
[ 37.058495] lock_acquire+0x118/0x26c
[ 37.058777] _raw_write_lock+0x4c/0x88
[ 37.059053] kvcache_dict_free+0x24/0x104
[ 37.059353] lua_lsm_file_free_security+0x210/0x2bc
[ 37.059691] security_file_free+0x5c/0xa4
[ 37.059991] __fput+0x1a0/0x2f0
[ 37.060242] delayed_fput+0x44/0x58
[ 37.060514] process_one_work+0x210/0x548
[ 37.060815] worker_thread+0x244/0x380
[ 37.061096] kthread+0x138/0x260
[ 37.061348] ret_from_fork+0x10/0x20
[ 37.061622] IN-SOFTIRQ-W at:
[ 37.061790] lock_acquire+0x118/0x26c
[ 37.062117] _raw_write_lock+0x4c/0x88
[ 37.062405] kvcache_dict_free+0x24/0x104
[ 37.062730] lua_lsm_inode_free_security_rcu+0x1d4/0x274
[ 37.063097] inode_free_by_rcu+0x54/0x9c
[ 37.063390] rcu_core+0x474/0xa50
[ 37.063652] rcu_core_si+0x10/0x1c
[ 37.063917] handle_softirqs+0x178/0x42c
[ 37.064213] __do_softirq+0x14/0x20
[ 37.064475] ____do_softirq+0x10/0x1c
[ 37.064739] call_on_irq_stack+0x30/0x48
[ 37.065014] do_softirq_own_stack+0x1c/0x28
[ 37.065307] __irq_exit_rcu+0xd4/0x194
[ 37.065583] irq_exit_rcu+0x10/0x34
[ 37.065901] el1_interrupt+0x38/0x54
[ 37.066155] el1h_64_irq_handler+0x18/0x24
[ 37.066399] el1h_64_irq+0x6c/0x70
[ 37.066660] do_idle+0xe8/0x26c
[ 37.066891] cpu_startup_entry+0x34/0x38
[ 37.067168] kernel_init+0x0/0x128
[ 37.067418] start_kernel+0x304/0x3c0
[ 37.067679] __primary_switched+0x88/0x90
[ 37.067959] INITIAL USE at:
[ 37.068115] lock_acquire+0x118/0x26c
[ 37.068375] _raw_write_lock+0x4c/0x88
[ 37.068637] kvcache_dict_free+0x24/0x104
[ 37.068917] lua_lsm_file_free_security+0x210/0x2bc
[ 37.069222] security_file_free+0x5c/0xa4
[ 37.069499] __fput+0x1a0/0x2f0
[ 37.069726] delayed_fput+0x44/0x58
[ 37.070043] process_one_work+0x210/0x548
[ 37.070282] worker_thread+0x244/0x380
[ 37.070499] kthread+0x138/0x260
[ 37.070713] ret_from_fork+0x10/0x20
[ 37.070923] }
[ 37.070992] ... key at: [<ffff800082ce7398>] kvcache_dict_init.__key+0x0/0x10
[ 37.071308]
[ 37.071308] the dependencies between the lock to be acquired
[ 37.071309] and SOFTIRQ-irq-unsafe lock:
[ 37.071759] -> (fs_reclaim){+.+.}-{0:0} {
[ 37.071923] HARDIRQ-ON-W at:
[ 37.072052] lock_acquire+0x118/0x26c
[ 37.072268] fs_reclaim_acquire+0x64/0xd0
[ 37.072499] mem_cgroup_css_alloc+0xdc/0x6e4
[ 37.072740] cgroup_init_subsys+0x7c/0x1d0
[ 37.072974] cgroup_init+0x2d8/0x490
[ 37.073187] start_kernel+0x2f4/0x3c0
[ 37.073403] __primary_switched+0x88/0x90
[ 37.073633] SOFTIRQ-ON-W at:
[ 37.073761] lock_acquire+0x118/0x26c
[ 37.074010] fs_reclaim_acquire+0x64/0xd0
[ 37.074241] mem_cgroup_css_alloc+0xdc/0x6e4
[ 37.074482] cgroup_init_subsys+0x7c/0x1d0
[ 37.074735] cgroup_init+0x2d8/0x490
[ 37.074947] start_kernel+0x2f4/0x3c0
[ 37.075160] __primary_switched+0x88/0x90
[ 37.075388] INITIAL USE at:
[ 37.075512] lock_acquire+0x118/0x26c
[ 37.075722] fs_reclaim_acquire+0x64/0xd0
[ 37.075944] mem_cgroup_css_alloc+0xdc/0x6e4
[ 37.076169] cgroup_init_subsys+0x7c/0x1d0
[ 37.076399] cgroup_init+0x2d8/0x490
[ 37.076598] start_kernel+0x2f4/0x3c0
[ 37.076798] __primary_switched+0x88/0x90
[ 37.077012] }
[ 37.077078] ... key at: [<ffff800081f2b9f8>] __fs_reclaim_map+0x0/0x30
[ 37.077349] ... acquired at:
[ 37.077464] fs_reclaim_acquire+0x64/0xd0
[ 37.077628] __kmalloc_noprof+0xb0/0x4d4
[ 37.077787] kvcache_incr+0xe0/0x21c
[ 37.077967] shdict_incr+0x34/0x44
[ 37.078108] luaD_precall+0x330/0x674
[ 37.078259] luaV_execute+0xaac/0x119c
[ 37.078413] luaD_call+0xb0/0x128
[ 37.078550] f_call+0x1c/0x28
[ 37.078692] luaD_rawrunprotected+0x7c/0xb8
[ 37.078862] luaD_pcall+0x40/0x184
[ 37.079003] lua_pcall+0xac/0x190
[ 37.079191] lua_lsm_file_permission+0x1fc/0x36c
[ 37.079379] security_file_permission+0x4c/0xa8
[ 37.079562] rw_verify_area+0x54/0x138
[ 37.079715] vfs_read+0xa4/0x2b0
[ 37.079846] ksys_read+0x70/0xe4
[ 37.079974] __arm64_sys_read+0x1c/0x28
[ 37.080123] invoke_syscall+0x40/0xf8
[ 37.080269] el0_svc_common+0xa8/0xd8
[ 37.080413] do_el0_svc+0x1c/0x28
[ 37.080544] el0_svc+0x50/0xcc
[ 37.080665] el0t_64_sync_handler+0x84/0x12c
[ 37.080831] el0t_64_sync+0x198/0x19c
[ 37.080975]
[ 37.081031]
[ 37.081031] stack backtrace:
[ 37.081195] CPU: 1 UID: 0 PID: 1610 Comm: cat Tainted: G W 6.17.0-rc3+ #515 PREEMPT
[ 37.081535] Tainted: [W]=WARN
[ 37.081646] Hardware name: QEMU QEMU Virtual Machine, BIOS edk2-stable202408-prebuilt.qemu.org 08/13/2024
[ 37.082039] Call trace:
[ 37.082130] show_stack+0x18/0x24 (C)
[ 37.082269] __dump_stack+0x28/0x38
[ 37.082400] dump_stack_lvl+0x64/0x84
[ 37.082537] dump_stack+0x18/0x24
[ 37.082688] __lock_acquire+0x2b2c/0x2b90
[ 37.082837] lock_acquire+0x118/0x26c
[ 37.082972] fs_reclaim_acquire+0x64/0xd0
[ 37.083119] __kmalloc_noprof+0xb0/0x4d4
[ 37.083264] kvcache_incr+0xe0/0x21c
[ 37.083395] shdict_incr+0x34/0x44
[ 37.083520] luaD_precall+0x330/0x674
[ 37.083656] luaV_execute+0xaac/0x119c
[ 37.083793] luaD_call+0xb0/0x128
[ 37.083916] f_call+0x1c/0x28
[ 37.084025] luaD_rawrunprotected+0x7c/0xb8
[ 37.084180] luaD_pcall+0x40/0x184
[ 37.084306] lua_pcall+0xac/0x190
[ 37.084428] lua_lsm_file_permission+0x1fc/0x36c
[ 37.084598] security_file_permission+0x4c/0xa8
[ 37.084765] rw_verify_area+0x54/0x138
[ 37.084902] vfs_read+0xa4/0x2b0
[ 37.085021] ksys_read+0x70/0xe4
[ 37.085139] __arm64_sys_read+0x1c/0x28
[ 37.085280] invoke_syscall+0x40/0xf8
[ 37.085416] el0_svc_common+0xa8/0xd8
[ 37.085553] do_el0_svc+0x1c/0x28
[ 37.085676] el0_svc+0x50/0xcc
[ 37.085790] el0t_64_sync_handler+0x84/0x12c
[ 37.086018] el0t_64_sync+0x198/0x19c
Lazy kvcache initialization leaves a dictionary in INITING until __kvcache_dict_init() finishes. A same-CPU softirq hook can reenter the Lua path in that window, observe INITING for the current task's dictionary, and spin in kvcache_dict_ready() until the interrupted task context runs again. Disable bottom halves around the UNINIT -> INITING -> READY publication window so same-CPU softirq reentry cannot observe the transient state. While here, rename the inactive-cleanup static key from *_possible to *_armed to better match its one-way semantics after the first policy load. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Export the Lua runtime and lua-lsm auxiliary helpers needed by loadable API producer modules. Keep the exported surface limited to the functions used by the per-library modules. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Add the descriptor and registration entry points used by API libraries to publish their Lua functions to the lua-lsm core. The ABI also documents ownership, versioning, and metatable install contracts. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Move API object metatable creation behind a core-owned installer. Producer modules can attach their method tables without exporting the raw metatable construction helpers. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Add the registry that validates producer descriptors, audits registration attempts, replays libraries into live Lua VMs, and keeps CPU hotplug state synchronized. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Teach the lua-lsm core to build Lua states from the dynamic API library registry. Expose the VM and pool helpers needed by registry replay and invalidate stale pooled VMs by generation. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Register the kernel API surface through the new producer ABI. Keep object metatable setup in an open_extras callback, and route non-exported task lookup helpers through lua-lsm wrappers. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Register the filesystem API surface as an independent producer. Move filesystem object metatable installation into the producer callback so the library can be built separately from the core. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Register the networking API surface as an independent producer. Install socket-related object methods through the shared metatable helper instead of opening the library from the core. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Register the errno API surface through the producer ABI. Publish the errname helper and errno constants from the library callback. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Register the capability API surface through the producer ABI. Attach capability object methods through the shared metatable helper before publishing constants. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Register the signal API surface through the producer ABI. Use an empty function table and publish signal constants from the extras callback. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Document how lua-lsm API libraries register with the core and how the registry updates live Lua VMs. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Only task_blob_free() walked _MODULES before reusing a dirty VM, so pool overflow, drain, and register-time swap paths leaked policy module references and made unregister fail with -EBUSY. Move the walk into lua_state_free() under srcu_read_lock(&modules_ss) so every destruction path accounts uniformly. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Built-in (owner==NULL) producers are part of vmlinux text, already covered by the boot-time signature gate. The lockdown gate matches the signed-API gate and lets them through. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Make the helper name describe its actual contract more clearly. It recovers the owning lvm_state from a lua_State created by lua-lsm. The old name, lvm_state_from_state(), was ambiguous because both objects are kinds of state. Rename it and tighten the comment so the call sites read more clearly. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Rename lua_modules_free() to lvm_put_loaded_modules() so the helper name reflects its actual job: drop the loaded-module references recorded in a Lua VM and decrement module->nloaded. Update the associated comment and log messages to match. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Rename the heap-owned lvm_state cleanup helper so callers can tell it frees both the Lua state and the lvm_state storage. Keep the embedded state cleanup path separate through lua_state_free(). Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Make the signed API producer gate depend on module signature support. Without module signatures, the runtime signature check cannot make a trustworthy unsigned-module decision. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Mark replacement IRQ and current task VMs with the generation that will be published when API library registration commits. Also stamp offline CPU IRQ VMs after hotplug replay succeeds. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Detect task-owned Lua VMs that were built before the latest API library registration and replace them before returning the VM to hook dispatch. This lets existing tasks observe newly registered API libraries without mutating a VM that is currently in use. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Replace the internal registration notes with a user-facing guide for building Lua API producer modules outside the kernel tree. Include a small time library example, build commands, and policy usage. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
chenzongyao200127
force-pushed
the
lua-lsm-per-lib-ko
branch
from
June 17, 2026 07:51
e699b9b to
601cdce
Compare
Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Tighten Lua API producer admission around loadable modules. Rename the optional table initializer field to init_table, keep the reserved open hook opaque, and update in-tree producers accordingly. Drop the unconditional lockdown rejection and rely on the signed-producer policy when configured. Validate published callbacks against the pinned owner module's core text before replaying the library into live VMs. Reject API library names already occupied by the kernel Lua standard libraries so registration cannot silently succeed without installing the producer. Signed-off-by: Zongyao Chen <ZongYao.Chen@linux.alibaba.com>
Collaborator
Author
|
@uudiin Hi, please take a look at this PR when. If the diff is too large to review comfortably, I'm happy to split it into smaller logical commits (or separate PRs) to make the review easier — just let me know. |
uudiin
pushed a commit
that referenced
this pull request
Aug 21, 2026
The xfstests' test-case generic/642 finishes with corrupted HFS+ volume: sudo ./check generic/642 [sudo] password for slavad: FSTYP -- hfsplus PLATFORM -- Linux/x86_64 hfsplus-testing-0001 7.0.0-rc1+ #26 SMP PREEMPT_DYNAMIC Mon Mar 23 17:24:32 PDT 2026 MKFS_OPTIONS -- /dev/loop51 MOUNT_OPTIONS -- /dev/loop51 /mnt/scratch generic/642 6s ... _check_generic_filesystem: filesystem on /dev/loop51 is inconsistent (see xfstests-dev/results//generic/642.full for details) Ran: generic/642 Failures: generic/642 Failed 1 of 1 tests sudo fsck.hfs -d /dev/loop51 ** /dev/loop51 Using cacheBlockSize=32K cacheTotalBlock=1024 cacheSize=32768K. Executing fsck_hfs (version 540.1-Linux). ** Checking non-journaled HFS Plus Volume. The volume name is untitled ** Checking extents overflow file. ** Checking catalog file. ** Checking multi-linked files. ** Checking catalog hierarchy. ** Checking extended attributes file. invalid free nodes - calculated 1637 header 1260 Invalid B-tree header Invalid map node (8, 0) ** Checking volume bitmap. ** Checking volume information. Verify Status: VIStat = 0x0000, ABTStat = 0xc000 EBTStat = 0x0000 CBTStat = 0x0000 CatStat = 0x00000000 ** Repairing volume. ** Rechecking volume. ** Checking non-journaled HFS Plus Volume. The volume name is untitled ** Checking extents overflow file. ** Checking catalog file. ** Checking multi-linked files. ** Checking catalog hierarchy. ** Checking extended attributes file. ** Checking volume bitmap. ** Checking volume information. ** The volume untitled was repaired successfully. The fsck tool detected that Extended Attributes b-tree is corrupted. Namely, the free nodes number is incorrect and map node bitmap has inconsistent state. Analysis has shown that during b-tree closing there are still some lost b-tree's nodes in the hash out of b-tree structure. But this orphaned b-tree nodes are still accounted as used in map node bitmap: tree_cnid 8, nidx 0, node_count 1408, free_nodes 1403 tree_cnid 8, nidx 1, node_count 1408, free_nodes 1403 tree_cnid 8, nidx 3, node_count 1408, free_nodes 1403 tree_cnid 8, nidx 54, node_count 1408, free_nodes 1403 tree_cnid 8, nidx 67, node_count 1408, free_nodes 1403 tree_cnid 8, nidx 0, prev 0, next 0, parent 0, num_recs 3, type 0x1, height 0 tree_cnid 8, nidx 1, prev 0, next 0, parent 3, num_recs 1, type 0xff, height 1 tree_cnid 8, nidx 3, prev 0, next 0, parent 0, num_recs 1, type 0x0, height 2 tree_cnid 8, nidx 54, prev 29, next 46, parent 3, num_recs 0, type 0xff, height 1 tree_cnid 8, nidx 67, prev 8, next 14, parent 3, num_recs 0, type 0xff, height 1 This issue happens in hfs_bnode_split() logic during detection the possibility of moving half ot the records out of the node. The hfs_bnode_split() contains a loop that implements a roughly 50/50 split of the B-tree node's records by scanning the offset table to find where the data crosses the node's midpoint. If this logic detects the incapability of spliting the node, then it simply calls hfs_bnode_put() for newly created node. However, node is not set as HFS_BNODE_DELETED and real deletion of node doesn't happen. As a result, the empty node becomes orphaned but it is still accounted as used. Finally, fsck tool detects this inconsistency of HFS+ volume. This patch adds call of hfs_bnode_unlink() before hfs_bnode_put() for the case if new node cannot be used for spliting the existing node. sudo ./check generic/642 FSTYP -- hfsplus PLATFORM -- Linux/x86_64 hfsplus-testing-0001 7.0.0-rc1+ #26 SMP PREEMPT_DYNAMIC Fri Apr 3 12:39:13 PDT 2026 MKFS_OPTIONS -- /dev/loop51 MOUNT_OPTIONS -- /dev/loop51 /mnt/scratch generic/642 40s ... 39s Ran: generic/642 Passed all 1 tests Closes: hfs-linux-kernel/hfs-linux-kernel#242 cc: John Paul Adrian Glaubitz <glaubitz@physik.fu-berlin.de> cc: Yangtao Li <frank.li@vivo.com> cc: linux-fsdevel@vger.kernel.org Signed-off-by: Viacheslav Dubeyko <slava@dubeyko.com> Link: https://lore.kernel.org/r/20260403230556.614171-6-slava@dubeyko.com Signed-off-by: Viacheslav Dubeyko <slava@dubeyko.com>
uudiin
pushed a commit
that referenced
this pull request
Aug 21, 2026
ath12k_core_get_wsi_info() traverses the WSI (Wired Serial Interface) device graph starting from dev->of_node. The current code uses dev->of_node directly as the local traversal pointer and calls of_node_put() on error. Since the driver does not own a reference to dev->of_node, dropping it during traversal results in the following OF refcount underflow: OF: ERROR: of_node_release() detected bad of_node_put() on /soc@0/wifi@c000000 CPU: 1 UID: 0 PID: 210 Comm: insmod Not tainted 6.19.0-rc4-next-20260109-00023-g797dd36dc178 #26 PREEMPT Hardware name: Qualcomm Technologies, Inc. IPQ5332 MI01.2 (DT) Call trace: show_stack+0x18/0x24 (C) dump_stack_lvl+0x60/0x80 dump_stack+0x18/0x24 of_node_release+0x164/0x1a0 kobject_put+0xb4/0x278 of_node_put+0x18/0x28 ath12k_core_init+0x29c/0x5d4 [ath12k] ath12k_ahb_probe+0x950/0xc14 [ath12k] platform_probe+0x5c/0xa4 really_probe+0xc0/0x3ec __driver_probe_device+0x80/0x170 driver_probe_device+0x3c/0x120 __driver_attach+0xc4/0x218 OF: ERROR: next of_node_put() on this node will result in a kobject warning 'refcount_t: underflow; use-after-free.' Fix this by explicitly acquiring a reference to the starting node using of_node_get() and attaching automatic cleanup via __free(device_node). Each discovered WSI node is stored in ag->wsi_node[] with its own of_node_get() reference. These references are later released in ath12k_core_free_wsi_info() during driver teardown. Also remove unnecessary memset() of wsi_node array since cleanup now explicitly sets pointers to NULL. Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.6-01243-QCAHKSWPL_SILICONZ-1 Tested-on: IPQ5332 hw1.0 AHB WLAN.WBE.1.6-01275-QCAHKSWPL_SILICONZ-1 Fixes: 908c10c ("wifi: ath12k: parse multiple device information from Device Tree") Signed-off-by: Aaradhana Sahu <aaradhana.sahu@oss.qualcomm.com> Reviewed-by: Rameshkumar Sundaram <rameshkumar.sundaram@oss.qualcomm.com> Reviewed-by: Baochen Qiang <baochen.qiang@oss.qualcomm.com> Link: https://patch.msgid.link/20260410071300.2323603-1-aaradhana.sahu@oss.qualcomm.com Signed-off-by: Jeff Johnson <jeff.johnson@oss.qualcomm.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Add a registration path for Lua-LSM API libraries so the Lua-callable
surface can be provided by independent producer modules instead of being
fully tied to the core LSM object.
This allows the existing
kernel,fs,net,errno,capability,and
signallibraries to be built either into vmlinux or as loadableproducer modules, documents how external producers can register their
own Lua APIs, and exposes the live API library registry through
securityfsfor inspection.Changes
rollback handling.
closures may be reachable from Lua VMs.
enabled.
/sys/kernel/security/lua/api_libraries.securityfs example
Example output:
API set versionincrements when the registered Lua API library setchanges.
extra-initindicates whether the library defines anopen_extrascallback in addition to the plainluaL_Regfunctionarray.
Validation
The ignored checkpatch message types are limited to Lua API naming
(
luaL_Reg) and the standard new-file MAINTAINERS reminder.