4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
22 * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
23 * Use is subject to license terms.
26 #include <sys/asm_linkage.h>
27 #include <sys/asm_misc.h>
29 #if defined(lint) || defined(__lint)
30 #include <sys/types.h>
35 * Implementation as specific by ACPI 3.0 specification
38 * Global Lock Structure within the FACS
40 * |-----------------------------------------------------------------------|
41 * | Field | Bit Length | Bit Offset | Description |
42 * |---------|------------|------------|-----------------------------------|
43 * | Pending | 1 | 0 | Non-zero indicates that a request |
44 * | | | | for ownership of the global lock |
45 * | | | | is pending. |
46 * |---------|------------|------------|-----------------------------------|
47 * | Owned | 1 | 1 | Non-zero indicates that the Global|
48 * | | | | lock is owned. |
49 * |---------|------------|------------|-----------------------------------|
50 * | Reserved| 30 | 2 | Reserved for future use |
51 * |---------|------------|------------|-----------------------------------|
54 /* Offset of GlobalLock element in FACS structure */
55 #define GlobalLock 0x10
57 #if defined(lint) || defined(__lint)
61 __acpi_acquire_global_lock
(void
*Facs
)
67 ENTRY
(__acpi_acquire_global_lock
)
68 movq $
0xff, %rax
/ error return if FACS is null
69 orq
%rdi
, %rdi
/ %rdi contains pointer to FACS
71 leaq GlobalLock
(%rdi
), %rdi
/ make
%rdi point at the lock
73 movl
(%rdi
), %eax
/ get current value of Global Lock
75 andl $
0xFFFFFFFE, %edx
/ Clear pending bit
76 btsl $
1, %edx
/ Check
and set owner bit
77 adcl $
0, %edx
/ If owned
, set pending bit
79 cmpxchgl
%edx
, (%rdi
) / Attempt to set new value
80 jnz
0b / If
not set
, try again
81 cmpb $
3, %dl
/ Was it acquired
or marked pending?
82 sbbq
%rax
, %rax
/ acquired
= -1, pending
= 0
85 SET_SIZE
(__acpi_acquire_global_lock
)
89 ENTRY
(__acpi_acquire_global_lock
)
90 movl $
0xff, %eax
/ error return if FACS is null
91 movl
4(%esp
), %ecx
/ %ecx contains pointer to FACS
94 leal GlobalLock
(%ecx
), %ecx
/ make
%ecx point at the lock
98 andl $
0xFFFFFFFE, %edx
102 cmpxchgl
%edx
, (%ecx
)
108 SET_SIZE
(__acpi_acquire_global_lock
)
115 #if defined(lint) || defined(__lint)
119 __acpi_release_global_lock
(void
*Facs
)
125 ENTRY
(__acpi_release_global_lock
)
126 xorq
%rax
, %rax
/ error return if FACS is null
127 orq
%rdi
, %rdi
/ %rdi contains pointer to FACS
129 leaq GlobalLock
(%rdi
), %rdi
/ make
%rdi point at the lock
133 andl $
0xFFFFFFFC, %edx
135 cmpxchgl
%edx
, (%rdi
)
140 SET_SIZE
(__acpi_release_global_lock
)
142 #elif defined(__i386)
144 ENTRY
(__acpi_release_global_lock
)
145 xorl
%eax
, %eax
/ error return if FACS is null
146 movl
4(%esp
), %ecx
/ %ecx contains pointer to FACS
149 leal GlobalLock
(%ecx
), %ecx
/ make
%ecx point at the lock
153 andl $
0xFFFFFFFC, %edx
155 cmpxchgl
%edx
, (%ecx
)
160 SET_SIZE
(__acpi_release_global_lock
)
168 * execute WBINVD instruction
171 #if defined(lint) || defined(__lint)
183 SET_SIZE
(__acpi_wbinvd
)