amd64.il revision 7656:2621e50fdf4a
1246149Ssjg/*
2246149Ssjg * CDDL HEADER START
3246149Ssjg *
4246149Ssjg * The contents of this file are subject to the terms of the
5246149Ssjg * Common Development and Distribution License (the "License").
6246149Ssjg * You may not use this file except in compliance with the License.
7246149Ssjg *
8246149Ssjg * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9246149Ssjg * or http://www.opensolaris.org/os/licensing.
10246149Ssjg * See the License for the specific language governing permissions
11246149Ssjg * and limitations under the License.
12246149Ssjg *
13246149Ssjg * When distributing Covered Code, include this CDDL HEADER in each
14246149Ssjg * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15246149Ssjg * If applicable, add the following below this CDDL HEADER, with the
16246149Ssjg * fields enclosed by brackets "[]" replaced with your own identifying
17246149Ssjg * information: Portions Copyright [yyyy] [name of copyright owner]
18246149Ssjg *
19246149Ssjg * CDDL HEADER END
20246149Ssjg */
21246149Ssjg
22246149Ssjg/*
23246149Ssjg * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
24246149Ssjg * Use is subject to license terms.
25246149Ssjg */
26246149Ssjg
27246149Ssjg
28246149Ssjg/
29246149Ssjg/ Inline functions specific to the i86pc kernel running on bare metal.
30246149Ssjg/
31246149Ssjg
32246149Ssjg/
33246149Ssjg/ return value of cr3 register
34246149Ssjg/
35246149Ssjg	.inline	getcr3,0
36246149Ssjg	movq	%cr3, %rax
37246149Ssjg	.end
38246149Ssjg
39246149Ssjg/
40246149Ssjg/ reload cr3 register with its current value
41246149Ssjg/
42246149Ssjg	.inline	reload_cr3,0
43246149Ssjg	movq	%cr3, %rdi
44246149Ssjg	movq	%rdi, %cr3
45246149Ssjg	.end
46246149Ssjg
47246149Ssjg/
48246149Ssjg/ set cr3 register with new value
49246149Ssjg/
50246149Ssjg	.inline	setcr3,0
51246149Ssjg	movq	%rdi, %cr3
52246149Ssjg	.end
53246149Ssjg
54246149Ssjg/
55246149Ssjg/ return value of cr8 register
56246149Ssjg/
57246149Ssjg	.inline	getcr8,0
58246149Ssjg	movq	%cr8, %rax
59246149Ssjg	.end
60246149Ssjg
61246149Ssjg/
62246149Ssjg/ set cr8 register
63246149Ssjg/
64246149Ssjg	.inline	setcr8,0
65246149Ssjg	movq	%rdi, %cr8
66246149Ssjg	.end
67246149Ssjg
68246149Ssjg/
69246149Ssjg/ enable interrupts
70246149Ssjg/
71246149Ssjg	.inline	sti,0
72246149Ssjg	sti
73246149Ssjg	.end
74246149Ssjg
75246149Ssjg/
76246149Ssjg/ disable interrupts
77246149Ssjg/
78246149Ssjg	.inline cli,0
79246149Ssjg	cli
80246149Ssjg	.end
81246149Ssjg
82246149Ssjg/
83246149Ssjg/ disable interrupts and return value describing if interrupts were enabled
84246149Ssjg/
85246149Ssjg	.inline	clear_int_flag,0
86246149Ssjg	pushfq
87246149Ssjg	cli
88246149Ssjg	popq	%rax
89246149Ssjg	.end
90246149Ssjg
91246149Ssjg	.inline	intr_clear,0
92246149Ssjg	pushfq
93246149Ssjg	cli
94246149Ssjg	popq	%rax
95246149Ssjg	.end
96246149Ssjg
97246149Ssjg/
98246149Ssjg/ return the value of the flags register
99246149Ssjg/
100246149Ssjg	.inline	getflags,0
101246149Ssjg	pushfq
102246149Ssjg	popq	%rax
103246149Ssjg	.end
104246149Ssjg
105246149Ssjg/
106246149Ssjg/ restore interrupt enable flag to value returned from 'clear_int_flag' above
107246149Ssjg/
108246149Ssjg	.inline restore_int_flag,4
109246149Ssjg	testq	$0x200, %rdi
110246149Ssjg	jz	1f
111246149Ssjg	sti
112246149Ssjg1:
113246149Ssjg	.end
114246149Ssjg
115246149Ssjg	.inline intr_restore,4
116246149Ssjg	testq	$0x200, %rdi
117246149Ssjg	jz	1f
118246149Ssjg	sti
119246149Ssjg1:
120246149Ssjg	.end
121246149Ssjg
122246149Ssjg/
123246149Ssjg/ in and out
124246149Ssjg/
125246149Ssjg	.inline	inb,4
126246149Ssjg	movq	%rdi, %rdx
127246149Ssjg	xorq    %rax, %rax
128246149Ssjg	inb	(%dx)
129246149Ssjg	.end
130246149Ssjg
131246149Ssjg	.inline	inw,4
132246149Ssjg	movq	%rdi, %rdx
133246149Ssjg	xorq    %rax, %rax
134246149Ssjg	inw	(%dx)
135246149Ssjg	.end
136246149Ssjg
137246149Ssjg	.inline	inl,4
138246149Ssjg	movq	%rdi, %rdx
139246149Ssjg	xorq    %rax, %rax
140246149Ssjg	inl	(%dx)
141246149Ssjg	.end
142246149Ssjg
143246149Ssjg	.inline	outb,8
144246149Ssjg	movq	%rdi, %rdx
145246149Ssjg	movq	%rsi, %rax
146246149Ssjg	outb	(%dx)
147246149Ssjg	.end
148246149Ssjg
149246149Ssjg	.inline	outw,8
150246149Ssjg	movq	%rdi, %rdx
151246149Ssjg	movq	%rsi, %rax
152246149Ssjg	outw	(%dx)
153246149Ssjg	.end
154246149Ssjg
155246149Ssjg	.inline	outl,8
156246149Ssjg	movq	%rdi, %rdx
157246149Ssjg	movq	%rsi, %rax
158246149Ssjg	outl	(%dx)
159246149Ssjg	.end
160246149Ssjg
161246149Ssjg/*
162246149Ssjg * Call the halt instruction. This will put the CPU to sleep until
163246149Ssjg * it is again awoken via an interrupt.
164246149Ssjg * This function should be called with interrupts already disabled
165246149Ssjg * for the CPU.
166246149Ssjg * Note that "sti" will only enable interrupts at the end of the
167246149Ssjg * subsequent instruction...in this case: "hlt".
168246149Ssjg */
169246149Ssjg	.inline i86_halt,0
170246149Ssjg	sti
171246149Ssjg	hlt
172246149Ssjg	.end
173246149Ssjg/
174246149Ssjg/ execute the bsrw instruction
175246149Ssjg/
176246149Ssjg	.inline bsrw_insn,4
177246149Ssjg	xorl	%eax, %eax
178246149Ssjg	bsrw	%di, %ax
179246149Ssjg	.end
180246149Ssjg