1/*
2#notarget: cris*-*-elf
3#output: got: a\nthen: bc\nexit: 0\n
4*/
5
6/* This is a very limited subset of what ex1.c does; we just check that
7   thread creation (clone syscall) and pipe writes and reads work. */
8
9#include <stddef.h>
10#include <stdio.h>
11#include <stdlib.h>
12#include <unistd.h>
13#include <sched.h>
14#include <signal.h>
15#include <sys/types.h>
16#include <sys/wait.h>
17
18int pip[2];
19
20int
21process (void *arg)
22{
23  char *s = arg;
24  if (write (pip[1], s+2, 1) != 1) abort ();
25  if (write (pip[1], s+1, 1) != 1) abort ();
26  if (write (pip[1], s, 1) != 1) abort ();
27  return 0;
28}
29
30int
31main (void)
32{
33  int retcode;
34  int pid;
35  int st;
36  long stack[16384];
37  char buf[10] = {0};
38
39  retcode = pipe (pip);
40
41  if (retcode != 0)
42    {
43      fprintf (stderr, "Bad pipe %d\n", retcode);
44      abort ();
45    }
46
47  pid = clone (process, (char *) stack + sizeof (stack) - 64,
48	       (CLONE_VM | CLONE_FS | CLONE_FILES | CLONE_SIGHAND)
49	       | SIGCHLD, "cba");
50  if (pid <= 0)
51    {
52      fprintf (stderr, "Bad clone %d\n", pid);
53      abort ();
54    }
55
56  if ((retcode = read (pip[0], buf, 1)) != 1)
57    {
58      fprintf (stderr, "Bad read 1: %d\n", retcode);
59      abort ();
60    }
61  printf ("got: %c\n", buf[0]);
62  retcode = read (pip[0], buf, 2);
63  if (retcode == 1)
64    {
65      retcode = read (pip[0], buf+1, 1);
66      if (retcode != 1)
67	{
68	  fprintf (stderr, "Bad read 1.5: %d\n", retcode);
69	  abort ();
70	}
71      retcode = 2;
72    }
73  if (retcode != 2)
74    {
75      fprintf (stderr, "Bad read 2: %d\n", retcode);
76      abort ();
77    }
78
79  printf ("then: %s\n", buf);
80  retcode = wait4 (-1, &st, WNOHANG | __WCLONE, NULL);
81
82  if (retcode != pid || !WIFEXITED (st))
83    {
84      fprintf (stderr, "Bad wait %d %x\n", retcode, st);
85      abort ();
86    }
87
88  printf ("exit: %d\n", WEXITSTATUS (st));
89  return 0;
90}
91