[PATCH] rio driver rework continued #1
[powerpc.git] / kernel / kprobes.c
index 3ea6325..1fb9f75 100644 (file)
@@ -48,7 +48,7 @@
 static struct hlist_head kprobe_table[KPROBE_TABLE_SIZE];
 static struct hlist_head kretprobe_inst_table[KPROBE_TABLE_SIZE];
 
-DECLARE_MUTEX(kprobe_mutex);           /* Protects kprobe_table */
+DEFINE_MUTEX(kprobe_mutex);            /* Protects kprobe_table */
 DEFINE_SPINLOCK(kretprobe_lock);       /* Protects kretprobe_inst_table */
 static DEFINE_PER_CPU(struct kprobe *, kprobe_instance) = NULL;
 
@@ -344,23 +344,6 @@ void __kprobes kprobe_flush_task(struct task_struct *tk)
        spin_unlock_irqrestore(&kretprobe_lock, flags);
 }
 
-/*
- * This kprobe pre_handler is registered with every kretprobe. When probe
- * hits it will set up the return probe.
- */
-static int __kprobes pre_handler_kretprobe(struct kprobe *p,
-                                          struct pt_regs *regs)
-{
-       struct kretprobe *rp = container_of(p, struct kretprobe, kp);
-       unsigned long flags = 0;
-
-       /*TODO: consider to only swap the RA after the last pre_handler fired */
-       spin_lock_irqsave(&kretprobe_lock, flags);
-       arch_prepare_kretprobe(rp, regs);
-       spin_unlock_irqrestore(&kretprobe_lock, flags);
-       return 0;
-}
-
 static inline void free_rp_inst(struct kretprobe *rp)
 {
        struct kretprobe_instance *ri;
@@ -477,7 +460,7 @@ static int __kprobes __register_kprobe(struct kprobe *p,
        }
 
        p->nmissed = 0;
-       down(&kprobe_mutex);
+       mutex_lock(&kprobe_mutex);
        old_p = get_kprobe(p->addr);
        if (old_p) {
                ret = register_aggr_kprobe(old_p, p);
@@ -494,7 +477,7 @@ static int __kprobes __register_kprobe(struct kprobe *p,
        arch_arm_kprobe(p);
 
 out:
-       up(&kprobe_mutex);
+       mutex_unlock(&kprobe_mutex);
 
        if (ret && probed_mod)
                module_put(probed_mod);
@@ -513,10 +496,10 @@ void __kprobes unregister_kprobe(struct kprobe *p)
        struct kprobe *old_p, *list_p;
        int cleanup_p;
 
-       down(&kprobe_mutex);
+       mutex_lock(&kprobe_mutex);
        old_p = get_kprobe(p->addr);
        if (unlikely(!old_p)) {
-               up(&kprobe_mutex);
+               mutex_unlock(&kprobe_mutex);
                return;
        }
        if (p != old_p) {
@@ -524,7 +507,7 @@ void __kprobes unregister_kprobe(struct kprobe *p)
                        if (list_p == p)
                        /* kprobe p is a valid probe */
                                goto valid_p;
-               up(&kprobe_mutex);
+               mutex_unlock(&kprobe_mutex);
                return;
        }
 valid_p:
@@ -540,7 +523,7 @@ valid_p:
                cleanup_p = 0;
        }
 
-       up(&kprobe_mutex);
+       mutex_unlock(&kprobe_mutex);
 
        synchronize_sched();
        if (p->mod_refcounted &&
@@ -578,6 +561,23 @@ void __kprobes unregister_jprobe(struct jprobe *jp)
 
 #ifdef ARCH_SUPPORTS_KRETPROBES
 
+/*
+ * This kprobe pre_handler is registered with every kretprobe. When probe
+ * hits it will set up the return probe.
+ */
+static int __kprobes pre_handler_kretprobe(struct kprobe *p,
+                                          struct pt_regs *regs)
+{
+       struct kretprobe *rp = container_of(p, struct kretprobe, kp);
+       unsigned long flags = 0;
+
+       /*TODO: consider to only swap the RA after the last pre_handler fired */
+       spin_lock_irqsave(&kretprobe_lock, flags);
+       arch_prepare_kretprobe(rp, regs);
+       spin_unlock_irqrestore(&kretprobe_lock, flags);
+       return 0;
+}
+
 int __kprobes register_kretprobe(struct kretprobe *rp)
 {
        int ret = 0;
@@ -631,12 +631,12 @@ void __kprobes unregister_kretprobe(struct kretprobe *rp)
        unregister_kprobe(&rp->kp);
        /* No race here */
        spin_lock_irqsave(&kretprobe_lock, flags);
-       free_rp_inst(rp);
        while ((ri = get_used_rp_inst(rp)) != NULL) {
                ri->rp = NULL;
                hlist_del(&ri->uflist);
        }
        spin_unlock_irqrestore(&kretprobe_lock, flags);
+       free_rp_inst(rp);
 }
 
 static int __init init_kprobes(void)