]> git.proxmox.com Git - mirror_ubuntu-bionic-kernel.git/blob - arch/sparc64/solaris/entry64.S
Linux-2.6.12-rc2
[mirror_ubuntu-bionic-kernel.git] / arch / sparc64 / solaris / entry64.S
1 /* $Id: entry64.S,v 1.7 2002/02/09 19:49:31 davem Exp $
2 * entry64.S: Solaris syscall emulation entry point.
3 *
4 * Copyright (C) 1996,1997,1998 Jakub Jelinek (jj@sunsite.mff.cuni.cz)
5 * Copyright (C) 1995,1997 David S. Miller (davem@caip.rutgers.edu)
6 * Copyright (C) 1996 Miguel de Icaza (miguel@nuclecu.unam.mx)
7 */
8
9 #include <linux/errno.h>
10
11 #include <asm/head.h>
12 #include <asm/asi.h>
13 #include <asm/smp.h>
14 #include <asm/ptrace.h>
15 #include <asm/page.h>
16 #include <asm/signal.h>
17 #include <asm/pgtable.h>
18 #include <asm/processor.h>
19 #include <asm/thread_info.h>
20
21 #include "conv.h"
22
23 #define NR_SYSCALLS 256
24
25 .text
26 solaris_syscall_trace:
27 call syscall_trace
28 nop
29 srl %i0, 0, %o0
30 mov %i4, %o4
31 srl %i1, 0, %o1
32 mov %i5, %o5
33 andcc %l3, 1, %g0
34 be,pt %icc, 2f
35 srl %i2, 0, %o2
36 b,pt %xcc, 2f
37 add %sp, PTREGS_OFF, %o0
38
39 solaris_sucks:
40 /* Solaris is a big system which needs to be able to do all the things
41 * in Inf+1 different ways */
42 add %i6, 0x5c, %o0
43 mov %i0, %g1
44 mov %i1, %i0
45 mov %i2, %i1
46 srl %o0, 0, %o0
47 mov %i3, %i2
48 movrz %g1, 256, %g1 /* Ensure we don't loop forever */
49 mov %i4, %i3
50 mov %i5, %i4
51 ba,pt %xcc, solaris_sparc_syscall
52 exen: lduwa [%o0] ASI_S, %i5
53
54 exenf: ba,pt %xcc, solaris_sparc_syscall
55 clr %i5
56
57 /* For shared binaries, binfmt_elf32 already sets up personality
58 and exec_domain. This is to handle static binaries as well */
59 solaris_reg:
60 call solaris_register
61 nop
62 ba,pt %xcc, 1f
63 mov %i4, %o4
64
65 linux_syscall_for_solaris:
66 sethi %hi(sys_call_table32), %l6
67 or %l6, %lo(sys_call_table32), %l6
68 sll %l3, 2, %l4
69 ba,pt %xcc, 10f
70 lduw [%l6 + %l4], %l3
71
72 /* Solaris system calls enter here... */
73 .align 32
74 .globl solaris_sparc_syscall, entry64_personality_patch
75 solaris_sparc_syscall:
76 entry64_personality_patch:
77 ldub [%g4 + 0x0], %l0
78 cmp %g1, 255
79 bg,pn %icc, solaris_unimplemented
80 srl %g1, 0, %g1
81 sethi %hi(solaris_sys_table), %l7
82 or %l7, %lo(solaris_sys_table), %l7
83 brz,pn %g1, solaris_sucks
84 mov %i4, %o4
85 sll %g1, 2, %l4
86 cmp %l0, 1
87 bne,pn %icc, solaris_reg
88 1: srl %i0, 0, %o0
89 lduw [%l7 + %l4], %l3
90 srl %i1, 0, %o1
91 ldx [%g6 + TI_FLAGS], %l5
92 cmp %l3, NR_SYSCALLS
93 bleu,a,pn %xcc, linux_syscall_for_solaris
94 nop
95 andcc %l3, 1, %g0
96 bne,a,pn %icc, 10f
97 add %sp, PTREGS_OFF, %o0
98 10: srl %i2, 0, %o2
99 mov %i5, %o5
100 andn %l3, 3, %l7
101 andcc %l5, _TIF_SYSCALL_TRACE, %g0
102 bne,pn %icc, solaris_syscall_trace
103 mov %i0, %l5
104 2: call %l7
105 srl %i3, 0, %o3
106 ret_from_solaris:
107 stx %o0, [%sp + PTREGS_OFF + PT_V9_I0]
108 ldx [%g6 + TI_FLAGS], %l6
109 sra %o0, 0, %o0
110 mov %ulo(TSTATE_XCARRY | TSTATE_ICARRY), %g2
111 ldx [%sp + PTREGS_OFF + PT_V9_TSTATE], %g3
112 cmp %o0, -ERESTART_RESTARTBLOCK
113 sllx %g2, 32, %g2
114 bgeu,pn %xcc, 1f
115 andcc %l6, _TIF_SYSCALL_TRACE, %l6
116
117 /* System call success, clear Carry condition code. */
118 andn %g3, %g2, %g3
119 stx %g3, [%sp + PTREGS_OFF + PT_V9_TSTATE]
120 bne,pn %icc, solaris_syscall_trace2
121 ldx [%sp + PTREGS_OFF + PT_V9_TNPC], %l1
122 andcc %l1, 1, %g0
123 bne,pn %icc, 2f
124 clr %l6
125 add %l1, 0x4, %l2
126 stx %l1, [%sp + PTREGS_OFF + PT_V9_TPC] ! pc = npc
127 call rtrap
128 stx %l2, [%sp + PTREGS_OFF + PT_V9_TNPC] !npc = npc+4
129
130 /* When tnpc & 1, this comes from setcontext and we don't want to advance pc */
131 2: andn %l1, 3, %l1
132 call rtrap
133 stx %l1, [%sp + PTREGS_OFF + PT_V9_TNPC] !npc = npc&~3
134
135 1:
136 /* System call failure, set Carry condition code.
137 * Also, get abs(errno) to return to the process.
138 */
139 sub %g0, %o0, %o0
140 or %g3, %g2, %g3
141 cmp %o0, ERANGE /* 0-ERANGE are identity mapped */
142 bleu,pt %icc, 1f
143 cmp %o0, EMEDIUMTYPE
144 bgu,pn %icc, 1f
145 sethi %hi(solaris_err_table), %l6
146 sll %o0, 2, %o0
147 or %l6, %lo(solaris_err_table), %l6
148 ldsw [%l6 + %o0], %o0
149 1: stx %o0, [%sp + PTREGS_OFF + PT_V9_I0]
150 mov 1, %l6
151 stx %g3, [%sp + PTREGS_OFF + PT_V9_TSTATE]
152 bne,pn %icc, solaris_syscall_trace2
153 ldx [%sp + PTREGS_OFF + PT_V9_TNPC], %l1
154 andcc %l1, 1, %g0
155 bne,pn %icc, 2b
156 add %l1, 0x4, %l2
157 stx %l1, [%sp + PTREGS_OFF + PT_V9_TPC] ! pc = npc
158 call rtrap
159 stx %l2, [%sp + PTREGS_OFF + PT_V9_TNPC] !npc = npc+4
160
161 solaris_syscall_trace2:
162 call syscall_trace
163 add %l1, 0x4, %l2 /* npc = npc+4 */
164 andcc %l1, 1, %g0
165 bne,pn %icc, 2b
166 nop
167 stx %l1, [%sp + PTREGS_OFF + PT_V9_TPC]
168 call rtrap
169 stx %l2, [%sp + PTREGS_OFF + PT_V9_TNPC]
170
171 /* This one is tricky, so that's why we do it in assembly */
172 .globl solaris_sigsuspend
173 solaris_sigsuspend:
174 call do_sol_sigsuspend
175 nop
176 brlz,pn %o0, ret_from_solaris
177 nop
178 call sys_sigsuspend
179 stx %o0, [%sp + PTREGS_OFF + PT_V9_I0]
180
181 .globl solaris_getpid
182 solaris_getpid:
183 call sys_getppid
184 nop
185 call sys_getpid
186 stx %o0, [%sp + PTREGS_OFF + PT_V9_I1]
187 b,pt %xcc, ret_from_solaris
188 nop
189
190 .globl solaris_getuid
191 solaris_getuid:
192 call sys_geteuid
193 nop
194 call sys_getuid
195 stx %o1, [%sp + PTREGS_OFF + PT_V9_I1]
196 b,pt %xcc, ret_from_solaris
197 nop
198
199 .globl solaris_getgid
200 solaris_getgid:
201 call sys_getegid
202 nop
203 call sys_getgid
204 stx %o1, [%sp + PTREGS_OFF + PT_V9_I1]
205 b,pt %xcc, ret_from_solaris
206 nop
207
208 .globl solaris_unimplemented
209 solaris_unimplemented:
210 call do_sol_unimplemented
211 add %sp, PTREGS_OFF, %o0
212 ba,pt %xcc, ret_from_solaris
213 nop
214
215 .section __ex_table,#alloc
216 .align 4
217 .word exen, exenf
218