| @@ -2406,6 +2406,16 @@ long _do_fork(struct kernel_clone_args *args) · 2405 unmodified lines |
| 2406 | return nr; | 2406 | return nr; |
| 2407 | } | 2407 | } |
| 2408 | | 2408 | |
| | 2409 | bool legacy_clone_args_valid(const struct kernel_clone_args *kargs) |
| | 2410 | { |
| | 2411 | /* clone(CLONE_PIDFD) uses parent_tidptr to return a pidfd */ |
| | 2412 | if ((kargs->flags & CLONE_PIDFD) && |
| | 2413 | (kargs->flags & CLONE_PARENT_SETTID)) |
| | 2414 | return false; |
| | 2415 | |
| | 2416 | return true; |
| | 2417 | } |
| | 2418 | |
| 2409 | #ifndef CONFIG_HAVE_COPY_THREAD_TLS | 2419 | #ifndef CONFIG_HAVE_COPY_THREAD_TLS |
| 2410 | /* For compatibility with architectures that call do_fork directly rather than | 2420 | /* For compatibility with architectures that call do_fork directly rather than |
| 2411 | * using the syscall entry points below. */ | 2421 | * using the syscall entry points below. */ |
| @@ -2417,6 +2427,7 @@ long do_fork(unsigned long clone_flags, · 5 unmodified lines |
| 2417 | { | 2427 | { |
| 2418 | struct kernel_clone_args args = { | 2428 | struct kernel_clone_args args = { |
| 2419 | .flags = (clone_flags & ~CSIGNAL), | 2429 | .flags = (clone_flags & ~CSIGNAL), |
| | 2430 | .pidfd = parent_tidptr, |
| 2420 | .child_tid = child_tidptr, | 2431 | .child_tid = child_tidptr, |
| 2421 | .parent_tid = parent_tidptr, | 2432 | .parent_tid = parent_tidptr, |
| 2422 | .exit_signal = (clone_flags & CSIGNAL), | 2433 | .exit_signal = (clone_flags & CSIGNAL), |
| @@ -2424,6 +2435,9 @@ long do_fork(unsigned long clone_flags, · 1 unmodified line |
| 2424 | .stack_size = stack_size, | 2435 | .stack_size = stack_size, |
| 2425 | }; | 2436 | }; |
| 2426 | | 2437 | |
| | 2438 | if (!legacy_clone_args_valid(&args)) |
| | 2439 | return -EINVAL; |
| | 2440 | |
| 2427 | return _do_fork(&args); | 2441 | return _do_fork(&args); |
| 2428 | } | 2442 | } |
| 2429 | #endif | 2443 | #endif |
| @@ -2505,8 +2519,7 @@ SYSCALL_DEFINE5(clone, unsigned long, clone_flags, unsigned long, newsp, · 75 unmodified lines |
| 2505 | .tls = tls, | 2519 | .tls = tls, |
| 2506 | }; | 2520 | }; |
| 2507 | | 2521 | |
| 2508 | /* clone(CLONE_PIDFD) uses parent_tidptr to return a pidfd */ | 2522 | if (!legacy_clone_args_valid(&args)) |
| 2509 | if ((clone_flags & CLONE_PIDFD) && (clone_flags & CLONE_PARENT_SETTID)) | | |
| 2510 | return -EINVAL; | 2523 | return -EINVAL; |
| 2511 | | 2524 | |
| 2512 | return _do_fork(&args); | 2525 | return _do_fork(&args); |