1 #include <dbi_kprobes.h>
2 #include <dbi_kprobes_deps.h>
4 #include "us_proc_inst.h"
5 #include "us_slot_manager.h"
10 ******************************************************************************
12 ******************************************************************************
19 static int entry_handler_pf(struct kretprobe_instance *ri, struct pt_regs *regs)
21 struct pf_data *data = (struct pf_data *)ri->data;
24 data->addr = read_cr2();
26 data->addr = regs->ARM_r0;
28 #error this architecture is not supported
34 /* Detects when IPs are really loaded into phy mem and installs probes. */
35 static int ret_handler_pf(struct kretprobe_instance *ri, struct pt_regs *regs)
37 struct task_struct *task = current->group_leader;
38 struct mm_struct *mm = task->mm;
39 struct sspt_procs *procs = NULL;
41 * Because process threads have same address space
42 * we instrument only group_leader of all this threads
45 unsigned long addr = 0;
48 if (task->flags & PF_KTHREAD) {
52 if (!is_us_instrumentation()) {
56 data = (struct pf_data *)ri->data;
59 valid_addr = mm && page_present(mm, addr);
65 procs = sspt_procs_get_by_task_or_new(task);
68 if (us_proc_info.tgid == 0) {
69 if (check_dentry(task, us_proc_info.m_f_dentry)) {
70 us_proc_info.tgid = gl_nNotifyTgid = task->tgid;
71 procs = sspt_procs_get_by_task_or_new(task);
73 /* install probes in already mapped memory */
74 install_proc_probes(task, procs);
78 if (us_proc_info.tgid == task->tgid) {
79 procs = sspt_procs_get_by_task_or_new(task);
84 unsigned long page = addr & PAGE_MASK;
85 install_page_probes(page, task, procs);
92 static struct kretprobe pf_kretprobe = {
93 .entry_handler = entry_handler_pf,
94 .handler = ret_handler_pf,
95 .data_size = sizeof(struct pf_data)
101 ******************************************************************************
103 ******************************************************************************
106 static void recover_child(struct task_struct *child_task, struct sspt_procs *procs)
108 uninstall_us_proc_probes(child_task, procs, US_DISARM);
109 dbi_disarm_urp_inst_for_task(current, child_task);
112 static void rm_uprobes_child(struct task_struct *task)
114 struct sspt_procs *procs = sspt_procs_get_by_task(current);
116 recover_child(task, procs);
120 /* Delete uprobs in children at fork */
121 static int ret_handler_cp(struct kretprobe_instance *ri, struct pt_regs *regs)
123 struct task_struct* task = (struct task_struct *)regs_return_value(regs);
125 if(!task || IS_ERR(task))
128 if(task->mm != current->mm) /* check flags CLONE_VM */
129 rm_uprobes_child(task);
135 static struct kretprobe cp_kretprobe = {
136 .handler = ret_handler_cp,
142 ******************************************************************************
144 ******************************************************************************
147 /* Detects when target process removes IPs. */
148 static int mr_pre_handler(struct kprobe *p, struct pt_regs *regs)
150 struct sspt_procs *procs = NULL;
151 struct task_struct *task = (struct task_struct *)regs->ARM_r0; /* for ARM */
153 if (!is_us_instrumentation() || task->tgid != task->pid) {
158 procs = sspt_procs_get_by_task(task);
160 if (task->tgid == us_proc_info.tgid) {
161 procs = sspt_procs_get_by_task(task);
162 us_proc_info.tgid = 0;
167 int ret = uninstall_us_proc_probes(task, procs, US_UNREGS_PROBE);
169 printk("failed to uninstall IPs (%d)!\n", ret);
172 dbi_unregister_all_uprobes(task);
179 static struct kprobe mr_kprobe = {
180 .pre_handler = mr_pre_handler
186 ******************************************************************************
188 ******************************************************************************
191 static int remove_unmap_probes(struct task_struct *task, struct sspt_procs *procs, unsigned long start, size_t len)
193 struct mm_struct *mm = task->mm;
194 struct vm_area_struct *vma;
196 if ((start & ~PAGE_MASK) || start > TASK_SIZE || len > TASK_SIZE - start) {
200 if ((len = PAGE_ALIGN(len)) == 0) {
204 vma = find_vma(mm, start);
205 if (vma && check_vma(vma)) {
206 struct sspt_file *file;
207 unsigned long end = start + len;
208 struct dentry *dentry = vma->vm_file->f_dentry;
210 file = sspt_procs_find_file(procs, dentry);
212 if (vma->vm_start == start || vma->vm_end == end) {
213 unregister_us_file_probes(task, file, US_UNREGS_PROBE);
216 unsigned long page_addr;
217 struct sspt_page *page;
219 for (page_addr = vma->vm_start; page_addr < vma->vm_end; page_addr += PAGE_SIZE) {
220 page = sspt_find_page_mapped(file, page_addr);
222 sspt_unregister_page(page, US_UNREGS_PROBE, task);
226 if (sspt_file_check_install_pages(file)) {
236 /* Detects when target removes IPs. */
237 static int unmap_pre_handler(struct kprobe *p, struct pt_regs *regs)
240 struct mm_struct *mm = (struct mm_struct *)regs->ARM_r0;
241 unsigned long start = regs->ARM_r1;
242 size_t len = (size_t)regs->ARM_r2;
244 struct sspt_procs *procs = NULL;
245 struct task_struct *task = current;
247 //if user-space instrumentation is not set
248 if (!is_us_instrumentation()) {
252 procs = sspt_procs_get_by_task(task);
254 if (remove_unmap_probes(task, procs, start, len)) {
255 printk("ERROR do_munmap: start=%lx, len=%x\n", start, len);
263 static struct kprobe unmap_kprobe = {
264 .pre_handler = unmap_pre_handler
269 int register_helper(void)
273 /* install kprobe on 'do_munmap' to detect when for remove user space probes */
274 ret = dbi_register_kprobe(&unmap_kprobe);
276 printk("dbi_register_kprobe(do_munmap) result=%d!\n", ret);
280 /* install kprobe on 'mm_release' to detect when for remove user space probes */
281 ret = dbi_register_kprobe(&mr_kprobe);
283 printk("dbi_register_kprobe(mm_release) result=%d!\n", ret);
284 goto unregister_unmap;
288 /* install kretprobe on 'copy_process' */
289 ret = dbi_register_kretprobe(&cp_kretprobe);
291 printk("dbi_register_kretprobe(copy_process) result=%d!\n", ret);
295 /* install kretprobe on 'do_page_fault' to detect when they will be loaded */
296 ret = dbi_register_kretprobe(&pf_kretprobe);
298 printk("dbi_register_kretprobe(do_page_fault) result=%d!\n", ret);
305 dbi_unregister_kretprobe(&cp_kretprobe);
308 dbi_unregister_kprobe(&mr_kprobe, NULL);
311 dbi_unregister_kprobe(&unmap_kprobe, NULL);
316 void unregister_helper(void)
318 /* uninstall kretprobe with 'do_page_fault' */
319 dbi_unregister_kretprobe(&pf_kretprobe);
321 /* uninstall kretprobe with 'copy_process' */
322 dbi_unregister_kretprobe(&cp_kretprobe);
324 /* uninstall kprobe with 'mm_release' */
325 dbi_unregister_kprobe(&mr_kprobe, NULL);
327 /* uninstall kprobe with 'do_munmap' */
328 dbi_unregister_kprobe(&unmap_kprobe, NULL);
331 int init_helper(void)
334 addr = swap_ksyms("do_page_fault");
336 printk("Cannot find address for page fault function!\n");
339 pf_kretprobe.kp.addr = (kprobe_opcode_t *)addr;
341 addr = swap_ksyms("copy_process");
343 printk("Cannot find address for copy_process function!\n");
346 cp_kretprobe.kp.addr = (kprobe_opcode_t *)addr;
348 addr = swap_ksyms("mm_release");
350 printk("Cannot find address for mm_release function!\n");
353 mr_kprobe.addr = (kprobe_opcode_t *)addr;
355 addr = swap_ksyms("do_munmap");
357 printk("Cannot find address for do_munmap function!\n");
360 unmap_kprobe.addr = (kprobe_opcode_t *)addr;
365 void uninit_helper(void)