aboutsummaryrefslogtreecommitdiffstats
path: root/arch/um/os-Linux/helper.c
diff options
context:
space:
mode:
Diffstat (limited to 'arch/um/os-Linux/helper.c')
-rw-r--r--arch/um/os-Linux/helper.c54
1 files changed, 28 insertions, 26 deletions
diff --git a/arch/um/os-Linux/helper.c b/arch/um/os-Linux/helper.c
index cd15b9df5b5c..d13299cfa318 100644
--- a/arch/um/os-Linux/helper.c
+++ b/arch/um/os-Linux/helper.c
@@ -35,22 +35,23 @@ static int helper_child(void *arg)
35 char **argv = data->argv; 35 char **argv = data->argv;
36 int errval; 36 int errval;
37 37
38 if(helper_pause){ 38 if (helper_pause){
39 signal(SIGHUP, helper_hup); 39 signal(SIGHUP, helper_hup);
40 pause(); 40 pause();
41 } 41 }
42 if(data->pre_exec != NULL) 42 if (data->pre_exec != NULL)
43 (*data->pre_exec)(data->pre_data); 43 (*data->pre_exec)(data->pre_data);
44 execvp(argv[0], argv); 44 execvp(argv[0], argv);
45 errval = -errno; 45 errval = -errno;
46 printk("helper_child - execve of '%s' failed - errno = %d\n", argv[0], errno); 46 printk("helper_child - execve of '%s' failed - errno = %d\n", argv[0], errno);
47 os_write_file(data->fd, &errval, sizeof(errval)); 47 os_write_file(data->fd, &errval, sizeof(errval));
48 kill(os_getpid(), SIGKILL); 48 kill(os_getpid(), SIGKILL);
49 return(0); 49 return 0;
50} 50}
51 51
52/* Returns either the pid of the child process we run or -E* on failure. 52/* Returns either the pid of the child process we run or -E* on failure.
53 * XXX The alloc_stack here breaks if this is called in the tracing thread */ 53 * XXX The alloc_stack here breaks if this is called in the tracing thread, so
54 * we need to receive a preallocated stack (a local buffer is ok). */
54int run_helper(void (*pre_exec)(void *), void *pre_data, char **argv, 55int run_helper(void (*pre_exec)(void *), void *pre_data, char **argv,
55 unsigned long *stack_out) 56 unsigned long *stack_out)
56{ 57{
@@ -58,20 +59,21 @@ int run_helper(void (*pre_exec)(void *), void *pre_data, char **argv,
58 unsigned long stack, sp; 59 unsigned long stack, sp;
59 int pid, fds[2], ret, n; 60 int pid, fds[2], ret, n;
60 61
61 if((stack_out != NULL) && (*stack_out != 0)) 62 if ((stack_out != NULL) && (*stack_out != 0))
62 stack = *stack_out; 63 stack = *stack_out;
63 else stack = alloc_stack(0, __cant_sleep()); 64 else
64 if(stack == 0) 65 stack = alloc_stack(0, __cant_sleep());
66 if (stack == 0)
65 return -ENOMEM; 67 return -ENOMEM;
66 68
67 ret = os_pipe(fds, 1, 0); 69 ret = os_pipe(fds, 1, 0);
68 if(ret < 0){ 70 if (ret < 0) {
69 printk("run_helper : pipe failed, ret = %d\n", -ret); 71 printk("run_helper : pipe failed, ret = %d\n", -ret);
70 goto out_free; 72 goto out_free;
71 } 73 }
72 74
73 ret = os_set_exec_close(fds[1], 1); 75 ret = os_set_exec_close(fds[1], 1);
74 if(ret < 0){ 76 if (ret < 0) {
75 printk("run_helper : setting FD_CLOEXEC failed, ret = %d\n", 77 printk("run_helper : setting FD_CLOEXEC failed, ret = %d\n",
76 -ret); 78 -ret);
77 goto out_close; 79 goto out_close;
@@ -83,7 +85,7 @@ int run_helper(void (*pre_exec)(void *), void *pre_data, char **argv,
83 data.argv = argv; 85 data.argv = argv;
84 data.fd = fds[1]; 86 data.fd = fds[1];
85 pid = clone(helper_child, (void *) sp, CLONE_VM | SIGCHLD, &data); 87 pid = clone(helper_child, (void *) sp, CLONE_VM | SIGCHLD, &data);
86 if(pid < 0){ 88 if (pid < 0) {
87 ret = -errno; 89 ret = -errno;
88 printk("run_helper : clone failed, errno = %d\n", errno); 90 printk("run_helper : clone failed, errno = %d\n", errno);
89 goto out_close; 91 goto out_close;
@@ -95,10 +97,10 @@ int run_helper(void (*pre_exec)(void *), void *pre_data, char **argv,
95 /* Read the errno value from the child, if the exec failed, or get 0 if 97 /* Read the errno value from the child, if the exec failed, or get 0 if
96 * the exec succeeded because the pipe fd was set as close-on-exec. */ 98 * the exec succeeded because the pipe fd was set as close-on-exec. */
97 n = os_read_file(fds[0], &ret, sizeof(ret)); 99 n = os_read_file(fds[0], &ret, sizeof(ret));
98 if(n == 0) 100 if (n == 0) {
99 ret = pid; 101 ret = pid;
100 else { 102 } else {
101 if(n < 0){ 103 if (n < 0) {
102 printk("run_helper : read on pipe failed, ret = %d\n", 104 printk("run_helper : read on pipe failed, ret = %d\n",
103 -n); 105 -n);
104 ret = n; 106 ret = n;
@@ -112,10 +114,9 @@ out_close:
112 close(fds[1]); 114 close(fds[1]);
113 close(fds[0]); 115 close(fds[0]);
114out_free: 116out_free:
115 if(stack_out == NULL) 117 if ((stack_out == NULL) || (*stack_out == 0))
116 free_stack(stack, 0); 118 free_stack(stack, 0);
117 else *stack_out = stack; 119 return ret;
118 return(ret);
119} 120}
120 121
121int run_helper_thread(int (*proc)(void *), void *arg, unsigned int flags, 122int run_helper_thread(int (*proc)(void *), void *arg, unsigned int flags,
@@ -125,31 +126,32 @@ int run_helper_thread(int (*proc)(void *), void *arg, unsigned int flags,
125 int pid, status, err; 126 int pid, status, err;
126 127
127 stack = alloc_stack(stack_order, __cant_sleep()); 128 stack = alloc_stack(stack_order, __cant_sleep());
128 if(stack == 0) return(-ENOMEM); 129 if (stack == 0)
130 return -ENOMEM;
129 131
130 sp = stack + (page_size() << stack_order) - sizeof(void *); 132 sp = stack + (page_size() << stack_order) - sizeof(void *);
131 pid = clone(proc, (void *) sp, flags | SIGCHLD, arg); 133 pid = clone(proc, (void *) sp, flags | SIGCHLD, arg);
132 if(pid < 0){ 134 if (pid < 0) {
133 err = -errno; 135 err = -errno;
134 printk("run_helper_thread : clone failed, errno = %d\n", 136 printk("run_helper_thread : clone failed, errno = %d\n",
135 errno); 137 errno);
136 return err; 138 return err;
137 } 139 }
138 if(stack_out == NULL){ 140 if (stack_out == NULL) {
139 CATCH_EINTR(pid = waitpid(pid, &status, 0)); 141 CATCH_EINTR(pid = waitpid(pid, &status, 0));
140 if(pid < 0){ 142 if (pid < 0) {
141 err = -errno; 143 err = -errno;
142 printk("run_helper_thread - wait failed, errno = %d\n", 144 printk("run_helper_thread - wait failed, errno = %d\n",
143 errno); 145 errno);
144 pid = err; 146 pid = err;
145 } 147 }
146 if(!WIFEXITED(status) || (WEXITSTATUS(status) != 0)) 148 if (!WIFEXITED(status) || (WEXITSTATUS(status) != 0))
147 printk("run_helper_thread - thread returned status " 149 printk("run_helper_thread - thread returned status "
148 "0x%x\n", status); 150 "0x%x\n", status);
149 free_stack(stack, stack_order); 151 free_stack(stack, stack_order);
150 } 152 } else
151 else *stack_out = stack; 153 *stack_out = stack;
152 return(pid); 154 return pid;
153} 155}
154 156
155int helper_wait(int pid) 157int helper_wait(int pid)
@@ -157,9 +159,9 @@ int helper_wait(int pid)
157 int ret; 159 int ret;
158 160
159 CATCH_EINTR(ret = waitpid(pid, NULL, WNOHANG)); 161 CATCH_EINTR(ret = waitpid(pid, NULL, WNOHANG));
160 if(ret < 0){ 162 if (ret < 0) {
161 ret = -errno; 163 ret = -errno;
162 printk("helper_wait : waitpid failed, errno = %d\n", errno); 164 printk("helper_wait : waitpid failed, errno = %d\n", errno);
163 } 165 }
164 return(ret); 166 return ret;
165} 167}