OpenCores
URL https://opencores.org/ocsvn/test_project/test_project/trunk

Subversion Repositories test_project

[/] [test_project/] [trunk/] [linux_sd_driver/] [drivers/] [acpi/] [executer/] [exregion.c] - Blame information for rev 62

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 62 marcus.erl
 
2
/******************************************************************************
3
 *
4
 * Module Name: exregion - ACPI default op_region (address space) handlers
5
 *
6
 *****************************************************************************/
7
 
8
/*
9
 * Copyright (C) 2000 - 2007, R. Byron Moore
10
 * All rights reserved.
11
 *
12
 * Redistribution and use in source and binary forms, with or without
13
 * modification, are permitted provided that the following conditions
14
 * are met:
15
 * 1. Redistributions of source code must retain the above copyright
16
 *    notice, this list of conditions, and the following disclaimer,
17
 *    without modification.
18
 * 2. Redistributions in binary form must reproduce at minimum a disclaimer
19
 *    substantially similar to the "NO WARRANTY" disclaimer below
20
 *    ("Disclaimer") and any redistribution must be conditioned upon
21
 *    including a substantially similar Disclaimer requirement for further
22
 *    binary redistribution.
23
 * 3. Neither the names of the above-listed copyright holders nor the names
24
 *    of any contributors may be used to endorse or promote products derived
25
 *    from this software without specific prior written permission.
26
 *
27
 * Alternatively, this software may be distributed under the terms of the
28
 * GNU General Public License ("GPL") version 2 as published by the Free
29
 * Software Foundation.
30
 *
31
 * NO WARRANTY
32
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
33
 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
34
 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
35
 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
36
 * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
37
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
38
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
39
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
40
 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
41
 * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
42
 * POSSIBILITY OF SUCH DAMAGES.
43
 */
44
 
45
#include <acpi/acpi.h>
46
#include <acpi/acinterp.h>
47
 
48
#define _COMPONENT          ACPI_EXECUTER
49
ACPI_MODULE_NAME("exregion")
50
 
51
/*******************************************************************************
52
 *
53
 * FUNCTION:    acpi_ex_system_memory_space_handler
54
 *
55
 * PARAMETERS:  Function            - Read or Write operation
56
 *              Address             - Where in the space to read or write
57
 *              bit_width           - Field width in bits (8, 16, or 32)
58
 *              Value               - Pointer to in or out value
59
 *              handler_context     - Pointer to Handler's context
60
 *              region_context      - Pointer to context specific to the
61
 *                                    accessed region
62
 *
63
 * RETURN:      Status
64
 *
65
 * DESCRIPTION: Handler for the System Memory address space (Op Region)
66
 *
67
 ******************************************************************************/
68
acpi_status
69
acpi_ex_system_memory_space_handler(u32 function,
70
                                    acpi_physical_address address,
71
                                    u32 bit_width,
72
                                    acpi_integer * value,
73
                                    void *handler_context, void *region_context)
