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 (the "License").
6 * You may not use this file except in compliance with the License.
7 *
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.
12 *
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]
18 *
19 * CDDL HEADER END
20 */
21
22/*
23 * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
24 * Use is subject to license terms.
25 */
26/*
27 * Copyright (c) 2009, Intel Corporation.
28 * All rights reserved.
29 */
30
31#ifndef	_SYS_ACPIDEV_RSC_H
32#define	_SYS_ACPIDEV_RSC_H
33#include <sys/types.h>
34#include <sys/obpdefs.h>
35#include <sys/sunddi.h>
36#include <sys/acpi/acpi.h>
37#include <sys/acpica.h>
38
39#ifdef __cplusplus
40extern "C" {
41#endif
42
43/* ACPI bus range structure. */
44typedef struct acpidev_bus_range {
45	uint_t	bus_start;
46	uint_t	bus_end;
47} acpidev_bus_range_t;
48
49/*
50 * This structure is modeled after the 1275 "reg" property and
51 * "assigned-addresses" property for PCI device nodes.
52 * There's no standard definition available for ACPI devices.
53 * This structure is used to store resources returned by the ACPI
54 * _CRS method.
55 *
56 * The physical address format is:
57 *         Bit#:      33222222 22221111 11111100 00000000
58 *                    10987654 32109876 54321098 76543210
59 * phys_hi cell:      xxxxxxxx xxxxxxxx xxxxxxxx TSxxxTTT
60 * phys_hi(memory):   xxxxxxxx xxxxxxxx wxxxxxcc --xxx000
61 * phys_hi(io):       xxxxxxxx xxxxxxxx sdxxxxaa --xxx001
62 * phys_mid cell:     hhhhhhhh hhhhhhhh hhhhhhhh hhhhhhhh
63 * phys_low cell:     llllllll llllllll llllllll llllllll
64 *
65 * TTT        is type of resource. Such as MEMORY, IO etc.
66 * S          is 1 if address range is subtractive decoding
67 * T          is 1 if resource type is different on primary and
68 *	      secondary bus
69 * cc         is memory coherence type
70 * w          is 1 if memory is writable
71 * aa         ranges of decoded ports, ISA only, non-ISA only or full.
72 * d          is 1 if IO port decode 16 bit address, otherwise 10 bits.
73 * s          is 1 if translation is sparse.
74 * hh...hhh   is the 32-bit unsigned number
75 * ll...lll   is the 32-bit unsigned number
76 *
77 * The physical size format is:
78 *
79 * size_hi cell:  hhhhhhhh hhhhhhhh hhhhhhhh hhhhhhhh
80 * size_low cell: llllllll llllllll llllllll llllllll
81 *
82 * hh...hhh   is the 32-bit unsigned number
83 * ll...lll   is the 32-bit unsigned number
84 */
85typedef struct acpidev_phys_spec {
86	uint_t	phys_hi;		/* resource address, hi word */
87	uint_t	phys_mid;		/* resource address, middle word */
88	uint_t	phys_low;		/* resource address, low word */
89	uint_t	size_hi;		/* high word of size field */
90	uint_t	size_low;		/* low word of size field */
91} acpidev_phys_spec_t;
92
93typedef struct acpidev_phys_spec	acpidev_regspec_t;
94
95#define	ACPIDEV_REG_TYPE_M		0x00000007
96#define	ACPIDEV_REG_TYPE_MEMORY		0x00000000
97#define	ACPIDEV_REG_TYPE_IO		0x00000001
98#define	ACPIDEV_REG_SUB_DEC		0x00000040
99#define	ACPIDEV_REG_TRANSLATED		0x00000080
100
101#define	ACPIDEV_REG_MEM_COHERENT_M	0x00000300
102#define	ACPIDEV_REG_MEM_COHERENT_NC	0x00000000	/* Non-cachable */
103#define	ACPIDEV_REG_MEM_COHERENT_CA	0x00000100	/* Cachable */
104#define	ACPIDEV_REG_MEM_COHERENT_WC	0x00000200	/* Write-combining */
105#define	ACPIDEV_REG_MEM_COHERENT_PF	0x00000300	/* Prefectable */
106#define	ACPIDEV_REG_MEM_WRITABLE	0x00008000	/* Writable */
107
108#define	ACPIDEV_REG_IO_RANGE_M		0x00000300
109#define	ACPIDEV_REG_IO_RANGE_NONISA	0x00000100
110#define	ACPIDEV_REG_IO_RANGE_ISA	0x00000200
111#define	ACPIDEV_REG_IO_RANGE_FULL	0x00000300
112#define	ACPIDEV_REG_IO_DECODE16		0x00004000	/* Decode 16bit addr. */
113#define	ACPIDEV_REG_IO_SPARSE		0x00008000 /* Sparse translation. */
114
115typedef struct acpidev_ranges {
116	uint_t	child_hi;		/* child's address, hi word */
117	uint_t	child_mid;		/* child's address, middle word */
118	uint_t	child_low;		/* child's address, low word */
119	uint_t	parent_hi;		/* parent's address, hi word */
120	uint_t	parent_mid;		/* parent's address, middle word */
121	uint_t	parent_low;		/* parent's address, low word */
122	uint_t	size_hi;		/* high word of size field */
123	uint_t	size_low;		/* low word of size field */
124} acpidev_ranges_t;
125
126#ifdef	_KERNEL
127
128/* Maximum possible number of IRQs. */
129#define	ACPIDEV_RES_IRQ_MAX		16
130/* Maximum possible number of DMAs. */
131#define	ACPIDEV_RES_DMA_MAX		8
132
133/* Forward declaration */
134typedef	struct acpidev_resource_handle	*acpidev_resource_handle_t;
135
136/*
137 * Resource handler relative interfaces.
138 * Return values of acpidev_resource_get_xxx interfaces:
139 * AE_OK: succeed with resources stored in buffer and count updated.
140 * AE_LIMIT: buffer is too small, count updated to number of resources.
141 * AE_BAD_PARAMETER: invalid parameter
142 */
143extern acpidev_resource_handle_t acpidev_resource_handle_alloc(
144    boolean_t consumer);
145extern void acpidev_resource_handle_free(acpidev_resource_handle_t rhdl);
146
147extern ACPI_STATUS acpidev_resource_insert_reg(acpidev_resource_handle_t rhdl,
148    acpidev_regspec_t *regp);
149extern ACPI_STATUS acpidev_resource_get_regs(acpidev_resource_handle_t rhdl,
150    uint_t mask, uint_t value, acpidev_regspec_t *regp, uint_t *cntp);
151extern uint_t acpidev_resource_get_reg_count(acpidev_resource_handle_t rhdl,
152    uint_t mask, uint_t value);
153
154extern ACPI_STATUS acpidev_resource_insert_range(acpidev_resource_handle_t rhdl,
155    acpidev_ranges_t *rangep);
156extern ACPI_STATUS acpidev_resource_get_ranges(acpidev_resource_handle_t rhdl,
157    uint_t mask, uint_t value, acpidev_ranges_t *rangep, uint_t *cntp);
158extern uint_t acpidev_resource_get_range_count(acpidev_resource_handle_t rhdl,
159    uint_t mask, uint_t value);
160
161extern ACPI_STATUS acpidev_resource_insert_bus(acpidev_resource_handle_t rhdl,
162    acpidev_bus_range_t *busp);
163extern ACPI_STATUS acpidev_resource_get_buses(acpidev_resource_handle_t rhdl,
164    acpidev_bus_range_t *busp, uint_t *cntp);
165extern uint_t acpidev_resource_get_bus_count(acpidev_resource_handle_t rhdl);
166
167extern ACPI_STATUS acpidev_resource_insert_dma(acpidev_resource_handle_t rhdl,
168    int dma);
169extern ACPI_STATUS acpidev_resource_get_dmas(acpidev_resource_handle_t rhdl,
170    uint_t *dmap, uint_t *cntp);
171extern uint_t acpidev_resource_get_dma_count(acpidev_resource_handle_t rhdl);
172
173extern ACPI_STATUS acpidev_resource_insert_irq(acpidev_resource_handle_t rhdl,
174    int irq);
175extern ACPI_STATUS acpidev_resource_get_irqs(acpidev_resource_handle_t rhdl,
176    uint_t *irqp, uint_t *cntp);
177extern uint_t acpidev_resource_get_irq_count(acpidev_resource_handle_t rhdl);
178
179/*
180 * Walk resources returned by 'method' and store parsed resources into rhdlp.
181 * Caller needs to release rhdlp after using it.
182 * Return AE_OK on success with resource handle stored in 'rhdlp'.
183 */
184extern ACPI_STATUS acpidev_resource_walk(ACPI_HANDLE hdl, char *method,
185    boolean_t consumer, acpidev_resource_handle_t *rhdlp);
186
187/*
188 * Walk resources returned by the ACPI _CRS method and create device properties.
189 * Create 'reg', 'assigned-addresses', 'dma-channels' and 'interrupts'
190 * properties for resource consumer.
191 * Create 'ranges' and 'bus-range' properties for resource producer.
192 */
193extern ACPI_STATUS acpidev_resource_process(acpidev_walk_info_t *infop,
194    boolean_t consumer);
195
196#endif	/* _KERNEL */
197
198#ifdef __cplusplus
199}
200#endif
201
202#endif	/* _SYS_ACPIDEV_RSC_H */
203