This is the mail archive of the systemtap@sourceware.org mailing list for the systemtap project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[Patch 4/5][Djprobe]Djprobe Coexist with Kprobes


Hi,

This patch enables djprobe to insert several probes
in the same address.
In other words, multi-djprobes support.

-- 
Masami HIRAMATSU
2nd Research Dept.
Hitachi, Ltd., Systems Development Laboratory
E-mail: hiramatu@sdl.hitachi.co.jp

 arch/i386/kernel/kprobes.c |    8 +++++---
 include/linux/kprobes.h    |   13 ++++++++-----
 kernel/kprobes.c           |   11 +++++++----
 3 files changed, 20 insertions(+), 12 deletions(-)

diff -Narup linux-2.6.13-mm1.djp.3/arch/i386/kernel/kprobes.c linux-2.6.13-mm1.djp.4/arch/i386/kernel/kprobes.c
--- linux-2.6.13-mm1.djp.3/arch/i386/kernel/kprobes.c	2005-09-12 20:08:48.000000000 +0900
+++ linux-2.6.13-mm1.djp.4/arch/i386/kernel/kprobes.c	2005-09-28 20:06:23.000000000 +0900
@@ -614,9 +614,11 @@ static inline void __set_breakpoint_op(v
 static void asmlinkage djprobe_callback(struct djprobe_instance * djpi,
 					struct pt_regs *regs)
 {
-	/*TODO: use list*/
-	if (djpi->djp && djpi->djp->handler)
-		djpi->djp->handler(djpi->djp, regs);
+	struct djprobe * djp;
+	list_for_each_entry_rcu(djp, &djpi->plist, plist) {
+		if (djp->handler)
+			djp->handler(djp, regs);
+	}
 }

 /*
diff -Narup linux-2.6.13-mm1.djp.3/include/linux/kprobes.h linux-2.6.13-mm1.djp.4/include/linux/kprobes.h
--- linux-2.6.13-mm1.djp.3/include/linux/kprobes.h	2005-09-12 14:05:36.000000000 +0900
+++ linux-2.6.13-mm1.djp.4/include/linux/kprobes.h	2005-09-28 20:06:23.000000000 +0900
@@ -145,7 +145,7 @@ struct kretprobe_instance {

 /* djprobe's instance (internal use)*/
 struct djprobe_instance {
-	struct djprobe *djp;
+	struct list_head plist; /* list of djprobes for multiprobe support */
 #ifdef ARCH_SUPPORTS_DJPROBES
 	struct arch_djprobe_stub stub;
 #endif /* ARCH_SUPPORTS_DJPROBES */
@@ -153,7 +153,7 @@ struct djprobe_instance {
 	struct list_head list; /* list of djprobe_instances */
 	cpumask_t checked_cpus;
 };
-#define DJPI_EMPTY(djpi)  (djpi->djp==NULL)
+#define DJPI_EMPTY(djpi)  (list_empty(&djpi->plist))
 #define DJPI_CHECKED(djpi) (cpus_equal(djpi->checked_cpus, cpu_online_map))

 struct djprobe;
@@ -165,15 +165,18 @@ struct djprobe {
 #ifndef ARCH_SUPPORTS_DJPROBES
 	struct kprobe kp;
 #endif /* ARCH_SUPPORTS_DJPROBES */
+	/* list of djprobes */
+	struct list_head plist;
+
+	/* probing handler (pre-executed) */
+	djprobe_handler_t handler;
+
 	/* location of the probe point */
 	void * addr;
 	
 	/* sum of length of the replacing codes */
 	int size;
 	
-	/* probing handler (pre-executed) */
-	djprobe_handler_t handler;
-	
 	/* pointer for instance */
 	struct djprobe_instance * inst;
 };
diff -Narup linux-2.6.13-mm1.djp.3/kernel/kprobes.c linux-2.6.13-mm1.djp.4/kernel/kprobes.c
--- linux-2.6.13-mm1.djp.3/kernel/kprobes.c	2005-09-27 18:10:28.000000000 +0900
+++ linux-2.6.13-mm1.djp.4/kernel/kprobes.c	2005-09-28 20:06:23.000000000 +0900
@@ -751,12 +751,13 @@ int __kprobes register_djprobe(struct dj
 		return ret;

 	spin_lock(&djprobe_lock);
+	INIT_LIST_HEAD(&djp->plist);
 	/* check confliction with other djprobes */
 	djpi = __get_djprobe_instance(djp->addr, djp->size);
 	if (djpi) {
-		if (djpi->kp.addr == djp->addr && DJPI_EMPTY(djpi)) {
+		if (djpi->kp.addr == djp->addr) {
 			djp->inst = djpi;
-			djpi->djp = djp; /*TODO: use list*/
+			list_add_rcu(&djp->plist, &djpi->plist);
 			goto out;
 		} else {
 			ret = -EEXIST; /* a djprobe were inserted */
@@ -779,8 +780,9 @@ int __kprobes register_djprobe(struct dj
 	}
 	memset(djpi, 0, sizeof(struct djprobe_instance)); /* for kprobe */
 	/* attach */
+	INIT_LIST_HEAD(&djpi->plist);
 	djp->inst = djpi;
-	djpi->djp = djp; /*TODO: use list*/
+	list_add_rcu(&djp->plist, &djpi->plist);
 	djpi->kp.addr = djp->addr;
 	INIT_LIST_HEAD(&djpi->list);
 	list_add(&djpi->list, &djprobe_list);
@@ -798,6 +800,7 @@ int __kprobes register_djprobe(struct dj
 	ret = install_djprobe_instance(djpi);
 	if (ret < 0) { /* failed to install */
 		djp->inst = NULL;
+		list_del_rcu(&djp->plist);
 		djpi->kp.addr = NULL;
 		__free_djprobe_instance(djpi);
 	}
@@ -815,7 +818,7 @@ void __kprobes unregister_djprobe(struct
 	djpi = djp->inst;
 	spin_lock(&djprobe_lock);
 	djp->inst = NULL;
-	djpi->djp = NULL; /*TODO: use list*/
+	list_del_rcu(&djp->plist);
 	if (DJPI_EMPTY(djpi)) {
 		uninstall_djprobe_instance(djpi);
 	}




Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]