* added 0.99 linux version
[mascara-docs.git] / i386 / linux / linux-2.3.21 / arch / sparc / lib / locks.S
blob102541b18e6cfbb3107418e4a39269473980994c
1 /* $Id: locks.S,v 1.15 1998/10/14 09:18:55 jj Exp $
2  * locks.S: SMP low-level lock primitives on Sparc.
3  *
4  * Copyright (C) 1996 David S. Miller (davem@caip.rutgers.edu)
5  * Copyright (C) 1998 Anton Blanchard (anton@progsoc.uts.edu.au)
6  * Copyright (C) 1998 Jakub Jelinek   (jj@ultra.linux.cz)
7  */
9 #include <asm/cprefix.h>
10 #include <asm/ptrace.h>
11 #include <asm/psr.h>
12 #include <asm/smp.h>
13 #include <asm/spinlock.h>
15         .text
16         .align  4
18         /* This is called when the initial acquisition attempt of a spin
19          * lock fails.  The calling convention is weird, return address
20          * is in %o7 as usual but we agree with the caller to only touch
21          * and use %g2 as a temporary.  We are passed a ptr to the lock
22          * itself in %g1, %g4 must be restored into %o7 when we return,
23          * and the caller wants us to return to him at three instructions
24          * previous to the call instruction which got us here.  See how
25          * this is used in asm/spinlock.h if what I just said confuses
26          * you to no end.
27          */
28         .globl  ___spinlock_waitfor
29 ___spinlock_waitfor:
30 1:      orcc    %g2, 0x0, %g0
31         bne,a   1b
32          ldub   [%g1], %g2
33         ldstub  [%g1], %g2
34         jmpl    %o7 - 12, %g0
35          mov    %g4, %o7
37         /* Read/writer locks, as usual this is overly clever to make it
38          * as fast as possible.
39          */
41         /* caches... */
42 ___rw_read_enter_spin_on_wlock:
43         orcc    %g2, 0x0, %g0
44         be,a    ___rw_read_enter
45          ldstub [%g1 + 3], %g2
46         b       ___rw_read_enter_spin_on_wlock
47          ldub   [%g1 + 3], %g2
48 ___rw_read_exit_spin_on_wlock:
49         orcc    %g2, 0x0, %g0
50         be,a    ___rw_read_exit
51          ldstub [%g1 + 3], %g2
52         b       ___rw_read_exit_spin_on_wlock
53          ldub   [%g1 + 3], %g2
54 ___rw_write_enter_spin_on_wlock:
55         orcc    %g2, 0x0, %g0
56         be,a    ___rw_write_enter
57          ldstub [%g1 + 3], %g2
58         b       ___rw_write_enter_spin_on_wlock
59          ld     [%g1], %g2
61         .globl  ___rw_read_enter
62 ___rw_read_enter:
63         orcc    %g2, 0x0, %g0
64         bne,a   ___rw_read_enter_spin_on_wlock
65          ldub   [%g1 + 3], %g2
66         ld      [%g1], %g2
67         add     %g2, 1, %g2
68         st      %g2, [%g1]
69         retl
70          mov    %g4, %o7
72         .globl  ___rw_read_exit
73 ___rw_read_exit:
74         orcc    %g2, 0x0, %g0
75         bne,a   ___rw_read_exit_spin_on_wlock
76          ldub   [%g1 + 3], %g2
77         ld      [%g1], %g2
78         sub     %g2, 0x1ff, %g2
79         st      %g2, [%g1]
80         retl
81          mov    %g4, %o7
83         .globl  ___rw_write_enter
84 ___rw_write_enter:
85         orcc    %g2, 0x0, %g0
86         bne     ___rw_write_enter_spin_on_wlock
87          ld     [%g1], %g2
88         andncc  %g2, 0xff, %g0
89         bne,a   ___rw_write_enter_spin_on_wlock
90          stb    %g0, [%g1 + 3]
91         retl
92          mov    %g4, %o7