pthread_cond_signal.S 2.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136
  1. /* Copyright (C) 2003, 2004 Free Software Foundation, Inc.
  2. This file is part of the GNU C Library.
  3. The GNU C Library is free software; you can redistribute it and/or
  4. modify it under the terms of the GNU Lesser General Public
  5. License as published by the Free Software Foundation; either
  6. version 2.1 of the License, or (at your option) any later version.
  7. The GNU C Library is distributed in the hope that it will be useful,
  8. but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  10. Lesser General Public License for more details.
  11. You should have received a copy of the GNU Lesser General Public
  12. License along with the GNU C Library; if not, write to the Free
  13. Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
  14. 02111-1307 USA. */
  15. #include <sysdep.h>
  16. #include <lowlevelcond.h>
  17. #include <bits/kernel-features.h>
  18. #include "lowlevel-atomic.h"
  19. #define FUTEX_WAIT 0
  20. #define FUTEX_WAKE 1
  21. #define FUTEX_REQUEUE 3
  22. #define EINVAL 22
  23. .text
  24. /* int pthread_cond_signal (pthread_cond_t *cond) */
  25. .globl __pthread_cond_signal
  26. .type __pthread_cond_signal, @function
  27. .align 5
  28. __pthread_cond_signal:
  29. mov.l r8, @-r15
  30. sts.l pr, @-r15
  31. mov r4, r8
  32. /* Get internal lock. */
  33. mov #0, r3
  34. mov #1, r4
  35. #if cond_lock != 0
  36. CMPXCHG (r3, @(cond_lock,r8), r4, r2)
  37. #else
  38. CMPXCHG (r3, @r8, r4, r2)
  39. #endif
  40. bf 1f
  41. 2:
  42. mov.l @(total_seq+4,r8),r0
  43. mov.l @(total_seq,r8),r1
  44. mov.l @(wakeup_seq+4,r8), r2
  45. cmp/hi r2, r0
  46. bt 3f
  47. cmp/hi r0, r2
  48. bt 4f
  49. mov.l @(wakeup_seq,r8), r2
  50. cmp/hi r2, r1
  51. bf 4f
  52. 3:
  53. /* Bump the wakeup number. */
  54. mov #1, r2
  55. mov #0, r3
  56. clrt
  57. mov.l @(wakeup_seq,r8),r0
  58. mov.l @(wakeup_seq+4,r8),r1
  59. addc r2, r0
  60. addc r3, r1
  61. mov.l r0,@(wakeup_seq,r8)
  62. mov.l r1,@(wakeup_seq+4,r8)
  63. mov.l @(cond_futex,r8),r0
  64. add r2, r0
  65. mov.l r0,@(cond_futex,r8)
  66. /* Wake up one thread. */
  67. mov r8, r4
  68. add #cond_futex, r4
  69. mov #FUTEX_WAKE, r5
  70. mov #1, r6
  71. mov #0, r7
  72. mov #SYS_futex, r3
  73. extu.b r3, r3
  74. trapa #0x14
  75. SYSCALL_INST_PAD
  76. 4:
  77. /* Unlock. */
  78. #if cond_lock != 0
  79. DEC (@(cond_lock,r8), r2)
  80. #else
  81. DEC (@r8, r2)
  82. #endif
  83. tst r2, r2
  84. bf 5f
  85. 6:
  86. mov #0, r0
  87. lds.l @r15+, pr
  88. rts
  89. mov.l @r15+, r8
  90. 1:
  91. /* Initial locking failed. */
  92. mov r8, r5
  93. #if cond_lock != 0
  94. add #cond_lock, r5
  95. #endif
  96. mov.l .Lmwait4, r1
  97. bsrf r1
  98. mov r2, r4
  99. .Lmwait4b:
  100. bra 2b
  101. nop
  102. 5:
  103. /* Unlock in loop requires wakeup. */
  104. mov r8, r4
  105. #if cond_lock != 0
  106. add #cond_lock, r4
  107. #endif
  108. mov.l .Lmwake4, r1
  109. bsrf r1
  110. nop
  111. .Lmwake4b:
  112. bra 6b
  113. nop
  114. .align 2
  115. .Lmwait4:
  116. .long __lll_mutex_lock_wait-.Lmwait4b
  117. .Lmwake4:
  118. .long __lll_mutex_unlock_wake-.Lmwake4b
  119. .size __pthread_cond_signal, .-__pthread_cond_signal
  120. weak_alias (__pthread_cond_signal, pthread_cond_signal)