74
{
75
        acpi_status status = AE_OK;
76
        void *logical_addr_ptr = NULL;
77
        struct acpi_mem_space_context *mem_info = region_context;
78
        u32 length;
79
        acpi_size window_size;
80
#ifdef ACPI_MISALIGNMENT_NOT_SUPPORTED
81
        u32 remainder;
82
#endif
83
 
84
        ACPI_FUNCTION_TRACE(ex_system_memory_space_handler);
85
 
86
        /* Validate and translate the bit width */
87
 
88
        switch (bit_width) {
89
        case 8:
90
                length = 1;
91
                break;
92
 
93
        case 16:
94
                length = 2;
95
                break;
96
 
97
        case 32:
98
                length = 4;
99
                break;
100
 
101
        case 64:
102
                length = 8;
103
                break;
104
 
105
        default:
106
                ACPI_ERROR((AE_INFO, "Invalid SystemMemory width %d",
107
                            bit_width));
108
                return_ACPI_STATUS(AE_AML_OPERAND_VALUE);
109
        }
110
 
111
#ifdef ACPI_MISALIGNMENT_NOT_SUPPORTED
112
        /*
113
         * Hardware does not support non-aligned data transfers, we must verify
114
         * the request.
115
         */
116
        (void)acpi_ut_short_divide((acpi_integer) address, length, NULL,
117
                                   &remainder);
118
        if (remainder != 0) {
119
                return_ACPI_STATUS(AE_AML_ALIGNMENT);
120
        }
121
#endif
122
 
123
        /*
124
         * Does the request fit into the cached memory mapping?
125
         * Is 1) Address below the current mapping? OR
126
         *    2) Address beyond the current mapping?
127
         */
128
        if ((address < mem_info->mapped_physical_address) ||
129
            (((acpi_integer) address + length) > ((acpi_integer)
130
                                                  mem_info->
131
                                                  mapped_physical_address +
132
                                                  mem_info->mapped_length))) {
133
                /*
134
                 * The request cannot be resolved by the current memory mapping;
135
                 * Delete the existing mapping and create a new one.
136
                 */
137
                if (mem_info->mapped_length) {
138
 
139
                        /* Valid mapping, delete it */
140
 
141
                        acpi_os_unmap_memory(mem_info->mapped_logical_address,
142
                                             mem_info->mapped_length);
143
                }
144
 
145
                /*
146
                 * Don't attempt to map memory beyond the end of the region, and
147
                 * constrain the maximum mapping size to something reasonable.
148
                 */
149
                window_size = (acpi_size)
150
                    ((mem_info->address + mem_info->length) - address);
151
 
152
                if (window_size > ACPI_SYSMEM_REGION_WINDOW_SIZE) {
153
                        window_size = ACPI_SYSMEM_REGION_WINDOW_SIZE;
154
                }
155
 
156
                /* Create a new mapping starting at the address given */
157
 
158
                mem_info->mapped_logical_address =
159
                    acpi_os_map_memory((acpi_native_uint) address, window_size);
160
                if (!mem_info->mapped_logical_address) {
161
                        ACPI_ERROR((AE_INFO,
162
                                    "Could not map memory at %8.8X%8.8X, size %X",
163
                                    ACPI_FORMAT_UINT64(address),
164
                                    (u32) window_size));
165
                        mem_info->mapped_length = 0;
166
                        return_ACPI_STATUS(AE_NO_MEMORY);
167
                }
168
 
169
                /* Save the physical address and mapping size */
170
 
171
                mem_info->mapped_physical_address = address;
172
                mem_info->mapped_length = window_size;
173
        }
174
 
175
        /*
176
         * Generate a logical pointer corresponding to the address we want to
177
         * access
178
         */
179
        logical_addr_ptr = mem_info->mapped_logical_address +
180
            ((acpi_integer) address -
181
             (acpi_integer) mem_info->mapped_physical_address);
182
 
183
        ACPI_DEBUG_PRINT((ACPI_DB_INFO,
184
                          "System-Memory (width %d) R/W %d Address=%8.8X%8.8X\n",
185
                          bit_width, function, ACPI_FORMAT_UINT64(address)));
186
 
187
        /*
188
         * Perform the memory read or write
189
         *
190
         * Note: For machines that do not support non-aligned transfers, the target
191
         * address was checked for alignment above.  We do not attempt to break the
192
         * transfer up into smaller (byte-size) chunks because the AML specifically
193
         * asked for a transfer width that the hardware may require.
194
         */
195
        switch (function) {
196
        case ACPI_READ:
197
 
198
                *value = 0;
199
                switch (bit_width) {
200
                case 8:
201
                        *value = (acpi_integer) ACPI_GET8(logical_addr_ptr);
202
                        break;
203
 
204
                case 16:
205
                        *value = (acpi_integer) ACPI_GET16(logical_addr_ptr);
206
                        break;
207
 
208
                case 32:
209
                        *value = (acpi_integer) ACPI_GET32(logical_addr_ptr);
210
                        break;
211
 
212
                case 64:
213
                        *value = (acpi_integer) ACPI_GET64(logical_addr_ptr);
214
                        break;
215
 
216
                default:
217
                        /* bit_width was already validated */
218
                        break;
219
                }
220
                break;
221
 
222
        case ACPI_WRITE:
223
 
224
                switch (bit_width) {
225
                case 8:
226
                        ACPI_SET8(logical_addr_ptr) = (u8) * value;
227
                        break;
228
 
229
                case 16:
230
                        ACPI_SET16(logical_addr_ptr) = (u16) * value;
231
                        break;
232
 
233
                case 32:
234
                        ACPI_SET32(logical_addr_ptr) = (u32) * value;
235
                        break;
236
 
237
                case 64:
238
                        ACPI_SET64(logical_addr_ptr) = (u64) * value;
239
                        break;
240
 
241
                default:
242
                        /* bit_width was already validated */
243
                        break;
244
                }
245
                break;
246
 
247
        default:
248
                status = AE_BAD_PARAMETER;
249
                break;
250
        }
251
 
252
        return_ACPI_STATUS(status);
253
}
254
 
