aboutsummaryrefslogtreecommitdiffstats
path: root/arch/openrisc
diff options
context:
space:
mode:
authorJonas Bonn <jonas@southpole.se>2012-03-02 04:05:24 -0500
committerJonas Bonn <jonas@southpole.se>2012-03-06 04:37:00 -0500
commit6cbe5e95267449ea0b79c0b049342409949da3ac (patch)
tree21243a6c899b27f67338d77a28ccbe0f473272bc /arch/openrisc
parent2f099a280e92c259598d8ed8da82c7ec2dd49845 (diff)
openrisc: sanitize use of orig_gpr11
The pt_regs struct had both a 'syscallno' field and an 'orig_gpr11' field and it wasn't really clear how these were supposed to be used. This patch removes the syscallno field altogether and makes orig_gpr11 work more like other architectures: keep track of syscall number in progress or hold -1 for non-syscall exceptions. Signed-off-by: Jonas Bonn <jonas@southpole.se>
Diffstat (limited to 'arch/openrisc')
-rw-r--r--arch/openrisc/include/asm/ptrace.h6
-rw-r--r--arch/openrisc/include/asm/syscall.h7
-rw-r--r--arch/openrisc/kernel/entry.S16
-rw-r--r--arch/openrisc/kernel/ptrace.c4
-rw-r--r--arch/openrisc/kernel/signal.c2
-rw-r--r--arch/openrisc/kernel/traps.c8
6 files changed, 22 insertions, 21 deletions
diff --git a/arch/openrisc/include/asm/ptrace.h b/arch/openrisc/include/asm/ptrace.h
index e612ce4512c7..4651a737591d 100644
--- a/arch/openrisc/include/asm/ptrace.h
+++ b/arch/openrisc/include/asm/ptrace.h
@@ -73,9 +73,13 @@ struct pt_regs {
73 }; 73 };
74 }; 74 };
75 long pc; 75 long pc;
76 /* For restarting system calls:
77 * Set to syscall number for syscall exceptions,
78 * -1 for all other exceptions.
79 */
76 long orig_gpr11; /* For restarting system calls */ 80 long orig_gpr11; /* For restarting system calls */
77 long syscallno; /* Syscall number (used by strace) */
78 long dummy; /* Cheap alignment fix */ 81 long dummy; /* Cheap alignment fix */
82 long dummy2; /* Cheap alignment fix */
79}; 83};
80 84
81/* TODO: Rename this to REDZONE because that's what it is */ 85/* TODO: Rename this to REDZONE because that's what it is */
diff --git a/arch/openrisc/include/asm/syscall.h b/arch/openrisc/include/asm/syscall.h
index 9f0337055d26..b752bb67891d 100644
--- a/arch/openrisc/include/asm/syscall.h
+++ b/arch/openrisc/include/asm/syscall.h
@@ -25,7 +25,7 @@
25static inline int 25static inline int
26syscall_get_nr(struct task_struct *task, struct pt_regs *regs) 26syscall_get_nr(struct task_struct *task, struct pt_regs *regs)
27{ 27{
28 return regs->syscallno ? regs->syscallno : -1; 28 return regs->orig_gpr11;
29} 29}
30 30
31static inline void 31static inline void
@@ -50,10 +50,7 @@ static inline void
50syscall_set_return_value(struct task_struct *task, struct pt_regs *regs, 50syscall_set_return_value(struct task_struct *task, struct pt_regs *regs,
51 int error, long val) 51 int error, long val)
52{ 52{
53 if (error) 53 regs->gpr[11] = (long) error ?: val;
54 regs->gpr[11] = -error;
55 else
56 regs->gpr[11] = val;
57} 54}
58 55
59static inline void 56static inline void
diff --git a/arch/openrisc/kernel/entry.S b/arch/openrisc/kernel/entry.S
index d5f9c35a583f..6e61af8682b8 100644
--- a/arch/openrisc/kernel/entry.S
+++ b/arch/openrisc/kernel/entry.S
@@ -95,7 +95,6 @@ handler: ;\
95 /* r1, EPCR, ESR a already saved */ ;\ 95 /* r1, EPCR, ESR a already saved */ ;\
96 l.sw PT_GPR2(r1),r2 ;\ 96 l.sw PT_GPR2(r1),r2 ;\
97 l.sw PT_GPR3(r1),r3 ;\ 97 l.sw PT_GPR3(r1),r3 ;\
98 l.sw PT_ORIG_GPR11(r1),r11 ;\
99 /* r4 already save */ ;\ 98 /* r4 already save */ ;\
100 l.sw PT_GPR5(r1),r5 ;\ 99 l.sw PT_GPR5(r1),r5 ;\
101 l.sw PT_GPR6(r1),r6 ;\ 100 l.sw PT_GPR6(r1),r6 ;\
@@ -125,7 +124,9 @@ handler: ;\
125 /* r30 already save */ ;\ 124 /* r30 already save */ ;\
126/* l.sw PT_GPR30(r1),r30*/ ;\ 125/* l.sw PT_GPR30(r1),r30*/ ;\
127 l.sw PT_GPR31(r1),r31 ;\ 126 l.sw PT_GPR31(r1),r31 ;\
128 l.sw PT_SYSCALLNO(r1),r0 127 /* Store -1 in orig_gpr11 for non-syscall exceptions */ ;\
128 l.addi r30,r0,-1 ;\
129 l.sw PT_ORIG_GPR11(r1),r30
129 130
130#define UNHANDLED_EXCEPTION(handler,vector) \ 131#define UNHANDLED_EXCEPTION(handler,vector) \
131 .global handler ;\ 132 .global handler ;\
@@ -133,7 +134,6 @@ handler: ;\
133 /* r1, EPCR, ESR already saved */ ;\ 134 /* r1, EPCR, ESR already saved */ ;\
134 l.sw PT_GPR2(r1),r2 ;\ 135 l.sw PT_GPR2(r1),r2 ;\
135 l.sw PT_GPR3(r1),r3 ;\ 136 l.sw PT_GPR3(r1),r3 ;\
136 l.sw PT_ORIG_GPR11(r1),r11 ;\
137 l.sw PT_GPR5(r1),r5 ;\ 137 l.sw PT_GPR5(r1),r5 ;\
138 l.sw PT_GPR6(r1),r6 ;\ 138 l.sw PT_GPR6(r1),r6 ;\
139 l.sw PT_GPR7(r1),r7 ;\ 139 l.sw PT_GPR7(r1),r7 ;\
@@ -162,7 +162,9 @@ handler: ;\
162 /* r31 already saved */ ;\ 162 /* r31 already saved */ ;\
163 l.sw PT_GPR30(r1),r30 ;\ 163 l.sw PT_GPR30(r1),r30 ;\
164/* l.sw PT_GPR31(r1),r31 */ ;\ 164/* l.sw PT_GPR31(r1),r31 */ ;\
165 l.sw PT_SYSCALLNO(r1),r0 ;\ 165 /* Store -1 in orig_gpr11 for non-syscall exceptions */ ;\
166 l.addi r30,r0,-1 ;\
167 l.sw PT_ORIG_GPR11(r1),r30 ;\
166 l.addi r3,r1,0 ;\ 168 l.addi r3,r1,0 ;\
167 /* r4 is exception EA */ ;\ 169 /* r4 is exception EA */ ;\
168 l.addi r5,r0,vector ;\ 170 l.addi r5,r0,vector ;\
@@ -554,6 +556,7 @@ ENTRY(_sys_call_handler)
554 l.sw PT_GPR9(r1),r9 556 l.sw PT_GPR9(r1),r9
555 /* r10 already saved */ 557 /* r10 already saved */
556 l.sw PT_GPR11(r1),r11 558 l.sw PT_GPR11(r1),r11
559 /* orig_gpr11 must be set for syscalls */
557 l.sw PT_ORIG_GPR11(r1),r11 560 l.sw PT_ORIG_GPR11(r1),r11
558 /* r12,r13 already saved */ 561 /* r12,r13 already saved */
559 562
@@ -567,9 +570,6 @@ ENTRY(_sys_call_handler)
567 /* r30 is the only register we clobber in the fast path */ 570 /* r30 is the only register we clobber in the fast path */
568 /* r30 already saved */ 571 /* r30 already saved */
569/* l.sw PT_GPR30(r1),r30 */ 572/* l.sw PT_GPR30(r1),r30 */
570 /* This is used by do_signal to determine whether to check for
571 * syscall restart or not */
572 l.sw PT_SYSCALLNO(r1),r11
573 573
574_syscall_check_trace_enter: 574_syscall_check_trace_enter:
575 /* If TIF_SYSCALL_TRACE is set, then we want to do syscall tracing */ 575 /* If TIF_SYSCALL_TRACE is set, then we want to do syscall tracing */
@@ -731,7 +731,7 @@ _syscall_trace_enter:
731 * so that we can do the syscall for real and return to the syscall 731 * so that we can do the syscall for real and return to the syscall
732 * hot path. 732 * hot path.
733 */ 733 */
734 l.lwz r11,PT_SYSCALLNO(r1) 734 l.lwz r11,PT_GPR11(r1)
735 l.lwz r3,PT_GPR3(r1) 735 l.lwz r3,PT_GPR3(r1)
736 l.lwz r4,PT_GPR4(r1) 736 l.lwz r4,PT_GPR4(r1)
737 l.lwz r5,PT_GPR5(r1) 737 l.lwz r5,PT_GPR5(r1)
diff --git a/arch/openrisc/kernel/ptrace.c b/arch/openrisc/kernel/ptrace.c
index 7259047d5f9d..6deacb6b95a4 100644
--- a/arch/openrisc/kernel/ptrace.c
+++ b/arch/openrisc/kernel/ptrace.c
@@ -188,11 +188,11 @@ asmlinkage long do_syscall_trace_enter(struct pt_regs *regs)
188 */ 188 */
189 ret = -1L; 189 ret = -1L;
190 190
191 audit_syscall_entry(audit_arch(), regs->syscallno, 191 audit_syscall_entry(audit_arch(), regs->gpr[11],
192 regs->gpr[3], regs->gpr[4], 192 regs->gpr[3], regs->gpr[4],
193 regs->gpr[5], regs->gpr[6]); 193 regs->gpr[5], regs->gpr[6]);
194 194
195 return ret ? : regs->syscallno; 195 return ret ? : regs->gpr[11];
196} 196}
197 197
198asmlinkage void do_syscall_trace_leave(struct pt_regs *regs) 198asmlinkage void do_syscall_trace_leave(struct pt_regs *regs)
diff --git a/arch/openrisc/kernel/signal.c b/arch/openrisc/kernel/signal.c
index cf35ea032a70..e970743251ae 100644
--- a/arch/openrisc/kernel/signal.c
+++ b/arch/openrisc/kernel/signal.c
@@ -305,7 +305,7 @@ void do_signal(struct pt_regs *regs)
305 * below mean that the syscall executed to completion and no 305 * below mean that the syscall executed to completion and no
306 * restart is necessary. 306 * restart is necessary.
307 */ 307 */
308 if (regs->syscallno) { 308 if (regs->orig_gpr11) {
309 int restart = 0; 309 int restart = 0;
310 310
311 switch (regs->gpr[11]) { 311 switch (regs->gpr[11]) {
diff --git a/arch/openrisc/kernel/traps.c b/arch/openrisc/kernel/traps.c
index ab68ffc85750..a2ee12948f40 100644
--- a/arch/openrisc/kernel/traps.c
+++ b/arch/openrisc/kernel/traps.c
@@ -146,8 +146,8 @@ void show_registers(struct pt_regs *regs)
146 regs->gpr[24], regs->gpr[25], regs->gpr[26], regs->gpr[27]); 146 regs->gpr[24], regs->gpr[25], regs->gpr[26], regs->gpr[27]);
147 printk("GPR28: %08lx GPR29: %08lx GPR30: %08lx GPR31: %08lx\n", 147 printk("GPR28: %08lx GPR29: %08lx GPR30: %08lx GPR31: %08lx\n",
148 regs->gpr[28], regs->gpr[29], regs->gpr[30], regs->gpr[31]); 148 regs->gpr[28], regs->gpr[29], regs->gpr[30], regs->gpr[31]);
149 printk(" RES: %08lx oGPR11: %08lx syscallno: %08lx\n", 149 printk(" RES: %08lx oGPR11: %08lx\n",
150 regs->gpr[11], regs->orig_gpr11, regs->syscallno); 150 regs->gpr[11], regs->orig_gpr11);
151 151
152 printk("Process %s (pid: %d, stackpage=%08lx)\n", 152 printk("Process %s (pid: %d, stackpage=%08lx)\n",
153 current->comm, current->pid, (unsigned long)current); 153 current->comm, current->pid, (unsigned long)current);
@@ -208,8 +208,8 @@ void nommu_dump_state(struct pt_regs *regs,
208 regs->gpr[24], regs->gpr[25], regs->gpr[26], regs->gpr[27]); 208 regs->gpr[24], regs->gpr[25], regs->gpr[26], regs->gpr[27]);
209 printk("GPR28: %08lx GPR29: %08lx GPR30: %08lx GPR31: %08lx\n", 209 printk("GPR28: %08lx GPR29: %08lx GPR30: %08lx GPR31: %08lx\n",
210 regs->gpr[28], regs->gpr[29], regs->gpr[30], regs->gpr[31]); 210 regs->gpr[28], regs->gpr[29], regs->gpr[30], regs->gpr[31]);
211 printk(" RES: %08lx oGPR11: %08lx syscallno: %08lx\n", 211 printk(" RES: %08lx oGPR11: %08lx\n",
212 regs->gpr[11], regs->orig_gpr11, regs->syscallno); 212 regs->gpr[11], regs->orig_gpr11);
213 213
214 printk("Process %s (pid: %d, stackpage=%08lx)\n", 214 printk("Process %s (pid: %d, stackpage=%08lx)\n",
215 ((struct task_struct *)(__pa(current)))->comm, 215 ((struct task_struct *)(__pa(current)))->comm,