blob: b7b20e6ef8ca0cd314dc1a903f09a4b2de787e3f [file] [log] [blame]
The Android Open Source Project1dc9e472009-03-03 19:28:35 -08001/*
2 * Copyright (C) 2008 The Android Open Source Project
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 * * Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
10 * * Redistributions in binary form must reproduce the above copyright
11 * notice, this list of conditions and the following disclaimer in
12 * the documentation and/or other materials provided with the
13 * distribution.
14 *
15 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
16 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
17 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
18 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
19 * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
20 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
21 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
22 * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
23 * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
24 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
25 * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
26 * SUCH DAMAGE.
27 */
28#include <sys/atomics.h>
29
30#define FUTEX_SYSCALL 240
31#define FUTEX_WAIT 0
32#define FUTEX_WAKE 1
33
34int __futex_wait(volatile void *ftx, int val)
35{
36 int ret;
37 asm volatile (
38 "int $0x80;"
39 : "=a" (ret)
40 : "0" (FUTEX_SYSCALL),
41 "b" (ftx),
42 "c" (FUTEX_WAIT),
43 "d" (val),
44 "S" (0)
45 );
46 return ret;
47}
48
49int __futex_wake(volatile void *ftx, int count)
50{
51 int ret;
52 asm volatile (
53 "int $0x80;"
54 : "=a" (ret)
55 : "0" (FUTEX_SYSCALL),
56 "b" (ftx),
57 "c" (FUTEX_WAKE),
58 "d" (count)
59 );
60 return ret;
61}
62
63int __atomic_cmpxchg(int old, int new, volatile int* addr) {
64 int xchg;
65 asm volatile (
66 "lock;"
67 "cmpxchg %%ecx, (%%edx);"
68 "setne %%al;"
69 : "=a" (xchg)
70 : "a" (old),
71 "c" (new),
72 "d" (addr)
73 );
74 return xchg;
75}
76
77int __atomic_swap(int new, volatile int* addr) {
78 int old;
79 asm volatile (
80 "lock;"
81 "xchg %%ecx, (%%edx);"
82 : "=c" (old)
83 : "c" (new),
84 "d" (addr)
85 );
86 return old;
87}
88
89int __atomic_dec(volatile int* addr) {
90 int old;
91 do {
92 old = *addr;
93 } while (atomic_cmpxchg(old, old-1, addr));
94 return old;
95}
96
97int __atomic_inc(volatile int* addr) {
98 int old;
99 do {
100 old = *addr;
101 } while (atomic_cmpxchg(old, old+1, addr));
102 return old;
103}
104