xref: /haiku/src/system/libroot/os/arch/x86/atomic.S (revision 1e36cfc2721ef13a187c6f7354dc9cbc485e89d3)
1/*
2** Copyright 2003, Marcus Overhagen. All rights reserved.
3** Distributed under the terms of the OpenBeOS license.
4**
5** Copyright 2001, Travis Geiselbrecht. All rights reserved.
6** Distributed under the terms of the NewOS License.
7*/
8
9#define FUNCTION(x) .global x; .type x,@function; x
10
11.text
12
13/* int32	atomic_set(vint32 *value, int32 newValue) */
14FUNCTION(atomic_set):
15	movl		4(%esp),%edx
16	movl		8(%esp),%eax
17	lock
18	xchg		%eax,(%edx)
19	ret
20
21/* int32	atomic_test_and_set(vint32 *value, int32 newValue, int32 testAgainst) */
22FUNCTION(atomic_test_and_set):
23	movl		4(%esp),%edx
24	movl		8(%esp),%ecx
25	movl		12(%esp),%eax
26	lock
27	cmpxchgl	%ecx,(%edx)
28	ret
29
30/* int32	atomic_add(vint32 *value, int32 addValue) */
31FUNCTION(atomic_add):
32	movl		4(%esp),%edx
33	movl		8(%esp),%eax
34	lock
35	xaddl		%eax,(%edx)
36	ret
37
38/* int32	atomic_and(vint32 *value, int32 andValue) */
39FUNCTION(atomic_and):
40	movl		4(%esp),%edx
41_atomic_and1:
42	movl		8(%esp),%ecx
43	movl		(%edx),%eax
44	andl		%eax,%ecx
45	lock
46	cmpxchgl	%ecx,(%edx)
47	jnz			_atomic_and1
48	ret
49
50/* int32	atomic_or(vint32 *value, int32 orValue) */
51FUNCTION(atomic_or):
52	movl		4(%esp),%edx
53_atomic_or1:
54	movl		8(%esp),%ecx
55	movl		(%edx),%eax
56	orl			%eax,%ecx
57	lock
58	cmpxchgl	%ecx,(%edx)
59	jnz			_atomic_or1
60	ret
61
62/* int32	atomic_get(vint32 *value) */
63FUNCTION(atomic_get):
64	movl		4(%esp), %edx
65_atomic_get1:
66	movl		(%edx), %eax
67	movl		%eax, %ecx
68	lock
69	cmpxchgl	%ecx, (%edx)
70	jnz			_atomic_get1
71	ret
72
73/* int64	atomic_set64(vint64 *value, int64 newValue) */
74FUNCTION(atomic_set64):
75	push		%ebp
76	push		%ebx
77	movl		12(%esp), %ebp	/* value */
78	movl		16(%esp), %ebx	/* newValue low */
79	movl		20(%esp), %ecx	/* newValue high */
80_atomic_set64_1:
81	movl		(%ebp), %eax	/* testAgainst low */
82	movl		4(%ebp), %edx	/* testAgainst high */
83	lock
84	cmpxchg8b	(%ebp)
85	jnz			_atomic_set64_1
86	pop			%ebx
87	pop			%ebp
88	ret
89
90/* int64	atomic_test_and_set64(vint64 *value, int64 newValue, int64 testAgainst) */
91FUNCTION(atomic_test_and_set64):
92	push		%ebp
93	push		%ebx
94	movl		12(%esp), %ebp	/* value */
95	movl		16(%esp), %ebx	/* newValue low */
96	movl		20(%esp), %ecx	/* newValue high */
97	movl		24(%esp), %eax	/* testAgainst low */
98	movl		28(%esp), %edx	/* testAgainst high */
99	lock
100	cmpxchg8b	(%ebp)
101	pop			%ebx
102	pop			%ebp
103	ret
104
105/* int64	atomic_add64(vint64 *value, int64 addValue) */
106FUNCTION(atomic_add64):
107	push		%ebp
108	push		%ebx
109	movl		12(%esp), %ebp
110_atomic_add64_1:
111	movl		(%ebp), %eax
112	movl		4(%ebp), %edx
113	movl		%eax, %ebx
114	movl		%edx, %ecx
115	addl		16(%esp), %ebx
116	adcl		20(%esp), %ecx
117	lock
118	cmpxchg8b	(%ebp)
119	jnz			_atomic_add64_1
120	pop			%ebx
121	pop			%ebp
122	ret
123
124/* int64	atomic_and64(vint64 *value, int64 andValue) */
125FUNCTION(atomic_and64):
126	push		%ebp
127	push		%ebx
128	movl		12(%esp), %ebp
129_atomic_and64_1:
130	movl		(%ebp), %eax
131	movl		4(%ebp), %edx
132	movl		%eax, %ebx
133	movl		%edx, %ecx
134	andl		16(%esp), %ebx
135	andl		20(%esp), %ecx
136	lock
137	cmpxchg8b	(%ebp)
138	jnz			_atomic_and64_1
139	pop			%ebx
140	pop			%ebp
141	ret
142
143/* int64	atomic_or64(vint64 *value, int64 orValue) */
144FUNCTION(atomic_or64):
145	push		%ebp
146	push		%ebx
147	movl		12(%esp), %ebp
148_atomic_or64_1:
149	movl		(%ebp), %eax
150	movl		4(%ebp), %edx
151	movl		%eax, %ebx
152	movl		%edx, %ecx
153	orl			16(%esp), %ebx
154	orl			20(%esp), %ecx
155	lock
156	cmpxchg8b	(%ebp)
157	jnz			_atomic_or64_1
158	pop			%ebx
159	pop			%ebp
160	ret
161
162/* int64	atomic_get64(vint64 *value) */
163FUNCTION(atomic_get64):
164	push		%ebp
165	push		%ebx
166	movl		12(%esp), %ebp
167_atomic_get64_1:
168	movl		(%ebp), %eax
169	movl		4(%ebp), %edx
170	movl		%eax, %ebx
171	movl		%edx, %ecx
172	lock
173	cmpxchg8b	(%ebp)
174	jnz			_atomic_get64_1
175	pop			%ebx
176	pop			%ebp
177	ret
178