255
/*******************************************************************************
256
 *
257
 * FUNCTION:    acpi_ex_system_io_space_handler
258
 *
259
 * PARAMETERS:  Function            - Read or Write operation
260
 *              Address             - Where in the space to read or write
261
 *              bit_width           - Field width in bits (8, 16, or 32)
262
 *              Value               - Pointer to in or out value
263
 *              handler_context     - Pointer to Handler's context
264
 *              region_context      - Pointer to context specific to the
265
 *                                    accessed region
266
 *
267
 * RETURN:      Status
268
 *
269
 * DESCRIPTION: Handler for the System IO address space (Op Region)
270
 *
271
 ******************************************************************************/
272
 
273
acpi_status
274
acpi_ex_system_io_space_handler(u32 function,
275
                                acpi_physical_address address,
276
                                u32 bit_width,
277
                                acpi_integer * value,
278
                                void *handler_context, void *region_context)
279
{
280
        acpi_status status = AE_OK;
281
        u32 value32;
282
 
283
        ACPI_FUNCTION_TRACE(ex_system_io_space_handler);
284
 
285
        ACPI_DEBUG_PRINT((ACPI_DB_INFO,
286
                          "System-IO (width %d) R/W %d Address=%8.8X%8.8X\n",
287
                          bit_width, function, ACPI_FORMAT_UINT64(address)));
288
 
289
        /* Decode the function parameter */
290
 
291
        switch (function) {
292
        case ACPI_READ:
293
 
294
                status = acpi_os_read_port((acpi_io_address) address,
295
                                           &value32, bit_width);
296
                *value = value32;
297
                break;
298
 
299
        case ACPI_WRITE:
300
 
301
                status = acpi_os_write_port((acpi_io_address) address,
302
                                            (u32) * value, bit_width);
303
                break;
304
 
305
        default:
306
                status = AE_BAD_PARAMETER;
307
                break;
308
        }
309
 
310
        return_ACPI_STATUS(status);
311
}
312
 
313
/*******************************************************************************
314
 *
315
 * FUNCTION:    acpi_ex_pci_config_space_handler
316
 *
317
 * PARAMETERS:  Function            - Read or Write operation
318
 *              Address             - Where in the space to read or write
319
 *              bit_width           - Field width in bits (8, 16, or 32)
320
 *              Value               - Pointer to in or out value
321
 *              handler_context     - Pointer to Handler's context
322
 *              region_context      - Pointer to context specific to the
323
 *                                    accessed region
324
 *
325
 * RETURN:      Status
326
 *
327
 * DESCRIPTION: Handler for the PCI Config address space (Op Region)
328
 *
329
 ******************************************************************************/
330
 
331
acpi_status
332
acpi_ex_pci_config_space_handler(u32 function,
333
                                 acpi_physical_address address,
334
                                 u32 bit_width,
335
                                 acpi_integer * value,
336
                                 void *handler_context, void *region_context)
337
{
338
        acpi_status status = AE_OK;
339
        struct acpi_pci_id *pci_id;
340
        u16 pci_register;
341
 
342
        ACPI_FUNCTION_TRACE(ex_pci_config_space_handler);
343
 
344
        /*
345
         *  The arguments to acpi_os(Read|Write)pci_configuration are:
346
         *
347
         *  pci_segment is the PCI bus segment range 0-31
348
         *  pci_bus     is the PCI bus number range 0-255
349
         *  pci_device  is the PCI device number range 0-31
350
         *  pci_function is the PCI device function number
351
         *  pci_register is the Config space register range 0-255 bytes
352
         *
353
         *  Value - input value for write, output address for read
354
         *
355
         */
356
        pci_id = (struct acpi_pci_id *)region_context;
357
        pci_register = (u16) (u32) address;
358
 
359
        ACPI_DEBUG_PRINT((ACPI_DB_INFO,
360
                          "Pci-Config %d (%d) Seg(%04x) Bus(%04x) Dev(%04x) Func(%04x) Reg(%04x)\n",
361
                          function, bit_width, pci_id->segment, pci_id->bus,
362
                          pci_id->device, pci_id->function, pci_register));
363
 
364
        switch (function) {
365
        case ACPI_READ:
366
 
367
                *value = 0;
368
                status = acpi_os_read_pci_configuration(pci_id, pci_register,
369
                                                        value, bit_width);
370
                break;
371
 
372
        case ACPI_WRITE:
373
 
374
                status = acpi_os_write_pci_configuration(pci_id, pci_register,
375
                                                         *value, bit_width);
376
                break;
377
 
378
        default:
379
 
380
                status = AE_BAD_PARAMETER;
381
                break;
382
        }
383
 
384
        return_ACPI_STATUS(status);
385
}
386
 
