我尝试使用 kretprobe 挂钩系统调用 __x64_sys_execve。因此,在条目处理程序中,我尝试获取其参数,并使用 strncpy_from_user 获取 char* 文件名 (char**)argv。但是在编译模块和 insmod 后,从 dmesg 没有得到任何新内容,当我尝试时删除模块,它被杀死并且系统崩溃。
我的代码:
#ifndef _LARGEFILE64_SOURCE
#define _LARGEFILE64_SOURCE
#endif
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/syscalls.h>
#include <linux/file.h>
#include <linux/fs.h>
#include <linux/string.h>
#include <linux/mm.h>
#include <linux/sched.h>
#include <linux/unistd.h>
#include <asm/pgtable.h>
#include <asm/uaccess.h>
#include <asm/ptrace.h>
#include <linux/kprobes.h>
#include <linux/net.h>
#include <linux/in.h>
/*
** module macros
*/
MODULE_LICENSE("GPL");
MODULE_AUTHOR("sena");
MODULE_DESCRIPTION("hook execve");
#define MAX_LENGTH 256
#define PREDEFINED_RET -2024
#define SUCCESS_RET 1
#define MAX_ARGS 10
#define MAX_ARG_LENGTH 50
typedef struct execve_data_t{
char filename[MAX_LENGTH];
char argv[MAX_ARGS][MAX_ARG_LENGTH];
} execve_data_t;
execve_data_t execve_data;
static int sys_execve_kretprobe_entry_handler(struct kretprobe_instance *ri, struct pt_regs *regs){
memset(&execve_data, 0, sizeof(execve_data));
struct pt_regs *user_regs;
user_regs = regs->di;
char __user* __user* argv_tmp = (char __user* __user*)user_regs->si; //maybe stuck here
if(strncpy_from_user(execve_data.filename, (char __user*)user_regs->di, sizeof(execve_data.filename)) > 0){
pr_info("execve filename success\n");
}
for(int i = 0 ; i < MAX_ARGS ; i++){
if(!argv_tmp[i]) break;
if(strncpy_from_user(execve_data.argv[i], (char __user*)argv_tmp[i], sizeof(execve_data.argv[i])) > 0){
pr_info("execve argv: %s", execve_data.argv[i]);
}
else{
break;
}
}
return 0;
}
struct kretprobe syscall_execve_kretprobe = {
.kp.symbol_name = "__x64_sys_execve",
.entry_handler = sys_execve_kretprobe_entry_handler,
.maxactive = 20, // Maximum number of concurrent probes
};
static int __init audit_init(void)
{
int err = 0;
err += register_kretprobe(&syscall_execve_kretprobe);
if (err) {
pr_err("register_kprobe() failed: %d\n", err);
return err;
}
else{
pr_info("register_kprobe() init: %d\n", err);
}
return 0;
}
static void __exit audit_exit(void)
{
unregister_kretprobe(&syscall_execve_kretprobe);
pr_info("kprobe unregistered\n");
}
module_init(audit_init);
module_exit(audit_exit);
我猜问题全都与argv有关,因为如果我将entry_handler替换为:
static int sys_execve_kretprobe_entry_handler(struct kretprobe_instance *ri, struct pt_regs *regs){
memset(&execve_data, 0, sizeof(execve_data));
struct pt_regs *user_regs;
user_regs = regs->di;
if(strncpy_from_user(execve_data.filename, (char __user*)user_regs->di, sizeof(execve_data.filename)) > 0){
pr_info("execve filename success\n");
}
return 0;
}
那么它与文件名配合得很好。
我在 dmesg 中遇到错误
[ 77.019298] execve filename success
[ 77.019307] BUG: unable to handle page fault for address: 0000212400c64d20
[ 77.019312] #PF: supervisor read access in kernel mode
[ 77.019315] #PF: error_code(0x0001) - permissions violation
[ 77.019318] PGD 7ae64067 P4D 7ae64067 PUD 3131d067 PMD 5239067 PTE 8000000091a8e845
[ 77.019327] Oops: 0001 [#1] PREEMPT SMP NOPTI
[ 77.019364] CPU: 0 PID: 4118 Comm: code Tainted: G OE 6.5.0-41-generic #41~22.04.2-Ubuntu
[ 77.019369] Hardware name: VMware, Inc. VMware Virtual Platform/440BX Desktop Reference Platform, BIOS 6.00 07/22/2020
[ 77.019371] RIP: 0010:sys_execve_kretprobe_entry_handler+0x5d/0xf0 [AuditModule]
[ 77.019384] Code: 8b 46 70 48 8b 70 70 4c 8b 68 68 e8 8d 0a f9 c0 48 85 c0 7e 0c 48 c7 c7 86 c1 93 c0 e8 fc f4 86 c0 49 c7 c4 00 8f 93 c0 31 db <4d> 8b 75 00 4d 85 f6 74 43 4c 63 fb 49 83 ff 0a 77 53 ba 14 00 00
[ 77.019387] RSP: 0018:ffffc90005547cb0 EFLAGS: 00010246
[ 77.019391] RAX: 0000000000000017 RBX: 0000000000000000 RCX: 0000000000000000
[ 77.019393] RDX: 0000000000000000 RSI: 0000000000000000 RDI: 0000000000000000
[ 77.019395] RBP: ffffc90005547cd8 R08: 0000000000000000 R09: 0000000000000000
[ 77.019398] R10: 0000000000000000 R11: 0000000000000000 R12: ffffffffc0938f00
[ 77.019400] R13: 0000212400c64d20 R14: ffffffffc09382e0 R15: ffff888139e1fec0
[ 77.019403] FS: 00007b20a38b8e80(0000) GS:ffff888139e00000(0000) knlGS:0000000000000000
[ 77.019405] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033
[ 77.019408] CR2: 0000212400c64d20 CR3: 000000000518c000 CR4: 00000000003506f0
[ 77.019412] Call Trace:
[ 77.019415] <TASK>
[ 77.019420] ? show_regs+0x6d/0x80
[ 77.019453] ? __die+0x24/0x80
[ 77.019458] ? page_fault_oops+0x99/0x1b0
[ 77.019476] ? do_user_addr_fault+0x31d/0x6b0
[ 77.019479] ? srso_alias_return_thunk+0x5/0x7f
[ 77.019497] ? exc_page_fault+0x83/0x1b0
[ 77.019503] ? asm_exc_page_fault+0x27/0x30
[ 77.019535] ? sys_execve_kretprobe_entry_handler+0x5d/0xf0 [AuditModule]
[ 77.019543] pre_handler_kretprobe+0x3f/0xa0
[ 77.019549] ? __x64_sys_execve+0x1/0x60
[ 77.019568] kprobe_ftrace_handler+0x125/0x240
[ 77.019584] ? __x64_sys_execve+0x5/0x60
[ 77.019588] 0xffffffffc09430f7
[ 77.019612] RIP: 0010:__x64_sys_execve+0x1/0x60
[ 77.019615] Code: ff 45 31 c0 45 31 c9 e9 ad 0f c8 00 66 66 2e 0f 1f 84 00 00 00 00 00 66 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 e8 <cb> 12 48 3f 55 48 89 e5 41 54 53 4c 8b 67 60 48 8b 5f 68 48 8b 7f
[ 77.019618] RSP: 0018:ffffc90005547e30 EFLAGS: 00000202 ORIG_RAX: 0000000000000000
[ 77.019622] RAX: 000000000000003b RBX: ffffc90005547f58 RCX: 0000000000000000
[ 77.019624] RDX: ffffffffffffffff RSI: 000000000000003b RDI: ffffc90005547f58
[ 77.019627] RBP: ffffc90005547e38 R08: 0000000000000000 R09: 0000000000000000
[ 77.019629] R10: 0000000000000000 R11: 0000000000000000 R12: 0000000000000000
[ 77.019631] R13: 0000000000000000 R14: 0000000000000000 R15: 0000000000000000
[ 77.019637] ? __x64_sys_execve+0x5/0x60
[ 77.019640] ? x64_sys_call+0x7a3/0x20b0
[ 77.019676] ? __x64_sys_execve+0x5/0x60
[ 77.019679] ? x64_sys_call+0x7a3/0x20b0
[ 77.019682] do_syscall_64+0x55/0x90
[ 77.019686] ? srso_alias_return_thunk+0x5/0x7f
[ 77.019690] ? __count_memcg_events+0x7d/0x110
[ 77.019713] ? srso_alias_return_thunk+0x5/0x7f
[ 77.019716] ? count_memcg_events.constprop.0+0x2a/0x50
[ 77.019722] ? srso_alias_return_thunk+0x5/0x7f
[ 77.019725] ? handle_mm_fault+0xad/0x360
[ 77.019730] ? srso_alias_return_thunk+0x5/0x7f
[ 77.019733] ? do_user_addr_fault+0x238/0x6b0
[ 77.019748] ? srso_alias_return_thunk+0x5/0x7f
[ 77.019752] ? exit_to_user_mode_prepare+0x30/0xb0
[ 77.019768] ? srso_alias_return_thunk+0x5/0x7f
[ 77.019771] ? irqentry_exit_to_user_mode+0x17/0x20
[ 77.019775] ? srso_alias_return_thunk+0x5/0x7f
[ 77.019778] ? irqentry_exit+0x43/0x50
[ 77.019782] ? srso_alias_return_thunk+0x5/0x7f
[ 77.019784] ? exc_page_fault+0x94/0x1b0
[ 77.019787] entry_SYSCALL_64_after_hwframe+0x73/0xdd
[ 77.019789] RIP: 0033:0x7b20a470117b
[ 77.019794] Code: 41 89 01 eb da 66 2e 0f 1f 84 00 00 00 00 00 f7 d8 64 41 89 01 eb d6 0f 1f 84 00 00 00 00 00 f3 0f 1e fa b8 3b 00 00 00 0f 05 <48> 3d 01 f0 ff ff 73 01 c3 48 8b 0d e5 8c 10 00 f7 d8 64 89 01 48
[ 77.019796] RSP: 002b:00007ffd6725eb78 EFLAGS: 00000202 ORIG_RAX: 000000000000003b
[ 77.019798] RAX: ffffffffffffffda RBX: 0000212400c64d20 RCX: 00007b20a470117b
[ 77.019799] RDX: 000021240083d200 RSI: 0000212400c64d20 RDI: 00007ffd6725f770
[ 77.019801] RBP: 00007ffd6725ec00 R08: 00007ffd6725ec10 R09: 0000000000000000
[ 77.019802] R10: 0000000000000008 R11: 0000000000000202 R12: 000021240083d200
[ 77.019804] R13: 00007ffd6725f770 R14: 00007ffd6725ec10 R15: 00007ffd6725ede0
[ 77.019808] </TASK>
[ 77.019809] Modules linked in: AuditModule(OE) isofs bnep intel_rapl_msr vsock_loopback vmw_vsock_virtio_transport_common vmw_vsock_vmci_transport vsock vmw_balloon snd_ens1371 snd_ac97_codec gameport ac97_bus snd_pcm binfmt_misc intel_rapl_common nls_iso8859_1 crct10dif_pclmul polyval_clmulni polyval_generic ghash_clmulni_intel sha256_ssse3 sha1_ssse3 snd_seq_midi aesni_intel crypto_simd cryptd snd_seq_midi_event snd_rawmidi snd_seq snd_seq_device joydev input_leds serio_raw snd_timer btusb btrtl btbcm btintel btmtk snd bluetooth ecdh_generic ecc soundcore vmw_vmci mac_hid sch_fq_codel vmwgfx drm_ttm_helper ttm drm_kms_helper msr parport_pc ppdev lp parport drm efi_pstore ip_tables x_tables autofs4 hid_generic crc32_pclmul psmouse usbhid hid ahci e1000 libahci mptspi mptscsih mptbase scsi_transport_spi i2c_piix4 pata_acpi
[ 77.019885] CR2: 0000212400c64d20
[ 77.019887] ---[ end trace 0000000000000000 ]---
[ 77.019889] RIP: 0010:sys_execve_kretprobe_entry_handler+0x5d/0xf0 [AuditModule]
[ 77.019893] Code: 8b 46 70 48 8b 70 70 4c 8b 68 68 e8 8d 0a f9 c0 48 85 c0 7e 0c 48 c7 c7 86 c1 93 c0 e8 fc f4 86 c0 49 c7 c4 00 8f 93 c0 31 db <4d> 8b 75 00 4d 85 f6 74 43 4c 63 fb 49 83 ff 0a 77 53 ba 14 00 00
[ 77.019904] RSP: 0018:ffffc90005547cb0 EFLAGS: 00010246
[ 77.019906] RAX: 0000000000000017 RBX: 0000000000000000 RCX: 0000000000000000
[ 77.019908] RDX: 0000000000000000 RSI: 0000000000000000 RDI: 0000000000000000
[ 77.019909] RBP: ffffc90005547cd8 R08: 0000000000000000 R09: 0000000000000000
[ 77.019911] R10: 0000000000000000 R11: 0000000000000000 R12: ffffffffc0938f00
[ 77.019912] R13: 0000212400c64d20 R14: ffffffffc09382e0 R15: ffff888139e1fec0
[ 77.019914] FS: 00007b20a38b8e80(0000) GS:ffff888139e00000(0000) knlGS:0000000000000000
[ 77.019915] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033
[ 77.019917] CR2: 0000212400c64d20 CR3: 000000000518c000 CR4: 00000000003506f0
[ 77.019920] note: code[4118] exited with irqs disabled
[ 77.019938] note: code[4118] exited with preempt_count 1
[ 77.034386] execve filename success
[ 77.034396] BUG: unable to handle page fault for address: 00005e44508637b8
[ 77.034399] #PF: supervisor read access in kernel mode
[ 77.034401] #PF: error_code(0x0001) - permissions violation
[ 77.034403] PGD 5209067 P4D 5209067 PUD b18cc067 PMD b18cb067 PTE 80000000b62d6867
[ 77.034409] Oops: 0001 [#2] PREEMPT SMP NOPTI
[ 77.034412] CPU: 1 PID: 4125 Comm: ps.sh Tainted: G D OE 6.5.0-41-generic #41~22.04.2-Ubuntu
[ 77.034415] Hardware name: VMware, Inc. VMware Virtual Platform/440BX Desktop Reference Platform, BIOS 6.00 07/22/2020
[ 77.034417] RIP: 0010:sys_execve_kretprobe_entry_handler+0x5d/0xf0 [AuditModule]
[ 77.034426] Code: 8b 46 70 48 8b 70 70 4c 8b 68 68 e8 8d 0a f9 c0 48 85 c0 7e 0c 48 c7 c7 86 c1 93 c0 e8 fc f4 86 c0 49 c7 c4 00 8f 93 c0 31 db <4d> 8b 75 00 4d 85 f6 74 43 4c 63 fb 49 83 ff 0a 77 53 ba 14 00 00
[ 77.034464] RSP: 0018:ffffc90002717d10 EFLAGS: 00010246
[ 77.034466] RAX: 0000000000000017 RBX: 0000000000000000 RCX: 0000000000000000
[ 77.034468] RDX: 0000000000000000 RSI: 0000000000000000 RDI: 0000000000000000
[ 77.034469] RBP: ffffc90002717d38 R08: 0000000000000000 R09: 0000000000000000
[ 77.034471] R10: 0000000000000000 R11: 0000000000000000 R12: ffffffffc0938f00
[ 77.034472] R13: 00005e44508637b8 R14: ffffffffc09382e0 R15: ffff888139e5fec0
[ 77.034474] FS: 00007f69d5c19740(0000) GS:ffff888139e40000(0000) knlGS:0000000000000000
[ 77.034476] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033
[ 77.034478] CR2: 00005e44508637b8 CR3: 000000006d7f0000 CR4: 00000000003506e0
[ 77.034481] Call Trace:
[ 77.034483] <TASK>
[ 77.034486] ? show_regs+0x6d/0x80
[ 77.034493] ? __die+0x24/0x80
[ 77.034496] ? page_fault_oops+0x99/0x1b0
[ 77.034501] ? do_user_addr_fault+0x31d/0x6b0
[ 77.034504] ? srso_alias_return_thunk+0x5/0x7f
[ 77.034510] ? exc_page_fault+0x83/0x1b0
[ 77.034514] ? asm_exc_page_fault+0x27/0x30
[ 77.034521] ? sys_execve_kretprobe_entry_handler+0x5d/0xf0 [AuditModule]
[ 77.034526] pre_handler_kretprobe+0x3f/0xa0
[ 77.034531] ? __x64_sys_execve+0x1/0x60
[ 77.034535] kprobe_ftrace_handler+0x125/0x240
[ 77.034540] ? __x64_sys_execve+0x5/0x60
[ 77.034543] 0xffffffffc09430f7
[ 77.034593] RIP: 0010:__x64_sys_execve+0x1/0x60
[ 77.034615] Code: ff 45 31 c0 45 31 c9 e9 ad 0f c8 00 66 66 2e 0f 1f 84 00 00 00 00 00 66 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 e8 <cb> 12 48 3f 55 48 89 e5 41 54 53 4c 8b 67 60 48 8b 5f 68 48 8b 7f
[ 77.034616] RSP: 0018:ffffc90002717e90 EFLAGS: 00000202 ORIG_RAX: 0000000000000000
[ 77.034620] RAX: 000000000000003b RBX: ffffc90002717f58 RCX: 0000000000000000
[ 77.034622] RDX: ffffffffffffffff RSI: 000000000000003b RDI: ffffc90002717f58
[ 77.034623] RBP: ffffc90002717e98 R08: 0000000000000000 R09: 0000000000000000
[ 77.034625] R10: 0000000000000000 R11: 0000000000000000 R12: 0000000000000000
[ 77.034626] R13: 0000000000000000 R14: 0000000000000000 R15: 0000000000000000
[ 77.034630] ? __x64_sys_execve+0x5/0x60
[ 77.034632] ? x64_sys_call+0x7a3/0x20b0
[ 77.034636] ? __x64_sys_execve+0x5/0x60
[ 77.034638] ? x64_sys_call+0x7a3/0x20b0
[ 77.034640] do_syscall_64+0x55/0x90
[ 77.034646] ? srso_alias_return_thunk+0x5/0x7f
[ 77.034674] ? do_user_addr_fault+0x238/0x6b0
[ 77.034677] ? srso_alias_return_thunk+0x5/0x7f
[ 77.034679] ? exit_to_user_mode_prepare+0x30/0xb0
[ 77.034687] ? srso_alias_return_thunk+0x5/0x7f
[ 77.034689] ? irqentry_exit_to_user_mode+0x17/0x20
[ 77.034693] ? srso_alias_return_thunk+0x5/0x7f
[ 77.034696] ? irqentry_exit+0x43/0x50
[ 77.034698] ? srso_alias_return_thunk+0x5/0x7f
[ 77.034700] ? exc_page_fault+0x94/0x1b0
[ 77.034703] entry_SYSCALL_64_after_hwframe+0x73/0xdd
[ 77.034706] RIP: 0033:0x7f69d58eb08b
[ 77.034710] Code: f8 01 0f 8e bd fe ff ff 5b 48 8d 3d 4f 6a 13 00 5d 41 5c e9 87 62 fa ff 0f 1f 80 00 00 00 00 f3 0f 1e fa b8 3b 00 00 00 0f 05 <48> 3d 01 f0 ff ff 73 01 c3 48 8b 0d 75 ed 12 00 f7 d8 64 89 01 48
[ 77.034712] RSP: 002b:00007ffd1b60e5c8 EFLAGS: 00000246 ORIG_RAX: 000000000000003b
[ 77.034714] RAX: ffffffffffffffda RBX: 00005e44508637b8 RCX: 00007f69d58eb08b
[ 77.034716] RDX: 00005e4451fba498 RSI: 00005e44508637b8 RDI: 00005e4451fba750
[ 77.034717] RBP: 00005e445085c027 R08: 00005e445085c1ff R09: 00005e4451fba490
[ 77.034719] R10: 0000000000000000 R11: 0000000000000246 R12: 00005e4451fba498
[ 77.034720] R13: 00007ffd1b60e6b8 R14: 00005e4451fba498 R15: 00005e4451fba750
[ 77.034724] </TASK>
[ 77.034726] Modules linked in: AuditModule(OE) isofs bnep intel_rapl_msr vsock_loopback vmw_vsock_virtio_transport_common vmw_vsock_vmci_transport vsock vmw_balloon snd_ens1371 snd_ac97_codec gameport ac97_bus snd_pcm binfmt_misc intel_rapl_common nls_iso8859_1 crct10dif_pclmul polyval_clmulni polyval_generic ghash_clmulni_intel sha256_ssse3 sha1_ssse3 snd_seq_midi aesni_intel crypto_simd cryptd snd_seq_midi_event snd_rawmidi snd_seq snd_seq_device joydev input_leds serio_raw snd_timer btusb btrtl btbcm btintel btmtk snd bluetooth ecdh_generic ecc soundcore vmw_vmci mac_hid sch_fq_codel vmwgfx drm_ttm_helper ttm drm_kms_helper msr parport_pc ppdev lp parport drm efi_pstore ip_tables x_tables autofs4 hid_generic crc32_pclmul psmouse usbhid hid ahci e1000 libahci mptspi mptscsih mptbase scsi_transport_spi i2c_piix4 pata_acpi
[ 77.034814] CR2: 00005e44508637b8
[ 77.034817] ---[ end trace 0000000000000000 ]---
[ 77.034818] RIP: 0010:sys_execve_kretprobe_entry_handler+0x5d/0xf0 [AuditModule]
[ 77.034823] Code: 8b 46 70 48 8b 70 70 4c 8b 68 68 e8 8d 0a f9 c0 48 85 c0 7e 0c 48 c7 c7 86 c1 93 c0 e8 fc f4 86 c0 49 c7 c4 00 8f 93 c0 31 db <4d> 8b 75 00 4d 85 f6 74 43 4c 63 fb 49 83 ff 0a 77 53 ba 14 00 00
[ 77.034824] RSP: 0018:ffffc90005547cb0 EFLAGS: 00010246
[ 77.034826] RAX: 0000000000000017 RBX: 0000000000000000 RCX: 0000000000000000
[ 77.034828] RDX: 0000000000000000 RSI: 0000000000000000 RDI: 0000000000000000
[ 77.034829] RBP: ffffc90005547cd8 R08: 0000000000000000 R09: 0000000000000000
[ 77.034831] R10: 0000000000000000 R11: 0000000000000000 R12: ffffffffc0938f00
[ 77.034832] R13: 0000212400c64d20 R14: ffffffffc09382e0 R15: ffff888139e1fec0
[ 77.034834] FS: 00007f69d5c19740(0000) GS:ffff888139e40000(0000) knlGS:0000000000000000
[ 77.034836] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033
[ 77.034837] CR2: 00005e44508637b8 CR3: 000000006d7f0000 CR4: 00000000003506e0
[ 77.034840] note: ps.sh[4125] exited with irqs disabled
[ 77.034869] note: ps.sh[4125] exited with preempt_count 1
我的系统:VMWare上的Ubuntu22.04
内核:6.5.0-41-generic
user_regs = regs->di;
char __user* __user* argv_tmp = (char __user* __user*)user_regs->si;
出于某种原因,您认为
regs->di
指向用户寄存器。
据我所知,情况并非如此——代码应该只使用内核传入的
regs
(换句话说,你有一个不必要的额外间接)。