Skip site navigation (1)Skip section navigation (2)
Date:      Sun, 9 May 2004 13:40:24 -0700 (PDT)
From:      Marcel Moolenaar <marcel@FreeBSD.org>
To:        Perforce Change Reviews <perforce@freebsd.org>
Subject:   PERFORCE change 52550 for review
Message-ID:  <200405092040.i49KeOVd040729@repoman.freebsd.org>

next in thread | raw e-mail | index | archive | help
http://perforce.freebsd.org/chv.cgi?CH=52550

Change 52550 by marcel@marcel_nfs on 2004/05/09 13:39:48

	Replace all direct references to ddb_regs.tf_esp with a call
	to get_esp(). In get_esp() we handle the fact that tf_esp is
	valid only when crossing the user-kernel boundary.
	
	For some strange reason, backtraces for threads other than the
	one that entered the debugger do not work reliably yet.

Affected files ...

.. //depot/projects/gdb/sys/i386/i386/db_trace.c#3 edit

Differences ...

==== //depot/projects/gdb/sys/i386/i386/db_trace.c#3 (text+ko) ====

@@ -58,6 +58,13 @@
 static db_varfcn_t db_ss;
 static db_varfcn_t db_esp;
 
+static __inline int
+get_esp(void)
+{
+	return ((ISPL(ddb_regs.tf_cs)) ? ddb_regs.tf_esp :
+	    (db_expr_t)kdb_frame + offsetof(struct trapframe, tf_esp));
+}
+
 /*
  * Machine register set.
  */
@@ -118,8 +125,7 @@
 db_esp (struct db_variable *vp, db_expr_t *valuep, int op)
 {
 	if (op == DB_VAR_GET)
-		*valuep = (ISPL(ddb_regs.tf_cs)) ? ddb_regs.tf_esp :
-		    ddb_regs.tf_ebp;
+		*valuep = get_esp();
 	else if (ISPL(ddb_regs.tf_cs))
 		ddb_regs.tf_esp = *valuep;
 	return (0);
@@ -294,8 +300,7 @@
 		tf = (struct trapframe *)((int)*fp + 8);
 
 	if (INKERNEL((int) tf)) {
-		esp = (ISPL(tf->tf_cs) == SEL_UPL) ?
-		    tf->tf_esp : (int)&tf->tf_esp;
+		esp = get_esp();
 		eip = tf->tf_eip;
 		ebp = tf->tf_ebp;
 		switch (frame_type) {
@@ -394,26 +399,22 @@
 				int instr;
 
 				instr = db_get_value(callpc, 4, FALSE);
-				if ((instr & 0x00ffffff) == 0x00e58955) {
+				if ((instr & 0xffffff) == 0x00e58955) {
 					/* pushl %ebp; movl %esp, %ebp */
-					actframe = (struct i386_frame *)
-					    (ddb_regs.tf_esp - 4);
-				} else if ((instr & 0x0000ffff) == 0x0000e589) {
+					actframe = (void *)(get_esp() - 4);
+				} else if ((instr & 0xffff) == 0x0000e589) {
 					/* movl %esp, %ebp */
-					actframe = (struct i386_frame *)
-					    ddb_regs.tf_esp;
+					actframe = (void *)get_esp();
 					if (ddb_regs.tf_ebp == 0) {
-						/* Fake caller's frame better. */
+						/* Fake frame better. */
 						frame = actframe;
 					}
-				} else if ((instr & 0x000000ff) == 0x000000c3) {
+				} else if ((instr & 0xff) == 0x000000c3) {
 					/* ret */
-					actframe = (struct i386_frame *)
-					    (ddb_regs.tf_esp - 4);
+					actframe = (void *)(get_esp() - 4);
 				} else if (offset == 0) {
-					/* Probably a symbol in assembler code. */
-					actframe = (struct i386_frame *)
-					    (ddb_regs.tf_esp - 4);
+					/* Probably an assembler symbol. */
+					actframe = (void *)(get_esp() - 4);
 				}
 			} else if (strcmp(name, "fork_trampoline") == 0) {
 				/*



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200405092040.i49KeOVd040729>