387
/*******************************************************************************
388
 *
389
 * FUNCTION:    acpi_ex_cmos_space_handler
390
 *
391
 * PARAMETERS:  Function            - Read or Write operation
392
 *              Address             - Where in the space to read or write
393
 *              bit_width           - Field width in bits (8, 16, or 32)
394
 *              Value               - Pointer to in or out value
395
 *              handler_context     - Pointer to Handler's context
396
 *              region_context      - Pointer to context specific to the
397
 *                                    accessed region
398
 *
399
 * RETURN:      Status
400
 *
401
 * DESCRIPTION: Handler for the CMOS address space (Op Region)
402
 *
403
 ******************************************************************************/
404
 
405
acpi_status
406
acpi_ex_cmos_space_handler(u32 function,
407
                           acpi_physical_address address,
408
                           u32 bit_width,
409
                           acpi_integer * value,
410
                           void *handler_context, void *region_context)
411
{
412
        acpi_status status = AE_OK;
413
 
414
        ACPI_FUNCTION_TRACE(ex_cmos_space_handler);
415
 
416
        return_ACPI_STATUS(status);
417
}
418
 
419
/*******************************************************************************
420
 *
421
 * FUNCTION:    acpi_ex_pci_bar_space_handler
422
 *
423
 * PARAMETERS:  Function            - Read or Write operation
424
 *              Address             - Where in the space to read or write
425
 *              bit_width           - Field width in bits (8, 16, or 32)
426
 *              Value               - Pointer to in or out value
427
 *              handler_context     - Pointer to Handler's context
428
 *              region_context      - Pointer to context specific to the
429
 *                                    accessed region
430
 *
431
 * RETURN:      Status
432
 *
433
 * DESCRIPTION: Handler for the PCI bar_target address space (Op Region)
434
 *
435
 ******************************************************************************/
436
 
437
acpi_status
438
acpi_ex_pci_bar_space_handler(u32 function,
439
                              acpi_physical_address address,
440
                              u32 bit_width,
441
                              acpi_integer * value,
442
                              void *handler_context, void *region_context)
443
{
444
        acpi_status status = AE_OK;
445
 
446
        ACPI_FUNCTION_TRACE(ex_pci_bar_space_handler);
447
 
448
        return_ACPI_STATUS(status);
449
}
450
 
451
/*******************************************************************************
452
 *
453
 * FUNCTION:    acpi_ex_data_table_space_handler
454
 *
455
 * PARAMETERS:  Function            - Read or Write operation
456
 *              Address             - Where in the space to read or write
457
 *              bit_width           - Field width in bits (8, 16, or 32)
458
 *              Value               - Pointer to in or out value
459
 *              handler_context     - Pointer to Handler's context
460
 *              region_context      - Pointer to context specific to the
461
 *                                    accessed region
462
 *
463
 * RETURN:      Status
464
 *
465
 * DESCRIPTION: Handler for the Data Table address space (Op Region)
466
 *
467
 ******************************************************************************/
468
 
469
acpi_status
470
acpi_ex_data_table_space_handler(u32 function,
471
                                 acpi_physical_address address,
472
                                 u32 bit_width,
473
                                 acpi_integer * value,
474
                                 void *handler_context, void *region_context)
475
{
476
        ACPI_FUNCTION_TRACE(ex_data_table_space_handler);
477
 
478
        /* Perform the memory read or write */
479
 
480
        switch (function) {
481
        case ACPI_READ:
482
 
483
                ACPI_MEMCPY(ACPI_CAST_PTR(char, value),
484
                            ACPI_PHYSADDR_TO_PTR(address),
485
                            ACPI_DIV_8(bit_width));
486
                break;
487
 
488
        case ACPI_WRITE:
489
        default:
490
 
491
                return_ACPI_STATUS(AE_SUPPORT);
492
        }
493
 
494
        return_ACPI_STATUS(AE_OK);
495
}

powered by: WebSVN 2.1.0

© copyright 1999-2025 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.