diff options
author | Jeff Dike <jdike@addtoit.com> | 2007-07-16 02:38:56 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2007-07-16 12:05:38 -0400 |
commit | c43990162fc7f9d2f15a12797fdc6f9c0905f704 (patch) | |
tree | 64f8b776c4807da48971f3c24ca157c5e6ab921f /arch/um/os-Linux | |
parent | 42a359e31a0e438b5b978a8f0fecdbd3c86bb033 (diff) |
uml: simplify helper stack handling
run_helper and run_helper_thread had arguments which were the same in all
callers. run_helper's stack_out was always NULL and run_helper_thread's
stack_order was always 0. These are now gone, and the constants folded
into the code.
Also fixed leaks of the helper stack in the AIO and SIGIO code.
Signed-off-by: Jeff Dike <jdike@linux.intel.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'arch/um/os-Linux')
-rw-r--r-- | arch/um/os-Linux/aio.c | 11 | ||||
-rw-r--r-- | arch/um/os-Linux/drivers/ethertap_user.c | 2 | ||||
-rw-r--r-- | arch/um/os-Linux/drivers/tuntap_user.c | 2 | ||||
-rw-r--r-- | arch/um/os-Linux/helper.c | 19 | ||||
-rw-r--r-- | arch/um/os-Linux/sigio.c | 19 |
5 files changed, 27 insertions, 26 deletions
diff --git a/arch/um/os-Linux/aio.c b/arch/um/os-Linux/aio.c index 9bf944f6a1db..b126df4ea168 100644 --- a/arch/um/os-Linux/aio.c +++ b/arch/um/os-Linux/aio.c | |||
@@ -177,6 +177,7 @@ static int do_not_aio(struct aio_thread_req *req) | |||
177 | static int aio_req_fd_r = -1; | 177 | static int aio_req_fd_r = -1; |
178 | static int aio_req_fd_w = -1; | 178 | static int aio_req_fd_w = -1; |
179 | static int aio_pid = -1; | 179 | static int aio_pid = -1; |
180 | static unsigned long aio_stack; | ||
180 | 181 | ||
181 | static int not_aio_thread(void *arg) | 182 | static int not_aio_thread(void *arg) |
182 | { | 183 | { |
@@ -212,7 +213,6 @@ static int not_aio_thread(void *arg) | |||
212 | 213 | ||
213 | static int init_aio_24(void) | 214 | static int init_aio_24(void) |
214 | { | 215 | { |
215 | unsigned long stack; | ||
216 | int fds[2], err; | 216 | int fds[2], err; |
217 | 217 | ||
218 | err = os_pipe(fds, 1, 1); | 218 | err = os_pipe(fds, 1, 1); |
@@ -227,7 +227,7 @@ static int init_aio_24(void) | |||
227 | goto out_close_pipe; | 227 | goto out_close_pipe; |
228 | 228 | ||
229 | err = run_helper_thread(not_aio_thread, NULL, | 229 | err = run_helper_thread(not_aio_thread, NULL, |
230 | CLONE_FILES | CLONE_VM | SIGCHLD, &stack, 0); | 230 | CLONE_FILES | CLONE_VM | SIGCHLD, &aio_stack); |
231 | if(err < 0) | 231 | if(err < 0) |
232 | goto out_close_pipe; | 232 | goto out_close_pipe; |
233 | 233 | ||
@@ -252,7 +252,6 @@ out: | |||
252 | #define DEFAULT_24_AIO 0 | 252 | #define DEFAULT_24_AIO 0 |
253 | static int init_aio_26(void) | 253 | static int init_aio_26(void) |
254 | { | 254 | { |
255 | unsigned long stack; | ||
256 | int err; | 255 | int err; |
257 | 256 | ||
258 | if(io_setup(256, &ctx)){ | 257 | if(io_setup(256, &ctx)){ |
@@ -263,7 +262,7 @@ static int init_aio_26(void) | |||
263 | } | 262 | } |
264 | 263 | ||
265 | err = run_helper_thread(aio_thread, NULL, | 264 | err = run_helper_thread(aio_thread, NULL, |
266 | CLONE_FILES | CLONE_VM | SIGCHLD, &stack, 0); | 265 | CLONE_FILES | CLONE_VM | SIGCHLD, &aio_stack); |
267 | if(err < 0) | 266 | if(err < 0) |
268 | return err; | 267 | return err; |
269 | 268 | ||
@@ -365,8 +364,10 @@ __initcall(init_aio); | |||
365 | 364 | ||
366 | static void exit_aio(void) | 365 | static void exit_aio(void) |
367 | { | 366 | { |
368 | if(aio_pid != -1) | 367 | if (aio_pid != -1) { |
369 | os_kill_process(aio_pid, 1); | 368 | os_kill_process(aio_pid, 1); |
369 | free_stack(aio_stack, 0); | ||
370 | } | ||
370 | } | 371 | } |
371 | 372 | ||
372 | __uml_exitcall(exit_aio); | 373 | __uml_exitcall(exit_aio); |
diff --git a/arch/um/os-Linux/drivers/ethertap_user.c b/arch/um/os-Linux/drivers/ethertap_user.c index acba30161287..cac01b31ea95 100644 --- a/arch/um/os-Linux/drivers/ethertap_user.c +++ b/arch/um/os-Linux/drivers/ethertap_user.c | |||
@@ -117,7 +117,7 @@ static int etap_tramp(char *dev, char *gate, int control_me, | |||
117 | pe_data.control_remote = control_remote; | 117 | pe_data.control_remote = control_remote; |
118 | pe_data.control_me = control_me; | 118 | pe_data.control_me = control_me; |
119 | pe_data.data_me = data_me; | 119 | pe_data.data_me = data_me; |
120 | pid = run_helper(etap_pre_exec, &pe_data, args, NULL); | 120 | pid = run_helper(etap_pre_exec, &pe_data, args); |
121 | 121 | ||
122 | if(pid < 0) | 122 | if(pid < 0) |
123 | err = pid; | 123 | err = pid; |
diff --git a/arch/um/os-Linux/drivers/tuntap_user.c b/arch/um/os-Linux/drivers/tuntap_user.c index 11a9779dc9f1..f848b4ea9343 100644 --- a/arch/um/os-Linux/drivers/tuntap_user.c +++ b/arch/um/os-Linux/drivers/tuntap_user.c | |||
@@ -83,7 +83,7 @@ static int tuntap_open_tramp(char *gate, int *fd_out, int me, int remote, | |||
83 | data.stdout = remote; | 83 | data.stdout = remote; |
84 | data.close_me = me; | 84 | data.close_me = me; |
85 | 85 | ||
86 | pid = run_helper(tuntap_pre_exec, &data, argv, NULL); | 86 | pid = run_helper(tuntap_pre_exec, &data, argv); |
87 | 87 | ||
88 | if(pid < 0) | 88 | if(pid < 0) |
89 | return -pid; | 89 | return -pid; |
diff --git a/arch/um/os-Linux/helper.c b/arch/um/os-Linux/helper.c index 97bed16bf4c7..9cf48d0577cc 100644 --- a/arch/um/os-Linux/helper.c +++ b/arch/um/os-Linux/helper.c | |||
@@ -44,17 +44,13 @@ static int helper_child(void *arg) | |||
44 | /* Returns either the pid of the child process we run or -E* on failure. | 44 | /* Returns either the pid of the child process we run or -E* on failure. |
45 | * XXX The alloc_stack here breaks if this is called in the tracing thread, so | 45 | * XXX The alloc_stack here breaks if this is called in the tracing thread, so |
46 | * we need to receive a preallocated stack (a local buffer is ok). */ | 46 | * we need to receive a preallocated stack (a local buffer is ok). */ |
47 | int run_helper(void (*pre_exec)(void *), void *pre_data, char **argv, | 47 | int run_helper(void (*pre_exec)(void *), void *pre_data, char **argv) |
48 | unsigned long *stack_out) | ||
49 | { | 48 | { |
50 | struct helper_data data; | 49 | struct helper_data data; |
51 | unsigned long stack, sp; | 50 | unsigned long stack, sp; |
52 | int pid, fds[2], ret, n; | 51 | int pid, fds[2], ret, n; |
53 | 52 | ||
54 | if ((stack_out != NULL) && (*stack_out != 0)) | 53 | stack = alloc_stack(0, __cant_sleep()); |
55 | stack = *stack_out; | ||
56 | else | ||
57 | stack = alloc_stack(0, __cant_sleep()); | ||
58 | if (stack == 0) | 54 | if (stack == 0) |
59 | return -ENOMEM; | 55 | return -ENOMEM; |
60 | 56 | ||
@@ -113,22 +109,21 @@ out_close: | |||
113 | close(fds[1]); | 109 | close(fds[1]); |
114 | close(fds[0]); | 110 | close(fds[0]); |
115 | out_free: | 111 | out_free: |
116 | if ((stack_out == NULL) || (*stack_out == 0)) | 112 | free_stack(stack, 0); |
117 | free_stack(stack, 0); | ||
118 | return ret; | 113 | return ret; |
119 | } | 114 | } |
120 | 115 | ||
121 | int run_helper_thread(int (*proc)(void *), void *arg, unsigned int flags, | 116 | int run_helper_thread(int (*proc)(void *), void *arg, unsigned int flags, |
122 | unsigned long *stack_out, int stack_order) | 117 | unsigned long *stack_out) |
123 | { | 118 | { |
124 | unsigned long stack, sp; | 119 | unsigned long stack, sp; |
125 | int pid, status, err; | 120 | int pid, status, err; |
126 | 121 | ||
127 | stack = alloc_stack(stack_order, __cant_sleep()); | 122 | stack = alloc_stack(0, __cant_sleep()); |
128 | if (stack == 0) | 123 | if (stack == 0) |
129 | return -ENOMEM; | 124 | return -ENOMEM; |
130 | 125 | ||
131 | sp = stack + (UM_KERN_PAGE_SIZE << stack_order) - sizeof(void *); | 126 | sp = stack + UM_KERN_PAGE_SIZE - sizeof(void *); |
132 | pid = clone(proc, (void *) sp, flags | SIGCHLD, arg); | 127 | pid = clone(proc, (void *) sp, flags | SIGCHLD, arg); |
133 | if (pid < 0) { | 128 | if (pid < 0) { |
134 | err = -errno; | 129 | err = -errno; |
@@ -147,7 +142,7 @@ int run_helper_thread(int (*proc)(void *), void *arg, unsigned int flags, | |||
147 | if (!WIFEXITED(status) || (WEXITSTATUS(status) != 0)) | 142 | if (!WIFEXITED(status) || (WEXITSTATUS(status) != 0)) |
148 | printk("run_helper_thread - thread returned status " | 143 | printk("run_helper_thread - thread returned status " |
149 | "0x%x\n", status); | 144 | "0x%x\n", status); |
150 | free_stack(stack, stack_order); | 145 | free_stack(stack, 0); |
151 | } else | 146 | } else |
152 | *stack_out = stack; | 147 | *stack_out = stack; |
153 | return pid; | 148 | return pid; |
diff --git a/arch/um/os-Linux/sigio.c b/arch/um/os-Linux/sigio.c index 8d4e0c6b8c92..2c23cb261188 100644 --- a/arch/um/os-Linux/sigio.c +++ b/arch/um/os-Linux/sigio.c | |||
@@ -26,6 +26,7 @@ | |||
26 | * exitcall. | 26 | * exitcall. |
27 | */ | 27 | */ |
28 | static int write_sigio_pid = -1; | 28 | static int write_sigio_pid = -1; |
29 | static unsigned long write_sigio_stack; | ||
29 | 30 | ||
30 | /* These arrays are initialized before the sigio thread is started, and | 31 | /* These arrays are initialized before the sigio thread is started, and |
31 | * the descriptors closed after it is killed. So, it can't see them change. | 32 | * the descriptors closed after it is killed. So, it can't see them change. |
@@ -144,8 +145,10 @@ static void update_thread(void) | |||
144 | return; | 145 | return; |
145 | fail: | 146 | fail: |
146 | /* Critical section start */ | 147 | /* Critical section start */ |
147 | if(write_sigio_pid != -1) | 148 | if (write_sigio_pid != -1) { |
148 | os_kill_process(write_sigio_pid, 1); | 149 | os_kill_process(write_sigio_pid, 1); |
150 | free_stack(write_sigio_stack, 0); | ||
151 | } | ||
149 | write_sigio_pid = -1; | 152 | write_sigio_pid = -1; |
150 | close(sigio_private[0]); | 153 | close(sigio_private[0]); |
151 | close(sigio_private[1]); | 154 | close(sigio_private[1]); |
@@ -243,7 +246,6 @@ static struct pollfd *setup_initial_poll(int fd) | |||
243 | 246 | ||
244 | static void write_sigio_workaround(void) | 247 | static void write_sigio_workaround(void) |
245 | { | 248 | { |
246 | unsigned long stack; | ||
247 | struct pollfd *p; | 249 | struct pollfd *p; |
248 | int err; | 250 | int err; |
249 | int l_write_sigio_fds[2]; | 251 | int l_write_sigio_fds[2]; |
@@ -293,7 +295,8 @@ static void write_sigio_workaround(void) | |||
293 | memcpy(sigio_private, l_sigio_private, sizeof(l_sigio_private)); | 295 | memcpy(sigio_private, l_sigio_private, sizeof(l_sigio_private)); |
294 | 296 | ||
295 | write_sigio_pid = run_helper_thread(write_sigio_thread, NULL, | 297 | write_sigio_pid = run_helper_thread(write_sigio_thread, NULL, |
296 | CLONE_FILES | CLONE_VM, &stack, 0); | 298 | CLONE_FILES | CLONE_VM, |
299 | &write_sigio_stack); | ||
297 | 300 | ||
298 | if (write_sigio_pid < 0) | 301 | if (write_sigio_pid < 0) |
299 | goto out_clear; | 302 | goto out_clear; |
@@ -356,10 +359,12 @@ out: | |||
356 | 359 | ||
357 | static void sigio_cleanup(void) | 360 | static void sigio_cleanup(void) |
358 | { | 361 | { |
359 | if(write_sigio_pid != -1){ | 362 | if (write_sigio_pid == -1) |
360 | os_kill_process(write_sigio_pid, 1); | 363 | return; |
361 | write_sigio_pid = -1; | 364 | |
362 | } | 365 | os_kill_process(write_sigio_pid, 1); |
366 | free_stack(write_sigio_stack, 0); | ||
367 | write_sigio_pid = -1; | ||
363 | } | 368 | } |
364 | 369 | ||
365 | __uml_exitcall(sigio_cleanup); | 370 | __uml_exitcall(sigio_cleanup); |