History

Merge tag 'fork-v5.9' of git://git.kernel.org/pub/scm/linux/kernel/git/brauner/linux

Pull fork cleanups from Christian Brauner: "This is cleanup series from when we reworked a chunk of the process creation paths in the kernel and switched to struct {kernel_}clone_args. High-level this does two main things: - Remove the double export of both do_fork() and _do_fork() where do_fork() used the incosistent legacy clone calling convention. Now we only export _do_fork() which is based on struct kernel_clone_args. - Remove the copy_thread_tls()/copy_thread() split making the architecture specific HAVE_COYP_THREAD_TLS config option obsolete. This switches all remaining architectures to select HAVE_COPY_THREAD_TLS and thus to the copy_thread_tls() calling convention. The current split makes the process creation codepaths more convoluted than they need to be. Each architecture has their own copy_thread() function unless it selects HAVE_COPY_THREAD_TLS then it has a copy_thread_tls() function. The split is not needed anymore nowadays, all architectures support CLONE_SETTLS but quite a few of them never bothered to select HAVE_COPY_THREAD_TLS and instead simply continued to use copy_thread() and use the old calling convention. Removing this split cleans up the process creation codepaths and paves the way for implementing clone3() on such architectures since it requires the copy_thread_tls() calling convention. After having made each architectures support copy_thread_tls() this series simply renames that function back to copy_thread(). It also switches all architectures that call do_fork() directly over to _do_fork() and the struct kernel_clone_args calling convention. This is a corollary of switching the architectures that did not yet support it over to copy_thread_tls() since do_fork() is conditional on not supporting copy_thread_tls() (Mostly because it lacks a separate argument for tls which is trivial to fix but there's no need for this function to exist.). The do_fork() removal is in itself already useful as it allows to to remove the export of both do_fork() and _do_fork() we currently have in favor of only _do_fork(). This has already been discussed back when we added clone3(). The legacy clone() calling convention is - as is probably well-known - somewhat odd: # # ABI hall of shame # config CLONE_BACKWARDS config CLONE_BACKWARDS2 config CLONE_BACKWARDS3 that is aggravated by the fact that some architectures such as sparc follow the CLONE_BACKWARDSx calling convention but don't really select the corresponding config option since they call do_fork() directly. So do_fork() enforces a somewhat arbitrary calling convention in the first place that doesn't really help the individual architectures that deviate from it. They can thus simply be switched to _do_fork() enforcing a single calling convention. (I really hope that any new architectures will __not__ try to implement their own calling conventions...) Most architectures already have made a similar switch (m68k comes to mind). Overall this removes more code than it adds even with a good portion of added comments. It simplifies a chunk of arch specific assembly either by moving the code into C or by simply rewriting the assembly. Architectures that have been touched in non-trivial ways have all been actually boot and stress tested: sparc and ia64 have been tested with Debian 9 images. They are the two architectures which have been touched the most. All non-trivial changes to architectures have seen acks from the relevant maintainers. nios2 with a custom built buildroot image. h8300 I couldn't get something bootable to test on but the changes have been fairly automatic and I'm sure we'll hear people yell if I broke something there. All other architectures that have been touched in trivial ways have been compile tested for each single patch of the series via git rebase -x "make ..." v5.8-rc2. arm{64} and x86{_64} have been boot tested even though they have just been trivially touched (removal of the HAVE_COPY_THREAD_TLS macro from their Kconfig) because well they are basically "core architectures" and since it is trivial to get your hands on a useable image" * tag 'fork-v5.9' of git://git.kernel.org/pub/scm/linux/kernel/git/brauner/linux: arch: rename copy_thread_tls() back to copy_thread() arch: remove HAVE_COPY_THREAD_TLS unicore: switch to copy_thread_tls() sh: switch to copy_thread_tls() nds32: switch to copy_thread_tls() microblaze: switch to copy_thread_tls() hexagon: switch to copy_thread_tls() c6x: switch to copy_thread_tls() alpha: switch to copy_thread_tls() fork: remove do_fork() h8300: select HAVE_COPY_THREAD_TLS, switch to kernel_clone_args nios2: enable HAVE_COPY_THREAD_TLS, switch to kernel_clone_args ia64: enable HAVE_COPY_THREAD_TLS, switch to kernel_clone_args sparc: unconditionally enable HAVE_COPY_THREAD_TLS sparc: share process creation helpers between sparc and sparc64 sparc64: enable HAVE_COPY_THREAD_TLS fork: fold legacy_clone_args_valid() into _do_fork()

Linus Torvalds committed 6 years ago

Commit 9ba27412 parents 0a72761 714acdb52 files · +274 −286Browse files

Unified · Split

52 files
  1. arch/Kconfig +0 −7
  2. arch/alpha/kernel/process.c +4 −5
  3. arch/arc/Kconfig +0 −1
  4. arch/arc/kernel/process.c +3 −2
  5. arch/arm/Kconfig +0 −1
  6. arch/arm/kernel/process.c +2 −3
  7. arch/arm64/Kconfig +0 −1
  8. arch/arm64/kernel/process.c +1 −1
  9. arch/c6x/kernel/process.c +2 −2
  10. arch/csky/Kconfig +0 −1
  11. arch/csky/kernel/process.c +1 −1
  12. arch/h8300/kernel/process.c +12 −5
  13. arch/hexagon/kernel/process.c +3 −3
  14. arch/ia64/kernel/entry.S +13 −19
  15. arch/ia64/kernel/process.c +23 −6
  16. arch/m68k/Kconfig +0 −1
  17. arch/m68k/kernel/process.c +2 −6
  18. arch/microblaze/kernel/process.c +3 −3
  19. arch/mips/Kconfig +0 −1
  20. arch/mips/kernel/process.c +3 −2
  21. arch/nds32/kernel/process.c +2 −2
  22. arch/nios2/kernel/entry.S +1 −6
  23. arch/nios2/kernel/process.c +20 −3
  24. arch/openrisc/Kconfig +0 −1
  25. arch/openrisc/kernel/process.c +3 −3
  26. arch/parisc/Kconfig +0 −1
  27. arch/parisc/kernel/process.c +1 −1
  28. arch/powerpc/Kconfig +0 −1
  29. arch/powerpc/kernel/process.c +1 −1
  30. arch/riscv/Kconfig +0 −1
  31. arch/riscv/kernel/process.c +2 −2
  32. arch/s390/Kconfig +0 −1
  33. arch/s390/kernel/process.c +2 −2
  34. arch/sh/kernel/process_32.c +3 −3
  35. arch/sparc/include/asm/syscalls.h +3 −4
  36. arch/sparc/kernel/Makefile +1 −0
  37. arch/sparc/kernel/entry.S +7 −22
  38. arch/sparc/kernel/kernel.h +5 −6
  39. arch/sparc/kernel/process.c +110 −0
  40. arch/sparc/kernel/process_32.c +3 −30
  41. arch/sparc/kernel/process_64.c +3 −37
  42. arch/sparc/kernel/syscalls.S +13 −10
  43. arch/um/Kconfig +0 −1
  44. arch/um/kernel/process.c +1 −1
  45. arch/x86/Kconfig +0 −1
  46. arch/x86/kernel/process.c +2 −2
  47. arch/x86/kernel/sys_ia32.c +0 −3
  48. arch/x86/kernel/unwind_frame.c +1 −1
  49. arch/xtensa/Kconfig +0 −1
  50. arch/xtensa/kernel/process.c +1 −1
  51. include/linux/sched/task.h +1 −16
  52. kernel/fork.c +16 −51
