source: mainline/kernel/arch/sparc64/include/asm.h@ a2a5529

lfn serial ticket/834-toolchain-update topic/msim-upgrade topic/simplify-dev-export
Last change on this file since a2a5529 was a2a5529, checked in by Jakub Vana <jakub.vana@…>, 17 years ago

Support for serial port console on IA64 as a compensation for keyboard - based on SPARC ns16550 driver

  • Property mode set to 100644
File size: 8.7 KB
RevLine 
[2a99fa8]1/*
[df4ed85]2 * Copyright (c) 2005 Jakub Jermar
[2a99fa8]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 *
9 * - Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * - Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 * - The name of the author may not be used to endorse or promote products
15 * derived from this software without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
18 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
19 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
20 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
21 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
22 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 */
28
[0ffa3ef5]29/** @addtogroup sparc64
[b45c443]30 * @{
31 */
32/** @file
33 */
34
[0ffa3ef5]35#ifndef KERN_sparc64_ASM_H_
36#define KERN_sparc64_ASM_H_
[2a99fa8]37
[b3f8fb7]38#include <arch/arch.h>
[2a99fa8]39#include <arch/types.h>
[f4c2b6a]40#include <typedefs.h>
[b3f8fb7]41#include <align.h>
[75e1db0]42#include <arch/register.h>
[2a99fa8]43#include <config.h>
[b254b3b]44#include <arch/stack.h>
[2a99fa8]45
[a2a5529]46typedef uint64_t ioport_t;
47
48
49static inline void outb(ioport_t port,uint8_t v)
50{
51 *((uint8_t *)(port)) = v;
52}
53
54static inline void outw(ioport_t port,uint16_t v)
55{
56 *((uint16_t *)(port)) = v;
57}
58
59static inline void outl(ioport_t port,uint32_t v)
60{
61 *((uint32_t *)(port)) = v;
62}
63
64
65
66static inline uint8_t inb(ioport_t port)
67{
68 return *((uint8_t *)(port));
69}
70
71static inline uint16_t inw(ioport_t port)
72{
73 return *((uint16_t *)(port));
74}
75
76static inline uint32_t inl(ioport_t port)
77{
78 return *((uint32_t *)(port));
79}
80
81
82
83
84
[75e1db0]85/** Read Processor State register.
86 *
87 * @return Value of PSTATE register.
88 */
[7f1c620]89static inline uint64_t pstate_read(void)
[75e1db0]90{
[7f1c620]91 uint64_t v;
[75e1db0]92
[e7b7be3f]93 asm volatile ("rdpr %%pstate, %0\n" : "=r" (v));
[75e1db0]94
95 return v;
96}
97
98/** Write Processor State register.
99 *
[abbc16e]100 * @param v New value of PSTATE register.
[75e1db0]101 */
[7f1c620]102static inline void pstate_write(uint64_t v)
[75e1db0]103{
[e7b7be3f]104 asm volatile ("wrpr %0, %1, %%pstate\n" : : "r" (v), "i" (0));
[75e1db0]105}
106
[096d11e5]107/** Read TICK_compare Register.
108 *
109 * @return Value of TICK_comapre register.
110 */
[7f1c620]111static inline uint64_t tick_compare_read(void)
[096d11e5]112{
[7f1c620]113 uint64_t v;
[096d11e5]114
[e7b7be3f]115 asm volatile ("rd %%tick_cmpr, %0\n" : "=r" (v));
[096d11e5]116
117 return v;
118}
119
120/** Write TICK_compare Register.
121 *
[abbc16e]122 * @param v New value of TICK_comapre register.
[096d11e5]123 */
[7f1c620]124static inline void tick_compare_write(uint64_t v)
[096d11e5]125{
[e7b7be3f]126 asm volatile ("wr %0, %1, %%tick_cmpr\n" : : "r" (v), "i" (0));
[096d11e5]127}
128
129/** Read TICK Register.
130 *
131 * @return Value of TICK register.
132 */
[7f1c620]133static inline uint64_t tick_read(void)
[096d11e5]134{
[7f1c620]135 uint64_t v;
[096d11e5]136
[e7b7be3f]137 asm volatile ("rdpr %%tick, %0\n" : "=r" (v));
[096d11e5]138
139 return v;
140}
141
142/** Write TICK Register.
143 *
[abbc16e]144 * @param v New value of TICK register.
[096d11e5]145 */
[7f1c620]146static inline void tick_write(uint64_t v)
[096d11e5]147{
[e7b7be3f]148 asm volatile ("wrpr %0, %1, %%tick\n" : : "r" (v), "i" (0));
[096d11e5]149}
150
[6eabb6e6]151/** Read FPRS Register.
152 *
153 * @return Value of FPRS register.
154 */
155static inline uint64_t fprs_read(void)
156{
157 uint64_t v;
158
[e7b7be3f]159 asm volatile ("rd %%fprs, %0\n" : "=r" (v));
[6eabb6e6]160
161 return v;
162}
163
164/** Write FPRS Register.
165 *
166 * @param v New value of FPRS register.
167 */
168static inline void fprs_write(uint64_t v)
169{
[e7b7be3f]170 asm volatile ("wr %0, %1, %%fprs\n" : : "r" (v), "i" (0));
[6eabb6e6]171}
172
[39494010]173/** Read SOFTINT Register.
174 *
175 * @return Value of SOFTINT register.
176 */
[7f1c620]177static inline uint64_t softint_read(void)
[39494010]178{
[7f1c620]179 uint64_t v;
[39494010]180
[e7b7be3f]181 asm volatile ("rd %%softint, %0\n" : "=r" (v));
[39494010]182
183 return v;
184}
185
186/** Write SOFTINT Register.
187 *
[abbc16e]188 * @param v New value of SOFTINT register.
[39494010]189 */
[7f1c620]190static inline void softint_write(uint64_t v)
[39494010]191{
[e7b7be3f]192 asm volatile ("wr %0, %1, %%softint\n" : : "r" (v), "i" (0));
[39494010]193}
[75e1db0]194
[1120276]195/** Write CLEAR_SOFTINT Register.
196 *
197 * Bits set in CLEAR_SOFTINT register will be cleared in SOFTINT register.
198 *
[abbc16e]199 * @param v New value of CLEAR_SOFTINT register.
[1120276]200 */
[7f1c620]201static inline void clear_softint_write(uint64_t v)
[1120276]202{
[e7b7be3f]203 asm volatile ("wr %0, %1, %%clear_softint\n" : : "r" (v), "i" (0));
[1120276]204}
205
[f9a56c0]206/** Write SET_SOFTINT Register.
207 *
208 * Bits set in SET_SOFTINT register will be set in SOFTINT register.
209 *
210 * @param v New value of SET_SOFTINT register.
211 */
212static inline void set_softint_write(uint64_t v)
213{
[e7b7be3f]214 asm volatile ("wr %0, %1, %%set_softint\n" : : "r" (v), "i" (0));
[f9a56c0]215}
216
[2a99fa8]217/** Enable interrupts.
218 *
219 * Enable interrupts and return previous
220 * value of IPL.
221 *
222 * @return Old interrupt priority level.
223 */
224static inline ipl_t interrupts_enable(void) {
[75e1db0]225 pstate_reg_t pstate;
[7f1c620]226 uint64_t value;
[75e1db0]227
228 value = pstate_read();
229 pstate.value = value;
230 pstate.ie = true;
231 pstate_write(pstate.value);
232
233 return (ipl_t) value;
[2a99fa8]234}
235
236/** Disable interrupts.
237 *
238 * Disable interrupts and return previous
239 * value of IPL.
240 *
241 * @return Old interrupt priority level.
242 */
243static inline ipl_t interrupts_disable(void) {
[75e1db0]244 pstate_reg_t pstate;
[7f1c620]245 uint64_t value;
[75e1db0]246
247 value = pstate_read();
248 pstate.value = value;
249 pstate.ie = false;
250 pstate_write(pstate.value);
251
252 return (ipl_t) value;
[2a99fa8]253}
254
255/** Restore interrupt priority level.
256 *
257 * Restore IPL.
258 *
259 * @param ipl Saved interrupt priority level.
260 */
261static inline void interrupts_restore(ipl_t ipl) {
[75e1db0]262 pstate_reg_t pstate;
263
264 pstate.value = pstate_read();
265 pstate.ie = ((pstate_reg_t) ipl).ie;
266 pstate_write(pstate.value);
[2a99fa8]267}
268
269/** Return interrupt priority level.
270 *
271 * Return IPL.
272 *
273 * @return Current interrupt priority level.
274 */
275static inline ipl_t interrupts_read(void) {
[75e1db0]276 return (ipl_t) pstate_read();
[2a99fa8]277}
278
279/** Return base address of current stack.
280 *
281 * Return the base address of the current stack.
282 * The stack is assumed to be STACK_SIZE bytes long.
283 * The stack must start on page boundary.
284 */
[7f1c620]285static inline uintptr_t get_stack_base(void)
[2a99fa8]286{
[b254b3b]287 uintptr_t unbiased_sp;
[437ee6a4]288
[e7b7be3f]289 asm volatile ("add %%sp, %1, %0\n" : "=r" (unbiased_sp) : "i" (STACK_BIAS));
[437ee6a4]290
[b254b3b]291 return ALIGN_DOWN(unbiased_sp, STACK_SIZE);
[2a99fa8]292}
293
[2cf87e50]294/** Read Version Register.
295 *
296 * @return Value of VER register.
297 */
[7f1c620]298static inline uint64_t ver_read(void)
[2cf87e50]299{
[7f1c620]300 uint64_t v;
[2cf87e50]301
[e7b7be3f]302 asm volatile ("rdpr %%ver, %0\n" : "=r" (v));
[2cf87e50]303
304 return v;
305}
306
[d78d603]307/** Read Trap Program Counter register.
[8ac5fe7]308 *
[d78d603]309 * @return Current value in TPC.
[8ac5fe7]310 */
[d78d603]311static inline uint64_t tpc_read(void)
[8ac5fe7]312{
[7f1c620]313 uint64_t v;
[8ac5fe7]314
[e7b7be3f]315 asm volatile ("rdpr %%tpc, %0\n" : "=r" (v));
[8ac5fe7]316
317 return v;
318}
319
[d78d603]320/** Read Trap Level register.
[b6fba84]321 *
[d78d603]322 * @return Current value in TL.
[b6fba84]323 */
[d78d603]324static inline uint64_t tl_read(void)
[b6fba84]325{
[7f1c620]326 uint64_t v;
[b6fba84]327
[e7b7be3f]328 asm volatile ("rdpr %%tl, %0\n" : "=r" (v));
[b6fba84]329
330 return v;
331}
332
[d78d603]333/** Read Trap Base Address register.
[7cb53f62]334 *
[d78d603]335 * @return Current value in TBA.
[7cb53f62]336 */
[d78d603]337static inline uint64_t tba_read(void)
[7cb53f62]338{
[7f1c620]339 uint64_t v;
[7cb53f62]340
[e7b7be3f]341 asm volatile ("rdpr %%tba, %0\n" : "=r" (v));
[7cb53f62]342
343 return v;
344}
[b6fba84]345
[8ac5fe7]346/** Write Trap Base Address register.
347 *
[abbc16e]348 * @param v New value of TBA.
[8ac5fe7]349 */
[7f1c620]350static inline void tba_write(uint64_t v)
[8ac5fe7]351{
[e7b7be3f]352 asm volatile ("wrpr %0, %1, %%tba\n" : : "r" (v), "i" (0));
[8ac5fe7]353}
354
[7f1c620]355/** Load uint64_t from alternate space.
[b00fdde]356 *
357 * @param asi ASI determining the alternate space.
358 * @param va Virtual address within the ASI.
359 *
360 * @return Value read from the virtual address in the specified address space.
361 */
[7f1c620]362static inline uint64_t asi_u64_read(asi_t asi, uintptr_t va)
[b00fdde]363{
[7f1c620]364 uint64_t v;
[b00fdde]365
[e7b7be3f]366 asm volatile ("ldxa [%1] %2, %0\n" : "=r" (v) : "r" (va), "i" ((unsigned) asi));
[b00fdde]367
368 return v;
369}
370
[7f1c620]371/** Store uint64_t to alternate space.
[b00fdde]372 *
373 * @param asi ASI determining the alternate space.
374 * @param va Virtual address within the ASI.
375 * @param v Value to be written.
376 */
[7f1c620]377static inline void asi_u64_write(asi_t asi, uintptr_t va, uint64_t v)
[b00fdde]378{
[e7b7be3f]379 asm volatile ("stxa %0, [%1] %2\n" : : "r" (v), "r" (va), "i" ((unsigned) asi) : "memory");
[b00fdde]380}
381
[0fa6044]382/** Flush all valid register windows to memory. */
383static inline void flushw(void)
384{
[e7b7be3f]385 asm volatile ("flushw\n");
[0fa6044]386}
387
[fd85ae5]388/** Switch to nucleus by setting TL to 1. */
389static inline void nucleus_enter(void)
390{
[e7b7be3f]391 asm volatile ("wrpr %g0, 1, %tl\n");
[fd85ae5]392}
393
394/** Switch from nucleus by setting TL to 0. */
395static inline void nucleus_leave(void)
396{
[e7b7be3f]397 asm volatile ("wrpr %g0, %g0, %tl\n");
[fd85ae5]398}
399
[45b26dad]400/** Read UPA_CONFIG register.
401 *
402 * @return Value of the UPA_CONFIG register.
403 */
404static inline uint64_t upa_config_read(void)
405{
406 return asi_u64_read(ASI_UPA_CONFIG, 0);
407}
408
[e11ae91]409extern void cpu_halt(void);
410extern void cpu_sleep(void);
[9a5b556]411extern void asm_delay_loop(const uint32_t usec);
[e11ae91]412
413extern uint64_t read_from_ag_g7(void);
414extern void write_to_ag_g6(uint64_t val);
415extern void write_to_ag_g7(uint64_t val);
416extern void write_to_ig_g6(uint64_t val);
[2a99fa8]417
[cfa70add]418extern void switch_to_userspace(uint64_t pc, uint64_t sp, uint64_t uarg);
[ed166f7]419
[2a99fa8]420#endif
[b45c443]421
[0ffa3ef5]422/** @}
[b45c443]423 */
Note: See TracBrowser for help on using the repository browser.