aboutsummaryrefslogtreecommitdiffstats
path: root/arch/alpha
diff options
context:
space:
mode:
authorAl Viro <viro@zeniv.linux.org.uk>2012-10-18 01:11:58 -0400
committerAl Viro <viro@zeniv.linux.org.uk>2012-11-28 21:49:03 -0500
commite0e431aa45416982eb3fddf34cedc72f1c3b3ce3 (patch)
tree10f3e3009387881a3c4a209b9d72c453aae865a1 /arch/alpha
parent2b067fc9dd143be5e0ee94bae0fbd28ea0a407f8 (diff)
alpha: simplify fork and friends
* no need to restore everything from switch_stack when we only need $26 * no need to pass current_pt_regs() manually, we can just as easily calculate it in alpha_clone/alpha_vfork ($8 + constant) * interpretation of zero usp as "use the parent's" is simpler in copy_thread(); let fork and vfork just pass 0. Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
Diffstat (limited to 'arch/alpha')
-rw-r--r--arch/alpha/kernel/entry.S17
-rw-r--r--arch/alpha/kernel/process.c16
2 files changed, 14 insertions, 19 deletions
diff --git a/arch/alpha/kernel/entry.S b/arch/alpha/kernel/entry.S
index a7607832dd4f..cc6d34e9e2ea 100644
--- a/arch/alpha/kernel/entry.S
+++ b/arch/alpha/kernel/entry.S
@@ -617,7 +617,6 @@ ret_from_kernel_thread:
617 .ent sys_fork 617 .ent sys_fork
618sys_fork: 618sys_fork:
619 .prologue 0 619 .prologue 0
620 mov $sp, $21
621 bsr $1, do_switch_stack 620 bsr $1, do_switch_stack
622 bis $31, SIGCHLD, $16 621 bis $31, SIGCHLD, $16
623 mov $31, $17 622 mov $31, $17
@@ -625,7 +624,9 @@ sys_fork:
625 mov $31, $19 624 mov $31, $19
626 mov $31, $20 625 mov $31, $20
627 jsr $26, alpha_clone 626 jsr $26, alpha_clone
628 bsr $1, undo_switch_stack 627fork_out:
628 ldq $26, 56($sp)
629 lda $sp, SWITCH_STACK_SIZE($sp)
629 ret 630 ret
630.end sys_fork 631.end sys_fork
631 632
@@ -634,12 +635,10 @@ sys_fork:
634 .ent sys_clone 635 .ent sys_clone
635sys_clone: 636sys_clone:
636 .prologue 0 637 .prologue 0
637 mov $sp, $21
638 bsr $1, do_switch_stack 638 bsr $1, do_switch_stack
639 /* $16, $17, $18, $19, $20 come from the user. */ 639 /* $16, $17, $18, $19, $20 come from the user. */
640 jsr $26, alpha_clone 640 lda $26, fork_out
641 bsr $1, undo_switch_stack 641 jsr $31, alpha_clone
642 ret
643.end sys_clone 642.end sys_clone
644 643
645 .align 4 644 .align 4
@@ -647,11 +646,9 @@ sys_clone:
647 .ent sys_vfork 646 .ent sys_vfork
648sys_vfork: 647sys_vfork:
649 .prologue 0 648 .prologue 0
650 mov $sp, $16
651 bsr $1, do_switch_stack 649 bsr $1, do_switch_stack
652 jsr $26, alpha_vfork 650 lda $26, fork_out
653 bsr $1, undo_switch_stack 651 jsr $31, alpha_vfork
654 ret
655.end sys_vfork 652.end sys_vfork
656 653
657 .align 4 654 .align 4
diff --git a/arch/alpha/kernel/process.c b/arch/alpha/kernel/process.c
index 51987dcf79b8..ad86c099b6f5 100644
--- a/arch/alpha/kernel/process.c
+++ b/arch/alpha/kernel/process.c
@@ -246,19 +246,17 @@ release_thread(struct task_struct *dead_task)
246int 246int
247alpha_clone(unsigned long clone_flags, unsigned long usp, 247alpha_clone(unsigned long clone_flags, unsigned long usp,
248 int __user *parent_tid, int __user *child_tid, 248 int __user *parent_tid, int __user *child_tid,
249 unsigned long tls_value, struct pt_regs *regs) 249 unsigned long tls_value)
250{ 250{
251 if (!usp) 251 return do_fork(clone_flags, usp, current_pt_regs(), 0,
252 usp = rdusp(); 252 parent_tid, child_tid);
253
254 return do_fork(clone_flags, usp, regs, 0, parent_tid, child_tid);
255} 253}
256 254
257int 255int
258alpha_vfork(struct pt_regs *regs) 256alpha_vfork(void)
259{ 257{
260 return do_fork(CLONE_VFORK | CLONE_VM | SIGCHLD, rdusp(), 258 return do_fork(CLONE_VFORK | CLONE_VM | SIGCHLD, 0,
261 regs, 0, NULL, NULL); 259 current_pt_regs(), 0, NULL, NULL);
262} 260}
263 261
264/* 262/*
@@ -301,7 +299,7 @@ copy_thread(unsigned long clone_flags, unsigned long usp,
301 stack = ((struct switch_stack *) regs) - 1; 299 stack = ((struct switch_stack *) regs) - 1;
302 *childstack = *stack; 300 *childstack = *stack;
303 childstack->r26 = (unsigned long) ret_from_fork; 301 childstack->r26 = (unsigned long) ret_from_fork;
304 childti->pcb.usp = usp; 302 childti->pcb.usp = usp ?: rdusp();
305 childti->pcb.ksp = (unsigned long) childstack; 303 childti->pcb.ksp = (unsigned long) childstack;
306 childti->pcb.flags = 1; /* set FEN, clear everything else */ 304 childti->pcb.flags = 1; /* set FEN, clear everything else */
307 305