xref: /titanic_51/usr/src/uts/sun4/ml/subr_asm.s (revision a1b5e537933659371285214eae1db2603e6364b4)
1/*
2 * CDDL HEADER START
3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License, Version 1.0 only
6 * (the "License").  You may not use this file except in compliance
7 * with the License.
8 *
9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10 * or http://www.opensolaris.org/os/licensing.
11 * See the License for the specific language governing permissions
12 * and limitations under the License.
13 *
14 * When distributing Covered Code, include this CDDL HEADER in each
15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16 * If applicable, add the following below this CDDL HEADER, with the
17 * fields enclosed by brackets "[]" replaced with your own identifying
18 * information: Portions Copyright [yyyy] [name of copyright owner]
19 *
20 * CDDL HEADER END
21 */
22/*
23 * Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
24 * Use is subject to license terms.
25 */
26
27#pragma ident	"%Z%%M%	%I%	%E% SMI"
28
29/*
30 * General machine architecture & implementation specific
31 * assembly language routines.
32 */
33#if defined(lint)
34#include <sys/types.h>
35#include <sys/machsystm.h>
36#include <sys/t_lock.h>
37#else	/* lint */
38#include "assym.h"
39#endif	/* lint */
40
41#include <sys/asm_linkage.h>
42#include <sys/async.h>
43#include <sys/machthread.h>
44
45#if defined(lint)
46caddr_t
47set_trap_table(void)
48{
49	return ((caddr_t)0);
50}
51#else /* lint */
52
53	ENTRY(set_trap_table)
54	set	trap_table, %o1
55	rdpr	%tba, %o0
56	wrpr	%o1, %tba
57	retl
58	wrpr	%g0, WSTATE_KERN, %wstate
59	SET_SIZE(set_trap_table)
60
61#endif /* lint */
62
63#if defined(lint)
64
65/*ARGSUSED*/
66void
67stphys(uint64_t physaddr, int value)
68{}
69
70/*ARGSUSED*/
71int
72ldphys(uint64_t physaddr)
73{ return (0); }
74
75/*ARGSUSED*/
76void
77stdphys(uint64_t physaddr, uint64_t value)
78{}
79
80/*ARGSUSED*/
81uint64_t
82lddphys(uint64_t physaddr)
83{ return (0x0ull); }
84
85/* ARGSUSED */
86void
87stphysio(u_longlong_t physaddr, uint_t value)
88{}
89
90/* ARGSUSED */
91uint_t
92ldphysio(u_longlong_t physaddr)
93{ return(0); }
94
95/* ARGSUSED */
96void
97sthphysio(u_longlong_t physaddr, ushort_t value)
98{}
99
100/* ARGSUSED */
101ushort_t
102ldhphysio(u_longlong_t physaddr)
103{ return(0); }
104
105/* ARGSUSED */
106void
107stbphysio(u_longlong_t physaddr, uchar_t value)
108{}
109
110/* ARGSUSED */
111uchar_t
112ldbphysio(u_longlong_t physaddr)
113{ return(0); }
114
115/*ARGSUSED*/
116void
117stdphysio(u_longlong_t physaddr, u_longlong_t value)
118{}
119
120/*ARGSUSED*/
121u_longlong_t
122lddphysio(u_longlong_t physaddr)
123{ return (0ull); }
124
125#else
126
127	! Store long word value at physical address
128	!
129	! void  stdphys(uint64_t physaddr, uint64_t value)
130	!
131	ENTRY(stdphys)
132	/*
133	 * disable interrupts, clear Address Mask to access 64 bit physaddr
134	 */
135	rdpr	%pstate, %o4
136	andn	%o4, PSTATE_IE | PSTATE_AM, %o5
137	wrpr	%o5, 0, %pstate
138	stxa	%o1, [%o0]ASI_MEM
139	retl
140	wrpr	%g0, %o4, %pstate	! restore earlier pstate register value
141	SET_SIZE(stdphys)
142
143
144	! Store long word value at physical i/o address
145	!
146	! void  stdphysio(u_longlong_t physaddr, u_longlong_t value)
147	!
148	ENTRY(stdphysio)
149	/*
150	 * disable interrupts, clear Address Mask to access 64 bit physaddr
151	 */
152	rdpr	%pstate, %o4
153	andn	%o4, PSTATE_IE | PSTATE_AM, %o5
154	wrpr	%o5, 0, %pstate		! clear IE, AM bits
155	stxa	%o1, [%o0]ASI_IO
156	retl
157	wrpr	%g0, %o4, %pstate	! restore earlier pstate register value
158	SET_SIZE(stdphysio)
159
160
161	!
162	! Load long word value at physical address
163	!
164	! uint64_t lddphys(uint64_t physaddr)
165	!
166	ENTRY(lddphys)
167	rdpr	%pstate, %o4
168	andn	%o4, PSTATE_IE | PSTATE_AM, %o5
169	wrpr	%o5, 0, %pstate
170	ldxa	[%o0]ASI_MEM, %o0
171	retl
172	wrpr	%g0, %o4, %pstate	! restore earlier pstate register value
173	SET_SIZE(lddphys)
174
175	!
176	! Load long word value at physical i/o address
177	!
178	! unsigned long long lddphysio(u_longlong_t physaddr)
179	!
180	ENTRY(lddphysio)
181	rdpr	%pstate, %o4
182	andn	%o4, PSTATE_IE | PSTATE_AM, %o5
183	wrpr	%o5, 0, %pstate	! clear IE, AM bits
184	ldxa	[%o0]ASI_IO, %o0
185	retl
186	wrpr	%g0, %o4, %pstate	! restore earlier pstate register value
187	SET_SIZE(lddphysio)
188
189	!
190	! Store value at physical address
191	!
192	! void  stphys(uint64_t physaddr, int value)
193	!
194	ENTRY(stphys)
195	rdpr	%pstate, %o4
196	andn	%o4, PSTATE_IE | PSTATE_AM, %o5
197	wrpr	%o5, 0, %pstate
198	sta	%o1, [%o0]ASI_MEM
199	retl
200	wrpr	%g0, %o4, %pstate	! restore earlier pstate register value
201	SET_SIZE(stphys)
202
203
204	!
205	! load value at physical address
206	!
207	! int   ldphys(uint64_t physaddr)
208	!
209	ENTRY(ldphys)
210	rdpr	%pstate, %o4
211	andn	%o4, PSTATE_IE | PSTATE_AM, %o5
212	wrpr	%o5, 0, %pstate
213	lda	[%o0]ASI_MEM, %o0
214	srl	%o0, 0, %o0	! clear upper 32 bits
215	retl
216	wrpr	%g0, %o4, %pstate	! restore earlier pstate register value
217	SET_SIZE(ldphys)
218
219	!
220	! Store value into physical address in I/O space
221	!
222	! void stphysio(u_longlong_t physaddr, uint_t value)
223	!
224	ENTRY_NP(stphysio)
225	rdpr	%pstate, %o4		/* read PSTATE reg */
226	andn	%o4, PSTATE_IE | PSTATE_AM, %o5
227	wrpr	%o5, 0, %pstate
228	stwa	%o1, [%o0]ASI_IO	/* store value via bypass ASI */
229	retl
230	wrpr	%g0, %o4, %pstate	/* restore the PSTATE */
231	SET_SIZE(stphysio)
232
233	!
234	! Store value into physical address in I/O space
235	!
236	! void sthphysio(u_longlong_t physaddr, ushort_t value)
237	!
238	ENTRY_NP(sthphysio)
239	rdpr	%pstate, %o4		/* read PSTATE reg */
240	andn	%o4, PSTATE_IE | PSTATE_AM, %o5
241	wrpr	%o5, 0, %pstate
242	stha	%o1, [%o0]ASI_IO	/* store value via bypass ASI */
243	retl
244	wrpr	%g0, %o4, %pstate		/* restore the PSTATE */
245	SET_SIZE(sthphysio)
246
247	!
248	! Store value into one byte physical address in I/O space
249	!
250	! void stbphysio(u_longlong_t physaddr, uchar_t value)
251	!
252	ENTRY_NP(stbphysio)
253	rdpr	%pstate, %o4		/* read PSTATE reg */
254	andn	%o4, PSTATE_IE | PSTATE_AM, %o5
255	wrpr	%o5, 0, %pstate
256	stba	%o1, [%o0]ASI_IO	/* store byte via bypass ASI */
257	retl
258	wrpr	%g0, %o4, %pstate	/* restore the PSTATE */
259	SET_SIZE(stbphysio)
260
261	!
262	! load value at physical address in I/O space
263	!
264	! uint_t   ldphysio(u_longlong_t physaddr)
265	!
266	ENTRY_NP(ldphysio)
267	rdpr	%pstate, %o4		/* read PSTATE reg */
268	andn	%o4, PSTATE_IE | PSTATE_AM, %o5
269	wrpr	%o5, 0, %pstate
270	lduwa	[%o0]ASI_IO, %o0	/* load value via bypass ASI */
271	retl
272	wrpr	%g0, %o4, %pstate	/* restore pstate */
273	SET_SIZE(ldphysio)
274
275	!
276	! load value at physical address in I/O space
277	!
278	! ushort_t   ldhphysio(u_longlong_t physaddr)
279	!
280	ENTRY_NP(ldhphysio)
281	rdpr	%pstate, %o4		/* read PSTATE reg */
282	andn	%o4, PSTATE_IE | PSTATE_AM, %o5
283	wrpr	%o5, 0, %pstate
284	lduha	[%o0]ASI_IO, %o0	/* load value via bypass ASI */
285	retl
286	wrpr	%g0, %o4, %pstate	/* restore pstate */
287	SET_SIZE(ldhphysio)
288
289	!
290	! load byte value at physical address in I/O space
291	!
292	! uchar_t   ldbphysio(u_longlong_t physaddr)
293	!
294	ENTRY_NP(ldbphysio)
295	rdpr	%pstate, %o4		/* read PSTATE reg */
296	andn	%o4, PSTATE_IE | PSTATE_AM, %o5
297	wrpr	%o5, 0, %pstate
298	lduba	[%o0]ASI_IO, %o0	/* load value via bypass ASI */
299	retl
300	wrpr	%g0, %o4, %pstate	/* restore pstate */
301	SET_SIZE(ldbphysio)
302#endif  /* lint */
303
304/*
305 * save_gsr(kfpu_t *fp)
306 * Store the graphics status register
307 */
308
309#if defined(lint) || defined(__lint)
310
311/* ARGSUSED */
312void
313save_gsr(kfpu_t *fp)
314{}
315
316#else	/* lint */
317
318	ENTRY_NP(save_gsr)
319	rd	%gsr, %g2			! save gsr
320	retl
321	stx	%g2, [%o0 + FPU_GSR]
322	SET_SIZE(save_gsr)
323
324#endif	/* lint */
325
326#if defined(lint) || defined(__lint)
327
328/* ARGSUSED */
329void
330restore_gsr(kfpu_t *fp)
331{}
332
333#else	/* lint */
334
335	ENTRY_NP(restore_gsr)
336	ldx	[%o0 + FPU_GSR], %g2
337	wr	%g2, %g0, %gsr
338	retl
339	nop
340	SET_SIZE(restore_gsr)
341
342#endif	/* lint */
343
344/*
345 * uint64_t
346 * _fp_read_pgsr()
347 * Get the graphics status register info from fp and return it
348 */
349
350#if defined(lint) || defined(__lint)
351
352/* ARGSUSED */
353uint64_t
354_fp_read_pgsr(kfpu_t *fp)
355{ return 0; }
356
357#else	/* lint */
358
359	ENTRY_NP(_fp_read_pgsr)
360	retl
361	rd	%gsr, %o0
362	SET_SIZE(_fp_read_pgsr)
363
364#endif	/* lint */
365
366
367/*
368 * uint64_t
369 * get_gsr(kfpu_t *fp)
370 * Get the graphics status register info from fp and return it
371 */
372
373#if defined(lint) || defined(__lint)
374
375/* ARGSUSED */
376uint64_t
377get_gsr(kfpu_t *fp)
378{ return 0; }
379
380#else	/* lint */
381
382	ENTRY_NP(get_gsr)
383	retl
384	ldx	[%o0 + FPU_GSR], %o0
385	SET_SIZE(get_gsr)
386
387#endif
388
389/*
390 * _fp_write_pgsr(uint64_t *buf, kfpu_t *fp)
391 * Set the graphics status register info to fp from buf
392 */
393
394#if defined(lint) || defined(__lint)
395
396/* ARGSUSED */
397void
398_fp_write_pgsr(uint64_t buf, kfpu_t *fp)
399{}
400
401#else	/* lint */
402
403	ENTRY_NP(_fp_write_pgsr)
404	retl
405	mov	%o0, %gsr
406	SET_SIZE(_fp_write_pgsr)
407
408#endif	/* lint */
409
410/*
411 * set_gsr(uint64_t buf, kfpu_t *fp)
412 * Set the graphics status register info to fp from buf
413 */
414
415#if defined(lint) || defined(__lint)
416
417/* ARGSUSED */
418void
419set_gsr(uint64_t buf, kfpu_t *fp)
420{}
421
422#else	/* lint */
423
424	ENTRY_NP(set_gsr)
425	retl
426	stx	%o0, [%o1 + FPU_GSR]
427	SET_SIZE(set_gsr)
428
429#endif	/* lint */
430
431#if defined(lint) || defined(__lint)
432void
433kdi_cpu_index(void)
434{
435}
436
437#else	/* lint */
438
439	ENTRY_NP(kdi_cpu_index)
440	CPU_INDEX(%g1, %g2)
441	jmp	%g7
442	nop
443	SET_SIZE(kdi_cpu_index)
444
445#endif	/* lint */
446