Commit | Line | Data |
---|---|---|
1da177e4 LT |
1 | /* |
2 | * Copyright (C) 2002 Jeff Dike (jdike@karaya.com) | |
3 | * Licensed under the GPL | |
4 | */ | |
5 | ||
6 | #include "linux/kernel.h" | |
7 | #include "linux/mm.h" | |
8 | #include "asm/signal.h" | |
9 | #include "asm/ptrace.h" | |
10 | #include "asm/uaccess.h" | |
11 | #include "asm/pgalloc.h" | |
12 | #include "asm/tlbflush.h" | |
1da177e4 LT |
13 | #include "kern_util.h" |
14 | #include "irq_user.h" | |
1da177e4 LT |
15 | #include "mem_user.h" |
16 | #include "os.h" | |
17 | #include "tlb.h" | |
18 | #include "mode.h" | |
19 | ||
20 | static int exec_tramp(void *sig_stack) | |
21 | { | |
22 | init_new_thread_stack(sig_stack, NULL); | |
e64bd134 | 23 | init_new_thread_signals(); |
1da177e4 LT |
24 | os_stop_process(os_getpid()); |
25 | return(0); | |
26 | } | |
27 | ||
28 | void flush_thread_tt(void) | |
29 | { | |
30 | unsigned long stack; | |
31 | int new_pid; | |
32 | ||
33 | stack = alloc_stack(0, 0); | |
34 | if(stack == 0){ | |
35 | printk(KERN_ERR | |
36 | "flush_thread : failed to allocate temporary stack\n"); | |
37 | do_exit(SIGKILL); | |
38 | } | |
39 | ||
579b3ea5 | 40 | new_pid = start_fork_tramp(task_stack_page(current), stack, 0, exec_tramp); |
1da177e4 LT |
41 | if(new_pid < 0){ |
42 | printk(KERN_ERR | |
43 | "flush_thread : new thread failed, errno = %d\n", | |
44 | -new_pid); | |
45 | do_exit(SIGKILL); | |
46 | } | |
47 | ||
48 | if(current_thread->cpu == 0) | |
49 | forward_interrupts(new_pid); | |
50 | current->thread.request.op = OP_EXEC; | |
51 | current->thread.request.u.exec.pid = new_pid; | |
52 | unprotect_stack((unsigned long) current_thread); | |
53 | os_usr1_process(os_getpid()); | |
54 | change_sig(SIGUSR1, 1); | |
55 | ||
56 | change_sig(SIGUSR1, 0); | |
57 | enable_timer(); | |
58 | free_page(stack); | |
59 | protect_memory(uml_reserved, high_physmem - uml_reserved, 1, 1, 0, 1); | |
57598fd7 | 60 | stack_protections((unsigned long) current_thread); |
1da177e4 LT |
61 | force_flush_all(); |
62 | unblock_signals(); | |
63 | } | |
64 | ||
65 | void start_thread_tt(struct pt_regs *regs, unsigned long eip, | |
66 | unsigned long esp) | |
67 | { | |
68 | set_fs(USER_DS); | |
69 | flush_tlb_mm(current->mm); | |
70 | PT_REGS_IP(regs) = eip; | |
71 | PT_REGS_SP(regs) = esp; | |
72 | PT_FIX_EXEC_STACK(esp); | |
73 | } | |
74 | ||
75 | /* | |
76 | * Overrides for Emacs so that we follow Linus's tabbing style. | |
77 | * Emacs will notice this stuff at the end of the file and automatically | |
78 | * adjust the settings for this buffer only. This must remain at the end | |
79 | * of the file. | |
80 | * --------------------------------------------------------------------------- | |
81 | * Local variables: | |
82 | * c-file-style: "linux" | |
83 | * End: | |
84 | */ |