patch-2.1.115 linux/arch/sparc64/kernel/ptrace.c

Next file: linux/arch/sparc64/kernel/rtrap.S
Previous file: linux/arch/sparc64/kernel/psycho.c
Back to the patch index
Back to the overall index

diff -u --recursive --new-file v2.1.114/linux/arch/sparc64/kernel/ptrace.c linux/arch/sparc64/kernel/ptrace.c
@@ -24,6 +24,7 @@
 #include <asm/system.h>
 #include <asm/uaccess.h>
 #include <asm/psrcompat.h>
+#include <asm/visasm.h>
 
 #define MAGIC_CONSTANT 0x80000000
 
@@ -355,9 +356,11 @@
 	case 0:
 		v = t->ksp;
 		break;
+#if 0
 	case 4:
 		v = t->kpc;
 		break;
+#endif
 	case 8:
 		v = t->kpsr;
 		break;
@@ -832,11 +835,11 @@
 				unsigned int insn;
 			} fpq[16];
 		} *fps = (struct fps *) addr;
-		unsigned long *fpregs = (unsigned long *)(child->tss.kregs+1);
+		unsigned long *fpregs = (unsigned long *)(((char *)child) + AOFF_task_fpregs);
 
 		if (copy_to_user(&fps->regs[0], fpregs,
 				 (32 * sizeof(unsigned int))) ||
-		    __put_user(((unsigned int)fpregs[32]), (&fps->fsr)) ||
+		    __put_user(child->tss.xfsr[0], (&fps->fsr)) ||
 		    __put_user(0, (&fps->fpqd)) ||
 		    __put_user(0, (&fps->flags)) ||
 		    __put_user(0, (&fps->extra)) ||
@@ -853,11 +856,11 @@
 			unsigned int regs[64];
 			unsigned long fsr;
 		} *fps = (struct fps *) addr;
-		unsigned long *fpregs = (unsigned long *)(child->tss.kregs+1);
+		unsigned long *fpregs = (unsigned long *)(((char *)child) + AOFF_task_fpregs);
 
 		if (copy_to_user(&fps->regs[0], fpregs,
 				 (64 * sizeof(unsigned int))) ||
-		    __put_user(fpregs[32], (&fps->fsr))) {
+		    __put_user(child->tss.xfsr[0], (&fps->fsr))) {
 			pt_error_return(regs, EFAULT);
 			goto out;
 		}
@@ -877,7 +880,7 @@
 				unsigned int insn;
 			} fpq[16];
 		} *fps = (struct fps *) addr;
-		unsigned long *fpregs = (unsigned long *)(child->tss.kregs+1);
+		unsigned long *fpregs = (unsigned long *)(((char *)child) + AOFF_task_fpregs);
 		unsigned fsr;
 
 		if (copy_from_user(fpregs, &fps->regs[0],
@@ -886,8 +889,11 @@
 			pt_error_return(regs, EFAULT);
 			goto out;
 		}
-		fpregs[32] &= 0xffffffff00000000UL;
-		fpregs[32] |= fsr;
+		child->tss.xfsr[0] &= 0xffffffff00000000UL;
+		child->tss.xfsr[0] |= fsr;
+		if (!(child->tss.fpsaved[0] & FPRS_FEF))
+			child->tss.gsr[0] = 0;
+		child->tss.fpsaved[0] |= (FPRS_FEF | FPRS_DL);
 		pt_succ_return(regs, 0);
 		goto out;
 	}
@@ -897,14 +903,17 @@
 			unsigned int regs[64];
 			unsigned long fsr;
 		} *fps = (struct fps *) addr;
-		unsigned long *fpregs = (unsigned long *)(child->tss.kregs+1);
+		unsigned long *fpregs = (unsigned long *)(((char *)child) + AOFF_task_fpregs);
 
 		if (copy_from_user(fpregs, &fps->regs[0],
 				   (64 * sizeof(unsigned int))) ||
-		    __get_user(fpregs[32], (&fps->fsr))) {
+		    __get_user(child->tss.xfsr[0], (&fps->fsr))) {
 			pt_error_return(regs, EFAULT);
 			goto out;
 		}
+		if (!(child->tss.fpsaved[0] & FPRS_FEF))
+			child->tss.gsr[0] = 0;
+		child->tss.fpsaved[0] |= (FPRS_FEF | FPRS_DL | FPRS_DU);
 		pt_succ_return(regs, 0);
 		goto out;
 	}

FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen, slshen@lbl.gov