diff options
Diffstat (limited to 'drivers/acpi/resources/rsio.c')
-rw-r--r-- | drivers/acpi/resources/rsio.c | 545 |
1 files changed, 545 insertions, 0 deletions
diff --git a/drivers/acpi/resources/rsio.c b/drivers/acpi/resources/rsio.c new file mode 100644 index 000000000000..972c746d37e4 --- /dev/null +++ b/drivers/acpi/resources/rsio.c | |||
@@ -0,0 +1,545 @@ | |||
1 | /******************************************************************************* | ||
2 | * | ||
3 | * Module Name: rsio - IO and DMA resource descriptors | ||
4 | * | ||
5 | ******************************************************************************/ | ||
6 | |||
7 | /* | ||
8 | * Copyright (C) 2000 - 2005, R. Byron Moore | ||
9 | * All rights reserved. | ||
10 | * | ||
11 | * Redistribution and use in source and binary forms, with or without | ||
12 | * modification, are permitted provided that the following conditions | ||
13 | * are met: | ||
14 | * 1. Redistributions of source code must retain the above copyright | ||
15 | * notice, this list of conditions, and the following disclaimer, | ||
16 | * without modification. | ||
17 | * 2. Redistributions in binary form must reproduce at minimum a disclaimer | ||
18 | * substantially similar to the "NO WARRANTY" disclaimer below | ||
19 | * ("Disclaimer") and any redistribution must be conditioned upon | ||
20 | * including a substantially similar Disclaimer requirement for further | ||
21 | * binary redistribution. | ||
22 | * 3. Neither the names of the above-listed copyright holders nor the names | ||
23 | * of any contributors may be used to endorse or promote products derived | ||
24 | * from this software without specific prior written permission. | ||
25 | * | ||
26 | * Alternatively, this software may be distributed under the terms of the | ||
27 | * GNU General Public License ("GPL") version 2 as published by the Free | ||
28 | * Software Foundation. | ||
29 | * | ||
30 | * NO WARRANTY | ||
31 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS | ||
32 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT | ||
33 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR | ||
34 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT | ||
35 | * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | ||
36 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | ||
37 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||
38 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||
39 | * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING | ||
40 | * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE | ||
41 | * POSSIBILITY OF SUCH DAMAGES. | ||
42 | */ | ||
43 | |||
44 | |||
45 | #include <acpi/acpi.h> | ||
46 | #include <acpi/acresrc.h> | ||
47 | |||
48 | #define _COMPONENT ACPI_RESOURCES | ||
49 | ACPI_MODULE_NAME ("rsio") | ||
50 | |||
51 | |||
52 | /******************************************************************************* | ||
53 | * | ||
54 | * FUNCTION: acpi_rs_io_resource | ||
55 | * | ||
56 | * PARAMETERS: byte_stream_buffer - Pointer to the resource input byte | ||
57 | * stream | ||
58 | * bytes_consumed - Pointer to where the number of bytes | ||
59 | * consumed the byte_stream_buffer is | ||
60 | * returned | ||
61 | * output_buffer - Pointer to the return data buffer | ||
62 | * structure_size - Pointer to where the number of bytes | ||
63 | * in the return data struct is returned | ||
64 | * | ||
65 | * RETURN: Status | ||
66 | * | ||
67 | * DESCRIPTION: Take the resource byte stream and fill out the appropriate | ||
68 | * structure pointed to by the output_buffer. Return the | ||
69 | * number of bytes consumed from the byte stream. | ||
70 | * | ||
71 | ******************************************************************************/ | ||
72 | |||
73 | acpi_status | ||
74 | acpi_rs_io_resource ( | ||
75 | u8 *byte_stream_buffer, | ||
76 | acpi_size *bytes_consumed, | ||
77 | u8 **output_buffer, | ||
78 | acpi_size *structure_size) | ||
79 | { | ||
80 | u8 *buffer = byte_stream_buffer; | ||
81 | struct acpi_resource *output_struct = (void *) *output_buffer; | ||
82 | u16 temp16 = 0; | ||
83 | u8 temp8 = 0; | ||
84 | acpi_size struct_size = ACPI_SIZEOF_RESOURCE (struct acpi_resource_io); | ||
85 | |||
86 | |||
87 | ACPI_FUNCTION_TRACE ("rs_io_resource"); | ||
88 | |||
89 | |||
90 | /* | ||
91 | * The number of bytes consumed are Constant | ||
92 | */ | ||
93 | *bytes_consumed = 8; | ||
94 | |||
95 | output_struct->id = ACPI_RSTYPE_IO; | ||
96 | |||
97 | /* | ||
98 | * Check Decode | ||
99 | */ | ||
100 | buffer += 1; | ||
101 | temp8 = *buffer; | ||
102 | |||
103 | output_struct->data.io.io_decode = temp8 & 0x01; | ||
104 | |||
105 | /* | ||
106 | * Check min_base Address | ||
107 | */ | ||
108 | buffer += 1; | ||
109 | ACPI_MOVE_16_TO_16 (&temp16, buffer); | ||
110 | |||
111 | output_struct->data.io.min_base_address = temp16; | ||
112 | |||
113 | /* | ||
114 | * Check max_base Address | ||
115 | */ | ||
116 | buffer += 2; | ||
117 | ACPI_MOVE_16_TO_16 (&temp16, buffer); | ||
118 | |||
119 | output_struct->data.io.max_base_address = temp16; | ||
120 | |||
121 | /* | ||
122 | * Check Base alignment | ||
123 | */ | ||
124 | buffer += 2; | ||
125 | temp8 = *buffer; | ||
126 | |||
127 | output_struct->data.io.alignment = temp8; | ||
128 | |||
129 | /* | ||
130 | * Check range_length | ||
131 | */ | ||
132 | buffer += 1; | ||
133 | temp8 = *buffer; | ||
134 | |||
135 | output_struct->data.io.range_length = temp8; | ||
136 | |||
137 | /* | ||
138 | * Set the Length parameter | ||
139 | */ | ||
140 | output_struct->length = (u32) struct_size; | ||
141 | |||
142 | /* | ||
143 | * Return the final size of the structure | ||
144 | */ | ||
145 | *structure_size = struct_size; | ||
146 | return_ACPI_STATUS (AE_OK); | ||
147 | } | ||
148 | |||
149 | |||
150 | /******************************************************************************* | ||
151 | * | ||
152 | * FUNCTION: acpi_rs_fixed_io_resource | ||
153 | * | ||
154 | * PARAMETERS: byte_stream_buffer - Pointer to the resource input byte | ||
155 | * stream | ||
156 | * bytes_consumed - Pointer to where the number of bytes | ||
157 | * consumed the byte_stream_buffer is | ||
158 | * returned | ||
159 | * output_buffer - Pointer to the return data buffer | ||
160 | * structure_size - Pointer to where the number of bytes | ||
161 | * in the return data struct is returned | ||
162 | * | ||
163 | * RETURN: Status | ||
164 | * | ||
165 | * DESCRIPTION: Take the resource byte stream and fill out the appropriate | ||
166 | * structure pointed to by the output_buffer. Return the | ||
167 | * number of bytes consumed from the byte stream. | ||
168 | * | ||
169 | ******************************************************************************/ | ||
170 | |||
171 | acpi_status | ||
172 | acpi_rs_fixed_io_resource ( | ||
173 | u8 *byte_stream_buffer, | ||
174 | acpi_size *bytes_consumed, | ||
175 | u8 **output_buffer, | ||
176 | acpi_size *structure_size) | ||
177 | { | ||
178 | u8 *buffer = byte_stream_buffer; | ||
179 | struct acpi_resource *output_struct = (void *) *output_buffer; | ||
180 | u16 temp16 = 0; | ||
181 | u8 temp8 = 0; | ||
182 | acpi_size struct_size = ACPI_SIZEOF_RESOURCE (struct acpi_resource_fixed_io); | ||
183 | |||
184 | |||
185 | ACPI_FUNCTION_TRACE ("rs_fixed_io_resource"); | ||
186 | |||
187 | |||
188 | /* | ||
189 | * The number of bytes consumed are Constant | ||
190 | */ | ||
191 | *bytes_consumed = 4; | ||
192 | |||
193 | output_struct->id = ACPI_RSTYPE_FIXED_IO; | ||
194 | |||
195 | /* | ||
196 | * Check Range Base Address | ||
197 | */ | ||
198 | buffer += 1; | ||
199 | ACPI_MOVE_16_TO_16 (&temp16, buffer); | ||
200 | |||
201 | output_struct->data.fixed_io.base_address = temp16; | ||
202 | |||
203 | /* | ||
204 | * Check range_length | ||
205 | */ | ||
206 | buffer += 2; | ||
207 | temp8 = *buffer; | ||
208 | |||
209 | output_struct->data.fixed_io.range_length = temp8; | ||
210 | |||
211 | /* | ||
212 | * Set the Length parameter | ||
213 | */ | ||
214 | output_struct->length = (u32) struct_size; | ||
215 | |||
216 | /* | ||
217 | * Return the final size of the structure | ||
218 | */ | ||
219 | *structure_size = struct_size; | ||
220 | return_ACPI_STATUS (AE_OK); | ||
221 | } | ||
222 | |||
223 | |||
224 | /******************************************************************************* | ||
225 | * | ||
226 | * FUNCTION: acpi_rs_io_stream | ||
227 | * | ||
228 | * PARAMETERS: linked_list - Pointer to the resource linked list | ||
229 | * output_buffer - Pointer to the user's return buffer | ||
230 | * bytes_consumed - Pointer to where the number of bytes | ||
231 | * used in the output_buffer is returned | ||
232 | * | ||
233 | * RETURN: Status | ||
234 | * | ||
235 | * DESCRIPTION: Take the linked list resource structure and fills in the | ||
236 | * the appropriate bytes in a byte stream | ||
237 | * | ||
238 | ******************************************************************************/ | ||
239 | |||
240 | acpi_status | ||
241 | acpi_rs_io_stream ( | ||
242 | struct acpi_resource *linked_list, | ||
243 | u8 **output_buffer, | ||
244 | acpi_size *bytes_consumed) | ||
245 | { | ||
246 | u8 *buffer = *output_buffer; | ||
247 | u16 temp16 = 0; | ||
248 | u8 temp8 = 0; | ||
249 | |||
250 | |||
251 | ACPI_FUNCTION_TRACE ("rs_io_stream"); | ||
252 | |||
253 | |||
254 | /* | ||
255 | * The descriptor field is static | ||
256 | */ | ||
257 | *buffer = 0x47; | ||
258 | buffer += 1; | ||
259 | |||
260 | /* | ||
261 | * Io Information Byte | ||
262 | */ | ||
263 | temp8 = (u8) (linked_list->data.io.io_decode & 0x01); | ||
264 | |||
265 | *buffer = temp8; | ||
266 | buffer += 1; | ||
267 | |||
268 | /* | ||
269 | * Set the Range minimum base address | ||
270 | */ | ||
271 | temp16 = (u16) linked_list->data.io.min_base_address; | ||
272 | |||
273 | ACPI_MOVE_16_TO_16 (buffer, &temp16); | ||
274 | buffer += 2; | ||
275 | |||
276 | /* | ||
277 | * Set the Range maximum base address | ||
278 | */ | ||
279 | temp16 = (u16) linked_list->data.io.max_base_address; | ||
280 | |||
281 | ACPI_MOVE_16_TO_16 (buffer, &temp16); | ||
282 | buffer += 2; | ||
283 | |||
284 | /* | ||
285 | * Set the base alignment | ||
286 | */ | ||
287 | temp8 = (u8) linked_list->data.io.alignment; | ||
288 | |||
289 | *buffer = temp8; | ||
290 | buffer += 1; | ||
291 | |||
292 | /* | ||
293 | * Set the range length | ||
294 | */ | ||
295 | temp8 = (u8) linked_list->data.io.range_length; | ||
296 | |||
297 | *buffer = temp8; | ||
298 | buffer += 1; | ||
299 | |||
300 | /* | ||
301 | * Return the number of bytes consumed in this operation | ||
302 | */ | ||
303 | *bytes_consumed = ACPI_PTR_DIFF (buffer, *output_buffer); | ||
304 | return_ACPI_STATUS (AE_OK); | ||
305 | } | ||
306 | |||
307 | |||
308 | /******************************************************************************* | ||
309 | * | ||
310 | * FUNCTION: acpi_rs_fixed_io_stream | ||
311 | * | ||
312 | * PARAMETERS: linked_list - Pointer to the resource linked list | ||
313 | * output_buffer - Pointer to the user's return buffer | ||
314 | * bytes_consumed - Pointer to where the number of bytes | ||
315 | * used in the output_buffer is returned | ||
316 | * | ||
317 | * RETURN: Status | ||
318 | * | ||
319 | * DESCRIPTION: Take the linked list resource structure and fills in the | ||
320 | * the appropriate bytes in a byte stream | ||
321 | * | ||
322 | ******************************************************************************/ | ||
323 | |||
324 | acpi_status | ||
325 | acpi_rs_fixed_io_stream ( | ||
326 | struct acpi_resource *linked_list, | ||
327 | u8 **output_buffer, | ||
328 | acpi_size *bytes_consumed) | ||
329 | { | ||
330 | u8 *buffer = *output_buffer; | ||
331 | u16 temp16 = 0; | ||
332 | u8 temp8 = 0; | ||
333 | |||
334 | |||
335 | ACPI_FUNCTION_TRACE ("rs_fixed_io_stream"); | ||
336 | |||
337 | |||
338 | /* | ||
339 | * The descriptor field is static | ||
340 | */ | ||
341 | *buffer = 0x4B; | ||
342 | |||
343 | buffer += 1; | ||
344 | |||
345 | /* | ||
346 | * Set the Range base address | ||
347 | */ | ||
348 | temp16 = (u16) linked_list->data.fixed_io.base_address; | ||
349 | |||
350 | ACPI_MOVE_16_TO_16 (buffer, &temp16); | ||
351 | buffer += 2; | ||
352 | |||
353 | /* | ||
354 | * Set the range length | ||
355 | */ | ||
356 | temp8 = (u8) linked_list->data.fixed_io.range_length; | ||
357 | |||
358 | *buffer = temp8; | ||
359 | buffer += 1; | ||
360 | |||
361 | /* | ||
362 | * Return the number of bytes consumed in this operation | ||
363 | */ | ||
364 | *bytes_consumed = ACPI_PTR_DIFF (buffer, *output_buffer); | ||
365 | return_ACPI_STATUS (AE_OK); | ||
366 | } | ||
367 | |||
368 | |||
369 | /******************************************************************************* | ||
370 | * | ||
371 | * FUNCTION: acpi_rs_dma_resource | ||
372 | * | ||
373 | * PARAMETERS: byte_stream_buffer - Pointer to the resource input byte | ||
374 | * stream | ||
375 | * bytes_consumed - Pointer to where the number of bytes | ||
376 | * consumed the byte_stream_buffer is | ||
377 | * returned | ||
378 | * output_buffer - Pointer to the return data buffer | ||
379 | * structure_size - Pointer to where the number of bytes | ||
380 | * in the return data struct is returned | ||
381 | * | ||
382 | * RETURN: Status | ||
383 | * | ||
384 | * DESCRIPTION: Take the resource byte stream and fill out the appropriate | ||
385 | * structure pointed to by the output_buffer. Return the | ||
386 | * number of bytes consumed from the byte stream. | ||
387 | * | ||
388 | ******************************************************************************/ | ||
389 | |||
390 | acpi_status | ||
391 | acpi_rs_dma_resource ( | ||
392 | u8 *byte_stream_buffer, | ||
393 | acpi_size *bytes_consumed, | ||
394 | u8 **output_buffer, | ||
395 | acpi_size *structure_size) | ||
396 | { | ||
397 | u8 *buffer = byte_stream_buffer; | ||
398 | struct acpi_resource *output_struct = (void *) *output_buffer; | ||
399 | u8 temp8 = 0; | ||
400 | u8 index; | ||
401 | u8 i; | ||
402 | acpi_size struct_size = ACPI_SIZEOF_RESOURCE (struct acpi_resource_dma); | ||
403 | |||
404 | |||
405 | ACPI_FUNCTION_TRACE ("rs_dma_resource"); | ||
406 | |||
407 | |||
408 | /* | ||
409 | * The number of bytes consumed are Constant | ||
410 | */ | ||
411 | *bytes_consumed = 3; | ||
412 | output_struct->id = ACPI_RSTYPE_DMA; | ||
413 | |||
414 | /* | ||
415 | * Point to the 8-bits of Byte 1 | ||
416 | */ | ||
417 | buffer += 1; | ||
418 | temp8 = *buffer; | ||
419 | |||
420 | /* Decode the DMA channel bits */ | ||
421 | |||
422 | for (i = 0, index = 0; index < 8; index++) { | ||
423 | if ((temp8 >> index) & 0x01) { | ||
424 | output_struct->data.dma.channels[i] = index; | ||
425 | i++; | ||
426 | } | ||
427 | } | ||
428 | |||
429 | /* Zero DMA channels is valid */ | ||
430 | |||
431 | output_struct->data.dma.number_of_channels = i; | ||
432 | if (i > 0) { | ||
433 | /* | ||
434 | * Calculate the structure size based upon the number of interrupts | ||
435 | */ | ||
436 | struct_size += ((acpi_size) i - 1) * 4; | ||
437 | } | ||
438 | |||
439 | /* | ||
440 | * Point to Byte 2 | ||
441 | */ | ||
442 | buffer += 1; | ||
443 | temp8 = *buffer; | ||
444 | |||
445 | /* | ||
446 | * Check for transfer preference (Bits[1:0]) | ||
447 | */ | ||
448 | output_struct->data.dma.transfer = temp8 & 0x03; | ||
449 | |||
450 | if (0x03 == output_struct->data.dma.transfer) { | ||
451 | ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Invalid DMA.Transfer preference (3)\n")); | ||
452 | return_ACPI_STATUS (AE_BAD_DATA); | ||
453 | } | ||
454 | |||
455 | /* | ||
456 | * Get bus master preference (Bit[2]) | ||
457 | */ | ||
458 | output_struct->data.dma.bus_master = (temp8 >> 2) & 0x01; | ||
459 | |||
460 | /* | ||
461 | * Get channel speed support (Bits[6:5]) | ||
462 | */ | ||
463 | output_struct->data.dma.type = (temp8 >> 5) & 0x03; | ||
464 | |||
465 | /* | ||
466 | * Set the Length parameter | ||
467 | */ | ||
468 | output_struct->length = (u32) struct_size; | ||
469 | |||
470 | /* | ||
471 | * Return the final size of the structure | ||
472 | */ | ||
473 | *structure_size = struct_size; | ||
474 | return_ACPI_STATUS (AE_OK); | ||
475 | } | ||
476 | |||
477 | |||
478 | /******************************************************************************* | ||
479 | * | ||
480 | * FUNCTION: acpi_rs_dma_stream | ||
481 | * | ||
482 | * PARAMETERS: linked_list - Pointer to the resource linked list | ||
483 | * output_buffer - Pointer to the user's return buffer | ||
484 | * bytes_consumed - Pointer to where the number of bytes | ||
485 | * used in the output_buffer is returned | ||
486 | * | ||
487 | * RETURN: Status | ||
488 | * | ||
489 | * DESCRIPTION: Take the linked list resource structure and fills in the | ||
490 | * the appropriate bytes in a byte stream | ||
491 | * | ||
492 | ******************************************************************************/ | ||
493 | |||
494 | acpi_status | ||
495 | acpi_rs_dma_stream ( | ||
496 | struct acpi_resource *linked_list, | ||
497 | u8 **output_buffer, | ||
498 | acpi_size *bytes_consumed) | ||
499 | { | ||
500 | u8 *buffer = *output_buffer; | ||
501 | u16 temp16 = 0; | ||
502 | u8 temp8 = 0; | ||
503 | u8 index; | ||
504 | |||
505 | |||
506 | ACPI_FUNCTION_TRACE ("rs_dma_stream"); | ||
507 | |||
508 | |||
509 | /* | ||
510 | * The descriptor field is static | ||
511 | */ | ||
512 | *buffer = 0x2A; | ||
513 | buffer += 1; | ||
514 | temp8 = 0; | ||
515 | |||
516 | /* | ||
517 | * Loop through all of the Channels and set the mask bits | ||
518 | */ | ||
519 | for (index = 0; | ||
520 | index < linked_list->data.dma.number_of_channels; | ||
521 | index++) { | ||
522 | temp16 = (u16) linked_list->data.dma.channels[index]; | ||
523 | temp8 |= 0x1 << temp16; | ||
524 | } | ||
525 | |||
526 | *buffer = temp8; | ||
527 | buffer += 1; | ||
528 | |||
529 | /* | ||
530 | * Set the DMA Info | ||
531 | */ | ||
532 | temp8 = (u8) ((linked_list->data.dma.type & 0x03) << 5); | ||
533 | temp8 |= ((linked_list->data.dma.bus_master & 0x01) << 2); | ||
534 | temp8 |= (linked_list->data.dma.transfer & 0x03); | ||
535 | |||
536 | *buffer = temp8; | ||
537 | buffer += 1; | ||
538 | |||
539 | /* | ||
540 | * Return the number of bytes consumed in this operation | ||
541 | */ | ||
542 | *bytes_consumed = ACPI_PTR_DIFF (buffer, *output_buffer); | ||
543 | return_ACPI_STATUS (AE_OK); | ||
544 | } | ||
545 | |||