linux-user: Fix CLONE_PARENT_SETTID when using fork-like clone
The CLONE_PARENT_SETTID option requires the implementation to store the child thread ID at the location pointed to by parent_tid in the parent's memory. Fix our implementation and move the code from the client side (where fork returned 0), to the parent side and store the return value from the fork call (which is the client TID) in the parent_tid pointer. Resolves: https://gitlab.com/qemu-project/qemu/-/work_items/3340 Signed-off-by: Helge Deller <deller@gmx.de> Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
Helge Deller committed
Apr 24, 2026 at 15:17 UTC
b03a6ac6fa5d7775b9f912fa5c39f7b92388c6a2
1 file changed
+2
-2
linux-user/syscall.c
+2
-2
@@ -7050,8 +7050,6 @@ static int do_fork(CPUArchState *env, unsigned int flags, abi_ulong newsp,
7050
the child process gets its own copy of the lock. */
7051
if (flags & CLONE_CHILD_SETTID)
7052
put_user_u32(sys_gettid(), child_tidptr);
7053
- if (flags & CLONE_PARENT_SETTID)
7054
- put_user_u32(sys_gettid(), parent_tidptr);
7053
ts = get_task_state(cpu);
7054
if (flags & CLONE_SETTLS)
7055
cpu_set_tls (env, newtls);
@@ -7059,6 +7057,8 @@ static int do_fork(CPUArchState *env, unsigned int flags, abi_ulong newsp,
7057
ts->child_tidptr = child_tidptr;
7058
} else {
7059
cpu_clone_regs_parent(env, flags);
7060
+ if (flags & CLONE_PARENT_SETTID)
7061
+ put_user_u32(ret, parent_tidptr);
7062
if (flags & CLONE_PIDFD) {
7063
int pid_fd = 0;
7064
#if defined(__NR_pidfd_open) && defined(TARGET_NR_pidfd_open)