/* Test if CLONE_VM does not change pthread pid/tid field (BZ #19957)
   Copyright (C) 2016-2018 Free Software Foundation, Inc.
   This file is part of the GNU C Library.

   The GNU C Library is free software; you can redistribute it and/or
   modify it under the terms of the GNU Lesser General Public
   License as published by the Free Software Foundation; either
   version 2.1 of the License, or (at your option) any later version.

   The GNU C Library is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
   Lesser General Public License for more details.

   You should have received a copy of the GNU Lesser General Public
   License along with the GNU C Library; if not, see
   <http://www.gnu.org/licenses/>.  */

#include <sched.h>
#include <signal.h>
#include <string.h>
#include <stdio.h>
#include <fcntl.h>
#include <unistd.h>
#include <stddef.h>
#include <stdbool.h>
#include <stdint.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <sys/syscall.h>

#include <stackinfo.h>  /* For _STACK_GROWS_{UP,DOWN}.  */

#include <support/check.h>

static int sig;
static int pipefd[2];

static int
f (void *a)
{
  close (pipefd[0]);

  pid_t ppid = getppid ();
  pid_t pid = getpid ();
  pid_t tid = syscall (__NR_gettid);

  if (write (pipefd[1], &ppid, sizeof ppid) != sizeof (ppid))
    FAIL_EXIT1 ("write ppid failed\n");
  if (write (pipefd[1], &pid, sizeof pid) != sizeof (pid))
    FAIL_EXIT1 ("write pid failed\n");
  if (write (pipefd[1], &tid, sizeof tid) != sizeof (tid))
    FAIL_EXIT1 ("write tid failed\n");

  return 0;
}


static int
do_test (void)
{
  sig = SIGRTMIN;
  sigset_t ss;
  sigemptyset (&ss);
  sigaddset (&ss, sig);
  if (sigprocmask (SIG_BLOCK, &ss, NULL) != 0)
    FAIL_EXIT1 ("sigprocmask failed: %m");

  if (pipe2 (pipefd, O_CLOEXEC))
    FAIL_EXIT1 ("pipe failed: %m");

  int clone_flags = 0;
#ifdef __ia64__
  extern int __clone2 (int (*__fn) (void *__arg), void *__child_stack_base,
		       size_t __child_stack_size, int __flags,
		       void *__arg, ...);
  char st[256 * 1024] __attribute__ ((aligned));
  pid_t p = __clone2 (f, st, sizeof (st), clone_flags, 0);
#else
  char st[128 * 1024] __attribute__ ((aligned));
#if _STACK_GROWS_DOWN
  pid_t p = clone (f, st + sizeof (st), clone_flags, 0);
#elif _STACK_GROWS_UP
  pid_t p = clone (f, st, clone_flags, 0);
#else
#error "Define either _STACK_GROWS_DOWN or _STACK_GROWS_UP"
#endif
#endif

  close (pipefd[1]);

  if (p == -1)
    FAIL_EXIT1("clone failed: %m");

  pid_t ppid, pid, tid;
  if (read (pipefd[0], &ppid, sizeof pid) != sizeof pid)
    {
      kill (p, SIGKILL);
      FAIL_EXIT1 ("read ppid failed: %m");
    }
  if (read (pipefd[0], &pid, sizeof pid) != sizeof pid)
    {
      kill (p, SIGKILL);
      FAIL_EXIT1 ("read pid failed: %m");
    }
  if (read (pipefd[0], &tid, sizeof tid) != sizeof tid)
    {
      kill (p, SIGKILL);
      FAIL_EXIT1 ("read tid failed: %m");
    }

  close (pipefd[0]);

  int ret = 0;

  pid_t own_pid = getpid ();
  pid_t own_tid = syscall (__NR_gettid);

  /* Some sanity checks for clone syscall: returned ppid should be current
     pid and both returned tid/pid should be different from current one.  */
  if ((ppid != own_pid) || (pid == own_pid) || (tid == own_tid))
    FAIL_RET ("ppid=%i pid=%i tid=%i | own_pid=%i own_tid=%i",
	      (int)ppid, (int)pid, (int)tid, (int)own_pid, (int)own_tid);

  int e;
  if (waitpid (p, &e, __WCLONE) != p)
    {
      kill (p, SIGKILL);
      FAIL_EXIT1 ("waitpid failed");
    }
  if (!WIFEXITED (e))
    {
      if (WIFSIGNALED (e))
	printf ("died from signal %s\n", strsignal (WTERMSIG (e)));
      else
	puts ("did not terminate correctly");
      exit (EXIT_FAILURE);
    }
  if (WEXITSTATUS (e) != 0)
    FAIL_EXIT1 ("exit code %d", WEXITSTATUS (e));

  return ret;
}

#include <support/test-driver.c>
