]>
Commit | Line | Data |
---|---|---|
76a50749 UD |
1 | /* Copyright (C) 2002 Free Software Foundation, Inc. |
2 | This file is part of the GNU C Library. | |
3 | Contributed by Ulrich Drepper <drepper@redhat.com>, 2002. | |
4 | ||
5 | The GNU C Library is free software; you can redistribute it and/or | |
6 | modify it under the terms of the GNU Lesser General Public | |
7 | License as published by the Free Software Foundation; either | |
8 | version 2.1 of the License, or (at your option) any later version. | |
9 | ||
10 | The GNU C Library is distributed in the hope that it will be useful, | |
11 | but WITHOUT ANY WARRANTY; without even the implied warranty of | |
12 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
13 | Lesser General Public License for more details. | |
14 | ||
15 | You should have received a copy of the GNU Lesser General Public | |
16 | License along with the GNU C Library; if not, write to the Free | |
17 | Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA | |
18 | 02111-1307 USA. */ | |
19 | ||
20 | #include <sysdep.h> | |
21 | ||
22 | .text | |
23 | ||
24 | #ifdef UP | |
25 | # define LOCK | |
26 | #else | |
27 | # define LOCK lock | |
28 | #endif | |
29 | ||
30 | #define SYS_gettimeofday __NR_gettimeofday | |
31 | #define SYS_futex 240 | |
32 | #define FUTEX_WAIT 0 | |
33 | #define FUTEX_WAKE 1 | |
34 | ||
35 | #define ETIMEDOUT 110 | |
36 | ||
37 | ||
38 | .globl __lll_lock_wait | |
39 | .type __lll_lock_wait,@function | |
40 | .hidden __lll_lock_wait | |
41 | .align 16 | |
42 | __lll_lock_wait: | |
43 | pushl %esi | |
44 | pushl %ebx | |
45 | pushl %edx | |
46 | ||
47 | movl %ecx, %ebx | |
48 | xorl %esi, %esi /* No timeout. */ | |
49 | xorl %ecx, %ecx /* movl $FUTEX_WAIT, %ecx */ | |
50 | 1: | |
51 | leal -1(%eax), %edx /* account for the preceeded xadd. */ | |
52 | movl $SYS_futex, %eax | |
53 | int $0x80 | |
54 | ||
55 | orl $-1, %eax /* Load -1. */ | |
56 | LOCK | |
57 | xaddl %eax, (%ebx) | |
58 | jne 1b | |
59 | ||
60 | movl $-1, (%ebx) | |
61 | ||
62 | popl %edx | |
63 | popl %ebx | |
64 | popl %esi | |
65 | ret | |
66 | .size __lll_lock_wait,.-__lll_lock_wait | |
67 | ||
68 | ||
69 | .globl lll_unlock_wake_cb | |
70 | .type lll_unlock_wake_cb,@function | |
71 | .hidden lll_unlock_wake_cb | |
72 | .align 16 | |
73 | lll_unlock_wake_cb: | |
74 | pushl %esi | |
75 | pushl %ebx | |
76 | pushl %ecx | |
77 | pushl %edx | |
78 | ||
79 | movl 20(%esp), %ebx | |
80 | LOCK | |
81 | incl (%ebx) | |
82 | jng 1f | |
83 | ||
84 | popl %edx | |
85 | popl %ecx | |
86 | popl %ebx | |
87 | popl %esi | |
88 | ret | |
89 | .size lll_unlock_wake_cb,.-lll_unlock_wake_cb | |
90 | ||
91 | ||
92 | .globl __lll_unlock_wake | |
93 | .type __lll_unlock_wake,@function | |
94 | .hidden __lll_unlock_wake | |
95 | __lll_unlock_wake: | |
96 | pushl %esi | |
97 | pushl %ebx | |
98 | pushl %ecx | |
99 | pushl %edx | |
100 | ||
101 | movl %eax, %ebx | |
102 | 1: movl $FUTEX_WAKE, %ecx | |
103 | movl $1, %edx /* Wake one thread. */ | |
104 | xorl %esi, %esi | |
105 | movl %edx, (%ebx) /* Stores '$1'. */ | |
106 | movl $SYS_futex, %eax | |
107 | int $0x80 | |
108 | ||
109 | popl %edx | |
110 | popl %ecx | |
111 | popl %ebx | |
112 | popl %esi | |
113 | ret | |
114 | .size __lll_unlock_wake,.-__lll_unlock_wake | |
115 | ||
116 | ||
117 | .globl __lll_timedwait_tid | |
118 | .type __lll_timedwait_tid,@function | |
119 | .hidden __lll_timedwait_tid | |
120 | __lll_timedwait_tid: | |
121 | pushl %edi | |
122 | pushl %esi | |
123 | pushl %ebx | |
124 | pushl %ebp | |
125 | ||
126 | movl %eax, %ebp | |
127 | movl %edx, %edi | |
128 | subl $8, %esp | |
129 | ||
130 | /* Get current time. */ | |
131 | 2: movl %esp, %ebx | |
132 | xorl %ecx, %ecx | |
133 | movl $SYS_gettimeofday, %eax | |
134 | int $0x80 | |
135 | ||
136 | /* Compute relative timeout. */ | |
137 | movl 4(%esp), %eax | |
138 | movl $1000, %edx | |
139 | mul %edx /* Milli seconds to nano seconds. */ | |
140 | movl (%edi), %ecx | |
141 | movl 4(%edi), %edx | |
142 | subl (%esp), %ecx | |
143 | subl %eax, %edx | |
144 | jns 5f | |
145 | addl $1000000000, %edx | |
146 | decl %ecx | |
147 | 5: testl %ecx, %ecx | |
148 | js 6f /* Time is already up. */ | |
149 | ||
150 | movl %ecx, (%esp) /* Store relative timeout. */ | |
151 | movl %edx, 4(%esp) | |
152 | ||
153 | movl (%ebp), %edx | |
154 | testl %edx, %edx | |
155 | jz 4f | |
156 | ||
157 | movl %esp, %esi | |
158 | xorl %ecx, %ecx /* movl $FUTEX_WAIT, %ecx */ | |
159 | movl %ebp, %ebx | |
160 | movl $SYS_futex, %eax | |
161 | int $0x80 | |
162 | ||
163 | movl %eax, %edx | |
164 | ||
165 | cmpl $0, (%ebx) | |
166 | jne 1f | |
167 | 4: xorl %eax, %eax | |
168 | ||
169 | 3: addl $8, %esp | |
170 | popl %ebp | |
171 | popl %ebx | |
172 | popl %esi | |
173 | popl %edi | |
174 | ret | |
175 | ||
176 | 1: cmpl $-ETIMEDOUT, %edx | |
177 | jne 2b | |
178 | 6: movl $ETIMEDOUT, %eax | |
179 | jmp 3b | |
180 | .size __lll_timedwait_tid,.-__lll_timedwait_tid |