diff options
author | Anatolii Nikulin <nikulin.a@samsung.com> | 2015-09-29 16:31:10 +0300 |
---|---|---|
committer | Dmitry Kovalenko <d.kovalenko@samsung.com> | 2015-09-29 06:35:27 -0700 |
commit | 34c86553dfd06f1e4fa2d9b15d6dccc65488167f (patch) | |
tree | 255681d47bb5a1d60abf42c110a1df095c706743 /uprobe | |
parent | 4e21be1d20b6760949c6d43765c178b063a0bbfc (diff) | |
download | swap-modules-34c86553dfd06f1e4fa2d9b15d6dccc65488167f.tar.gz swap-modules-34c86553dfd06f1e4fa2d9b15d6dccc65488167f.tar.bz2 swap-modules-34c86553dfd06f1e4fa2d9b15d6dccc65488167f.zip |
[FIX] fix spin lockup
Do not use lock while disarming current proccess
Change-Id: I7d234c5f0d2f5ea28edf8dd17aba315d3271ed58
Signed-off-by: Anatolii Nikulin <nikulin.a@samsung.com>
Diffstat (limited to 'uprobe')
-rw-r--r-- | uprobe/swap_uprobes.c | 16 |
1 files changed, 14 insertions, 2 deletions
diff --git a/uprobe/swap_uprobes.c b/uprobe/swap_uprobes.c index ae58061b..d34cf5cd 100644 --- a/uprobe/swap_uprobes.c +++ b/uprobe/swap_uprobes.c @@ -874,23 +874,35 @@ void __swap_unregister_uretprobe(struct uretprobe *rp, int disarm) struct uretprobe_instance *ri; __swap_unregister_uprobe(&rp->up, disarm); - spin_lock_irqsave(&uretprobe_lock, flags); + spin_lock_irqsave(&uretprobe_lock, flags); while ((ri = get_used_urp_inst(rp)) != NULL) { + bool is_current = ri->task == current; + + if (is_current) + spin_unlock_irqrestore(&uretprobe_lock, flags); + + /* FIXME: arch_disarm_urp_inst() for no current context */ if (arch_disarm_urp_inst(ri, ri->task, 0) != 0) printk(KERN_INFO "%s (%d/%d): " "cannot disarm urp instance (%08lx)\n", ri->task->comm, ri->task->tgid, ri->task->pid, (unsigned long)rp->up.kp.addr); + + if (is_current) + spin_lock_irqsave(&uretprobe_lock, flags); + recycle_urp_inst(ri); } + spin_unlock_irqrestore(&uretprobe_lock, flags); + spin_lock_irqsave(&uretprobe_lock, flags); while ((ri = get_used_urp_inst(rp)) != NULL) { ri->rp = NULL; hlist_del(&ri->uflist); } - spin_unlock_irqrestore(&uretprobe_lock, flags); + free_urp_inst(rp); } EXPORT_SYMBOL_GPL(__swap_unregister_uretprobe); |