]> git.ipfire.org Git - thirdparty/glibc.git/blame - nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_signal.S
Replace FSF snail mail address with URLs.
[thirdparty/glibc.git] / nptl / sysdeps / unix / sysv / linux / x86_64 / pthread_cond_signal.S
CommitLineData
42e69bcf 1/* Copyright (C) 2002-2005, 2007, 2009 Free Software Foundation, Inc.
d0aacb47
UD
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
59ba27a6
PE
16 License along with the GNU C Library; if not, see
17 <http://www.gnu.org/licenses/>. */
d0aacb47
UD
18
19#include <sysdep.h>
20#include <shlib-compat.h>
e51deae7 21#include <lowlevellock.h>
d0aacb47 22#include <lowlevelcond.h>
42e69bcf 23#include <pthread-pi-defines.h>
69431c9a 24#include <kernel-features.h>
e51deae7 25#include <pthread-errnos.h>
d0aacb47
UD
26
27
28 .text
29
30 /* int pthread_cond_signal (pthread_cond_t *cond) */
31 .globl __pthread_cond_signal
32 .type __pthread_cond_signal, @function
33 .align 16
34__pthread_cond_signal:
35
36 /* Get internal lock. */
7661d9f7 37 movq %rdi, %r8
d0aacb47 38 movl $1, %esi
3a226d33 39 xorl %eax, %eax
d0aacb47
UD
40 LOCK
41#if cond_lock == 0
3a226d33 42 cmpxchgl %esi, (%rdi)
d0aacb47 43#else
3a226d33 44 cmpxchgl %esi, cond_lock(%rdi)
d0aacb47 45#endif
3a226d33 46 jnz 1f
d0aacb47 47
75fccede 482: addq $cond_futex, %rdi
69431c9a 49 movq total_seq(%r8), %rcx
75fccede 50 cmpq wakeup_seq(%r8), %rcx
d0aacb47
UD
51 jbe 4f
52
53 /* Bump the wakeup number. */
75fccede
UD
54 addq $1, wakeup_seq(%r8)
55 addl $1, (%rdi)
d0aacb47
UD
56
57 /* Wake up one thread. */
5bd8a249 58 cmpq $-1, dep_mutex(%r8)
42e69bcf 59 movl $FUTEX_WAKE_OP, %esi
ee618985 60 movl $1, %edx
42e69bcf
UD
61 movl $SYS_futex, %eax
62 je 8f
63
64 /* Get the address of the mutex used. */
65 movq dep_mutex(%r8), %rcx
ec492239
AS
66 movl MUTEX_KIND(%rcx), %r11d
67 andl $(ROBUST_BIT|PI_BIT), %r11d
68 cmpl $PI_BIT, %r11d
b0948ffd 69 je 9f
42e69bcf 70
5bd8a249 71#ifdef __ASSUME_PRIVATE_FUTEX
5bd8a249 72 movl $(FUTEX_WAKE_OP|FUTEX_PRIVATE_FLAG), %esi
5bd8a249 73#else
42e69bcf 74 orl %fs:PRIVATE_FUTEX, %esi
5bd8a249 75#endif
42e69bcf
UD
76
778: movl $1, %r10d
a3615024
UD
78#if cond_lock != 0
79 addq $cond_lock, %r8
80#endif
81 movl $FUTEX_OP_CLEAR_WAKE_IF_GT_ONE, %r9d
82 syscall
83#if cond_lock != 0
84 subq $cond_lock, %r8
85#endif
86 /* For any kind of error, we try again with WAKE.
87 The general test also covers running on old kernels. */
88 cmpq $-4095, %rax
89 jae 7f
90
91 xorl %eax, %eax
92 retq
93
42e69bcf
UD
94 /* Wake up one thread and requeue none in the PI Mutex case. */
959: movl $(FUTEX_CMP_REQUEUE_PI|FUTEX_PRIVATE_FLAG), %esi
96 movq %rcx, %r8
97 xorq %r10, %r10
98 movl (%rdi), %r9d // XXX Can this be right?
99 syscall
100
101 leaq -cond_futex(%rdi), %r8
102
103 /* For any kind of error, we try again with WAKE.
104 The general test also covers running on old kernels. */
105 cmpq $-4095, %rax
106 jb 4f
107
1087:
109#ifdef __ASSUME_PRIVATE_FUTEX
110 andl $FUTEX_PRIVATE_FLAG, %esi
111#else
112 andl %fs:PRIVATE_FUTEX, %esi
113#endif
114 orl $FUTEX_WAKE, %esi
a3615024
UD
115 movl $SYS_futex, %eax
116 /* %rdx should be 1 already from $FUTEX_WAKE_OP syscall.
117 movl $1, %edx */
d0aacb47
UD
118 syscall
119
120 /* Unlock. */
1214: LOCK
7661d9f7
UD
122#if cond_lock == 0
123 decl (%r8)
124#else
69431c9a 125 decl cond_lock(%r8)
7661d9f7 126#endif
d0aacb47
UD
127 jne 5f
128
1296: xorl %eax, %eax
130 retq
131
132 /* Initial locking failed. */
1331:
134#if cond_lock != 0
135 addq $cond_lock, %rdi
136#endif
5bd8a249
UD
137 cmpq $-1, dep_mutex-cond_lock(%rdi)
138 movl $LLL_PRIVATE, %eax
e51deae7 139 movl $LLL_SHARED, %esi
5bd8a249 140 cmovne %eax, %esi
e51deae7 141 callq __lll_lock_wait
d0aacb47
UD
142#if cond_lock != 0
143 subq $cond_lock, %rdi
144#endif
145 jmp 2b
146
7661d9f7 147 /* Unlock in loop requires wakeup. */
69431c9a 1485:
69431c9a 149 movq %r8, %rdi
5bd8a249
UD
150#if cond_lock != 0
151 addq $cond_lock, %rdi
152#endif
153 cmpq $-1, dep_mutex-cond_lock(%rdi)
154 movl $LLL_PRIVATE, %eax
e51deae7 155 movl $LLL_SHARED, %esi
5bd8a249 156 cmovne %eax, %esi
e51deae7 157 callq __lll_unlock_wake
d0aacb47
UD
158 jmp 6b
159 .size __pthread_cond_signal, .-__pthread_cond_signal
160versioned_symbol (libpthread, __pthread_cond_signal, pthread_cond_signal,
161 GLIBC_2_3_2)