blob: 6f84724c306a8fd063b62b9b0e181131ebadf757 [file] [log] [blame]
Elliott Hughesbdff26d2013-02-11 17:08:16 -08001#include <machine/asm.h>
The Android Open Source Project1dc9e472009-03-03 19:28:35 -08002#include <sys/linux-syscalls.h>
3
Elliott Hughes5e3fc432013-02-11 16:36:48 -08004// int __pthread_clone(int (*fn)(void*), void* tls, int flags, void* arg);
Elliott Hughesbdff26d2013-02-11 17:08:16 -08005ENTRY(__pthread_clone)
The Android Open Source Project1dc9e472009-03-03 19:28:35 -08006 pushl %ebx
7 pushl %ecx
8 movl 16(%esp), %ecx
Jack Rencb082042012-03-21 17:48:13 +08009
10 # save tls
11 movl %ecx, %ebx
12 # 16-byte alignment on child stack
13 andl $~15, %ecx
The Android Open Source Project1dc9e472009-03-03 19:28:35 -080014
15 # insert arguments onto the child stack
16 movl 12(%esp), %eax
Jack Rencb082042012-03-21 17:48:13 +080017 movl %eax, -16(%ecx)
The Android Open Source Project1dc9e472009-03-03 19:28:35 -080018 movl 24(%esp), %eax
Jack Rencb082042012-03-21 17:48:13 +080019 movl %eax, -12(%ecx)
20 movl %ebx, -8(%ecx)
The Android Open Source Project1dc9e472009-03-03 19:28:35 -080021
Jack Rene480fc82011-09-21 12:44:11 +020022 subl $16, %ecx
Jack Rencb082042012-03-21 17:48:13 +080023 movl 20(%esp), %ebx
The Android Open Source Project1dc9e472009-03-03 19:28:35 -080024 movl $__NR_clone, %eax
25 int $0x80
26 test %eax, %eax
27 jns 1f
28
Jin Wei22d366c2012-08-08 15:15:16 +080029 # an error occurred, set errno and return -1
The Android Open Source Project1dc9e472009-03-03 19:28:35 -080030 negl %eax
31 call __set_errno
32 orl $-1, %eax
33 jmp 2f
34
351:
36 jnz 2f
37
38 # we're in the child thread now, call __thread_entry
39 # with the appropriate arguments on the child stack
40 # we already placed most of them
Jack Rencb082042012-03-21 17:48:13 +080041 call __thread_entry
The Android Open Source Project1dc9e472009-03-03 19:28:35 -080042 hlt
43
442:
45 popl %ecx
46 popl %ebx
47 ret
Elliott Hughesbdff26d2013-02-11 17:08:16 -080048END(__pthread_clone)
David 'Digit' Turner97cf7f32010-01-22 18:59:05 -080049
Jin Wei22d366c2012-08-08 15:15:16 +080050
51/*
52 * int __bionic_clone(unsigned long clone_flags,
53 * void* newsp,
54 * int *parent_tidptr,
55 * void *new_tls,
56 * int *child_tidptr,
57 * int (*fn)(void *),
58 * void *arg);
Bruce Beare16984422010-06-25 09:02:10 -070059 */
Elliott Hughesbdff26d2013-02-11 17:08:16 -080060ENTRY(__bionic_clone)
Jin Wei22d366c2012-08-08 15:15:16 +080061 pushl %ebx
62 pushl %esi
63 pushl %edi
64
65 # insert arguments onto the child stack
66 movl 20(%esp), %ecx
67 andl $~15, %ecx
68 movl 36(%esp), %eax
69 movl %eax, -16(%ecx)
70 movl 40(%esp), %eax
71 movl %eax, -12(%ecx)
72
73 subl $16, %ecx
74 movl 16(%esp), %ebx
75 movl 24(%esp), %edx
76 movl 32(%esp), %esi
77 movl 28(%esp), %edi
78 movl $__NR_clone, %eax
79 int $0x80
80 test %eax, %eax
81 jns 1f
82
83 # an error occurred, set errno and return -1
84 negl %eax
85 call __set_errno
86 orl $-1, %eax
87 jmp 2f
88
891:
90 jnz 2f
91
92 # we're in the child now, call __bionic_clone_entry
93 # with the appropriate arguments on the child stack
94 # we already placed most of them
95 call __bionic_clone_entry
96 hlt
97
982:
99 popl %edi
100 popl %esi
101 popl %ebx
102 ret
Elliott Hughesbdff26d2013-02-11 17:08:16 -0800103END(__bionic_clone)