kprobe可以动态跟踪某一内核函数的执行情况而无需修改内核,当然为了达到这样目的,我们需要自己写一个小的内核模块,不过这也要比修改内核源码要来得方便的多,我觉得这种方法可以形象地称之为“无损探测”。
下面是利用<>中的一小段代码,经过适当改写完善,来探测一个U盘加入系统时,do_execve所执行的环境参数。kprobe的原理大约是在执行被探测函数前先行获得控制权,执行内核模块所注册的回调函数,之后再把控制权转给被探测的函数,这个原理很有意思,有进一步分析的必要。
以下是内核模块代码:
- #include <linux/module.h>
- #include <linux/kprobes.h>
- #include <linux/kallsyms.h>
- struct kprobe kp;
- int handler_pre(struct kprobe *p, struct pt_regs *regs)
- {
- printk(KERN_INFO "|pid: %6d |comm: %10s |filename = %10s|\n",
- current->pid, current->comm, (char *)regs->di);
- return 0;
- }
- static __init int init_kprobe_sample(void)
- {
- kp.symbol_name = "do_execve";
- kp.pre_handler = handler_pre;
- register_kprobe(&kp);
- printk(KERN_INFO "---------------kprobe for execve--------------\n");
- return 0;
- }
- static __exit void cleanup_kprobe_sample(void)
- {
- unregister_kprobe(&kp);
- }
- module_init(init_kprobe_sample);
- module_exit(cleanup_kprobe_sample);
- MODULE_LICENSE("GPL");
insmod这个模块之后,探测活动就正式开始了,下面是往系统插入一个U盘时,kprobe回调函数的输出:
- root@build-server:/home/dennis/debug/kprobe# dmesg -c
- [10370.912471] usb 1-1.3: new high-speed USB device number 9 using ehci_hcd
- [10370.988796] |pid: 3296 |comm: kworker/u:3 |filename = /sbin/myhotplug|
- [10370.989038] |pid: 3297 |comm: kworker/u:3 |filename = /sbin/myhotplug|
- [10370.989146] |pid: 3298 |comm: udevd |filename = /lib/udev/mtp-probe|
- [10370.989192] |pid: 3299 |comm: myhotplug |filename = /bin/touch|
- [10370.989496] |pid: 3300 |comm: myhotplug |filename = /bin/touch|
- [10370.989730] scsi11 : usb-storage 1-1.3:1.0
- [10370.989768] |pid: 3303 |comm: kworker/u:3 |filename = /sbin/myhotplug|
- [10370.989861] |pid: 3304 |comm: kworker/u:3 |filename = /sbin/myhotplug|
- [10370.990137] |pid: 3305 |comm: myhotplug |filename = /bin/touch|
- [10370.990212] |pid: 3306 |comm: myhotplug |filename = /bin/touch|
- [10371.249360] |pid: 3307 |comm: udevd |filename = /lib/udev/usb_id|
- [10371.992667] scsi 11:0:0:0: Direct-Access TOSHIBA TransMemory 1.00 PQ: 0 ANSI: 2
- [10371.992972] |pid: 3309 |comm: kworker/u:3 |filename = /sbin/myhotplug|
- [10371.993341] |pid: 3310 |comm: myhotplug |filename = /bin/touch|
- [10371.993360] |pid: 3311 |comm: kworker/u:3 |filename = /sbin/myhotplug|
- [10371.993636] |pid: 3312 |comm: udevd |filename = /sbin/modprobe|
- [10371.993712] |pid: 3313 |comm: myhotplug |filename = /bin/touch|
- [10371.993777] |pid: 3314 |comm: kworker/u:3 |filename = /sbin/myhotplug|
- [10371.994364] |pid: 3316 |comm: kworker/u:2 |filename = /sbin/myhotplug|
- [10371.994563] |pid: 3317 |comm: myhotplug |filename = /bin/touch|
- [10371.994797] |pid: 3318 |comm: kworker/u:2 |filename = /sbin/myhotplug|
- [10371.994830] sd 11:0:0:0: Attached scsi generic sg3 type 0
- [10371.994886] |pid: 3319 |comm: kworker/u:2 |filename = /sbin/myhotplug|
- [10371.995249] |pid: 3320 |comm: myhotplug |filename = /bin/touch|
- [10371.995506] |pid: 3321 |comm: myhotplug |filename = /bin/touch|
- [10371.995538] |pid: 3322 |comm: myhotplug |filename = /bin/touch|
- [10371.995786] sd 11:0:0:0: [sdc] 15654848 512-byte logical blocks: (8.01 GB/7.46 GiB)
- [10371.996281] sd 11:0:0:0: [sdc] Write Protect is off
- [10371.996282] sd 11:0:0:0: [sdc] Mode Sense: 65 44 09 30
- [10371.996788] sd 11:0:0:0: [sdc] No Caching mode page present
- [10371.996862] sd 11:0:0:0: [sdc] Assuming drive cache: write through
- [10371.996996] |pid: 3323 |comm: kworker/u:2 |filename = /sbin/myhotplug|
- [10371.997387] |pid: 3324 |comm: myhotplug |filename = /bin/touch|
- [10371.999537] sd 11:0:0:0: [sdc] No Caching mode page present
- [10371.999609] sd 11:0:0:0: [sdc] Assuming drive cache: write through
- [10372.000283] sdc: sdc1
- [10372.000358] |pid: 3325 |comm: kworker/u:2 |filename = /sbin/myhotplug|
- [10372.000458] |pid: 3326 |comm: kworker/u:2 |filename = /sbin/myhotplug|
- [10372.000711] |pid: 3327 |comm: myhotplug |filename = /bin/touch|
- [10372.000820] |pid: 3328 |comm: myhotplug |filename = /bin/touch|
- [10372.000865] |pid: 3329 |comm: udevd |filename = /lib/udev/usb_id|
- [10372.001676] |pid: 3330 |comm: udevd |filename = /lib/udev/path_id|
- [10372.002411] sd 11:0:0:0: [sdc] No Caching mode page present
- [10372.002459] |pid: 3331 |comm: udevd |filename = /sbin/blkid|
- [10372.002484] sd 11:0:0:0: [sdc] Assuming drive cache: write through
- [10372.002564] sd 11:0:0:0: [sdc] Attached SCSI removable disk
- [10372.066849] |pid: 3332 |comm: udevd |filename = /lib/udev/udisks-part-id|
- [10372.070023] |pid: 3333 |comm: udevd |filename = /lib/udev/hdparm|
- [10372.070633] |pid: 3334 |comm: hdparm |filename = /bin/grep|
- [10372.071212] |pid: 3335 |comm: hdparm |filename = /bin/egrep|
- [10372.071930] |pid: 3337 |comm: hdparm |filename = /bin/egrep|
- [10372.073162] |pid: 3339 |comm: udevd |filename = /sbin/blkid|
- [10372.127677] |pid: 3341 |comm: udevd |filename = /lib/udev/udisks-part-id|
- [10373.752620] |pid: 3342 |comm: bash |filename = /bin/dmesg|
如果仔细分析上面的输出,会发现不少有趣的信息,比如udevd与mtp-probe,hdparm等等。
这时候,do_execve就要抱怨了,因为它的隐私全被人家给窥视了,如果遇到再狠一点的角色,估计连底裤都不剩下了,呵呵,kprobe就是这样一个具有窥私癖的东西。
阅读(2315) | 评论(0) | 转发(0) |