arch/Kconfig+0−7
@@ -754,13 +754,6 @@ config ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT · 753 unmodified lines
754 depends on MMU754 depends on MMU
755 select ARCH_HAS_ELF_RANDOMIZE755 select ARCH_HAS_ELF_RANDOMIZE
756 756
757config HAVE_COPY_THREAD_TLS
758 bool
759 help
760 Architecture provides copy_thread_tls to accept tls argument via
761 normal C parameter passing, rather than extracting the syscall
762 argument from pt_regs.
763
764config HAVE_STACK_VALIDATION757config HAVE_STACK_VALIDATION
765 bool758 bool
766 help759 help
arch/alpha/kernel/process.c+4−5
@@ -233,10 +233,9 @@ release_thread(struct task_struct *dead_task) · 232 unmodified lines
233/*233/*
234 * Copy architecture-specific thread state234 * Copy architecture-specific thread state
235 */235 */
236int236int copy_thread(unsigned long clone_flags, unsigned long usp,
237copy_thread(unsigned long clone_flags, unsigned long usp,237 unsigned long kthread_arg, struct task_struct *p,
238 unsigned long kthread_arg,238 unsigned long tls)
239 struct task_struct *p)
240{239{
241 extern void ret_from_fork(void);240 extern void ret_from_fork(void);
242 extern void ret_from_kernel_thread(void);241 extern void ret_from_kernel_thread(void);
@@ -267,7 +266,7 @@ copy_thread(unsigned long clone_flags, unsigned long usp, · 24 unmodified lines
267 required for proper operation in the case of a threaded266 required for proper operation in the case of a threaded
268 application calling fork. */267 application calling fork. */
269 if (clone_flags & CLONE_SETTLS)268 if (clone_flags & CLONE_SETTLS)
270 childti->pcb.unique = regs->r20;269 childti->pcb.unique = tls;
271 else270 else
272 regs->r20 = 0; /* OSF/1 has some strange fork() semantics. */271 regs->r20 = 0; /* OSF/1 has some strange fork() semantics. */
273 childti->pcb.usp = usp ?: rdusp();272 childti->pcb.usp = usp ?: rdusp();
arch/arc/Kconfig+0−1
@@ -29,7 +29,6 @@ config ARC · 28 unmodified lines
29 select GENERIC_SMP_IDLE_THREAD29 select GENERIC_SMP_IDLE_THREAD
30 select HAVE_ARCH_KGDB30 select HAVE_ARCH_KGDB
31 select HAVE_ARCH_TRACEHOOK31 select HAVE_ARCH_TRACEHOOK
32 select HAVE_COPY_THREAD_TLS
33 select HAVE_DEBUG_STACKOVERFLOW32 select HAVE_DEBUG_STACKOVERFLOW
34 select HAVE_DEBUG_KMEMLEAK33 select HAVE_DEBUG_KMEMLEAK
35 select HAVE_FUTEX_CMPXCHG if FUTEX34 select HAVE_FUTEX_CMPXCHG if FUTEX
arch/arc/kernel/process.c+3−2
@@ -173,8 +173,9 @@ asmlinkage void ret_from_fork(void); · 172 unmodified lines
173 * | user_r25 |173 * | user_r25 |
174 * ------------------ <===== END of PAGE174 * ------------------ <===== END of PAGE
175 */175 */
176int copy_thread_tls(unsigned long clone_flags, unsigned long usp,176int copy_thread(unsigned long clone_flags, unsigned long usp,
177 unsigned long kthread_arg, struct task_struct *p, unsigned long tls)177 unsigned long kthread_arg, struct task_struct *p,
178 unsigned long tls)
178{179{
179 struct pt_regs *c_regs; /* child's pt_regs */180 struct pt_regs *c_regs; /* child's pt_regs */
180 unsigned long *childksp; /* to unwind out of __switch_to() */181 unsigned long *childksp; /* to unwind out of __switch_to() */
arch/arm/Kconfig+0−1
@@ -72,7 +72,6 @@ config ARM · 71 unmodified lines
72 select HAVE_ARM_SMCCC if CPU_V772 select HAVE_ARM_SMCCC if CPU_V7
73 select HAVE_EBPF_JIT if !CPU_ENDIAN_BE3273 select HAVE_EBPF_JIT if !CPU_ENDIAN_BE32
74 select HAVE_CONTEXT_TRACKING74 select HAVE_CONTEXT_TRACKING
75 select HAVE_COPY_THREAD_TLS
76 select HAVE_C_RECORDMCOUNT75 select HAVE_C_RECORDMCOUNT
77 select HAVE_DEBUG_KMEMLEAK if !XIP_KERNEL76 select HAVE_DEBUG_KMEMLEAK if !XIP_KERNEL
78 select HAVE_DMA_CONTIGUOUS if MMU77 select HAVE_DMA_CONTIGUOUS if MMU
arch/arm/kernel/process.c+2−3
@@ -225,9 +225,8 @@ void release_thread(struct task_struct *dead_task) · 224 unmodified lines
225 225
226asmlinkage void ret_from_fork(void) __asm__("ret_from_fork");226asmlinkage void ret_from_fork(void) __asm__("ret_from_fork");
227 227
228int228int copy_thread(unsigned long clone_flags, unsigned long stack_start,
229copy_thread_tls(unsigned long clone_flags, unsigned long stack_start,229 unsigned long stk_sz, struct task_struct *p, unsigned long tls)
230 unsigned long stk_sz, struct task_struct *p, unsigned long tls)
231{230{
232 struct thread_info *thread = task_thread_info(p);231 struct thread_info *thread = task_thread_info(p);
233 struct pt_regs *childregs = task_pt_regs(p);232 struct pt_regs *childregs = task_pt_regs(p);
arch/arm64/Kconfig+0−1
@@ -149,7 +149,6 @@ config ARM64 · 148 unmodified lines
149 select HAVE_CMPXCHG_DOUBLE149 select HAVE_CMPXCHG_DOUBLE
150 select HAVE_CMPXCHG_LOCAL150 select HAVE_CMPXCHG_LOCAL
151 select HAVE_CONTEXT_TRACKING151 select HAVE_CONTEXT_TRACKING
152 select HAVE_COPY_THREAD_TLS
153 select HAVE_DEBUG_BUGVERBOSE152 select HAVE_DEBUG_BUGVERBOSE
154 select HAVE_DEBUG_KMEMLEAK153 select HAVE_DEBUG_KMEMLEAK
155 select HAVE_DMA_CONTIGUOUS154 select HAVE_DMA_CONTIGUOUS
arch/arm64/kernel/process.c+1−1
@@ -375,7 +375,7 @@ int arch_dup_task_struct(struct task_struct *dst, struct task_struct *src) · 374 unmodified lines
375 375
376asmlinkage void ret_from_fork(void) asm("ret_from_fork");376asmlinkage void ret_from_fork(void) asm("ret_from_fork");
377 377
378int copy_thread_tls(unsigned long clone_flags, unsigned long stack_start,378int copy_thread(unsigned long clone_flags, unsigned long stack_start,
379 unsigned long stk_sz, struct task_struct *p, unsigned long tls)379 unsigned long stk_sz, struct task_struct *p, unsigned long tls)
380{380{
381 struct pt_regs *childregs = task_pt_regs(p);381 struct pt_regs *childregs = task_pt_regs(p);
arch/c6x/kernel/process.c+2−2
@@ -105,8 +105,8 @@ void start_thread(struct pt_regs *regs, unsigned int pc, unsigned long usp) · 104 unmodified lines
105 * Copy a new thread context in its stack.105 * Copy a new thread context in its stack.
106 */106 */
107int copy_thread(unsigned long clone_flags, unsigned long usp,107int copy_thread(unsigned long clone_flags, unsigned long usp,
108 unsigned long ustk_size,108 unsigned long ustk_size, struct task_struct *p,
109 struct task_struct *p)109 unsigned long tls)
110{110{
111 struct pt_regs *childregs;111 struct pt_regs *childregs;
112 112
arch/csky/Kconfig+0−1
@@ -38,7 +38,6 @@ config CSKY · 37 unmodified lines
38 select GX6605S_TIMER if CPU_CK61038 select GX6605S_TIMER if CPU_CK610
39 select HAVE_ARCH_TRACEHOOK39 select HAVE_ARCH_TRACEHOOK
40 select HAVE_ARCH_AUDITSYSCALL40 select HAVE_ARCH_AUDITSYSCALL
41 select HAVE_COPY_THREAD_TLS
42 select HAVE_DEBUG_BUGVERBOSE41 select HAVE_DEBUG_BUGVERBOSE
43 select HAVE_DYNAMIC_FTRACE42 select HAVE_DYNAMIC_FTRACE
44 select HAVE_DYNAMIC_FTRACE_WITH_REGS43 select HAVE_DYNAMIC_FTRACE_WITH_REGS
arch/csky/kernel/process.c+1−1
@@ -40,7 +40,7 @@ unsigned long thread_saved_pc(struct task_struct *tsk) · 39 unmodified lines
40 return sw->r15;40 return sw->r15;
41}41}
42 42
43int copy_thread_tls(unsigned long clone_flags,43int copy_thread(unsigned long clone_flags,
44 unsigned long usp,44 unsigned long usp,
45 unsigned long kthread_arg,45 unsigned long kthread_arg,
46 struct task_struct *p,46 struct task_struct *p,
arch/h8300/kernel/process.c+12−5
@@ -105,9 +105,8 @@ void flush_thread(void) · 104 unmodified lines
105{105{
106}106}
107 107
108int copy_thread(unsigned long clone_flags,108int copy_thread(unsigned long clone_flags, unsigned long usp,
109 unsigned long usp, unsigned long topstk,109 unsigned long topstk, struct task_struct *p, unsigned long tls)
110 struct task_struct *p)
111{110{
112 struct pt_regs *childregs;111 struct pt_regs *childregs;
113 112
@@ -159,11 +158,19 @@ asmlinkage int sys_clone(unsigned long __user *args) · 45 unmodified lines
159 unsigned long newsp;158 unsigned long newsp;
160 uintptr_t parent_tidptr;159 uintptr_t parent_tidptr;
161 uintptr_t child_tidptr;160 uintptr_t child_tidptr;
161 struct kernel_clone_args kargs = {};
162 162
163 get_user(clone_flags, &args[0]);163 get_user(clone_flags, &args[0]);
164 get_user(newsp, &args[1]);164 get_user(newsp, &args[1]);
165 get_user(parent_tidptr, &args[2]);165 get_user(parent_tidptr, &args[2]);
166 get_user(child_tidptr, &args[3]);166 get_user(child_tidptr, &args[3]);
167 return do_fork(clone_flags, newsp, 0,167
168 (int __user *)parent_tidptr, (int __user *)child_tidptr);168 kargs.flags = (lower_32_bits(clone_flags) & ~CSIGNAL);
169 kargs.pidfd = (int __user *)parent_tidptr;
170 kargs.child_tid = (int __user *)child_tidptr;
171 kargs.parent_tid = (int __user *)parent_tidptr;
172 kargs.exit_signal = (lower_32_bits(clone_flags) & CSIGNAL);
173 kargs.stack = newsp;
174
175 return _do_fork(&kargs);
169}176}
arch/hexagon/kernel/process.c+3−3
@@ -50,8 +50,8 @@ void arch_cpu_idle(void) · 49 unmodified lines
50/*50/*
51 * Copy architecture-specific thread state51 * Copy architecture-specific thread state
52 */52 */
53int copy_thread(unsigned long clone_flags, unsigned long usp,53int copy_thread(unsigned long clone_flags, unsigned long usp, unsigned long arg,
54 unsigned long arg, struct task_struct *p)54 struct task_struct *p, unsigned long tls)
55{55{
56 struct thread_info *ti = task_thread_info(p);56 struct thread_info *ti = task_thread_info(p);
57 struct hexagon_switch_stack *ss;57 struct hexagon_switch_stack *ss;
@@ -100,7 +100,7 @@ int copy_thread(unsigned long clone_flags, unsigned long usp, · 42 unmodified lines
100 * ugp is used to provide TLS support.100 * ugp is used to provide TLS support.
101 */101 */
102 if (clone_flags & CLONE_SETTLS)102 if (clone_flags & CLONE_SETTLS)
103 childregs->ugp = childregs->r04;103 childregs->ugp = tls;
104 104
105 /*105 /*
106 * Parent sees new pid -- not necessary, not even possible at106 * Parent sees new pid -- not necessary, not even possible at
arch/ia64/kernel/entry.S+13−19
@@ -112,19 +112,16 @@ GLOBAL_ENTRY(sys_clone2) · 111 unmodified lines
112 .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(8)112 .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(8)
113 alloc r16=ar.pfs,8,2,6,0113 alloc r16=ar.pfs,8,2,6,0
114 DO_SAVE_SWITCH_STACK114 DO_SAVE_SWITCH_STACK
115 adds r2=PT(R16)+IA64_SWITCH_STACK_SIZE+16,sp
116 mov loc0=rp115 mov loc0=rp
117 mov loc1=r16 // save ar.pfs across do_fork116 mov loc1=r16 // save ar.pfs across ia64_clone
118 .body117 .body
118 mov out0=in0
119 mov out1=in1119 mov out1=in1
120 mov out2=in2120 mov out2=in2
121 tbit.nz p6,p0=in0,CLONE_SETTLS_BIT121 mov out3=in3
122 mov out3=in3 // parent_tidptr: valid only w/CLONE_PARENT_SETTID122 mov out4=in4
123 ;;123 mov out5=in5
124(p6) st8 [r2]=in5 // store TLS in r16 for copy_thread()124 br.call.sptk.many rp=ia64_clone
125 mov out4=in4 // child_tidptr: valid only w/CLONE_CHILD_SETTID or CLONE_CHILD_CLEARTID
126 mov out0=in0 // out0 = clone_flags
127 br.call.sptk.many rp=do_fork
128.ret1: .restore sp125.ret1: .restore sp
129 adds sp=IA64_SWITCH_STACK_SIZE,sp // pop the switch stack126 adds sp=IA64_SWITCH_STACK_SIZE,sp // pop the switch stack
130 mov ar.pfs=loc1127 mov ar.pfs=loc1
@@ -143,19 +140,16 @@ GLOBAL_ENTRY(sys_clone) · 12 unmodified lines
143 .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(8)140 .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(8)
144 alloc r16=ar.pfs,8,2,6,0141 alloc r16=ar.pfs,8,2,6,0
145 DO_SAVE_SWITCH_STACK142 DO_SAVE_SWITCH_STACK
146 adds r2=PT(R16)+IA64_SWITCH_STACK_SIZE+16,sp
147 mov loc0=rp143 mov loc0=rp
148 mov loc1=r16 // save ar.pfs across do_fork144 mov loc1=r16 // save ar.pfs across ia64_clone
149 .body145 .body
146 mov out0=in0
150 mov out1=in1147 mov out1=in1
151 mov out2=16 // stacksize (compensates for 16-byte scratch area)148 mov out2=16 // stacksize (compensates for 16-byte scratch area)
152 tbit.nz p6,p0=in0,CLONE_SETTLS_BIT149 mov out3=in3
153 mov out3=in2 // parent_tidptr: valid only w/CLONE_PARENT_SETTID150 mov out4=in4
154 ;;151 mov out5=in5
155(p6) st8 [r2]=in4 // store TLS in r13 (tp)152 br.call.sptk.many rp=ia64_clone
156 mov out4=in3 // child_tidptr: valid only w/CLONE_CHILD_SETTID or CLONE_CHILD_CLEARTID
157 mov out0=in0 // out0 = clone_flags
158 br.call.sptk.many rp=do_fork
159.ret2: .restore sp153.ret2: .restore sp
160 adds sp=IA64_SWITCH_STACK_SIZE,sp // pop the switch stack154 adds sp=IA64_SWITCH_STACK_SIZE,sp // pop the switch stack
161 mov ar.pfs=loc1155 mov ar.pfs=loc1
@@ -590,7 +584,7 @@ GLOBAL_ENTRY(ia64_ret_from_clone) · 428 unmodified lines
590 nop.i 0584 nop.i 0
591 /*585 /*
592 * We need to call schedule_tail() to complete the scheduling process.586 * We need to call schedule_tail() to complete the scheduling process.
593 * Called by ia64_switch_to() after do_fork()->copy_thread(). r8 contains the587 * Called by ia64_switch_to() after ia64_clone()->copy_thread(). r8 contains the
594 * address of the previously executing task.588 * address of the previously executing task.
595 */589 */
596 br.call.sptk.many rp=ia64_invoke_schedule_tail590 br.call.sptk.many rp=ia64_invoke_schedule_tail
arch/ia64/kernel/process.c+23−6
@@ -296,7 +296,7 @@ ia64_load_extra (struct task_struct *task) · 295 unmodified lines
296 pfm_load_regs(task);296 pfm_load_regs(task);
297 297
298 info = __this_cpu_read(pfm_syst_info);298 info = __this_cpu_read(pfm_syst_info);
299 if (info & PFM_CPUINFO_SYST_WIDE) 299 if (info & PFM_CPUINFO_SYST_WIDE)
300 pfm_syst_wide_update_task(task, info, 1);300 pfm_syst_wide_update_task(task, info, 1);
301#endif301#endif
302}302}
@@ -310,7 +310,7 @@ ia64_load_extra (struct task_struct *task) · 7 unmodified lines
310 *310 *
311 * <clone syscall> <some kernel call frames>311 * <clone syscall> <some kernel call frames>
312 * sys_clone :312 * sys_clone :
313 * do_fork do_fork313 * _do_fork _do_fork
314 * copy_thread copy_thread314 * copy_thread copy_thread
315 *315 *
316 * This means that the stack layout is as follows:316 * This means that the stack layout is as follows:
@@ -333,9 +333,8 @@ ia64_load_extra (struct task_struct *task) · 16 unmodified lines
333 * so there is nothing to worry about.333 * so there is nothing to worry about.
334 */334 */
335int335int
336copy_thread(unsigned long clone_flags,336copy_thread(unsigned long clone_flags, unsigned long user_stack_base,
337 unsigned long user_stack_base, unsigned long user_stack_size,337 unsigned long user_stack_size, struct task_struct *p, unsigned long tls)
338 struct task_struct *p)
339{338{
340 extern char ia64_ret_from_clone;339 extern char ia64_ret_from_clone;
341 struct switch_stack *child_stack, *stack;340 struct switch_stack *child_stack, *stack;
@@ -416,7 +415,7 @@ copy_thread(unsigned long clone_flags, · 74 unmodified lines
416 rbs_size = stack->ar_bspstore - rbs;415 rbs_size = stack->ar_bspstore - rbs;
417 memcpy((void *) child_rbs, (void *) rbs, rbs_size);416 memcpy((void *) child_rbs, (void *) rbs, rbs_size);
418 if (clone_flags & CLONE_SETTLS)417 if (clone_flags & CLONE_SETTLS)
419 child_ptregs->r13 = regs->r16; /* see sys_clone2() in entry.S */418 child_ptregs->r13 = tls;
420 if (user_stack_base) {419 if (user_stack_base) {
421 child_ptregs->r12 = user_stack_base + user_stack_size - 16;420 child_ptregs->r12 = user_stack_base + user_stack_size - 16;
422 child_ptregs->ar_bspstore = user_stack_base;421 child_ptregs->ar_bspstore = user_stack_base;
@@ -441,6 +440,24 @@ copy_thread(unsigned long clone_flags, · 18 unmodified lines
441 return retval;440 return retval;
442}441}
443 442
443asmlinkage long ia64_clone(unsigned long clone_flags, unsigned long stack_start,
444 unsigned long stack_size, unsigned long parent_tidptr,
445 unsigned long child_tidptr, unsigned long tls)
446{
447 struct kernel_clone_args args = {
448 .flags = (lower_32_bits(clone_flags) & ~CSIGNAL),
449 .pidfd = (int __user *)parent_tidptr,
450 .child_tid = (int __user *)child_tidptr,
451 .parent_tid = (int __user *)parent_tidptr,
452 .exit_signal = (lower_32_bits(clone_flags) & CSIGNAL),
453 .stack = stack_start,
454 .stack_size = stack_size,
455 .tls = tls,
456 };
457
458 return _do_fork(&args);
459}
460
444static void461static void
445do_copy_task_regs (struct task_struct *task, struct unw_frame_info *info, void *arg)462do_copy_task_regs (struct task_struct *task, struct unw_frame_info *info, void *arg)
446{463{
arch/m68k/Kconfig+0−1
@@ -14,7 +14,6 @@ config M68K · 13 unmodified lines
14 select HAVE_AOUT if MMU14 select HAVE_AOUT if MMU
15 select HAVE_ASM_MODVERSIONS15 select HAVE_ASM_MODVERSIONS
16 select HAVE_DEBUG_BUGVERBOSE16 select HAVE_DEBUG_BUGVERBOSE
17 select HAVE_COPY_THREAD_TLS
18 select GENERIC_IRQ_SHOW17 select GENERIC_IRQ_SHOW
19 select GENERIC_ATOMIC6418 select GENERIC_ATOMIC64
20 select HAVE_UID1619 select HAVE_UID16
arch/m68k/kernel/process.c+2−6
@@ -125,9 +125,6 @@ asmlinkage int m68k_clone(struct pt_regs *regs) · 124 unmodified lines
125 .tls = regs->d5,125 .tls = regs->d5,
126 };126 };
127 127
128 if (!legacy_clone_args_valid(&args))
129 return -EINVAL;
130
131 return _do_fork(&args);128 return _do_fork(&args);
132}129}
133 130
@@ -141,9 +138,8 @@ asmlinkage int m68k_clone3(struct pt_regs *regs) · 7 unmodified lines
141 return sys_clone3((struct clone_args __user *)regs->d1, regs->d2);138 return sys_clone3((struct clone_args __user *)regs->d1, regs->d2);
142}139}
143 140
144int copy_thread_tls(unsigned long clone_flags, unsigned long usp,141int copy_thread(unsigned long clone_flags, unsigned long usp, unsigned long arg,
145 unsigned long arg, struct task_struct *p,142 struct task_struct *p, unsigned long tls)
146 unsigned long tls)
147{143{
148 struct fork_frame {144 struct fork_frame {
149 struct switch_stack sw;145 struct switch_stack sw;
arch/microblaze/kernel/process.c+3−3
@@ -54,8 +54,8 @@ void flush_thread(void) · 53 unmodified lines
54{54{
55}55}
56 56
57int copy_thread(unsigned long clone_flags, unsigned long usp,57int copy_thread(unsigned long clone_flags, unsigned long usp, unsigned long arg,
58 unsigned long arg, struct task_struct *p)58 struct task_struct *p, unsigned long tls)
59{59{
60 struct pt_regs *childregs = task_pt_regs(p);60 struct pt_regs *childregs = task_pt_regs(p);
61 struct thread_info *ti = task_thread_info(p);61 struct thread_info *ti = task_thread_info(p);
@@ -114,7 +114,7 @@ int copy_thread(unsigned long clone_flags, unsigned long usp, · 52 unmodified lines
114 * which contains TLS area114 * which contains TLS area
115 */115 */
116 if (clone_flags & CLONE_SETTLS)116 if (clone_flags & CLONE_SETTLS)
117 childregs->r21 = childregs->r10;117 childregs->r21 = tls;
118 118
119 return 0;119 return 0;
120}120}
arch/mips/Kconfig+0−1
@@ -51,7 +51,6 @@ config MIPS · 50 unmodified lines
51 select HAVE_CBPF_JIT if !64BIT && !CPU_MICROMIPS51 select HAVE_CBPF_JIT if !64BIT && !CPU_MICROMIPS
52 select HAVE_CONTEXT_TRACKING52 select HAVE_CONTEXT_TRACKING
53 select HAVE_TIF_NOHZ53 select HAVE_TIF_NOHZ
54 select HAVE_COPY_THREAD_TLS
55 select HAVE_C_RECORDMCOUNT54 select HAVE_C_RECORDMCOUNT
56 select HAVE_DEBUG_KMEMLEAK55 select HAVE_DEBUG_KMEMLEAK
57 select HAVE_DEBUG_STACKOVERFLOW56 select HAVE_DEBUG_STACKOVERFLOW
arch/mips/kernel/process.c+3−2
@@ -119,8 +119,9 @@ int arch_dup_task_struct(struct task_struct *dst, struct task_struct *src) · 118 unmodified lines
119/*119/*
120 * Copy architecture-specific thread state120 * Copy architecture-specific thread state
121 */121 */
122int copy_thread_tls(unsigned long clone_flags, unsigned long usp,122int copy_thread(unsigned long clone_flags, unsigned long usp,
123 unsigned long kthread_arg, struct task_struct *p, unsigned long tls)123 unsigned long kthread_arg, struct task_struct *p,
124 unsigned long tls)
124{125{
125 struct thread_info *ti = task_thread_info(p);126 struct thread_info *ti = task_thread_info(p);
126 struct pt_regs *childregs, *regs = current_pt_regs();127 struct pt_regs *childregs, *regs = current_pt_regs();
arch/nds32/kernel/process.c+2−2
@@ -150,7 +150,7 @@ DEFINE_PER_CPU(struct task_struct *, __entry_task); · 149 unmodified lines
150 150
151asmlinkage void ret_from_fork(void) __asm__("ret_from_fork");151asmlinkage void ret_from_fork(void) __asm__("ret_from_fork");
152int copy_thread(unsigned long clone_flags, unsigned long stack_start,152int copy_thread(unsigned long clone_flags, unsigned long stack_start,
153 unsigned long stk_sz, struct task_struct *p)153 unsigned long stk_sz, struct task_struct *p, unsigned long tls)
154{154{
155 struct pt_regs *childregs = task_pt_regs(p);155 struct pt_regs *childregs = task_pt_regs(p);
156 156
@@ -170,7 +170,7 @@ int copy_thread(unsigned long clone_flags, unsigned long stack_start, · 13 unmodified lines
170 childregs->uregs[0] = 0;170 childregs->uregs[0] = 0;
171 childregs->osp = 0;171 childregs->osp = 0;
172 if (clone_flags & CLONE_SETTLS)172 if (clone_flags & CLONE_SETTLS)
173 childregs->uregs[25] = childregs->uregs[3];173 childregs->uregs[25] = tls;
174 }174 }
175 /* cpu context switching */175 /* cpu context switching */
176 p->thread.cpu_context.pc = (unsigned long)ret_from_fork;176 p->thread.cpu_context.pc = (unsigned long)ret_from_fork;
arch/nios2/kernel/entry.S+1−6
@@ -389,12 +389,7 @@ ENTRY(ret_from_interrupt) · 388 unmodified lines
389 */389 */
390ENTRY(sys_clone)390ENTRY(sys_clone)
391 SAVE_SWITCH_STACK391 SAVE_SWITCH_STACK
392 addi sp, sp, -4392 call nios2_clone
393 stw r7, 0(sp) /* Pass 5th arg thru stack */
394 mov r7, r6 /* 4th arg is 3rd of clone() */
395 mov r6, zero /* 3rd arg always 0 */
396 call do_fork
397 addi sp, sp, 4
398 RESTORE_SWITCH_STACK393 RESTORE_SWITCH_STACK
399 ret394 ret
400 395
arch/nios2/kernel/process.c+20−3
@@ -100,8 +100,8 @@ void flush_thread(void) · 99 unmodified lines
100{100{
101}101}
102 102
103int copy_thread(unsigned long clone_flags,103int copy_thread(unsigned long clone_flags, unsigned long usp, unsigned long arg,
104 unsigned long usp, unsigned long arg, struct task_struct *p)104 struct task_struct *p, unsigned long tls)
105{105{
106 struct pt_regs *childregs = task_pt_regs(p);106 struct pt_regs *childregs = task_pt_regs(p);
107 struct pt_regs *regs;107 struct pt_regs *regs;
@@ -140,7 +140,7 @@ int copy_thread(unsigned long clone_flags, · 32 unmodified lines
140 140
141 /* Initialize tls register. */141 /* Initialize tls register. */
142 if (clone_flags & CLONE_SETTLS)142 if (clone_flags & CLONE_SETTLS)
143 childstack->r23 = regs->r8;143 childstack->r23 = tls;
144 144
145 return 0;145 return 0;
146}146}
@@ -259,3 +259,20 @@ int dump_fpu(struct pt_regs *regs, elf_fpregset_t *r) · 112 unmodified lines
259{259{
260 return 0; /* Nios2 has no FPU and thus no FPU registers */260 return 0; /* Nios2 has no FPU and thus no FPU registers */
261}261}
262
263asmlinkage int nios2_clone(unsigned long clone_flags, unsigned long newsp,
264 int __user *parent_tidptr, int __user *child_tidptr,
265 unsigned long tls)
266{
267 struct kernel_clone_args args = {
268 .flags = (lower_32_bits(clone_flags) & ~CSIGNAL),
269 .pidfd = parent_tidptr,
270 .child_tid = child_tidptr,
271 .parent_tid = parent_tidptr,
272 .exit_signal = (lower_32_bits(clone_flags) & CSIGNAL),
273 .stack = newsp,
274 .tls = tls,
275 };
276
277 return _do_fork(&args);
278}
arch/openrisc/Kconfig+0−1
@@ -16,7 +16,6 @@ config OPENRISC · 15 unmodified lines
16 select HANDLE_DOMAIN_IRQ16 select HANDLE_DOMAIN_IRQ
17 select GPIOLIB17 select GPIOLIB
18 select HAVE_ARCH_TRACEHOOK18 select HAVE_ARCH_TRACEHOOK
19 select HAVE_COPY_THREAD_TLS
20 select SPARSE_IRQ19 select SPARSE_IRQ
21 select GENERIC_IRQ_CHIP20 select GENERIC_IRQ_CHIP
22 select GENERIC_IRQ_PROBE21 select GENERIC_IRQ_PROBE
arch/openrisc/kernel/process.c+3−3
@@ -116,7 +116,7 @@ void release_thread(struct task_struct *dead_task) · 115 unmodified lines
116extern asmlinkage void ret_from_fork(void);116extern asmlinkage void ret_from_fork(void);
117 117
118/*118/*
119 * copy_thread_tls119 * copy_thread
120 * @clone_flags: flags120 * @clone_flags: flags
121 * @usp: user stack pointer or fn for kernel thread121 * @usp: user stack pointer or fn for kernel thread
122 * @arg: arg to fn for kernel thread; always NULL for userspace thread122 * @arg: arg to fn for kernel thread; always NULL for userspace thread
@@ -147,8 +147,8 @@ extern asmlinkage void ret_from_fork(void); · 24 unmodified lines
147 */147 */
148 148
149int149int
150copy_thread_tls(unsigned long clone_flags, unsigned long usp,150copy_thread(unsigned long clone_flags, unsigned long usp, unsigned long arg,
151 unsigned long arg, struct task_struct *p, unsigned long tls)151 struct task_struct *p, unsigned long tls)
152{152{
153 struct pt_regs *userregs;153 struct pt_regs *userregs;
154 struct pt_regs *kregs;154 struct pt_regs *kregs;
arch/parisc/Kconfig+0−1
@@ -62,7 +62,6 @@ config PARISC · 61 unmodified lines
62 select HAVE_FTRACE_MCOUNT_RECORD if HAVE_DYNAMIC_FTRACE62 select HAVE_FTRACE_MCOUNT_RECORD if HAVE_DYNAMIC_FTRACE
63 select HAVE_KPROBES_ON_FTRACE63 select HAVE_KPROBES_ON_FTRACE
64 select HAVE_DYNAMIC_FTRACE_WITH_REGS64 select HAVE_DYNAMIC_FTRACE_WITH_REGS
65 select HAVE_COPY_THREAD_TLS
66 65
67 help66 help
68 The PA-RISC microprocessor is designed by Hewlett-Packard and used67 The PA-RISC microprocessor is designed by Hewlett-Packard and used
arch/parisc/kernel/process.c+1−1
@@ -208,7 +208,7 @@ arch_initcall(parisc_idle_init); · 207 unmodified lines
208 * Copy architecture-specific thread state208 * Copy architecture-specific thread state
209 */209 */
210int210int
211copy_thread_tls(unsigned long clone_flags, unsigned long usp,211copy_thread(unsigned long clone_flags, unsigned long usp,
212 unsigned long kthread_arg, struct task_struct *p, unsigned long tls)212 unsigned long kthread_arg, struct task_struct *p, unsigned long tls)
213{213{
214 struct pt_regs *cregs = &(p->thread.regs);214 struct pt_regs *cregs = &(p->thread.regs);
arch/powerpc/Kconfig+0−1
@@ -186,7 +186,6 @@ config PPC · 185 unmodified lines
186 select HAVE_STACKPROTECTOR if PPC32 && $(cc-option,-mstack-protector-guard=tls -mstack-protector-guard-reg=r2)186 select HAVE_STACKPROTECTOR if PPC32 && $(cc-option,-mstack-protector-guard=tls -mstack-protector-guard-reg=r2)
187 select HAVE_CONTEXT_TRACKING if PPC64187 select HAVE_CONTEXT_TRACKING if PPC64
188 select HAVE_TIF_NOHZ if PPC64188 select HAVE_TIF_NOHZ if PPC64
189 select HAVE_COPY_THREAD_TLS
190 select HAVE_DEBUG_KMEMLEAK189 select HAVE_DEBUG_KMEMLEAK
191 select HAVE_DEBUG_STACKOVERFLOW190 select HAVE_DEBUG_STACKOVERFLOW
192 select HAVE_DYNAMIC_FTRACE191 select HAVE_DYNAMIC_FTRACE
arch/powerpc/kernel/process.c+1−1
@@ -1593,7 +1593,7 @@ static void setup_ksp_vsid(struct task_struct *p, unsigned long sp) · 1592 unmodified lines
1593/*1593/*
1594 * Copy architecture-specific thread state1594 * Copy architecture-specific thread state
1595 */1595 */
1596int copy_thread_tls(unsigned long clone_flags, unsigned long usp,1596int copy_thread(unsigned long clone_flags, unsigned long usp,
1597 unsigned long kthread_arg, struct task_struct *p,1597 unsigned long kthread_arg, struct task_struct *p,
1598 unsigned long tls)1598 unsigned long tls)
1599{1599{
arch/riscv/Kconfig+0−1
@@ -54,7 +54,6 @@ config RISCV · 53 unmodified lines
54 select HAVE_ARCH_SECCOMP_FILTER54 select HAVE_ARCH_SECCOMP_FILTER
55 select HAVE_ARCH_TRACEHOOK55 select HAVE_ARCH_TRACEHOOK
56 select HAVE_ASM_MODVERSIONS56 select HAVE_ASM_MODVERSIONS
57 select HAVE_COPY_THREAD_TLS
58 select HAVE_DMA_CONTIGUOUS if MMU57 select HAVE_DMA_CONTIGUOUS if MMU
59 select HAVE_EBPF_JIT if MMU58 select HAVE_EBPF_JIT if MMU
60 select HAVE_FUTEX_CMPXCHG if FUTEX59 select HAVE_FUTEX_CMPXCHG if FUTEX
arch/riscv/kernel/process.c+2−2
@@ -101,8 +101,8 @@ int arch_dup_task_struct(struct task_struct *dst, struct task_struct *src) · 100 unmodified lines
101 return 0;101 return 0;
102}102}
103 103
104int copy_thread_tls(unsigned long clone_flags, unsigned long usp,104int copy_thread(unsigned long clone_flags, unsigned long usp, unsigned long arg,
105 unsigned long arg, struct task_struct *p, unsigned long tls)105 struct task_struct *p, unsigned long tls)
106{106{
107 struct pt_regs *childregs = task_pt_regs(p);107 struct pt_regs *childregs = task_pt_regs(p);
108 108
arch/s390/Kconfig+0−1
@@ -136,7 +136,6 @@ config S390 · 135 unmodified lines
136 select HAVE_EBPF_JIT if PACK_STACK && HAVE_MARCH_Z196_FEATURES136 select HAVE_EBPF_JIT if PACK_STACK && HAVE_MARCH_Z196_FEATURES
137 select HAVE_CMPXCHG_DOUBLE137 select HAVE_CMPXCHG_DOUBLE
138 select HAVE_CMPXCHG_LOCAL138 select HAVE_CMPXCHG_LOCAL
139 select HAVE_COPY_THREAD_TLS
140 select HAVE_DEBUG_KMEMLEAK139 select HAVE_DEBUG_KMEMLEAK
141 select HAVE_DMA_CONTIGUOUS140 select HAVE_DMA_CONTIGUOUS
142 select HAVE_DYNAMIC_FTRACE141 select HAVE_DYNAMIC_FTRACE
arch/s390/kernel/process.c+2−2
@@ -80,8 +80,8 @@ int arch_dup_task_struct(struct task_struct *dst, struct task_struct *src) · 79 unmodified lines
80 return 0;80 return 0;
81}81}
82 82
83int copy_thread_tls(unsigned long clone_flags, unsigned long new_stackp,83int copy_thread(unsigned long clone_flags, unsigned long new_stackp,
84 unsigned long arg, struct task_struct *p, unsigned long tls)84 unsigned long arg, struct task_struct *p, unsigned long tls)
85{85{
86 struct fake_frame86 struct fake_frame
87 {87 {
arch/sh/kernel/process_32.c+3−3
@@ -115,8 +115,8 @@ EXPORT_SYMBOL(dump_fpu); · 114 unmodified lines
115asmlinkage void ret_from_fork(void);115asmlinkage void ret_from_fork(void);
116asmlinkage void ret_from_kernel_thread(void);116asmlinkage void ret_from_kernel_thread(void);
117 117
118int copy_thread(unsigned long clone_flags, unsigned long usp,118int copy_thread(unsigned long clone_flags, unsigned long usp, unsigned long arg,
119 unsigned long arg, struct task_struct *p)119 struct task_struct *p, unsigned long tls)
120{120{
121 struct thread_info *ti = task_thread_info(p);121 struct thread_info *ti = task_thread_info(p);
122 struct pt_regs *childregs;122 struct pt_regs *childregs;
@@ -158,7 +158,7 @@ int copy_thread(unsigned long clone_flags, unsigned long usp, · 35 unmodified lines
158 ti->addr_limit = USER_DS;158 ti->addr_limit = USER_DS;
159 159
160 if (clone_flags & CLONE_SETTLS)160 if (clone_flags & CLONE_SETTLS)
161 childregs->gbr = childregs->regs[0];161 childregs->gbr = tls;
162 162
163 childregs->regs[0] = 0; /* Set return value for child */163 childregs->regs[0] = 0; /* Set return value for child */
164 p->thread.pc = (unsigned long) ret_from_fork;164 p->thread.pc = (unsigned long) ret_from_fork;
arch/sparc/include/asm/syscalls.h+3−4
@@ -4,9 +4,8 @@ · 3 unmodified lines
4 4
5struct pt_regs;5struct pt_regs;
6 6
7asmlinkage long sparc_do_fork(unsigned long clone_flags,7asmlinkage long sparc_fork(struct pt_regs *regs);
8 unsigned long stack_start,8asmlinkage long sparc_vfork(struct pt_regs *regs);
9 struct pt_regs *regs,9asmlinkage long sparc_clone(struct pt_regs *regs);
10 unsigned long stack_size);
11 10
12#endif /* _SPARC64_SYSCALLS_H */11#endif /* _SPARC64_SYSCALLS_H */
arch/sparc/kernel/Makefile+1−0
@@ -33,6 +33,7 @@ obj-y += irq_$(BITS).o · 32 unmodified lines
33obj-$(CONFIG_SPARC32) += sun4m_irq.o sun4d_irq.o33obj-$(CONFIG_SPARC32) += sun4m_irq.o sun4d_irq.o
34 34
35obj-y += process_$(BITS).o35obj-y += process_$(BITS).o
36obj-y += process.o
36obj-y += signal_$(BITS).o37obj-y += signal_$(BITS).o
37obj-y += sigutil_$(BITS).o38obj-y += sigutil_$(BITS).o
38obj-$(CONFIG_SPARC32) += ioport.o39obj-$(CONFIG_SPARC32) += ioport.o
arch/sparc/kernel/entry.S+7−22
@@ -869,14 +869,11 @@ flush_patch_two: · 868 unmodified lines
869 ld [%curptr + TI_TASK], %o4869 ld [%curptr + TI_TASK], %o4
870 rd %psr, %g4870 rd %psr, %g4
871 WRITE_PAUSE871 WRITE_PAUSE
872 mov SIGCHLD, %o0 ! arg0: clone flags
873 rd %wim, %g5872 rd %wim, %g5
874 WRITE_PAUSE873 WRITE_PAUSE
875 mov %fp, %o1 ! arg1: usp
876 std %g4, [%o4 + AOFF_task_thread + AOFF_thread_fork_kpsr]874 std %g4, [%o4 + AOFF_task_thread + AOFF_thread_fork_kpsr]
877 add %sp, STACKFRAME_SZ, %o2 ! arg2: pt_regs ptr875 add %sp, STACKFRAME_SZ, %o0
878 mov 0, %o3876 call sparc_fork
879 call sparc_do_fork
880 mov %l5, %o7877 mov %l5, %o7
881 878
882 /* Whee, kernel threads! */879 /* Whee, kernel threads! */
@@ -888,19 +885,11 @@ flush_patch_three: · 5 unmodified lines
888 ld [%curptr + TI_TASK], %o4885 ld [%curptr + TI_TASK], %o4
889 rd %psr, %g4886 rd %psr, %g4
890 WRITE_PAUSE887 WRITE_PAUSE
891
892 /* arg0,1: flags,usp -- loaded already */
893 cmp %o1, 0x0 ! Is new_usp NULL?
894 rd %wim, %g5888 rd %wim, %g5
895 WRITE_PAUSE889 WRITE_PAUSE
896 be,a 1f
897 mov %fp, %o1 ! yes, use callers usp
898 andn %o1, 7, %o1 ! no, align to 8 bytes
8991:
900 std %g4, [%o4 + AOFF_task_thread + AOFF_thread_fork_kpsr]890 std %g4, [%o4 + AOFF_task_thread + AOFF_thread_fork_kpsr]
901 add %sp, STACKFRAME_SZ, %o2 ! arg2: pt_regs ptr891 add %sp, STACKFRAME_SZ, %o0
902 mov 0, %o3892 call sparc_clone
903 call sparc_do_fork
904 mov %l5, %o7893 mov %l5, %o7
905 894
906 /* Whee, real vfork! */895 /* Whee, real vfork! */
@@ -914,13 +903,9 @@ flush_patch_four: · 7 unmodified lines
914 rd %wim, %g5903 rd %wim, %g5
915 WRITE_PAUSE904 WRITE_PAUSE
916 std %g4, [%o4 + AOFF_task_thread + AOFF_thread_fork_kpsr]905 std %g4, [%o4 + AOFF_task_thread + AOFF_thread_fork_kpsr]
917 sethi %hi(0x4000 | 0x0100 | SIGCHLD), %o0906 sethi %hi(sparc_vfork), %l1
918 mov %fp, %o1907 jmpl %l1 + %lo(sparc_vfork), %g0
919 or %o0, %lo(0x4000 | 0x0100 | SIGCHLD), %o0908 add %sp, STACKFRAME_SZ, %o0
920 sethi %hi(sparc_do_fork), %l1
921 mov 0, %o3
922 jmpl %l1 + %lo(sparc_do_fork), %g0
923 add %sp, STACKFRAME_SZ, %o2
924 909
925 .align 4910 .align 4
926linux_sparc_ni_syscall:911linux_sparc_ni_syscall:
arch/sparc/kernel/kernel.h+5−6
@@ -14,6 +14,11 @@ extern const char *sparc_pmu_type; · 13 unmodified lines
14extern unsigned int fsr_storage;14extern unsigned int fsr_storage;
15extern int ncpus_probed;15extern int ncpus_probed;
16 16
17/* process{_32,_64}.c */
18asmlinkage long sparc_clone(struct pt_regs *regs);
19asmlinkage long sparc_fork(struct pt_regs *regs);
20asmlinkage long sparc_vfork(struct pt_regs *regs);
21
17#ifdef CONFIG_SPARC6422#ifdef CONFIG_SPARC64
18/* setup_64.c */23/* setup_64.c */
19struct seq_file;24struct seq_file;
@@ -153,12 +158,6 @@ void floppy_hardint(void); · 133 unmodified lines
153extern unsigned long sun4m_cpu_startup;158extern unsigned long sun4m_cpu_startup;
154extern unsigned long sun4d_cpu_startup;159extern unsigned long sun4d_cpu_startup;
155 160
156/* process_32.c */
157asmlinkage int sparc_do_fork(unsigned long clone_flags,
158 unsigned long stack_start,
159 struct pt_regs *regs,
160 unsigned long stack_size);
161
162/* signal_32.c */161/* signal_32.c */
163asmlinkage void do_sigreturn(struct pt_regs *regs);162asmlinkage void do_sigreturn(struct pt_regs *regs);
164asmlinkage void do_rt_sigreturn(struct pt_regs *regs);163asmlinkage void do_rt_sigreturn(struct pt_regs *regs);
arch/sparc/kernel/process.c+110−0
@@ -0,0 +1,110 @@
1// SPDX-License-Identifier: GPL-2.0
2
3/*
4 * This file handles the architecture independent parts of process handling..
5 */
6
7#include <linux/compat.h>
8#include <linux/errno.h>
9#include <linux/kernel.h>
10#include <linux/ptrace.h>
11#include <linux/sched.h>
12#include <linux/sched/task.h>
13#include <linux/sched/task_stack.h>
14#include <linux/signal.h>
15
16#include "kernel.h"
17
18asmlinkage long sparc_fork(struct pt_regs *regs)
19{
20 unsigned long orig_i1 = regs->u_regs[UREG_I1];
21 long ret;
22 struct kernel_clone_args args = {
23 .exit_signal = SIGCHLD,
24 /* Reuse the parent's stack for the child. */
25 .stack = regs->u_regs[UREG_FP],
26 };
27
28 ret = _do_fork(&args);
29
30 /* If we get an error and potentially restart the system
31 * call, we're screwed because copy_thread() clobbered
32 * the parent's %o1. So detect that case and restore it
33 * here.
34 */
35 if ((unsigned long)ret >= -ERESTART_RESTARTBLOCK)
36 regs->u_regs[UREG_I1] = orig_i1;
37
38 return ret;
39}
40
41asmlinkage long sparc_vfork(struct pt_regs *regs)
42{
43 unsigned long orig_i1 = regs->u_regs[UREG_I1];
44 long ret;
45
46 struct kernel_clone_args args = {
47 .flags = CLONE_VFORK | CLONE_VM,
48 .exit_signal = SIGCHLD,
49 /* Reuse the parent's stack for the child. */
50 .stack = regs->u_regs[UREG_FP],
51 };
52
53 ret = _do_fork(&args);
54
55 /* If we get an error and potentially restart the system
56 * call, we're screwed because copy_thread() clobbered
57 * the parent's %o1. So detect that case and restore it
58 * here.
59 */
60 if ((unsigned long)ret >= -ERESTART_RESTARTBLOCK)
61 regs->u_regs[UREG_I1] = orig_i1;
62
63 return ret;
64}
65
66asmlinkage long sparc_clone(struct pt_regs *regs)
67{
68 unsigned long orig_i1 = regs->u_regs[UREG_I1];
69 unsigned int flags = lower_32_bits(regs->u_regs[UREG_I0]);
70 long ret;
71
72 struct kernel_clone_args args = {
73 .flags = (flags & ~CSIGNAL),
74 .exit_signal = (flags & CSIGNAL),
75 .tls = regs->u_regs[UREG_I3],
76 };
77
78#ifdef CONFIG_COMPAT
79 if (test_thread_flag(TIF_32BIT)) {
80 args.pidfd = compat_ptr(regs->u_regs[UREG_I2]);
81 args.child_tid = compat_ptr(regs->u_regs[UREG_I4]);
82 args.parent_tid = compat_ptr(regs->u_regs[UREG_I2]);
83 } else
84#endif
85 {
86 args.pidfd = (int __user *)regs->u_regs[UREG_I2];
87 args.child_tid = (int __user *)regs->u_regs[UREG_I4];
88 args.parent_tid = (int __user *)regs->u_regs[UREG_I2];
89 }
90
91 /* Did userspace give setup a separate stack for the child or are we
92 * reusing the parent's?
93 */
94 if (regs->u_regs[UREG_I1])
95 args.stack = regs->u_regs[UREG_I1];
96 else
97 args.stack = regs->u_regs[UREG_FP];
98
99 ret = _do_fork(&args);
100
101 /* If we get an error and potentially restart the system
102 * call, we're screwed because copy_thread() clobbered
103 * the parent's %o1. So detect that case and restore it
104 * here.
105 */
106 if ((unsigned long)ret >= -ERESTART_RESTARTBLOCK)
107 regs->u_regs[UREG_I1] = orig_i1;
108
109 return ret;
110}
arch/sparc/kernel/process_32.c+3−30
@@ -257,33 +257,6 @@ clone_stackframe(struct sparc_stackf __user *dst, · 256 unmodified lines
257 return sp;257 return sp;
258}258}
259 259
260asmlinkage int sparc_do_fork(unsigned long clone_flags,
261 unsigned long stack_start,
262 struct pt_regs *regs,
263 unsigned long stack_size)
264{
265 unsigned long parent_tid_ptr, child_tid_ptr;
266 unsigned long orig_i1 = regs->u_regs[UREG_I1];
267 long ret;
268
269 parent_tid_ptr = regs->u_regs[UREG_I2];
270 child_tid_ptr = regs->u_regs[UREG_I4];
271
272 ret = do_fork(clone_flags, stack_start, stack_size,
273 (int __user *) parent_tid_ptr,
274 (int __user *) child_tid_ptr);
275
276 /* If we get an error and potentially restart the system
277 * call, we're screwed because copy_thread() clobbered
278 * the parent's %o1. So detect that case and restore it
279 * here.
280 */
281 if ((unsigned long)ret >= -ERESTART_RESTARTBLOCK)
282 regs->u_regs[UREG_I1] = orig_i1;
283
284 return ret;
285}
286
287/* Copy a Sparc thread. The fork() return value conventions260/* Copy a Sparc thread. The fork() return value conventions
288 * under SunOS are nothing short of bletcherous:261 * under SunOS are nothing short of bletcherous:
289 * Parent --> %o0 == childs pid, %o1 == 0262 * Parent --> %o0 == childs pid, %o1 == 0
@@ -300,8 +273,8 @@ asmlinkage int sparc_do_fork(unsigned long clone_flags, · 10 unmodified lines
300extern void ret_from_fork(void);273extern void ret_from_fork(void);
301extern void ret_from_kernel_thread(void);274extern void ret_from_kernel_thread(void);
302 275
303int copy_thread(unsigned long clone_flags, unsigned long sp,276int copy_thread(unsigned long clone_flags, unsigned long sp, unsigned long arg,
304 unsigned long arg, struct task_struct *p)277 struct task_struct *p, unsigned long tls)
305{278{
306 struct thread_info *ti = task_thread_info(p);279 struct thread_info *ti = task_thread_info(p);
307 struct pt_regs *childregs, *regs = current_pt_regs();280 struct pt_regs *childregs, *regs = current_pt_regs();
@@ -403,7 +376,7 @@ int copy_thread(unsigned long clone_flags, unsigned long sp, · 95 unmodified lines
403 regs->u_regs[UREG_I1] = 0;376 regs->u_regs[UREG_I1] = 0;
404 377
405 if (clone_flags & CLONE_SETTLS)378 if (clone_flags & CLONE_SETTLS)
406 childregs->u_regs[UREG_G7] = regs->u_regs[UREG_I3];379 childregs->u_regs[UREG_G7] = tls;
407 380
408 return 0;381 return 0;
409}382}
arch/sparc/kernel/process_64.c+3−37
@@ -572,47 +572,13 @@ barf: · 571 unmodified lines
572 force_sig(SIGSEGV);572 force_sig(SIGSEGV);
573}573}
574 574
575asmlinkage long sparc_do_fork(unsigned long clone_flags,
576 unsigned long stack_start,
577 struct pt_regs *regs,
578 unsigned long stack_size)
579{
580 int __user *parent_tid_ptr, *child_tid_ptr;
581 unsigned long orig_i1 = regs->u_regs[UREG_I1];
582 long ret;
583
584#ifdef CONFIG_COMPAT
585 if (test_thread_flag(TIF_32BIT)) {
586 parent_tid_ptr = compat_ptr(regs->u_regs[UREG_I2]);
587 child_tid_ptr = compat_ptr(regs->u_regs[UREG_I4]);
588 } else
589#endif
590 {
591 parent_tid_ptr = (int __user *) regs->u_regs[UREG_I2];
592 child_tid_ptr = (int __user *) regs->u_regs[UREG_I4];
593 }
594
595 ret = do_fork(clone_flags, stack_start, stack_size,
596 parent_tid_ptr, child_tid_ptr);
597
598 /* If we get an error and potentially restart the system
599 * call, we're screwed because copy_thread() clobbered
600 * the parent's %o1. So detect that case and restore it
601 * here.
602 */
603 if ((unsigned long)ret >= -ERESTART_RESTARTBLOCK)
604 regs->u_regs[UREG_I1] = orig_i1;
605
606 return ret;
607}
608
609/* Copy a Sparc thread. The fork() return value conventions575/* Copy a Sparc thread. The fork() return value conventions
610 * under SunOS are nothing short of bletcherous:576 * under SunOS are nothing short of bletcherous:
611 * Parent --> %o0 == childs pid, %o1 == 0577 * Parent --> %o0 == childs pid, %o1 == 0
612 * Child --> %o0 == parents pid, %o1 == 1578 * Child --> %o0 == parents pid, %o1 == 1
613 */579 */
614int copy_thread(unsigned long clone_flags, unsigned long sp,580int copy_thread(unsigned long clone_flags, unsigned long sp, unsigned long arg,
615 unsigned long arg, struct task_struct *p)581 struct task_struct *p, unsigned long tls)
616{582{
617 struct thread_info *t = task_thread_info(p);583 struct thread_info *t = task_thread_info(p);
618 struct pt_regs *regs = current_pt_regs();584 struct pt_regs *regs = current_pt_regs();
@@ -670,7 +636,7 @@ int copy_thread(unsigned long clone_flags, unsigned long sp, · 51 unmodified lines
670 regs->u_regs[UREG_I1] = 0;636 regs->u_regs[UREG_I1] = 0;
671 637
672 if (clone_flags & CLONE_SETTLS)638 if (clone_flags & CLONE_SETTLS)
673 t->kregs->u_regs[UREG_G7] = regs->u_regs[UREG_I3];639 t->kregs->u_regs[UREG_G7] = tls;
674 640
675 return 0;641 return 0;
676}642}
arch/sparc/kernel/syscalls.S+13−10
@@ -86,19 +86,22 @@ sys32_rt_sigreturn: · 85 unmodified lines
86 * during system calls...86 * during system calls...
87 */87 */
88 .align 3288 .align 32
89sys_vfork: /* Under Linux, vfork and fork are just special cases of clone. */89sys_vfork:
90 sethi %hi(0x4000 | 0x0100 | SIGCHLD), %o090 flushw
91 or %o0, %lo(0x4000 | 0x0100 | SIGCHLD), %o091 ba,pt %xcc, sparc_vfork
92 ba,pt %xcc, sys_clone92 add %sp, PTREGS_OFF, %o0
93
94 .align 32
93sys_fork:95sys_fork:
94 clr %o196 flushw
95 mov SIGCHLD, %o097 ba,pt %xcc, sparc_fork
98 add %sp, PTREGS_OFF, %o0
99
100 .align 32
96sys_clone:101sys_clone:
97 flushw102 flushw
98 movrz %o1, %fp, %o1103 ba,pt %xcc, sparc_clone
99 mov 0, %o3104 add %sp, PTREGS_OFF, %o0
100 ba,pt %xcc, sparc_do_fork
101 add %sp, PTREGS_OFF, %o2
102 105
103 .globl ret_from_fork106 .globl ret_from_fork
104ret_from_fork:107ret_from_fork:
arch/um/Kconfig+0−1
@@ -14,7 +14,6 @@ config UML · 13 unmodified lines
14 select HAVE_FUTEX_CMPXCHG if FUTEX14 select HAVE_FUTEX_CMPXCHG if FUTEX
15 select HAVE_DEBUG_KMEMLEAK15 select HAVE_DEBUG_KMEMLEAK
16 select HAVE_DEBUG_BUGVERBOSE16 select HAVE_DEBUG_BUGVERBOSE
17 select HAVE_COPY_THREAD_TLS
18 select GENERIC_IRQ_SHOW17 select GENERIC_IRQ_SHOW
19 select GENERIC_CPU_DEVICES18 select GENERIC_CPU_DEVICES
20 select GENERIC_CLOCKEVENTS19 select GENERIC_CLOCKEVENTS
arch/um/kernel/process.c+1−1
@@ -152,7 +152,7 @@ void fork_handler(void) · 151 unmodified lines
152 userspace(&current->thread.regs.regs, current_thread_info()->aux_fp_regs);152 userspace(&current->thread.regs.regs, current_thread_info()->aux_fp_regs);
153}153}
154 154
155int copy_thread_tls(unsigned long clone_flags, unsigned long sp,155int copy_thread(unsigned long clone_flags, unsigned long sp,
156 unsigned long arg, struct task_struct * p, unsigned long tls)156 unsigned long arg, struct task_struct * p, unsigned long tls)
157{157{
158 void (*handler)(void);158 void (*handler)(void);
arch/x86/Kconfig+0−1
@@ -161,7 +161,6 @@ config X86 · 160 unmodified lines
161 select HAVE_CMPXCHG_DOUBLE161 select HAVE_CMPXCHG_DOUBLE
162 select HAVE_CMPXCHG_LOCAL162 select HAVE_CMPXCHG_LOCAL
163 select HAVE_CONTEXT_TRACKING if X86_64163 select HAVE_CONTEXT_TRACKING if X86_64
164 select HAVE_COPY_THREAD_TLS
165 select HAVE_C_RECORDMCOUNT164 select HAVE_C_RECORDMCOUNT
166 select HAVE_DEBUG_KMEMLEAK165 select HAVE_DEBUG_KMEMLEAK
167 select HAVE_DMA_CONTIGUOUS166 select HAVE_DMA_CONTIGUOUS
arch/x86/kernel/process.c+2−2
@@ -121,8 +121,8 @@ static int set_new_tls(struct task_struct *p, unsigned long tls) · 120 unmodified lines
121 return do_set_thread_area_64(p, ARCH_SET_FS, tls);121 return do_set_thread_area_64(p, ARCH_SET_FS, tls);
122}122}
123 123
124int copy_thread_tls(unsigned long clone_flags, unsigned long sp,124int copy_thread(unsigned long clone_flags, unsigned long sp, unsigned long arg,
125 unsigned long arg, struct task_struct *p, unsigned long tls)125 struct task_struct *p, unsigned long tls)
126{126{
127 struct inactive_task_frame *frame;127 struct inactive_task_frame *frame;
128 struct fork_frame *fork_frame;128 struct fork_frame *fork_frame;
arch/x86/kernel/sys_ia32.c+0−3
@@ -251,9 +251,6 @@ COMPAT_SYSCALL_DEFINE5(ia32_clone, unsigned long, clone_flags, · 250 unmodified lines
251 .tls = tls_val,251 .tls = tls_val,
252 };252 };
253 253
254 if (!legacy_clone_args_valid(&args))
255 return -EINVAL;
256
257 return _do_fork(&args);254 return _do_fork(&args);
258}255}
259#endif /* CONFIG_IA32_EMULATION */256#endif /* CONFIG_IA32_EMULATION */
arch/x86/kernel/unwind_frame.c+1−1
@@ -269,7 +269,7 @@ bool unwind_next_frame(struct unwind_state *state) · 268 unmodified lines
269 /*269 /*
270 * kthreads (other than the boot CPU's idle thread) have some270 * kthreads (other than the boot CPU's idle thread) have some
271 * partial regs at the end of their stack which were placed271 * partial regs at the end of their stack which were placed
272 * there by copy_thread_tls(). But the regs don't have any272 * there by copy_thread(). But the regs don't have any
273 * useful information, so we can skip them.273 * useful information, so we can skip them.
274 *274 *
275 * This user_mode() check is slightly broader than a PF_KTHREAD275 * This user_mode() check is slightly broader than a PF_KTHREAD
arch/xtensa/Kconfig+0−1
@@ -24,7 +24,6 @@ config XTENSA · 23 unmodified lines
24 select HAVE_ARCH_JUMP_LABEL if !XIP_KERNEL24 select HAVE_ARCH_JUMP_LABEL if !XIP_KERNEL
25 select HAVE_ARCH_KASAN if MMU && !XIP_KERNEL25 select HAVE_ARCH_KASAN if MMU && !XIP_KERNEL
26 select HAVE_ARCH_TRACEHOOK26 select HAVE_ARCH_TRACEHOOK
27 select HAVE_COPY_THREAD_TLS
28 select HAVE_DEBUG_KMEMLEAK27 select HAVE_DEBUG_KMEMLEAK
29 select HAVE_DMA_CONTIGUOUS28 select HAVE_DMA_CONTIGUOUS
30 select HAVE_EXIT_THREAD29 select HAVE_EXIT_THREAD
arch/xtensa/kernel/process.c+1−1
@@ -201,7 +201,7 @@ int arch_dup_task_struct(struct task_struct *dst, struct task_struct *src) · 200 unmodified lines
201 * involved. Much simpler to just not copy those live frames across.201 * involved. Much simpler to just not copy those live frames across.
202 */202 */
203 203
204int copy_thread_tls(unsigned long clone_flags, unsigned long usp_thread_fn,204int copy_thread(unsigned long clone_flags, unsigned long usp_thread_fn,
205 unsigned long thread_fn_arg, struct task_struct *p,205 unsigned long thread_fn_arg, struct task_struct *p,
206 unsigned long tls)206 unsigned long tls)
207{207{
include/linux/sched/task.h+1−16
@@ -66,22 +66,9 @@ extern void fork_init(void); · 65 unmodified lines
66 66
67extern void release_task(struct task_struct * p);67extern void release_task(struct task_struct * p);
68 68
69#ifdef CONFIG_HAVE_COPY_THREAD_TLS
70extern int copy_thread_tls(unsigned long, unsigned long, unsigned long,
71 struct task_struct *, unsigned long);
72#else
73extern int copy_thread(unsigned long, unsigned long, unsigned long,69extern int copy_thread(unsigned long, unsigned long, unsigned long,
74 struct task_struct *);70 struct task_struct *, unsigned long);
75 71
76/* Architectures that haven't opted into copy_thread_tls get the tls argument
77 * via pt_regs, so ignore the tls argument passed via C. */
78static inline int copy_thread_tls(
79 unsigned long clone_flags, unsigned long sp, unsigned long arg,
80 struct task_struct *p, unsigned long tls)
81{
82 return copy_thread(clone_flags, sp, arg, p);
83}
84#endif
85extern void flush_thread(void);72extern void flush_thread(void);
86 73
87#ifdef CONFIG_HAVE_EXIT_THREAD74#ifdef CONFIG_HAVE_EXIT_THREAD
@@ -97,8 +84,6 @@ extern void exit_files(struct task_struct *); · 9 unmodified lines
97extern void exit_itimers(struct signal_struct *);84extern void exit_itimers(struct signal_struct *);
98 85
99extern long _do_fork(struct kernel_clone_args *kargs);86extern long _do_fork(struct kernel_clone_args *kargs);
100extern bool legacy_clone_args_valid(const struct kernel_clone_args *kargs);
101extern long do_fork(unsigned long, unsigned long, unsigned long, int __user *, int __user *);
102struct task_struct *fork_idle(int);87struct task_struct *fork_idle(int);
103struct mm_struct *copy_init_mm(void);88struct mm_struct *copy_init_mm(void);
104extern pid_t kernel_thread(int (*fn)(void *), void *arg, unsigned long flags);89extern pid_t kernel_thread(int (*fn)(void *), void *arg, unsigned long flags);
kernel/fork.c+16−51
@@ -2097,8 +2097,7 @@ static __latent_entropy struct task_struct *copy_process( · 2096 unmodified lines
2097 retval = copy_io(clone_flags, p);2097 retval = copy_io(clone_flags, p);
2098 if (retval)2098 if (retval)
2099 goto bad_fork_cleanup_namespaces;2099 goto bad_fork_cleanup_namespaces;
2100 retval = copy_thread_tls(clone_flags, args->stack, args->stack_size, p,2100 retval = copy_thread(clone_flags, args->stack, args->stack_size, p, args->tls);
2101 args->tls);
2102 if (retval)2101 if (retval)
2103 goto bad_fork_cleanup_io;2102 goto bad_fork_cleanup_io;
2104 2103
@@ -2416,6 +2415,20 @@ long _do_fork(struct kernel_clone_args *args) · 311 unmodified lines
2416 int trace = 0;2415 int trace = 0;
2417 long nr;2416 long nr;
2418 2417
2418 /*
2419 * For legacy clone() calls, CLONE_PIDFD uses the parent_tid argument
2420 * to return the pidfd. Hence, CLONE_PIDFD and CLONE_PARENT_SETTID are
2421 * mutually exclusive. With clone3() CLONE_PIDFD has grown a separate
2422 * field in struct clone_args and it still doesn't make sense to have
2423 * them both point at the same memory location. Performing this check
2424 * here has the advantage that we don't need to have a separate helper
2425 * to check for legacy clone().
2426 */
2427 if ((args->flags & CLONE_PIDFD) &&
2428 (args->flags & CLONE_PARENT_SETTID) &&
2429 (args->pidfd == args->parent_tid))
2430 return -EINVAL;
2431
2419 /*2432 /*
2420 * Determine whether and which event to report to ptracer. When2433 * Determine whether and which event to report to ptracer. When
2421 * called from kernel_thread or CLONE_UNTRACED is explicitly2434 * called from kernel_thread or CLONE_UNTRACED is explicitly
@@ -2473,42 +2486,6 @@ long _do_fork(struct kernel_clone_args *args) · 51 unmodified lines
2473 return nr;2486 return nr;
2474}2487}
2475 2488
2476bool legacy_clone_args_valid(const struct kernel_clone_args *kargs)
2477{
2478 /* clone(CLONE_PIDFD) uses parent_tidptr to return a pidfd */
2479 if ((kargs->flags & CLONE_PIDFD) &&
2480 (kargs->flags & CLONE_PARENT_SETTID))
2481 return false;
2482
2483 return true;
2484}
2485
2486#ifndef CONFIG_HAVE_COPY_THREAD_TLS
2487/* For compatibility with architectures that call do_fork directly rather than
2488 * using the syscall entry points below. */
2489long do_fork(unsigned long clone_flags,
2490 unsigned long stack_start,
2491 unsigned long stack_size,
2492 int __user *parent_tidptr,
2493 int __user *child_tidptr)
2494{
2495 struct kernel_clone_args args = {
2496 .flags = (lower_32_bits(clone_flags) & ~CSIGNAL),
2497 .pidfd = parent_tidptr,
2498 .child_tid = child_tidptr,
2499 .parent_tid = parent_tidptr,
2500 .exit_signal = (lower_32_bits(clone_flags) & CSIGNAL),
2501 .stack = stack_start,
2502 .stack_size = stack_size,
2503 };
2504
2505 if (!legacy_clone_args_valid(&args))
2506 return -EINVAL;
2507
2508 return _do_fork(&args);
2509}
2510#endif
2511
2512/*2489/*
2513 * Create a kernel thread.2490 * Create a kernel thread.
2514 */2491 */
@@ -2587,24 +2564,12 @@ SYSCALL_DEFINE5(clone, unsigned long, clone_flags, unsigned long, newsp, · 72 unmodified lines
2587 .tls = tls,2564 .tls = tls,
2588 };2565 };
2589 2566
2590 if (!legacy_clone_args_valid(&args))
2591 return -EINVAL;
2592
2593 return _do_fork(&args);2567 return _do_fork(&args);
2594}2568}
2595#endif2569#endif
2596 2570
2597#ifdef __ARCH_WANT_SYS_CLONE32571#ifdef __ARCH_WANT_SYS_CLONE3
2598 2572
2599/*
2600 * copy_thread implementations handle CLONE_SETTLS by reading the TLS value from
2601 * the registers containing the syscall arguments for clone. This doesn't work
2602 * with clone3 since the TLS value is passed in clone_args instead.
2603 */
2604#ifndef CONFIG_HAVE_COPY_THREAD_TLS
2605#error clone3 requires copy_thread_tls support in arch
2606#endif
2607
2608noinline static int copy_clone_args_from_user(struct kernel_clone_args *kargs,2573noinline static int copy_clone_args_from_user(struct kernel_clone_args *kargs,
2609 struct clone_args __user *uargs,2574 struct clone_args __user *uargs,
2610 size_t usize)2575 size_t usize)
@@ -2919,7 +2884,7 @@ static int unshare_fd(unsigned long unshare_flags, struct files_struct **new_fdp · 308 unmodified lines
2919/*2884/*
2920 * unshare allows a process to 'unshare' part of the process2885 * unshare allows a process to 'unshare' part of the process
2921 * context which was originally shared using clone. copy_*2886 * context which was originally shared using clone. copy_*
2922 * functions used by do_fork() cannot be used here directly2887 * functions used by _do_fork() cannot be used here directly
2923 * because they modify an inactive task_struct that is being2888 * because they modify an inactive task_struct that is being
2924 * constructed. Here we are modifying the current, active,2889 * constructed. Here we are modifying the current, active,
2925 * task_struct.2890 * task_struct.