mirror of
https://github.com/edk2-porting/linux-next.git
synced 2024-12-19 02:34:01 +08:00
Merge back earlier ACPICA material.
This commit is contained in:
commit
fd0c940522
@ -237,7 +237,15 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
This feature is enabled by default.
|
||||
This option allows to turn off the feature.
|
||||
|
||||
acpi_no_auto_ssdt [HW,ACPI] Disable automatic loading of SSDT
|
||||
acpi_no_static_ssdt [HW,ACPI]
|
||||
Disable installation of static SSDTs at early boot time
|
||||
By default, SSDTs contained in the RSDT/XSDT will be
|
||||
installed automatically and they will appear under
|
||||
/sys/firmware/acpi/tables.
|
||||
This option turns off this feature.
|
||||
Note that specifying this option does not affect
|
||||
dynamic table installation which will install SSDT
|
||||
tables to /sys/firmware/acpi/tables/dynamic.
|
||||
|
||||
acpica_no_return_repair [HW, ACPI]
|
||||
Disable AML predefined validation mechanism
|
||||
|
@ -135,6 +135,7 @@ acpi-y += \
|
||||
rsxface.o
|
||||
|
||||
acpi-y += \
|
||||
tbdata.o \
|
||||
tbfadt.o \
|
||||
tbfind.o \
|
||||
tbinstal.o \
|
||||
|
170
drivers/acpi/acpica/acapps.h
Normal file
170
drivers/acpi/acpica/acapps.h
Normal file
@ -0,0 +1,170 @@
|
||||
/******************************************************************************
|
||||
*
|
||||
* Module Name: acapps - common include for ACPI applications/tools
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2000 - 2014, Intel Corp.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification.
|
||||
* 2. Redistributions in binary form must reproduce at minimum a disclaimer
|
||||
* substantially similar to the "NO WARRANTY" disclaimer below
|
||||
* ("Disclaimer") and any redistribution must be conditioned upon
|
||||
* including a substantially similar Disclaimer requirement for further
|
||||
* binary redistribution.
|
||||
* 3. Neither the names of the above-listed copyright holders nor the names
|
||||
* of any contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* Alternatively, this software may be distributed under the terms of the
|
||||
* GNU General Public License ("GPL") version 2 as published by the Free
|
||||
* Software Foundation.
|
||||
*
|
||||
* NO WARRANTY
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
* HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
||||
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
|
||||
* IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGES.
|
||||
*/
|
||||
|
||||
#ifndef _ACAPPS
|
||||
#define _ACAPPS
|
||||
|
||||
/* Common info for tool signons */
|
||||
|
||||
#define ACPICA_NAME "Intel ACPI Component Architecture"
|
||||
#define ACPICA_COPYRIGHT "Copyright (c) 2000 - 2014 Intel Corporation"
|
||||
|
||||
#if ACPI_MACHINE_WIDTH == 64
|
||||
#define ACPI_WIDTH "-64"
|
||||
|
||||
#elif ACPI_MACHINE_WIDTH == 32
|
||||
#define ACPI_WIDTH "-32"
|
||||
|
||||
#else
|
||||
#error unknown ACPI_MACHINE_WIDTH
|
||||
#define ACPI_WIDTH "-??"
|
||||
|
||||
#endif
|
||||
|
||||
/* Macros for signons and file headers */
|
||||
|
||||
#define ACPI_COMMON_SIGNON(utility_name) \
|
||||
"\n%s\n%s version %8.8X%s [%s]\n%s\n\n", \
|
||||
ACPICA_NAME, \
|
||||
utility_name, ((u32) ACPI_CA_VERSION), ACPI_WIDTH, __DATE__, \
|
||||
ACPICA_COPYRIGHT
|
||||
|
||||
#define ACPI_COMMON_HEADER(utility_name, prefix) \
|
||||
"%s%s\n%s%s version %8.8X%s [%s]\n%s%s\n%s\n", \
|
||||
prefix, ACPICA_NAME, \
|
||||
prefix, utility_name, ((u32) ACPI_CA_VERSION), ACPI_WIDTH, __DATE__, \
|
||||
prefix, ACPICA_COPYRIGHT, \
|
||||
prefix
|
||||
|
||||
/* Macros for usage messages */
|
||||
|
||||
#define ACPI_USAGE_HEADER(usage) \
|
||||
printf ("Usage: %s\nOptions:\n", usage);
|
||||
|
||||
#define ACPI_OPTION(name, description) \
|
||||
printf (" %-18s%s\n", name, description);
|
||||
|
||||
#define FILE_SUFFIX_DISASSEMBLY "dsl"
|
||||
#define ACPI_TABLE_FILE_SUFFIX ".dat"
|
||||
|
||||
/*
|
||||
* getopt
|
||||
*/
|
||||
int acpi_getopt(int argc, char **argv, char *opts);
|
||||
|
||||
int acpi_getopt_argument(int argc, char **argv);
|
||||
|
||||
extern int acpi_gbl_optind;
|
||||
extern int acpi_gbl_opterr;
|
||||
extern int acpi_gbl_sub_opt_char;
|
||||
extern char *acpi_gbl_optarg;
|
||||
|
||||
/*
|
||||
* cmfsize - Common get file size function
|
||||
*/
|
||||
u32 cm_get_file_size(FILE * file);
|
||||
|
||||
#ifndef ACPI_DUMP_APP
|
||||
/*
|
||||
* adisasm
|
||||
*/
|
||||
acpi_status
|
||||
ad_aml_disassemble(u8 out_to_file,
|
||||
char *filename, char *prefix, char **out_filename);
|
||||
|
||||
void ad_print_statistics(void);
|
||||
|
||||
acpi_status ad_find_dsdt(u8 **dsdt_ptr, u32 *dsdt_length);
|
||||
|
||||
void ad_dump_tables(void);
|
||||
|
||||
acpi_status ad_get_local_tables(void);
|
||||
|
||||
acpi_status
|
||||
ad_parse_table(struct acpi_table_header *table,
|
||||
acpi_owner_id * owner_id, u8 load_table, u8 external);
|
||||
|
||||
acpi_status ad_display_tables(char *filename, struct acpi_table_header *table);
|
||||
|
||||
acpi_status ad_display_statistics(void);
|
||||
|
||||
/*
|
||||
* adwalk
|
||||
*/
|
||||
void
|
||||
acpi_dm_cross_reference_namespace(union acpi_parse_object *parse_tree_root,
|
||||
struct acpi_namespace_node *namespace_root,
|
||||
acpi_owner_id owner_id);
|
||||
|
||||
void acpi_dm_dump_tree(union acpi_parse_object *origin);
|
||||
|
||||
void acpi_dm_find_orphan_methods(union acpi_parse_object *origin);
|
||||
|
||||
void
|
||||
acpi_dm_finish_namespace_load(union acpi_parse_object *parse_tree_root,
|
||||
struct acpi_namespace_node *namespace_root,
|
||||
acpi_owner_id owner_id);
|
||||
|
||||
void
|
||||
acpi_dm_convert_resource_indexes(union acpi_parse_object *parse_tree_root,
|
||||
struct acpi_namespace_node *namespace_root);
|
||||
|
||||
/*
|
||||
* adfile
|
||||
*/
|
||||
acpi_status ad_initialize(void);
|
||||
|
||||
char *fl_generate_filename(char *input_filename, char *suffix);
|
||||
|
||||
acpi_status
|
||||
fl_split_input_pathname(char *input_path,
|
||||
char **out_directory_path, char **out_filename);
|
||||
|
||||
char *ad_generate_filename(char *prefix, char *table_id);
|
||||
|
||||
void
|
||||
ad_write_table(struct acpi_table_header *table,
|
||||
u32 length, char *table_name, char *oem_table_id);
|
||||
#endif
|
||||
|
||||
#endif /* _ACAPPS */
|
@ -103,8 +103,8 @@ ACPI_INIT_GLOBAL(u8, acpi_gbl_auto_serialize_methods, TRUE);
|
||||
|
||||
/*
|
||||
* Create the predefined _OSI method in the namespace? Default is TRUE
|
||||
* because ACPI CA is fully compatible with other ACPI implementations.
|
||||
* Changing this will revert ACPI CA (and machine ASL) to pre-OSI behavior.
|
||||
* because ACPICA is fully compatible with other ACPI implementations.
|
||||
* Changing this will revert ACPICA (and machine ASL) to pre-OSI behavior.
|
||||
*/
|
||||
ACPI_INIT_GLOBAL(u8, acpi_gbl_create_osi_method, TRUE);
|
||||
|
||||
@ -160,10 +160,10 @@ ACPI_INIT_GLOBAL(u8, acpi_gbl_truncate_io_addresses, FALSE);
|
||||
ACPI_INIT_GLOBAL(u8, acpi_gbl_disable_auto_repair, FALSE);
|
||||
|
||||
/*
|
||||
* Optionally do not load any SSDTs from the RSDT/XSDT during initialization.
|
||||
* Optionally do not install any SSDTs from the RSDT/XSDT during initialization.
|
||||
* This can be useful for debugging ACPI problems on some machines.
|
||||
*/
|
||||
ACPI_INIT_GLOBAL(u8, acpi_gbl_disable_ssdt_table_load, FALSE);
|
||||
ACPI_INIT_GLOBAL(u8, acpi_gbl_disable_ssdt_table_install, FALSE);
|
||||
|
||||
/*
|
||||
* We keep track of the latest version of Windows that has been requested by
|
||||
@ -509,5 +509,6 @@ ACPI_INIT_GLOBAL(ACPI_FILE, acpi_gbl_debug_file, NULL);
|
||||
****************************************************************************/
|
||||
|
||||
extern const struct ah_predefined_name asl_predefined_info[];
|
||||
extern const struct ah_device_id asl_device_ids[];
|
||||
|
||||
#endif /* __ACGLOBAL_H__ */
|
||||
|
@ -733,7 +733,8 @@ union acpi_parse_value {
|
||||
#define ACPI_DASM_MATCHOP 0x06 /* Parent opcode is a Match() operator */
|
||||
#define ACPI_DASM_LNOT_PREFIX 0x07 /* Start of a Lnot_equal (etc.) pair of opcodes */
|
||||
#define ACPI_DASM_LNOT_SUFFIX 0x08 /* End of a Lnot_equal (etc.) pair of opcodes */
|
||||
#define ACPI_DASM_IGNORE 0x09 /* Not used at this time */
|
||||
#define ACPI_DASM_HID_STRING 0x09 /* String is a _HID or _CID */
|
||||
#define ACPI_DASM_IGNORE 0x0A /* Not used at this time */
|
||||
|
||||
/*
|
||||
* Generic operation (for example: If, While, Store)
|
||||
@ -1147,4 +1148,9 @@ struct ah_predefined_name {
|
||||
#endif
|
||||
};
|
||||
|
||||
struct ah_device_id {
|
||||
char *name;
|
||||
char *description;
|
||||
};
|
||||
|
||||
#endif /* __ACLOCAL_H__ */
|
||||
|
@ -53,6 +53,26 @@ acpi_status acpi_tb_validate_rsdp(struct acpi_table_rsdp *rsdp);
|
||||
|
||||
u8 *acpi_tb_scan_memory_for_rsdp(u8 *start_address, u32 length);
|
||||
|
||||
/*
|
||||
* tbdata - table data structure management
|
||||
*/
|
||||
acpi_status acpi_tb_get_next_root_index(u32 *table_index);
|
||||
|
||||
void
|
||||
acpi_tb_init_table_descriptor(struct acpi_table_desc *table_desc,
|
||||
acpi_physical_address address,
|
||||
u8 flags, struct acpi_table_header *table);
|
||||
|
||||
acpi_status
|
||||
acpi_tb_acquire_temp_table(struct acpi_table_desc *table_desc,
|
||||
acpi_physical_address address, u8 flags);
|
||||
|
||||
void acpi_tb_release_temp_table(struct acpi_table_desc *table_desc);
|
||||
|
||||
u8 acpi_tb_is_table_loaded(u32 table_index);
|
||||
|
||||
void acpi_tb_set_table_loaded_flag(u32 table_index, u8 is_loaded);
|
||||
|
||||
/*
|
||||
* tbfadt - FADT parse/convert/validate
|
||||
*/
|
||||
@ -72,22 +92,35 @@ acpi_tb_find_table(char *signature,
|
||||
*/
|
||||
acpi_status acpi_tb_resize_root_table_list(void);
|
||||
|
||||
acpi_status acpi_tb_verify_table(struct acpi_table_desc *table_desc);
|
||||
acpi_status acpi_tb_validate_table(struct acpi_table_desc *table_desc);
|
||||
|
||||
struct acpi_table_header *acpi_tb_table_override(struct acpi_table_header
|
||||
*table_header,
|
||||
struct acpi_table_desc
|
||||
*table_desc);
|
||||
void acpi_tb_invalidate_table(struct acpi_table_desc *table_desc);
|
||||
|
||||
acpi_status
|
||||
acpi_tb_add_table(struct acpi_table_desc *table_desc, u32 *table_index);
|
||||
acpi_tb_verify_table(struct acpi_table_desc *table_desc, char *signature);
|
||||
|
||||
void acpi_tb_override_table(struct acpi_table_desc *old_table_desc);
|
||||
|
||||
acpi_status
|
||||
acpi_tb_acquire_table(struct acpi_table_desc *table_desc,
|
||||
struct acpi_table_header **table_ptr,
|
||||
u32 *table_length, u8 *table_flags);
|
||||
|
||||
void
|
||||
acpi_tb_release_table(struct acpi_table_header *table,
|
||||
u32 table_length, u8 table_flags);
|
||||
|
||||
acpi_status
|
||||
acpi_tb_install_standard_table(acpi_physical_address address,
|
||||
u8 flags,
|
||||
u8 reload, u8 override, u32 *table_index);
|
||||
|
||||
acpi_status
|
||||
acpi_tb_store_table(acpi_physical_address address,
|
||||
struct acpi_table_header *table,
|
||||
u32 length, u8 flags, u32 *table_index);
|
||||
|
||||
void acpi_tb_delete_table(struct acpi_table_desc *table_desc);
|
||||
void acpi_tb_uninstall_table(struct acpi_table_desc *table_desc);
|
||||
|
||||
void acpi_tb_terminate(void);
|
||||
|
||||
@ -99,10 +132,6 @@ acpi_status acpi_tb_release_owner_id(u32 table_index);
|
||||
|
||||
acpi_status acpi_tb_get_owner_id(u32 table_index, acpi_owner_id *owner_id);
|
||||
|
||||
u8 acpi_tb_is_table_loaded(u32 table_index);
|
||||
|
||||
void acpi_tb_set_table_loaded_flag(u32 table_index, u8 is_loaded);
|
||||
|
||||
/*
|
||||
* tbutils - table manager utilities
|
||||
*/
|
||||
@ -124,8 +153,13 @@ void acpi_tb_check_dsdt_header(void);
|
||||
struct acpi_table_header *acpi_tb_copy_dsdt(u32 table_index);
|
||||
|
||||
void
|
||||
acpi_tb_install_table(acpi_physical_address address,
|
||||
char *signature, u32 table_index);
|
||||
acpi_tb_install_table_with_override(u32 table_index,
|
||||
struct acpi_table_desc *new_table_desc,
|
||||
u8 override);
|
||||
|
||||
acpi_status
|
||||
acpi_tb_install_fixed_table(acpi_physical_address address,
|
||||
char *signature, u32 table_index);
|
||||
|
||||
acpi_status acpi_tb_parse_root_table(acpi_physical_address rsdp_address);
|
||||
|
||||
|
@ -176,8 +176,7 @@ acpi_status acpi_ut_init_globals(void);
|
||||
|
||||
char *acpi_ut_get_mutex_name(u32 mutex_id);
|
||||
|
||||
const char *acpi_ut_get_notify_name(u32 notify_value);
|
||||
|
||||
const char *acpi_ut_get_notify_name(u32 notify_value, acpi_object_type type);
|
||||
#endif
|
||||
|
||||
char *acpi_ut_get_type_name(acpi_object_type type);
|
||||
@ -737,4 +736,11 @@ acpi_ut_method_error(const char *module_name,
|
||||
struct acpi_namespace_node *node,
|
||||
const char *path, acpi_status lookup_status);
|
||||
|
||||
/*
|
||||
* Utility functions for ACPI names and IDs
|
||||
*/
|
||||
const struct ah_predefined_name *acpi_ah_match_predefined_name(char *nameseg);
|
||||
|
||||
const struct ah_device_id *acpi_ah_match_hardware_id(char *hid);
|
||||
|
||||
#endif /* _ACUTILS_H */
|
||||
|
@ -167,7 +167,8 @@ acpi_ev_queue_notify_request(struct acpi_namespace_node * node,
|
||||
"Dispatching Notify on [%4.4s] (%s) Value 0x%2.2X (%s) Node %p\n",
|
||||
acpi_ut_get_node_name(node),
|
||||
acpi_ut_get_type_name(node->type), notify_value,
|
||||
acpi_ut_get_notify_name(notify_value), node));
|
||||
acpi_ut_get_notify_name(notify_value, ACPI_TYPE_ANY),
|
||||
node));
|
||||
|
||||
status = acpi_os_execute(OSL_NOTIFY_HANDLER, acpi_ev_notify_dispatch,
|
||||
info);
|
||||
|
@ -117,7 +117,7 @@ static u32 ACPI_SYSTEM_XFACE acpi_ev_sci_xrupt_handler(void *context)
|
||||
ACPI_FUNCTION_TRACE(ev_sci_xrupt_handler);
|
||||
|
||||
/*
|
||||
* We are guaranteed by the ACPI CA initialization/shutdown code that
|
||||
* We are guaranteed by the ACPICA initialization/shutdown code that
|
||||
* if this interrupt handler is installed, ACPI is enabled.
|
||||
*/
|
||||
|
||||
|
@ -239,7 +239,7 @@ acpi_remove_notify_handler(acpi_handle device,
|
||||
union acpi_operand_object *obj_desc;
|
||||
union acpi_operand_object *handler_obj;
|
||||
union acpi_operand_object *previous_handler_obj;
|
||||
acpi_status status;
|
||||
acpi_status status = AE_OK;
|
||||
u32 i;
|
||||
|
||||
ACPI_FUNCTION_TRACE(acpi_remove_notify_handler);
|
||||
@ -251,20 +251,17 @@ acpi_remove_notify_handler(acpi_handle device,
|
||||
return_ACPI_STATUS(AE_BAD_PARAMETER);
|
||||
}
|
||||
|
||||
/* Make sure all deferred notify tasks are completed */
|
||||
|
||||
acpi_os_wait_events_complete();
|
||||
|
||||
status = acpi_ut_acquire_mutex(ACPI_MTX_NAMESPACE);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
/* Root Object. Global handlers are removed here */
|
||||
|
||||
if (device == ACPI_ROOT_OBJECT) {
|
||||
for (i = 0; i < ACPI_NUM_NOTIFY_TYPES; i++) {
|
||||
if (handler_type & (i + 1)) {
|
||||
status =
|
||||
acpi_ut_acquire_mutex(ACPI_MTX_NAMESPACE);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
if (!acpi_gbl_global_notify[i].handler ||
|
||||
(acpi_gbl_global_notify[i].handler !=
|
||||
handler)) {
|
||||
@ -277,31 +274,40 @@ acpi_remove_notify_handler(acpi_handle device,
|
||||
|
||||
acpi_gbl_global_notify[i].handler = NULL;
|
||||
acpi_gbl_global_notify[i].context = NULL;
|
||||
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_NAMESPACE);
|
||||
|
||||
/* Make sure all deferred notify tasks are completed */
|
||||
|
||||
acpi_os_wait_events_complete();
|
||||
}
|
||||
}
|
||||
|
||||
goto unlock_and_exit;
|
||||
return_ACPI_STATUS(AE_OK);
|
||||
}
|
||||
|
||||
/* All other objects: Are Notifies allowed on this object? */
|
||||
|
||||
if (!acpi_ev_is_notify_object(node)) {
|
||||
status = AE_TYPE;
|
||||
goto unlock_and_exit;
|
||||
return_ACPI_STATUS(AE_TYPE);
|
||||
}
|
||||
|
||||
/* Must have an existing internal object */
|
||||
|
||||
obj_desc = acpi_ns_get_attached_object(node);
|
||||
if (!obj_desc) {
|
||||
status = AE_NOT_EXIST;
|
||||
goto unlock_and_exit;
|
||||
return_ACPI_STATUS(AE_NOT_EXIST);
|
||||
}
|
||||
|
||||
/* Internal object exists. Find the handler and remove it */
|
||||
|
||||
for (i = 0; i < ACPI_NUM_NOTIFY_TYPES; i++) {
|
||||
if (handler_type & (i + 1)) {
|
||||
status = acpi_ut_acquire_mutex(ACPI_MTX_NAMESPACE);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
handler_obj = obj_desc->common_notify.notify_list[i];
|
||||
previous_handler_obj = NULL;
|
||||
|
||||
@ -329,10 +335,17 @@ acpi_remove_notify_handler(acpi_handle device,
|
||||
handler_obj->notify.next[i];
|
||||
}
|
||||
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_NAMESPACE);
|
||||
|
||||
/* Make sure all deferred notify tasks are completed */
|
||||
|
||||
acpi_os_wait_events_complete();
|
||||
acpi_ut_remove_reference(handler_obj);
|
||||
}
|
||||
}
|
||||
|
||||
return_ACPI_STATUS(status);
|
||||
|
||||
unlock_and_exit:
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_NAMESPACE);
|
||||
return_ACPI_STATUS(status);
|
||||
@ -457,6 +470,8 @@ exit:
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
ACPI_EXPORT_SYMBOL(acpi_install_sci_handler)
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_remove_sci_handler
|
||||
@ -468,7 +483,6 @@ exit:
|
||||
* DESCRIPTION: Remove a handler for a System Control Interrupt.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
acpi_status acpi_remove_sci_handler(acpi_sci_handler address)
|
||||
{
|
||||
struct acpi_sci_handler_info *prev_sci_handler;
|
||||
@ -522,6 +536,8 @@ unlock_and_exit:
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
ACPI_EXPORT_SYMBOL(acpi_remove_sci_handler)
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_install_global_event_handler
|
||||
@ -537,7 +553,6 @@ unlock_and_exit:
|
||||
* Can be used to update event counters, etc.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
acpi_status
|
||||
acpi_install_global_event_handler(acpi_gbl_event_handler handler, void *context)
|
||||
{
|
||||
@ -840,10 +855,6 @@ acpi_remove_gpe_handler(acpi_handle gpe_device,
|
||||
return_ACPI_STATUS(AE_BAD_PARAMETER);
|
||||
}
|
||||
|
||||
/* Make sure all deferred GPE tasks are completed */
|
||||
|
||||
acpi_os_wait_events_complete();
|
||||
|
||||
status = acpi_ut_acquire_mutex(ACPI_MTX_EVENTS);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
return_ACPI_STATUS(status);
|
||||
@ -895,9 +906,17 @@ acpi_remove_gpe_handler(acpi_handle gpe_device,
|
||||
(void)acpi_ev_add_gpe_reference(gpe_event_info);
|
||||
}
|
||||
|
||||
acpi_os_release_lock(acpi_gbl_gpe_lock, flags);
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_EVENTS);
|
||||
|
||||
/* Make sure all deferred GPE tasks are completed */
|
||||
|
||||
acpi_os_wait_events_complete();
|
||||
|
||||
/* Now we can free the handler object */
|
||||
|
||||
ACPI_FREE(handler);
|
||||
return_ACPI_STATUS(status);
|
||||
|
||||
unlock_and_exit:
|
||||
acpi_os_release_lock(acpi_gbl_gpe_lock, flags);
|
||||
|
@ -343,16 +343,14 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc,
|
||||
struct acpi_walk_state *walk_state)
|
||||
{
|
||||
union acpi_operand_object *ddb_handle;
|
||||
struct acpi_table_header *table_header;
|
||||
struct acpi_table_header *table;
|
||||
struct acpi_table_desc table_desc;
|
||||
u32 table_index;
|
||||
acpi_status status;
|
||||
u32 length;
|
||||
|
||||
ACPI_FUNCTION_TRACE(ex_load_op);
|
||||
|
||||
ACPI_MEMSET(&table_desc, 0, sizeof(struct acpi_table_desc));
|
||||
|
||||
/* Source Object can be either an op_region or a Buffer/Field */
|
||||
|
||||
switch (obj_desc->common.type) {
|
||||
@ -380,17 +378,17 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc,
|
||||
|
||||
/* Get the table header first so we can get the table length */
|
||||
|
||||
table = ACPI_ALLOCATE(sizeof(struct acpi_table_header));
|
||||
if (!table) {
|
||||
table_header = ACPI_ALLOCATE(sizeof(struct acpi_table_header));
|
||||
if (!table_header) {
|
||||
return_ACPI_STATUS(AE_NO_MEMORY);
|
||||
}
|
||||
|
||||
status =
|
||||
acpi_ex_region_read(obj_desc,
|
||||
sizeof(struct acpi_table_header),
|
||||
ACPI_CAST_PTR(u8, table));
|
||||
length = table->length;
|
||||
ACPI_FREE(table);
|
||||
ACPI_CAST_PTR(u8, table_header));
|
||||
length = table_header->length;
|
||||
ACPI_FREE(table_header);
|
||||
|
||||
if (ACPI_FAILURE(status)) {
|
||||
return_ACPI_STATUS(status);
|
||||
@ -420,22 +418,19 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc,
|
||||
|
||||
/* Allocate a buffer for the table */
|
||||
|
||||
table_desc.pointer = ACPI_ALLOCATE(length);
|
||||
if (!table_desc.pointer) {
|
||||
table = ACPI_ALLOCATE(length);
|
||||
if (!table) {
|
||||
return_ACPI_STATUS(AE_NO_MEMORY);
|
||||
}
|
||||
|
||||
/* Read the entire table */
|
||||
|
||||
status = acpi_ex_region_read(obj_desc, length,
|
||||
ACPI_CAST_PTR(u8,
|
||||
table_desc.pointer));
|
||||
ACPI_CAST_PTR(u8, table));
|
||||
if (ACPI_FAILURE(status)) {
|
||||
ACPI_FREE(table_desc.pointer);
|
||||
ACPI_FREE(table);
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
table_desc.address = obj_desc->region.address;
|
||||
break;
|
||||
|
||||
case ACPI_TYPE_BUFFER: /* Buffer or resolved region_field */
|
||||
@ -452,10 +447,10 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc,
|
||||
|
||||
/* Get the actual table length from the table header */
|
||||
|
||||
table =
|
||||
table_header =
|
||||
ACPI_CAST_PTR(struct acpi_table_header,
|
||||
obj_desc->buffer.pointer);
|
||||
length = table->length;
|
||||
length = table_header->length;
|
||||
|
||||
/* Table cannot extend beyond the buffer */
|
||||
|
||||
@ -470,13 +465,12 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc,
|
||||
* Copy the table from the buffer because the buffer could be modified
|
||||
* or even deleted in the future
|
||||
*/
|
||||
table_desc.pointer = ACPI_ALLOCATE(length);
|
||||
if (!table_desc.pointer) {
|
||||
table = ACPI_ALLOCATE(length);
|
||||
if (!table) {
|
||||
return_ACPI_STATUS(AE_NO_MEMORY);
|
||||
}
|
||||
|
||||
ACPI_MEMCPY(table_desc.pointer, table, length);
|
||||
table_desc.address = ACPI_TO_INTEGER(table_desc.pointer);
|
||||
ACPI_MEMCPY(table, table_header, length);
|
||||
break;
|
||||
|
||||
default:
|
||||
@ -484,27 +478,32 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc,
|
||||
return_ACPI_STATUS(AE_AML_OPERAND_TYPE);
|
||||
}
|
||||
|
||||
/* Validate table checksum (will not get validated in tb_add_table) */
|
||||
|
||||
status = acpi_tb_verify_checksum(table_desc.pointer, length);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
ACPI_FREE(table_desc.pointer);
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
/* Complete the table descriptor */
|
||||
|
||||
table_desc.length = length;
|
||||
table_desc.flags = ACPI_TABLE_ORIGIN_ALLOCATED;
|
||||
|
||||
/* Install the new table into the local data structures */
|
||||
|
||||
status = acpi_tb_add_table(&table_desc, &table_index);
|
||||
ACPI_INFO((AE_INFO, "Dynamic OEM Table Load:"));
|
||||
(void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES);
|
||||
|
||||
status = acpi_tb_install_standard_table(ACPI_PTR_TO_PHYSADDR(table),
|
||||
ACPI_TABLE_ORIGIN_INTERNAL_VIRTUAL,
|
||||
TRUE, TRUE, &table_index);
|
||||
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_TABLES);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
|
||||
/* Delete allocated table buffer */
|
||||
|
||||
acpi_tb_delete_table(&table_desc);
|
||||
ACPI_FREE(table);
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
/*
|
||||
* Note: Now table is "INSTALLED", it must be validated before
|
||||
* loading.
|
||||
*/
|
||||
status =
|
||||
acpi_tb_validate_table(&acpi_gbl_root_table_list.
|
||||
tables[table_index]);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
@ -536,9 +535,6 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc,
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
ACPI_INFO((AE_INFO, "Dynamic OEM Table Load:"));
|
||||
acpi_tb_print_table_header(0, table_desc.pointer);
|
||||
|
||||
/* Remove the reference by added by acpi_ex_store above */
|
||||
|
||||
acpi_ut_remove_reference(ddb_handle);
|
||||
@ -546,8 +542,7 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc,
|
||||
/* Invoke table handler if present */
|
||||
|
||||
if (acpi_gbl_table_handler) {
|
||||
(void)acpi_gbl_table_handler(ACPI_TABLE_EVENT_LOAD,
|
||||
table_desc.pointer,
|
||||
(void)acpi_gbl_table_handler(ACPI_TABLE_EVENT_LOAD, table,
|
||||
acpi_gbl_table_handler_context);
|
||||
}
|
||||
|
||||
@ -575,6 +570,13 @@ acpi_status acpi_ex_unload_table(union acpi_operand_object *ddb_handle)
|
||||
|
||||
ACPI_FUNCTION_TRACE(ex_unload_table);
|
||||
|
||||
/*
|
||||
* Temporarily emit a warning so that the ASL for the machine can be
|
||||
* hopefully obtained. This is to say that the Unload() operator is
|
||||
* extremely rare if not completely unused.
|
||||
*/
|
||||
ACPI_WARNING((AE_INFO, "Received request to unload an ACPI table"));
|
||||
|
||||
/*
|
||||
* Validate the handle
|
||||
* Although the handle is partially validated in acpi_ex_reconfiguration()
|
||||
|
@ -134,9 +134,11 @@ static struct acpi_exdump_info acpi_ex_dump_method[9] = {
|
||||
{ACPI_EXD_POINTER, ACPI_EXD_OFFSET(method.aml_start), "Aml Start"}
|
||||
};
|
||||
|
||||
static struct acpi_exdump_info acpi_ex_dump_mutex[5] = {
|
||||
static struct acpi_exdump_info acpi_ex_dump_mutex[6] = {
|
||||
{ACPI_EXD_INIT, ACPI_EXD_TABLE_SIZE(acpi_ex_dump_mutex), NULL},
|
||||
{ACPI_EXD_UINT8, ACPI_EXD_OFFSET(mutex.sync_level), "Sync Level"},
|
||||
{ACPI_EXD_UINT8, ACPI_EXD_OFFSET(mutex.original_sync_level),
|
||||
"Original Sync Level"},
|
||||
{ACPI_EXD_POINTER, ACPI_EXD_OFFSET(mutex.owner_thread), "Owner Thread"},
|
||||
{ACPI_EXD_UINT16, ACPI_EXD_OFFSET(mutex.acquisition_depth),
|
||||
"Acquire Depth"},
|
||||
|
723
drivers/acpi/acpica/tbdata.c
Normal file
723
drivers/acpi/acpica/tbdata.c
Normal file
@ -0,0 +1,723 @@
|
||||
/******************************************************************************
|
||||
*
|
||||
* Module Name: tbdata - Table manager data structure functions
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2000 - 2014, Intel Corp.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification.
|
||||
* 2. Redistributions in binary form must reproduce at minimum a disclaimer
|
||||
* substantially similar to the "NO WARRANTY" disclaimer below
|
||||
* ("Disclaimer") and any redistribution must be conditioned upon
|
||||
* including a substantially similar Disclaimer requirement for further
|
||||
* binary redistribution.
|
||||
* 3. Neither the names of the above-listed copyright holders nor the names
|
||||
* of any contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* Alternatively, this software may be distributed under the terms of the
|
||||
* GNU General Public License ("GPL") version 2 as published by the Free
|
||||
* Software Foundation.
|
||||
*
|
||||
* NO WARRANTY
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
* HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
||||
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
|
||||
* IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGES.
|
||||
*/
|
||||
|
||||
#include <acpi/acpi.h>
|
||||
#include "accommon.h"
|
||||
#include "acnamesp.h"
|
||||
#include "actables.h"
|
||||
|
||||
#define _COMPONENT ACPI_TABLES
|
||||
ACPI_MODULE_NAME("tbdata")
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_init_table_descriptor
|
||||
*
|
||||
* PARAMETERS: table_desc - Table descriptor
|
||||
* address - Physical address of the table
|
||||
* flags - Allocation flags of the table
|
||||
* table - Pointer to the table
|
||||
*
|
||||
* RETURN: None
|
||||
*
|
||||
* DESCRIPTION: Initialize a new table descriptor
|
||||
*
|
||||
******************************************************************************/
|
||||
void
|
||||
acpi_tb_init_table_descriptor(struct acpi_table_desc *table_desc,
|
||||
acpi_physical_address address,
|
||||
u8 flags, struct acpi_table_header *table)
|
||||
{
|
||||
|
||||
/*
|
||||
* Initialize the table descriptor. Set the pointer to NULL, since the
|
||||
* table is not fully mapped at this time.
|
||||
*/
|
||||
ACPI_MEMSET(table_desc, 0, sizeof(struct acpi_table_desc));
|
||||
table_desc->address = address;
|
||||
table_desc->length = table->length;
|
||||
table_desc->flags = flags;
|
||||
ACPI_MOVE_32_TO_32(table_desc->signature.ascii, table->signature);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_acquire_table
|
||||
*
|
||||
* PARAMETERS: table_desc - Table descriptor
|
||||
* table_ptr - Where table is returned
|
||||
* table_length - Where table length is returned
|
||||
* table_flags - Where table allocation flags are returned
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: Acquire an ACPI table. It can be used for tables not
|
||||
* maintained in the acpi_gbl_root_table_list.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
acpi_status
|
||||
acpi_tb_acquire_table(struct acpi_table_desc *table_desc,
|
||||
struct acpi_table_header **table_ptr,
|
||||
u32 *table_length, u8 *table_flags)
|
||||
{
|
||||
struct acpi_table_header *table = NULL;
|
||||
|
||||
switch (table_desc->flags & ACPI_TABLE_ORIGIN_MASK) {
|
||||
case ACPI_TABLE_ORIGIN_INTERNAL_PHYSICAL:
|
||||
|
||||
table =
|
||||
acpi_os_map_memory(table_desc->address, table_desc->length);
|
||||
break;
|
||||
|
||||
case ACPI_TABLE_ORIGIN_INTERNAL_VIRTUAL:
|
||||
case ACPI_TABLE_ORIGIN_EXTERNAL_VIRTUAL:
|
||||
|
||||
table =
|
||||
ACPI_CAST_PTR(struct acpi_table_header,
|
||||
table_desc->address);
|
||||
break;
|
||||
|
||||
default:
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
/* Table is not valid yet */
|
||||
|
||||
if (!table) {
|
||||
return (AE_NO_MEMORY);
|
||||
}
|
||||
|
||||
/* Fill the return values */
|
||||
|
||||
*table_ptr = table;
|
||||
*table_length = table_desc->length;
|
||||
*table_flags = table_desc->flags;
|
||||
return (AE_OK);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_release_table
|
||||
*
|
||||
* PARAMETERS: table - Pointer for the table
|
||||
* table_length - Length for the table
|
||||
* table_flags - Allocation flags for the table
|
||||
*
|
||||
* RETURN: None
|
||||
*
|
||||
* DESCRIPTION: Release a table. The inverse of acpi_tb_acquire_table().
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
void
|
||||
acpi_tb_release_table(struct acpi_table_header *table,
|
||||
u32 table_length, u8 table_flags)
|
||||
{
|
||||
|
||||
switch (table_flags & ACPI_TABLE_ORIGIN_MASK) {
|
||||
case ACPI_TABLE_ORIGIN_INTERNAL_PHYSICAL:
|
||||
|
||||
acpi_os_unmap_memory(table, table_length);
|
||||
break;
|
||||
|
||||
case ACPI_TABLE_ORIGIN_INTERNAL_VIRTUAL:
|
||||
case ACPI_TABLE_ORIGIN_EXTERNAL_VIRTUAL:
|
||||
default:
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_acquire_temp_table
|
||||
*
|
||||
* PARAMETERS: table_desc - Table descriptor to be acquired
|
||||
* address - Address of the table
|
||||
* flags - Allocation flags of the table
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: This function validates the table header to obtain the length
|
||||
* of a table and fills the table descriptor to make its state as
|
||||
* "INSTALLED". Such a table descriptor is only used for verified
|
||||
* installation.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
acpi_status
|
||||
acpi_tb_acquire_temp_table(struct acpi_table_desc *table_desc,
|
||||
acpi_physical_address address, u8 flags)
|
||||
{
|
||||
struct acpi_table_header *table_header;
|
||||
|
||||
switch (flags & ACPI_TABLE_ORIGIN_MASK) {
|
||||
case ACPI_TABLE_ORIGIN_INTERNAL_PHYSICAL:
|
||||
|
||||
/* Get the length of the full table from the header */
|
||||
|
||||
table_header =
|
||||
acpi_os_map_memory(address,
|
||||
sizeof(struct acpi_table_header));
|
||||
if (!table_header) {
|
||||
return (AE_NO_MEMORY);
|
||||
}
|
||||
|
||||
acpi_tb_init_table_descriptor(table_desc, address, flags,
|
||||
table_header);
|
||||
acpi_os_unmap_memory(table_header,
|
||||
sizeof(struct acpi_table_header));
|
||||
return (AE_OK);
|
||||
|
||||
case ACPI_TABLE_ORIGIN_INTERNAL_VIRTUAL:
|
||||
case ACPI_TABLE_ORIGIN_EXTERNAL_VIRTUAL:
|
||||
|
||||
table_header = ACPI_CAST_PTR(struct acpi_table_header, address);
|
||||
if (!table_header) {
|
||||
return (AE_NO_MEMORY);
|
||||
}
|
||||
|
||||
acpi_tb_init_table_descriptor(table_desc, address, flags,
|
||||
table_header);
|
||||
return (AE_OK);
|
||||
|
||||
default:
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
/* Table is not valid yet */
|
||||
|
||||
return (AE_NO_MEMORY);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_release_temp_table
|
||||
*
|
||||
* PARAMETERS: table_desc - Table descriptor to be released
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: The inverse of acpi_tb_acquire_temp_table().
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
void acpi_tb_release_temp_table(struct acpi_table_desc *table_desc)
|
||||
{
|
||||
|
||||
/*
|
||||
* Note that the .Address is maintained by the callers of
|
||||
* acpi_tb_acquire_temp_table(), thus do not invoke acpi_tb_uninstall_table()
|
||||
* where .Address will be freed.
|
||||
*/
|
||||
acpi_tb_invalidate_table(table_desc);
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_validate_table
|
||||
*
|
||||
* PARAMETERS: table_desc - Table descriptor
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: This function is called to validate the table, the returned
|
||||
* table descriptor is in "VALIDATED" state.
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
acpi_status acpi_tb_validate_table(struct acpi_table_desc *table_desc)
|
||||
{
|
||||
acpi_status status = AE_OK;
|
||||
|
||||
ACPI_FUNCTION_TRACE(tb_validate_table);
|
||||
|
||||
/* Validate the table if necessary */
|
||||
|
||||
if (!table_desc->pointer) {
|
||||
status = acpi_tb_acquire_table(table_desc, &table_desc->pointer,
|
||||
&table_desc->length,
|
||||
&table_desc->flags);
|
||||
if (!table_desc->pointer) {
|
||||
status = AE_NO_MEMORY;
|
||||
}
|
||||
}
|
||||
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_invalidate_table
|
||||
*
|
||||
* PARAMETERS: table_desc - Table descriptor
|
||||
*
|
||||
* RETURN: None
|
||||
*
|
||||
* DESCRIPTION: Invalidate one internal ACPI table, this is the inverse of
|
||||
* acpi_tb_validate_table().
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
void acpi_tb_invalidate_table(struct acpi_table_desc *table_desc)
|
||||
{
|
||||
|
||||
ACPI_FUNCTION_TRACE(tb_invalidate_table);
|
||||
|
||||
/* Table must be validated */
|
||||
|
||||
if (!table_desc->pointer) {
|
||||
return_VOID;
|
||||
}
|
||||
|
||||
acpi_tb_release_table(table_desc->pointer, table_desc->length,
|
||||
table_desc->flags);
|
||||
table_desc->pointer = NULL;
|
||||
|
||||
return_VOID;
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_verify_table
|
||||
*
|
||||
* PARAMETERS: table_desc - Table descriptor
|
||||
* signature - Table signature to verify
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: This function is called to validate and verify the table, the
|
||||
* returned table descriptor is in "VALIDATED" state.
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
acpi_status
|
||||
acpi_tb_verify_table(struct acpi_table_desc *table_desc, char *signature)
|
||||
{
|
||||
acpi_status status = AE_OK;
|
||||
|
||||
ACPI_FUNCTION_TRACE(tb_verify_table);
|
||||
|
||||
/* Validate the table */
|
||||
|
||||
status = acpi_tb_validate_table(table_desc);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
return_ACPI_STATUS(AE_NO_MEMORY);
|
||||
}
|
||||
|
||||
/* If a particular signature is expected (DSDT/FACS), it must match */
|
||||
|
||||
if (signature && !ACPI_COMPARE_NAME(&table_desc->signature, signature)) {
|
||||
ACPI_BIOS_ERROR((AE_INFO,
|
||||
"Invalid signature 0x%X for ACPI table, expected [%s]",
|
||||
table_desc->signature.integer, signature));
|
||||
status = AE_BAD_SIGNATURE;
|
||||
goto invalidate_and_exit;
|
||||
}
|
||||
|
||||
/* Verify the checksum */
|
||||
|
||||
status =
|
||||
acpi_tb_verify_checksum(table_desc->pointer, table_desc->length);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
ACPI_EXCEPTION((AE_INFO, AE_NO_MEMORY,
|
||||
"%4.4s " ACPI_PRINTF_UINT
|
||||
" Attempted table install failed",
|
||||
acpi_ut_valid_acpi_name(table_desc->signature.
|
||||
ascii) ? table_desc->
|
||||
signature.ascii : "????",
|
||||
ACPI_FORMAT_TO_UINT(table_desc->address)));
|
||||
goto invalidate_and_exit;
|
||||
}
|
||||
|
||||
return_ACPI_STATUS(AE_OK);
|
||||
|
||||
invalidate_and_exit:
|
||||
acpi_tb_invalidate_table(table_desc);
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_resize_root_table_list
|
||||
*
|
||||
* PARAMETERS: None
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: Expand the size of global table array
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
acpi_status acpi_tb_resize_root_table_list(void)
|
||||
{
|
||||
struct acpi_table_desc *tables;
|
||||
u32 table_count;
|
||||
|
||||
ACPI_FUNCTION_TRACE(tb_resize_root_table_list);
|
||||
|
||||
/* allow_resize flag is a parameter to acpi_initialize_tables */
|
||||
|
||||
if (!(acpi_gbl_root_table_list.flags & ACPI_ROOT_ALLOW_RESIZE)) {
|
||||
ACPI_ERROR((AE_INFO,
|
||||
"Resize of Root Table Array is not allowed"));
|
||||
return_ACPI_STATUS(AE_SUPPORT);
|
||||
}
|
||||
|
||||
/* Increase the Table Array size */
|
||||
|
||||
if (acpi_gbl_root_table_list.flags & ACPI_ROOT_ORIGIN_ALLOCATED) {
|
||||
table_count = acpi_gbl_root_table_list.max_table_count;
|
||||
} else {
|
||||
table_count = acpi_gbl_root_table_list.current_table_count;
|
||||
}
|
||||
|
||||
tables = ACPI_ALLOCATE_ZEROED(((acpi_size) table_count +
|
||||
ACPI_ROOT_TABLE_SIZE_INCREMENT) *
|
||||
sizeof(struct acpi_table_desc));
|
||||
if (!tables) {
|
||||
ACPI_ERROR((AE_INFO,
|
||||
"Could not allocate new root table array"));
|
||||
return_ACPI_STATUS(AE_NO_MEMORY);
|
||||
}
|
||||
|
||||
/* Copy and free the previous table array */
|
||||
|
||||
if (acpi_gbl_root_table_list.tables) {
|
||||
ACPI_MEMCPY(tables, acpi_gbl_root_table_list.tables,
|
||||
(acpi_size) table_count *
|
||||
sizeof(struct acpi_table_desc));
|
||||
|
||||
if (acpi_gbl_root_table_list.flags & ACPI_ROOT_ORIGIN_ALLOCATED) {
|
||||
ACPI_FREE(acpi_gbl_root_table_list.tables);
|
||||
}
|
||||
}
|
||||
|
||||
acpi_gbl_root_table_list.tables = tables;
|
||||
acpi_gbl_root_table_list.max_table_count =
|
||||
table_count + ACPI_ROOT_TABLE_SIZE_INCREMENT;
|
||||
acpi_gbl_root_table_list.flags |= ACPI_ROOT_ORIGIN_ALLOCATED;
|
||||
|
||||
return_ACPI_STATUS(AE_OK);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_get_next_root_index
|
||||
*
|
||||
* PARAMETERS: table_index - Where table index is returned
|
||||
*
|
||||
* RETURN: Status and table index.
|
||||
*
|
||||
* DESCRIPTION: Allocate a new ACPI table entry to the global table list
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
acpi_status acpi_tb_get_next_root_index(u32 *table_index)
|
||||
{
|
||||
acpi_status status;
|
||||
|
||||
/* Ensure that there is room for the table in the Root Table List */
|
||||
|
||||
if (acpi_gbl_root_table_list.current_table_count >=
|
||||
acpi_gbl_root_table_list.max_table_count) {
|
||||
status = acpi_tb_resize_root_table_list();
|
||||
if (ACPI_FAILURE(status)) {
|
||||
return (status);
|
||||
}
|
||||
}
|
||||
|
||||
*table_index = acpi_gbl_root_table_list.current_table_count;
|
||||
acpi_gbl_root_table_list.current_table_count++;
|
||||
return (AE_OK);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_terminate
|
||||
*
|
||||
* PARAMETERS: None
|
||||
*
|
||||
* RETURN: None
|
||||
*
|
||||
* DESCRIPTION: Delete all internal ACPI tables
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
void acpi_tb_terminate(void)
|
||||
{
|
||||
u32 i;
|
||||
|
||||
ACPI_FUNCTION_TRACE(tb_terminate);
|
||||
|
||||
(void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES);
|
||||
|
||||
/* Delete the individual tables */
|
||||
|
||||
for (i = 0; i < acpi_gbl_root_table_list.current_table_count; i++) {
|
||||
acpi_tb_uninstall_table(&acpi_gbl_root_table_list.tables[i]);
|
||||
}
|
||||
|
||||
/*
|
||||
* Delete the root table array if allocated locally. Array cannot be
|
||||
* mapped, so we don't need to check for that flag.
|
||||
*/
|
||||
if (acpi_gbl_root_table_list.flags & ACPI_ROOT_ORIGIN_ALLOCATED) {
|
||||
ACPI_FREE(acpi_gbl_root_table_list.tables);
|
||||
}
|
||||
|
||||
acpi_gbl_root_table_list.tables = NULL;
|
||||
acpi_gbl_root_table_list.flags = 0;
|
||||
acpi_gbl_root_table_list.current_table_count = 0;
|
||||
|
||||
ACPI_DEBUG_PRINT((ACPI_DB_INFO, "ACPI Tables freed\n"));
|
||||
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_TABLES);
|
||||
return_VOID;
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_delete_namespace_by_owner
|
||||
*
|
||||
* PARAMETERS: table_index - Table index
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: Delete all namespace objects created when this table was loaded.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
acpi_status acpi_tb_delete_namespace_by_owner(u32 table_index)
|
||||
{
|
||||
acpi_owner_id owner_id;
|
||||
acpi_status status;
|
||||
|
||||
ACPI_FUNCTION_TRACE(tb_delete_namespace_by_owner);
|
||||
|
||||
status = acpi_ut_acquire_mutex(ACPI_MTX_TABLES);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
if (table_index >= acpi_gbl_root_table_list.current_table_count) {
|
||||
|
||||
/* The table index does not exist */
|
||||
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_TABLES);
|
||||
return_ACPI_STATUS(AE_NOT_EXIST);
|
||||
}
|
||||
|
||||
/* Get the owner ID for this table, used to delete namespace nodes */
|
||||
|
||||
owner_id = acpi_gbl_root_table_list.tables[table_index].owner_id;
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_TABLES);
|
||||
|
||||
/*
|
||||
* Need to acquire the namespace writer lock to prevent interference
|
||||
* with any concurrent namespace walks. The interpreter must be
|
||||
* released during the deletion since the acquisition of the deletion
|
||||
* lock may block, and also since the execution of a namespace walk
|
||||
* must be allowed to use the interpreter.
|
||||
*/
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_INTERPRETER);
|
||||
status = acpi_ut_acquire_write_lock(&acpi_gbl_namespace_rw_lock);
|
||||
|
||||
acpi_ns_delete_namespace_by_owner(owner_id);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
acpi_ut_release_write_lock(&acpi_gbl_namespace_rw_lock);
|
||||
|
||||
status = acpi_ut_acquire_mutex(ACPI_MTX_INTERPRETER);
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_allocate_owner_id
|
||||
*
|
||||
* PARAMETERS: table_index - Table index
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: Allocates owner_id in table_desc
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
acpi_status acpi_tb_allocate_owner_id(u32 table_index)
|
||||
{
|
||||
acpi_status status = AE_BAD_PARAMETER;
|
||||
|
||||
ACPI_FUNCTION_TRACE(tb_allocate_owner_id);
|
||||
|
||||
(void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES);
|
||||
if (table_index < acpi_gbl_root_table_list.current_table_count) {
|
||||
status =
|
||||
acpi_ut_allocate_owner_id(&
|
||||
(acpi_gbl_root_table_list.
|
||||
tables[table_index].owner_id));
|
||||
}
|
||||
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_TABLES);
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_release_owner_id
|
||||
*
|
||||
* PARAMETERS: table_index - Table index
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: Releases owner_id in table_desc
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
acpi_status acpi_tb_release_owner_id(u32 table_index)
|
||||
{
|
||||
acpi_status status = AE_BAD_PARAMETER;
|
||||
|
||||
ACPI_FUNCTION_TRACE(tb_release_owner_id);
|
||||
|
||||
(void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES);
|
||||
if (table_index < acpi_gbl_root_table_list.current_table_count) {
|
||||
acpi_ut_release_owner_id(&
|
||||
(acpi_gbl_root_table_list.
|
||||
tables[table_index].owner_id));
|
||||
status = AE_OK;
|
||||
}
|
||||
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_TABLES);
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_get_owner_id
|
||||
*
|
||||
* PARAMETERS: table_index - Table index
|
||||
* owner_id - Where the table owner_id is returned
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: returns owner_id for the ACPI table
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
acpi_status acpi_tb_get_owner_id(u32 table_index, acpi_owner_id * owner_id)
|
||||
{
|
||||
acpi_status status = AE_BAD_PARAMETER;
|
||||
|
||||
ACPI_FUNCTION_TRACE(tb_get_owner_id);
|
||||
|
||||
(void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES);
|
||||
if (table_index < acpi_gbl_root_table_list.current_table_count) {
|
||||
*owner_id =
|
||||
acpi_gbl_root_table_list.tables[table_index].owner_id;
|
||||
status = AE_OK;
|
||||
}
|
||||
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_TABLES);
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_is_table_loaded
|
||||
*
|
||||
* PARAMETERS: table_index - Index into the root table
|
||||
*
|
||||
* RETURN: Table Loaded Flag
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
u8 acpi_tb_is_table_loaded(u32 table_index)
|
||||
{
|
||||
u8 is_loaded = FALSE;
|
||||
|
||||
(void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES);
|
||||
if (table_index < acpi_gbl_root_table_list.current_table_count) {
|
||||
is_loaded = (u8)
|
||||
(acpi_gbl_root_table_list.tables[table_index].flags &
|
||||
ACPI_TABLE_IS_LOADED);
|
||||
}
|
||||
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_TABLES);
|
||||
return (is_loaded);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_set_table_loaded_flag
|
||||
*
|
||||
* PARAMETERS: table_index - Table index
|
||||
* is_loaded - TRUE if table is loaded, FALSE otherwise
|
||||
*
|
||||
* RETURN: None
|
||||
*
|
||||
* DESCRIPTION: Sets the table loaded flag to either TRUE or FALSE.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
void acpi_tb_set_table_loaded_flag(u32 table_index, u8 is_loaded)
|
||||
{
|
||||
|
||||
(void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES);
|
||||
if (table_index < acpi_gbl_root_table_list.current_table_count) {
|
||||
if (is_loaded) {
|
||||
acpi_gbl_root_table_list.tables[table_index].flags |=
|
||||
ACPI_TABLE_IS_LOADED;
|
||||
} else {
|
||||
acpi_gbl_root_table_list.tables[table_index].flags &=
|
||||
~ACPI_TABLE_IS_LOADED;
|
||||
}
|
||||
}
|
||||
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_TABLES);
|
||||
}
|
@ -332,15 +332,15 @@ void acpi_tb_parse_fadt(u32 table_index)
|
||||
|
||||
/* Obtain the DSDT and FACS tables via their addresses within the FADT */
|
||||
|
||||
acpi_tb_install_table((acpi_physical_address) acpi_gbl_FADT.Xdsdt,
|
||||
ACPI_SIG_DSDT, ACPI_TABLE_INDEX_DSDT);
|
||||
acpi_tb_install_fixed_table((acpi_physical_address) acpi_gbl_FADT.Xdsdt,
|
||||
ACPI_SIG_DSDT, ACPI_TABLE_INDEX_DSDT);
|
||||
|
||||
/* If Hardware Reduced flag is set, there is no FACS */
|
||||
|
||||
if (!acpi_gbl_reduced_hardware) {
|
||||
acpi_tb_install_table((acpi_physical_address) acpi_gbl_FADT.
|
||||
Xfacs, ACPI_SIG_FACS,
|
||||
ACPI_TABLE_INDEX_FACS);
|
||||
acpi_tb_install_fixed_table((acpi_physical_address)
|
||||
acpi_gbl_FADT.Xfacs, ACPI_SIG_FACS,
|
||||
ACPI_TABLE_INDEX_FACS);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -99,8 +99,8 @@ acpi_tb_find_table(char *signature,
|
||||
/* Table is not currently mapped, map it */
|
||||
|
||||
status =
|
||||
acpi_tb_verify_table(&acpi_gbl_root_table_list.
|
||||
tables[i]);
|
||||
acpi_tb_validate_table(&acpi_gbl_root_table_list.
|
||||
tables[i]);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -178,9 +178,13 @@ struct acpi_table_header *acpi_tb_copy_dsdt(u32 table_index)
|
||||
}
|
||||
|
||||
ACPI_MEMCPY(new_table, table_desc->pointer, table_desc->length);
|
||||
acpi_tb_delete_table(table_desc);
|
||||
table_desc->pointer = new_table;
|
||||
table_desc->flags = ACPI_TABLE_ORIGIN_ALLOCATED;
|
||||
acpi_tb_uninstall_table(table_desc);
|
||||
|
||||
acpi_tb_init_table_descriptor(&acpi_gbl_root_table_list.
|
||||
tables[ACPI_TABLE_INDEX_DSDT],
|
||||
ACPI_PTR_TO_PHYSADDR(new_table),
|
||||
ACPI_TABLE_ORIGIN_INTERNAL_VIRTUAL,
|
||||
new_table);
|
||||
|
||||
ACPI_INFO((AE_INFO,
|
||||
"Forced DSDT copy: length 0x%05X copied locally, original unmapped",
|
||||
@ -189,116 +193,6 @@ struct acpi_table_header *acpi_tb_copy_dsdt(u32 table_index)
|
||||
return (new_table);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_install_table
|
||||
*
|
||||
* PARAMETERS: address - Physical address of DSDT or FACS
|
||||
* signature - Table signature, NULL if no need to
|
||||
* match
|
||||
* table_index - Index into root table array
|
||||
*
|
||||
* RETURN: None
|
||||
*
|
||||
* DESCRIPTION: Install an ACPI table into the global data structure. The
|
||||
* table override mechanism is called to allow the host
|
||||
* OS to replace any table before it is installed in the root
|
||||
* table array.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
void
|
||||
acpi_tb_install_table(acpi_physical_address address,
|
||||
char *signature, u32 table_index)
|
||||
{
|
||||
struct acpi_table_header *table;
|
||||
struct acpi_table_header *final_table;
|
||||
struct acpi_table_desc *table_desc;
|
||||
|
||||
if (!address) {
|
||||
ACPI_ERROR((AE_INFO,
|
||||
"Null physical address for ACPI table [%s]",
|
||||
signature));
|
||||
return;
|
||||
}
|
||||
|
||||
/* Map just the table header */
|
||||
|
||||
table = acpi_os_map_memory(address, sizeof(struct acpi_table_header));
|
||||
if (!table) {
|
||||
ACPI_ERROR((AE_INFO,
|
||||
"Could not map memory for table [%s] at %p",
|
||||
signature, ACPI_CAST_PTR(void, address)));
|
||||
return;
|
||||
}
|
||||
|
||||
/* If a particular signature is expected (DSDT/FACS), it must match */
|
||||
|
||||
if (signature && !ACPI_COMPARE_NAME(table->signature, signature)) {
|
||||
ACPI_BIOS_ERROR((AE_INFO,
|
||||
"Invalid signature 0x%X for ACPI table, expected [%s]",
|
||||
*ACPI_CAST_PTR(u32, table->signature),
|
||||
signature));
|
||||
goto unmap_and_exit;
|
||||
}
|
||||
|
||||
/*
|
||||
* Initialize the table entry. Set the pointer to NULL, since the
|
||||
* table is not fully mapped at this time.
|
||||
*/
|
||||
table_desc = &acpi_gbl_root_table_list.tables[table_index];
|
||||
|
||||
table_desc->address = address;
|
||||
table_desc->pointer = NULL;
|
||||
table_desc->length = table->length;
|
||||
table_desc->flags = ACPI_TABLE_ORIGIN_MAPPED;
|
||||
ACPI_MOVE_32_TO_32(table_desc->signature.ascii, table->signature);
|
||||
|
||||
/*
|
||||
* ACPI Table Override:
|
||||
*
|
||||
* Before we install the table, let the host OS override it with a new
|
||||
* one if desired. Any table within the RSDT/XSDT can be replaced,
|
||||
* including the DSDT which is pointed to by the FADT.
|
||||
*
|
||||
* NOTE: If the table is overridden, then final_table will contain a
|
||||
* mapped pointer to the full new table. If the table is not overridden,
|
||||
* or if there has been a physical override, then the table will be
|
||||
* fully mapped later (in verify table). In any case, we must
|
||||
* unmap the header that was mapped above.
|
||||
*/
|
||||
final_table = acpi_tb_table_override(table, table_desc);
|
||||
if (!final_table) {
|
||||
final_table = table; /* There was no override */
|
||||
}
|
||||
|
||||
acpi_tb_print_table_header(table_desc->address, final_table);
|
||||
|
||||
/* Set the global integer width (based upon revision of the DSDT) */
|
||||
|
||||
if (table_index == ACPI_TABLE_INDEX_DSDT) {
|
||||
acpi_ut_set_integer_width(final_table->revision);
|
||||
}
|
||||
|
||||
/*
|
||||
* If we have a physical override during this early loading of the ACPI
|
||||
* tables, unmap the table for now. It will be mapped again later when
|
||||
* it is actually used. This supports very early loading of ACPI tables,
|
||||
* before virtual memory is fully initialized and running within the
|
||||
* host OS. Note: A logical override has the ACPI_TABLE_ORIGIN_OVERRIDE
|
||||
* flag set and will not be deleted below.
|
||||
*/
|
||||
if (final_table != table) {
|
||||
acpi_tb_delete_table(table_desc);
|
||||
}
|
||||
|
||||
unmap_and_exit:
|
||||
|
||||
/* Always unmap the table header that we mapped above */
|
||||
|
||||
acpi_os_unmap_memory(table, sizeof(struct acpi_table_header));
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_tb_get_root_table_entry
|
||||
@ -464,6 +358,7 @@ acpi_status __init acpi_tb_parse_root_table(acpi_physical_address rsdp_address)
|
||||
u32 length;
|
||||
u8 *table_entry;
|
||||
acpi_status status;
|
||||
u32 table_index;
|
||||
|
||||
ACPI_FUNCTION_TRACE(tb_parse_root_table);
|
||||
|
||||
@ -573,31 +468,24 @@ acpi_status __init acpi_tb_parse_root_table(acpi_physical_address rsdp_address)
|
||||
/* Initialize the root table array from the RSDT/XSDT */
|
||||
|
||||
for (i = 0; i < table_count; i++) {
|
||||
if (acpi_gbl_root_table_list.current_table_count >=
|
||||
acpi_gbl_root_table_list.max_table_count) {
|
||||
|
||||
/* There is no more room in the root table array, attempt resize */
|
||||
|
||||
status = acpi_tb_resize_root_table_list();
|
||||
if (ACPI_FAILURE(status)) {
|
||||
ACPI_WARNING((AE_INFO,
|
||||
"Truncating %u table entries!",
|
||||
(unsigned) (table_count -
|
||||
(acpi_gbl_root_table_list.
|
||||
current_table_count -
|
||||
2))));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* Get the table physical address (32-bit for RSDT, 64-bit for XSDT) */
|
||||
|
||||
acpi_gbl_root_table_list.tables[acpi_gbl_root_table_list.
|
||||
current_table_count].address =
|
||||
acpi_tb_get_root_table_entry(table_entry, table_entry_size);
|
||||
status =
|
||||
acpi_tb_install_standard_table(acpi_tb_get_root_table_entry
|
||||
(table_entry,
|
||||
table_entry_size),
|
||||
ACPI_TABLE_ORIGIN_INTERNAL_PHYSICAL,
|
||||
FALSE, TRUE, &table_index);
|
||||
|
||||
if (ACPI_SUCCESS(status) &&
|
||||
ACPI_COMPARE_NAME(&acpi_gbl_root_table_list.
|
||||
tables[table_index].signature,
|
||||
ACPI_SIG_FADT)) {
|
||||
acpi_tb_parse_fadt(table_index);
|
||||
}
|
||||
|
||||
table_entry += table_entry_size;
|
||||
acpi_gbl_root_table_list.current_table_count++;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -606,22 +494,5 @@ acpi_status __init acpi_tb_parse_root_table(acpi_physical_address rsdp_address)
|
||||
*/
|
||||
acpi_os_unmap_memory(table, length);
|
||||
|
||||
/*
|
||||
* Complete the initialization of the root table array by examining
|
||||
* the header of each table
|
||||
*/
|
||||
for (i = 2; i < acpi_gbl_root_table_list.current_table_count; i++) {
|
||||
acpi_tb_install_table(acpi_gbl_root_table_list.tables[i].
|
||||
address, NULL, i);
|
||||
|
||||
/* Special case for FADT - validate it then get the DSDT and FACS */
|
||||
|
||||
if (ACPI_COMPARE_NAME
|
||||
(&acpi_gbl_root_table_list.tables[i].signature,
|
||||
ACPI_SIG_FADT)) {
|
||||
acpi_tb_parse_fadt(i);
|
||||
}
|
||||
}
|
||||
|
||||
return_ACPI_STATUS(AE_OK);
|
||||
}
|
||||
|
@ -206,8 +206,8 @@ acpi_status
|
||||
acpi_get_table_header(char *signature,
|
||||
u32 instance, struct acpi_table_header *out_table_header)
|
||||
{
|
||||
u32 i;
|
||||
u32 j;
|
||||
u32 i;
|
||||
u32 j;
|
||||
struct acpi_table_header *header;
|
||||
|
||||
/* Parameter validation */
|
||||
@ -233,7 +233,7 @@ acpi_get_table_header(char *signature,
|
||||
if (!acpi_gbl_root_table_list.tables[i].pointer) {
|
||||
if ((acpi_gbl_root_table_list.tables[i].flags &
|
||||
ACPI_TABLE_ORIGIN_MASK) ==
|
||||
ACPI_TABLE_ORIGIN_MAPPED) {
|
||||
ACPI_TABLE_ORIGIN_INTERNAL_PHYSICAL) {
|
||||
header =
|
||||
acpi_os_map_memory(acpi_gbl_root_table_list.
|
||||
tables[i].address,
|
||||
@ -321,8 +321,8 @@ acpi_get_table_with_size(char *signature,
|
||||
u32 instance, struct acpi_table_header **out_table,
|
||||
acpi_size *tbl_size)
|
||||
{
|
||||
u32 i;
|
||||
u32 j;
|
||||
u32 i;
|
||||
u32 j;
|
||||
acpi_status status;
|
||||
|
||||
/* Parameter validation */
|
||||
@ -346,7 +346,7 @@ acpi_get_table_with_size(char *signature,
|
||||
}
|
||||
|
||||
status =
|
||||
acpi_tb_verify_table(&acpi_gbl_root_table_list.tables[i]);
|
||||
acpi_tb_validate_table(&acpi_gbl_root_table_list.tables[i]);
|
||||
if (ACPI_SUCCESS(status)) {
|
||||
*out_table = acpi_gbl_root_table_list.tables[i].pointer;
|
||||
*tbl_size = acpi_gbl_root_table_list.tables[i].length;
|
||||
@ -390,7 +390,7 @@ ACPI_EXPORT_SYMBOL(acpi_get_table)
|
||||
*
|
||||
******************************************************************************/
|
||||
acpi_status
|
||||
acpi_get_table_by_index(u32 table_index, struct acpi_table_header **table)
|
||||
acpi_get_table_by_index(u32 table_index, struct acpi_table_header ** table)
|
||||
{
|
||||
acpi_status status;
|
||||
|
||||
@ -416,8 +416,8 @@ acpi_get_table_by_index(u32 table_index, struct acpi_table_header **table)
|
||||
/* Table is not mapped, map it */
|
||||
|
||||
status =
|
||||
acpi_tb_verify_table(&acpi_gbl_root_table_list.
|
||||
tables[table_index]);
|
||||
acpi_tb_validate_table(&acpi_gbl_root_table_list.
|
||||
tables[table_index]);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_TABLES);
|
||||
return_ACPI_STATUS(status);
|
||||
|
@ -117,7 +117,7 @@ static acpi_status acpi_tb_load_namespace(void)
|
||||
tables[ACPI_TABLE_INDEX_DSDT].signature),
|
||||
ACPI_SIG_DSDT)
|
||||
||
|
||||
ACPI_FAILURE(acpi_tb_verify_table
|
||||
ACPI_FAILURE(acpi_tb_validate_table
|
||||
(&acpi_gbl_root_table_list.
|
||||
tables[ACPI_TABLE_INDEX_DSDT]))) {
|
||||
status = AE_NO_ACPI_TABLES;
|
||||
@ -128,7 +128,7 @@ static acpi_status acpi_tb_load_namespace(void)
|
||||
* Save the DSDT pointer for simple access. This is the mapped memory
|
||||
* address. We must take care here because the address of the .Tables
|
||||
* array can change dynamically as tables are loaded at run-time. Note:
|
||||
* .Pointer field is not validated until after call to acpi_tb_verify_table.
|
||||
* .Pointer field is not validated until after call to acpi_tb_validate_table.
|
||||
*/
|
||||
acpi_gbl_DSDT =
|
||||
acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_DSDT].pointer;
|
||||
@ -174,24 +174,11 @@ static acpi_status acpi_tb_load_namespace(void)
|
||||
(acpi_gbl_root_table_list.tables[i].
|
||||
signature), ACPI_SIG_PSDT))
|
||||
||
|
||||
ACPI_FAILURE(acpi_tb_verify_table
|
||||
ACPI_FAILURE(acpi_tb_validate_table
|
||||
(&acpi_gbl_root_table_list.tables[i]))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
/*
|
||||
* Optionally do not load any SSDTs from the RSDT/XSDT. This can
|
||||
* be useful for debugging ACPI problems on some machines.
|
||||
*/
|
||||
if (acpi_gbl_disable_ssdt_table_load) {
|
||||
ACPI_INFO((AE_INFO, "Ignoring %4.4s at %p",
|
||||
acpi_gbl_root_table_list.tables[i].signature.
|
||||
ascii, ACPI_CAST_PTR(void,
|
||||
acpi_gbl_root_table_list.
|
||||
tables[i].address)));
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Ignore errors while loading tables, get as many as possible */
|
||||
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_TABLES);
|
||||
@ -206,6 +193,45 @@ unlock_and_exit:
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_install_table
|
||||
*
|
||||
* PARAMETERS: address - Address of the ACPI table to be installed.
|
||||
* physical - Whether the address is a physical table
|
||||
* address or not
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: Dynamically install an ACPI table.
|
||||
* Note: This function should only be invoked after
|
||||
* acpi_initialize_tables() and before acpi_load_tables().
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
acpi_status __init
|
||||
acpi_install_table(acpi_physical_address address, u8 physical)
|
||||
{
|
||||
acpi_status status;
|
||||
u8 flags;
|
||||
u32 table_index;
|
||||
|
||||
ACPI_FUNCTION_TRACE(acpi_install_table);
|
||||
|
||||
if (physical) {
|
||||
flags = ACPI_TABLE_ORIGIN_EXTERNAL_VIRTUAL;
|
||||
} else {
|
||||
flags = ACPI_TABLE_ORIGIN_INTERNAL_PHYSICAL;
|
||||
}
|
||||
|
||||
status = acpi_tb_install_standard_table(address, flags,
|
||||
FALSE, FALSE, &table_index);
|
||||
|
||||
return_ACPI_STATUS(status);
|
||||
}
|
||||
|
||||
ACPI_EXPORT_SYMBOL_INIT(acpi_install_table)
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_load_table
|
||||
@ -222,11 +248,9 @@ unlock_and_exit:
|
||||
* to ensure that the table is not deleted or unmapped.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
acpi_status acpi_load_table(struct acpi_table_header *table)
|
||||
{
|
||||
acpi_status status;
|
||||
struct acpi_table_desc table_desc;
|
||||
u32 table_index;
|
||||
|
||||
ACPI_FUNCTION_TRACE(acpi_load_table);
|
||||
@ -237,14 +261,6 @@ acpi_status acpi_load_table(struct acpi_table_header *table)
|
||||
return_ACPI_STATUS(AE_BAD_PARAMETER);
|
||||
}
|
||||
|
||||
/* Init local table descriptor */
|
||||
|
||||
ACPI_MEMSET(&table_desc, 0, sizeof(struct acpi_table_desc));
|
||||
table_desc.address = ACPI_PTR_TO_PHYSADDR(table);
|
||||
table_desc.pointer = table;
|
||||
table_desc.length = table->length;
|
||||
table_desc.flags = ACPI_TABLE_ORIGIN_UNKNOWN;
|
||||
|
||||
/* Must acquire the interpreter lock during this operation */
|
||||
|
||||
status = acpi_ut_acquire_mutex(ACPI_MTX_INTERPRETER);
|
||||
@ -255,7 +271,24 @@ acpi_status acpi_load_table(struct acpi_table_header *table)
|
||||
/* Install the table and load it into the namespace */
|
||||
|
||||
ACPI_INFO((AE_INFO, "Host-directed Dynamic ACPI Table Load:"));
|
||||
status = acpi_tb_add_table(&table_desc, &table_index);
|
||||
(void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES);
|
||||
|
||||
status = acpi_tb_install_standard_table(ACPI_PTR_TO_PHYSADDR(table),
|
||||
ACPI_TABLE_ORIGIN_EXTERNAL_VIRTUAL,
|
||||
TRUE, FALSE, &table_index);
|
||||
|
||||
(void)acpi_ut_release_mutex(ACPI_MTX_TABLES);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
goto unlock_and_exit;
|
||||
}
|
||||
|
||||
/*
|
||||
* Note: Now table is "INSTALLED", it must be validated before
|
||||
* using.
|
||||
*/
|
||||
status =
|
||||
acpi_tb_validate_table(&acpi_gbl_root_table_list.
|
||||
tables[table_index]);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
goto unlock_and_exit;
|
||||
}
|
||||
|
@ -462,7 +462,7 @@ char *acpi_ut_get_mutex_name(u32 mutex_id)
|
||||
|
||||
/* Names for Notify() values, used for debug output */
|
||||
|
||||
static const char *acpi_gbl_notify_value_names[ACPI_NOTIFY_MAX + 1] = {
|
||||
static const char *acpi_gbl_generic_notify[ACPI_NOTIFY_MAX + 1] = {
|
||||
/* 00 */ "Bus Check",
|
||||
/* 01 */ "Device Check",
|
||||
/* 02 */ "Device Wake",
|
||||
@ -473,23 +473,75 @@ static const char *acpi_gbl_notify_value_names[ACPI_NOTIFY_MAX + 1] = {
|
||||
/* 07 */ "Power Fault",
|
||||
/* 08 */ "Capabilities Check",
|
||||
/* 09 */ "Device PLD Check",
|
||||
/* 10 */ "Reserved",
|
||||
/* 11 */ "System Locality Update",
|
||||
/* 12 */ "Shutdown Request"
|
||||
/* 0A */ "Reserved",
|
||||
/* 0B */ "System Locality Update",
|
||||
/* 0C */ "Shutdown Request"
|
||||
};
|
||||
|
||||
const char *acpi_ut_get_notify_name(u32 notify_value)
|
||||
static const char *acpi_gbl_device_notify[4] = {
|
||||
/* 80 */ "Status Change",
|
||||
/* 81 */ "Information Change",
|
||||
/* 82 */ "Device-Specific Change",
|
||||
/* 83 */ "Device-Specific Change"
|
||||
};
|
||||
|
||||
static const char *acpi_gbl_processor_notify[4] = {
|
||||
/* 80 */ "Performance Capability Change",
|
||||
/* 81 */ "C-State Change",
|
||||
/* 82 */ "Throttling Capability Change",
|
||||
/* 83 */ "Device-Specific Change"
|
||||
};
|
||||
|
||||
static const char *acpi_gbl_thermal_notify[4] = {
|
||||
/* 80 */ "Thermal Status Change",
|
||||
/* 81 */ "Thermal Trip Point Change",
|
||||
/* 82 */ "Thermal Device List Change",
|
||||
/* 83 */ "Thermal Relationship Change"
|
||||
};
|
||||
|
||||
const char *acpi_ut_get_notify_name(u32 notify_value, acpi_object_type type)
|
||||
{
|
||||
|
||||
/* 00 - 0C are common to all object types */
|
||||
|
||||
if (notify_value <= ACPI_NOTIFY_MAX) {
|
||||
return (acpi_gbl_notify_value_names[notify_value]);
|
||||
} else if (notify_value <= ACPI_MAX_SYS_NOTIFY) {
|
||||
return ("Reserved");
|
||||
} else if (notify_value <= ACPI_MAX_DEVICE_SPECIFIC_NOTIFY) {
|
||||
return ("Device Specific");
|
||||
} else {
|
||||
return ("Hardware Specific");
|
||||
return (acpi_gbl_generic_notify[notify_value]);
|
||||
}
|
||||
|
||||
/* 0D - 7F are reserved */
|
||||
|
||||
if (notify_value <= ACPI_MAX_SYS_NOTIFY) {
|
||||
return ("Reserved");
|
||||
}
|
||||
|
||||
/* 80 - 83 are per-object-type */
|
||||
|
||||
if (notify_value <= 0x83) {
|
||||
switch (type) {
|
||||
case ACPI_TYPE_ANY:
|
||||
case ACPI_TYPE_DEVICE:
|
||||
return (acpi_gbl_device_notify[notify_value - 0x80]);
|
||||
|
||||
case ACPI_TYPE_PROCESSOR:
|
||||
return (acpi_gbl_processor_notify[notify_value - 0x80]);
|
||||
|
||||
case ACPI_TYPE_THERMAL:
|
||||
return (acpi_gbl_thermal_notify[notify_value - 0x80]);
|
||||
|
||||
default:
|
||||
return ("Target object type does not support notifies");
|
||||
}
|
||||
}
|
||||
|
||||
/* 84 - BF are device-specific */
|
||||
|
||||
if (notify_value <= ACPI_MAX_DEVICE_SPECIFIC_NOTIFY) {
|
||||
return ("Device-Specific");
|
||||
}
|
||||
|
||||
/* C0 and above are hardware-specific */
|
||||
|
||||
return ("Hardware-Specific");
|
||||
}
|
||||
#endif
|
||||
|
||||
|
@ -353,7 +353,7 @@ void acpi_ut_print_string(char *string, u16 max_length)
|
||||
}
|
||||
|
||||
acpi_os_printf("\"");
|
||||
for (i = 0; string[i] && (i < max_length); i++) {
|
||||
for (i = 0; (i < max_length) && string[i]; i++) {
|
||||
|
||||
/* Escape sequences */
|
||||
|
||||
|
@ -1770,16 +1770,15 @@ acpi_status acpi_os_release_object(acpi_cache_t * cache, void *object)
|
||||
}
|
||||
#endif
|
||||
|
||||
static int __init acpi_no_auto_ssdt_setup(char *s)
|
||||
static int __init acpi_no_static_ssdt_setup(char *s)
|
||||
{
|
||||
printk(KERN_NOTICE PREFIX "SSDT auto-load disabled\n");
|
||||
acpi_gbl_disable_ssdt_table_install = TRUE;
|
||||
pr_info("ACPI: static SSDT installation disabled\n");
|
||||
|
||||
acpi_gbl_disable_ssdt_table_load = TRUE;
|
||||
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
__setup("acpi_no_auto_ssdt", acpi_no_auto_ssdt_setup);
|
||||
early_param("acpi_no_static_ssdt", acpi_no_static_ssdt_setup);
|
||||
|
||||
static int __init acpi_disable_return_repair(char *s)
|
||||
{
|
||||
|
@ -46,7 +46,7 @@
|
||||
|
||||
/* Current ACPICA subsystem version in YYYYMMDD format */
|
||||
|
||||
#define ACPI_CA_VERSION 0x20140214
|
||||
#define ACPI_CA_VERSION 0x20140325
|
||||
|
||||
#include <acpi/acconfig.h>
|
||||
#include <acpi/actypes.h>
|
||||
@ -75,7 +75,7 @@ extern u8 acpi_gbl_auto_serialize_methods;
|
||||
extern u8 acpi_gbl_copy_dsdt_locally;
|
||||
extern u8 acpi_gbl_create_osi_method;
|
||||
extern u8 acpi_gbl_disable_auto_repair;
|
||||
extern u8 acpi_gbl_disable_ssdt_table_load;
|
||||
extern u8 acpi_gbl_disable_ssdt_table_install;
|
||||
extern u8 acpi_gbl_do_not_use_xsdt;
|
||||
extern u8 acpi_gbl_enable_aml_debug_object;
|
||||
extern u8 acpi_gbl_enable_interpreter_slack;
|
||||
@ -164,6 +164,9 @@ acpi_decode_pld_buffer(u8 *in_buffer,
|
||||
/*
|
||||
* ACPI table load/unload interfaces
|
||||
*/
|
||||
acpi_status __init
|
||||
acpi_install_table(acpi_physical_address address, u8 physical);
|
||||
|
||||
acpi_status acpi_load_table(struct acpi_table_header *table);
|
||||
|
||||
acpi_status acpi_unload_parent_table(acpi_handle object);
|
||||
|
@ -367,12 +367,11 @@ struct acpi_table_desc {
|
||||
|
||||
/* Masks for Flags field above */
|
||||
|
||||
#define ACPI_TABLE_ORIGIN_UNKNOWN (0)
|
||||
#define ACPI_TABLE_ORIGIN_MAPPED (1)
|
||||
#define ACPI_TABLE_ORIGIN_ALLOCATED (2)
|
||||
#define ACPI_TABLE_ORIGIN_OVERRIDE (4)
|
||||
#define ACPI_TABLE_ORIGIN_MASK (7)
|
||||
#define ACPI_TABLE_IS_LOADED (8)
|
||||
#define ACPI_TABLE_ORIGIN_EXTERNAL_VIRTUAL (0) /* Virtual address, external maintained */
|
||||
#define ACPI_TABLE_ORIGIN_INTERNAL_PHYSICAL (1) /* Physical address, internally mapped */
|
||||
#define ACPI_TABLE_ORIGIN_INTERNAL_VIRTUAL (2) /* Virtual address, internallly allocated */
|
||||
#define ACPI_TABLE_ORIGIN_MASK (3)
|
||||
#define ACPI_TABLE_IS_LOADED (8)
|
||||
|
||||
/*
|
||||
* Get the remaining ACPI tables
|
||||
|
@ -64,4 +64,15 @@
|
||||
*/
|
||||
#define ACPI_UNUSED_VAR __attribute__ ((unused))
|
||||
|
||||
/*
|
||||
* Some versions of gcc implement strchr() with a buggy macro. So,
|
||||
* undef it here. Prevents error messages of this form (usually from the
|
||||
* file getopt.c):
|
||||
*
|
||||
* error: logical '&&' with non-zero constant will always evaluate as true
|
||||
*/
|
||||
#ifdef strchr
|
||||
#undef strchr
|
||||
#endif
|
||||
|
||||
#endif /* __ACGCC_H__ */
|
||||
|
@ -91,7 +91,7 @@
|
||||
#include <ctype.h>
|
||||
#include <unistd.h>
|
||||
|
||||
/* Disable kernel specific declarators */
|
||||
/* Define/disable kernel-specific declarators */
|
||||
|
||||
#ifndef __init
|
||||
#define __init
|
||||
@ -106,7 +106,8 @@
|
||||
#define ACPI_FLUSH_CPU_CACHE()
|
||||
#define ACPI_CAST_PTHREAD_T(pthread) ((acpi_thread_id) (pthread))
|
||||
|
||||
#if defined(__ia64__) || defined(__x86_64__) || defined(__aarch64__)
|
||||
#if defined(__ia64__) || defined(__x86_64__) ||\
|
||||
defined(__aarch64__) || defined(__PPC64__)
|
||||
#define ACPI_MACHINE_WIDTH 64
|
||||
#define COMPILER_DEPENDENT_INT64 long
|
||||
#define COMPILER_DEPENDENT_UINT64 unsigned long
|
||||
|
@ -68,7 +68,8 @@ WARNINGS += $(call cc-supports,-Wstrict-prototypes)
|
||||
WARNINGS += $(call cc-supports,-Wdeclaration-after-statement)
|
||||
|
||||
KERNEL_INCLUDE := ../../../include
|
||||
CFLAGS += -D_LINUX -DDEFINE_ALTERNATE_TYPES -I$(KERNEL_INCLUDE)
|
||||
ACPICA_INCLUDE := ../../../drivers/acpi/acpica
|
||||
CFLAGS += -D_LINUX -I$(KERNEL_INCLUDE) -I$(ACPICA_INCLUDE)
|
||||
CFLAGS += $(WARNINGS)
|
||||
|
||||
ifeq ($(strip $(V)),false)
|
||||
@ -101,10 +102,29 @@ endif
|
||||
# --- ACPIDUMP BEGIN ---
|
||||
|
||||
vpath %.c \
|
||||
tools/acpidump
|
||||
../../../drivers/acpi/acpica\
|
||||
tools/acpidump\
|
||||
common\
|
||||
os_specific/service_layers
|
||||
|
||||
CFLAGS += -DACPI_DUMP_APP -Itools/acpidump
|
||||
|
||||
DUMP_OBJS = \
|
||||
acpidump.o
|
||||
apdump.o\
|
||||
apfiles.o\
|
||||
apmain.o\
|
||||
osunixdir.o\
|
||||
osunixmap.o\
|
||||
tbprint.o\
|
||||
tbxfroot.o\
|
||||
utbuffer.o\
|
||||
utexcep.o\
|
||||
utmath.o\
|
||||
utstring.o\
|
||||
utxferror.o\
|
||||
oslinuxtbl.o\
|
||||
cmfsize.o\
|
||||
getopt.o
|
||||
|
||||
DUMP_OBJS := $(addprefix $(OUTPUT)tools/acpidump/,$(DUMP_OBJS))
|
||||
|
||||
|
101
tools/power/acpi/common/cmfsize.c
Normal file
101
tools/power/acpi/common/cmfsize.c
Normal file
@ -0,0 +1,101 @@
|
||||
/******************************************************************************
|
||||
*
|
||||
* Module Name: cfsize - Common get file size function
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2000 - 2014, Intel Corp.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification.
|
||||
* 2. Redistributions in binary form must reproduce at minimum a disclaimer
|
||||
* substantially similar to the "NO WARRANTY" disclaimer below
|
||||
* ("Disclaimer") and any redistribution must be conditioned upon
|
||||
* including a substantially similar Disclaimer requirement for further
|
||||
* binary redistribution.
|
||||
* 3. Neither the names of the above-listed copyright holders nor the names
|
||||
* of any contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* Alternatively, this software may be distributed under the terms of the
|
||||
* GNU General Public License ("GPL") version 2 as published by the Free
|
||||
* Software Foundation.
|
||||
*
|
||||
* NO WARRANTY
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
* HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
||||
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
|
||||
* IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGES.
|
||||
*/
|
||||
|
||||
#include <acpi/acpi.h>
|
||||
#include "accommon.h"
|
||||
#include "acapps.h"
|
||||
#include <stdio.h>
|
||||
|
||||
#define _COMPONENT ACPI_TOOLS
|
||||
ACPI_MODULE_NAME("cmfsize")
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: cm_get_file_size
|
||||
*
|
||||
* PARAMETERS: file - Open file descriptor
|
||||
*
|
||||
* RETURN: File Size. On error, -1 (ACPI_UINT32_MAX)
|
||||
*
|
||||
* DESCRIPTION: Get the size of a file. Uses seek-to-EOF. File must be open.
|
||||
* Does not disturb the current file pointer. Uses perror for
|
||||
* error messages.
|
||||
*
|
||||
******************************************************************************/
|
||||
u32 cm_get_file_size(FILE * file)
|
||||
{
|
||||
long file_size;
|
||||
long current_offset;
|
||||
|
||||
/* Save the current file pointer, seek to EOF to obtain file size */
|
||||
|
||||
current_offset = ftell(file);
|
||||
if (current_offset < 0) {
|
||||
goto offset_error;
|
||||
}
|
||||
|
||||
if (fseek(file, 0, SEEK_END)) {
|
||||
goto seek_error;
|
||||
}
|
||||
|
||||
file_size = ftell(file);
|
||||
if (file_size < 0) {
|
||||
goto offset_error;
|
||||
}
|
||||
|
||||
/* Restore original file pointer */
|
||||
|
||||
if (fseek(file, current_offset, SEEK_SET)) {
|
||||
goto seek_error;
|
||||
}
|
||||
|
||||
return ((u32)file_size);
|
||||
|
||||
offset_error:
|
||||
perror("Could not get file offset");
|
||||
return (ACPI_UINT32_MAX);
|
||||
|
||||
seek_error:
|
||||
perror("Could not seek file");
|
||||
return (ACPI_UINT32_MAX);
|
||||
}
|
239
tools/power/acpi/common/getopt.c
Normal file
239
tools/power/acpi/common/getopt.c
Normal file
@ -0,0 +1,239 @@
|
||||
/******************************************************************************
|
||||
*
|
||||
* Module Name: getopt
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2000 - 2014, Intel Corp.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification.
|
||||
* 2. Redistributions in binary form must reproduce at minimum a disclaimer
|
||||
* substantially similar to the "NO WARRANTY" disclaimer below
|
||||
* ("Disclaimer") and any redistribution must be conditioned upon
|
||||
* including a substantially similar Disclaimer requirement for further
|
||||
* binary redistribution.
|
||||
* 3. Neither the names of the above-listed copyright holders nor the names
|
||||
* of any contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* Alternatively, this software may be distributed under the terms of the
|
||||
* GNU General Public License ("GPL") version 2 as published by the Free
|
||||
* Software Foundation.
|
||||
*
|
||||
* NO WARRANTY
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
* HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
||||
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
|
||||
* IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGES.
|
||||
*/
|
||||
|
||||
/*
|
||||
* ACPICA getopt() implementation
|
||||
*
|
||||
* Option strings:
|
||||
* "f" - Option has no arguments
|
||||
* "f:" - Option requires an argument
|
||||
* "f^" - Option has optional single-char sub-options
|
||||
* "f|" - Option has required single-char sub-options
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <acpi/acpi.h>
|
||||
#include "accommon.h"
|
||||
#include "acapps.h"
|
||||
|
||||
#define ACPI_OPTION_ERROR(msg, badchar) \
|
||||
if (acpi_gbl_opterr) {fprintf (stderr, "%s%c\n", msg, badchar);}
|
||||
|
||||
int acpi_gbl_opterr = 1;
|
||||
int acpi_gbl_optind = 1;
|
||||
int acpi_gbl_sub_opt_char = 0;
|
||||
char *acpi_gbl_optarg;
|
||||
|
||||
static int current_char_ptr = 1;
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_getopt_argument
|
||||
*
|
||||
* PARAMETERS: argc, argv - from main
|
||||
*
|
||||
* RETURN: 0 if an argument was found, -1 otherwise. Sets acpi_gbl_Optarg
|
||||
* to point to the next argument.
|
||||
*
|
||||
* DESCRIPTION: Get the next argument. Used to obtain arguments for the
|
||||
* two-character options after the original call to acpi_getopt.
|
||||
* Note: Either the argument starts at the next character after
|
||||
* the option, or it is pointed to by the next argv entry.
|
||||
* (After call to acpi_getopt, we need to backup to the previous
|
||||
* argv entry).
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
int acpi_getopt_argument(int argc, char **argv)
|
||||
{
|
||||
acpi_gbl_optind--;
|
||||
current_char_ptr++;
|
||||
|
||||
if (argv[acpi_gbl_optind][(int)(current_char_ptr + 1)] != '\0') {
|
||||
acpi_gbl_optarg =
|
||||
&argv[acpi_gbl_optind++][(int)(current_char_ptr + 1)];
|
||||
} else if (++acpi_gbl_optind >= argc) {
|
||||
ACPI_OPTION_ERROR("Option requires an argument: -", 'v');
|
||||
|
||||
current_char_ptr = 1;
|
||||
return (-1);
|
||||
} else {
|
||||
acpi_gbl_optarg = argv[acpi_gbl_optind++];
|
||||
}
|
||||
|
||||
current_char_ptr = 1;
|
||||
return (0);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_getopt
|
||||
*
|
||||
* PARAMETERS: argc, argv - from main
|
||||
* opts - options info list
|
||||
*
|
||||
* RETURN: Option character or EOF
|
||||
*
|
||||
* DESCRIPTION: Get the next option
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
int acpi_getopt(int argc, char **argv, char *opts)
|
||||
{
|
||||
int current_char;
|
||||
char *opts_ptr;
|
||||
|
||||
if (current_char_ptr == 1) {
|
||||
if (acpi_gbl_optind >= argc ||
|
||||
argv[acpi_gbl_optind][0] != '-' ||
|
||||
argv[acpi_gbl_optind][1] == '\0') {
|
||||
return (EOF);
|
||||
} else if (strcmp(argv[acpi_gbl_optind], "--") == 0) {
|
||||
acpi_gbl_optind++;
|
||||
return (EOF);
|
||||
}
|
||||
}
|
||||
|
||||
/* Get the option */
|
||||
|
||||
current_char = argv[acpi_gbl_optind][current_char_ptr];
|
||||
|
||||
/* Make sure that the option is legal */
|
||||
|
||||
if (current_char == ':' ||
|
||||
(opts_ptr = strchr(opts, current_char)) == NULL) {
|
||||
ACPI_OPTION_ERROR("Illegal option: -", current_char);
|
||||
|
||||
if (argv[acpi_gbl_optind][++current_char_ptr] == '\0') {
|
||||
acpi_gbl_optind++;
|
||||
current_char_ptr = 1;
|
||||
}
|
||||
|
||||
return ('?');
|
||||
}
|
||||
|
||||
/* Option requires an argument? */
|
||||
|
||||
if (*++opts_ptr == ':') {
|
||||
if (argv[acpi_gbl_optind][(int)(current_char_ptr + 1)] != '\0') {
|
||||
acpi_gbl_optarg =
|
||||
&argv[acpi_gbl_optind++][(int)
|
||||
(current_char_ptr + 1)];
|
||||
} else if (++acpi_gbl_optind >= argc) {
|
||||
ACPI_OPTION_ERROR("Option requires an argument: -",
|
||||
current_char);
|
||||
|
||||
current_char_ptr = 1;
|
||||
return ('?');
|
||||
} else {
|
||||
acpi_gbl_optarg = argv[acpi_gbl_optind++];
|
||||
}
|
||||
|
||||
current_char_ptr = 1;
|
||||
}
|
||||
|
||||
/* Option has an optional argument? */
|
||||
|
||||
else if (*opts_ptr == '+') {
|
||||
if (argv[acpi_gbl_optind][(int)(current_char_ptr + 1)] != '\0') {
|
||||
acpi_gbl_optarg =
|
||||
&argv[acpi_gbl_optind++][(int)
|
||||
(current_char_ptr + 1)];
|
||||
} else if (++acpi_gbl_optind >= argc) {
|
||||
acpi_gbl_optarg = NULL;
|
||||
} else {
|
||||
acpi_gbl_optarg = argv[acpi_gbl_optind++];
|
||||
}
|
||||
|
||||
current_char_ptr = 1;
|
||||
}
|
||||
|
||||
/* Option has optional single-char arguments? */
|
||||
|
||||
else if (*opts_ptr == '^') {
|
||||
if (argv[acpi_gbl_optind][(int)(current_char_ptr + 1)] != '\0') {
|
||||
acpi_gbl_optarg =
|
||||
&argv[acpi_gbl_optind][(int)(current_char_ptr + 1)];
|
||||
} else {
|
||||
acpi_gbl_optarg = "^";
|
||||
}
|
||||
|
||||
acpi_gbl_sub_opt_char = acpi_gbl_optarg[0];
|
||||
acpi_gbl_optind++;
|
||||
current_char_ptr = 1;
|
||||
}
|
||||
|
||||
/* Option has a required single-char argument? */
|
||||
|
||||
else if (*opts_ptr == '|') {
|
||||
if (argv[acpi_gbl_optind][(int)(current_char_ptr + 1)] != '\0') {
|
||||
acpi_gbl_optarg =
|
||||
&argv[acpi_gbl_optind][(int)(current_char_ptr + 1)];
|
||||
} else {
|
||||
ACPI_OPTION_ERROR
|
||||
("Option requires a single-character suboption: -",
|
||||
current_char);
|
||||
|
||||
current_char_ptr = 1;
|
||||
return ('?');
|
||||
}
|
||||
|
||||
acpi_gbl_sub_opt_char = acpi_gbl_optarg[0];
|
||||
acpi_gbl_optind++;
|
||||
current_char_ptr = 1;
|
||||
}
|
||||
|
||||
/* Option with no arguments */
|
||||
|
||||
else {
|
||||
if (argv[acpi_gbl_optind][++current_char_ptr] == '\0') {
|
||||
current_char_ptr = 1;
|
||||
acpi_gbl_optind++;
|
||||
}
|
||||
|
||||
acpi_gbl_optarg = NULL;
|
||||
}
|
||||
|
||||
return (current_char);
|
||||
}
|
@ -1,18 +1,64 @@
|
||||
.TH ACPIDUMP 8
|
||||
.SH NAME
|
||||
acpidump \- Dump system's ACPI tables to an ASCII file.
|
||||
acpidump \- dump a system's ACPI tables to an ASCII file
|
||||
|
||||
.SH SYNOPSIS
|
||||
.ft B
|
||||
.B acpidump > acpidump.out
|
||||
.B acpidump
|
||||
.RI [ options ]
|
||||
.br
|
||||
|
||||
.SH DESCRIPTION
|
||||
\fBacpidump \fP dumps the systems ACPI tables to an ASCII file
|
||||
appropriate for attaching to a bug report.
|
||||
.B acpidump
|
||||
dumps the systems ACPI tables to an ASCII file appropriate for
|
||||
attaching to a bug report.
|
||||
|
||||
Subsequently, they can be processed by utilities in the ACPICA package.
|
||||
.SS Options
|
||||
no options worth worrying about.
|
||||
.PP
|
||||
.SH EXAMPLE
|
||||
|
||||
.SH OPTIONS
|
||||
acpidump options are as follow:
|
||||
.TP
|
||||
.B Options
|
||||
.TP
|
||||
.B \-b
|
||||
Dump tables to binary files
|
||||
.TP
|
||||
.B \-c
|
||||
Dump customized tables
|
||||
.TP
|
||||
.B \-h \-?
|
||||
This help message
|
||||
.TP
|
||||
.B \-o <File>
|
||||
Redirect output to file
|
||||
.TP
|
||||
.B \-r <Address>
|
||||
Dump tables from specified RSDP
|
||||
.TP
|
||||
.B \-s
|
||||
Print table summaries only
|
||||
.TP
|
||||
.B \-v
|
||||
Display version information
|
||||
.TP
|
||||
.B \-z
|
||||
Verbose mode
|
||||
.TP
|
||||
.B Table Options
|
||||
.TP
|
||||
.B \-a <Address>
|
||||
Get table via a physical address
|
||||
.TP
|
||||
.B \-f <BinaryFile>
|
||||
Get table via a binary file
|
||||
.TP
|
||||
.B \-n <Signature>
|
||||
Get table via a name/signature
|
||||
.TP
|
||||
Invocation without parameters dumps all available tables
|
||||
.TP
|
||||
Multiple mixed instances of -a, -f, and -n are supported
|
||||
|
||||
.SH EXAMPLES
|
||||
|
||||
.nf
|
||||
# acpidump > acpidump.out
|
||||
@ -50,10 +96,25 @@ ACPICA: https://acpica.org/
|
||||
.ta
|
||||
.nf
|
||||
/dev/mem
|
||||
/sys/firmware/acpi/tables/*
|
||||
/sys/firmware/acpi/tables/dynamic/*
|
||||
/sys/firmware/efi/systab
|
||||
.fi
|
||||
|
||||
.PP
|
||||
.SH AUTHOR
|
||||
.nf
|
||||
Written by Len Brown <len.brown@intel.com>
|
||||
.TP
|
||||
Original by:
|
||||
Len Brown <len.brown@intel.com>
|
||||
.TP
|
||||
Written by:
|
||||
Chao Guan <chao.guan@intel.com>
|
||||
.TP
|
||||
Updated by:
|
||||
Bob Moore <robert.moore@intel.com>
|
||||
Lv Zheng <lv.zheng@intel.com>
|
||||
|
||||
.SH SEE ALSO
|
||||
\&\fIacpixtract\fR\|(8), \fIiasl\fR\|(8).
|
||||
|
||||
.SH COPYRIGHT
|
||||
COPYRIGHT (c) 2013, Intel Corporation.
|
||||
|
1275
tools/power/acpi/os_specific/service_layers/oslinuxtbl.c
Normal file
1275
tools/power/acpi/os_specific/service_layers/oslinuxtbl.c
Normal file
File diff suppressed because it is too large
Load Diff
204
tools/power/acpi/os_specific/service_layers/osunixdir.c
Normal file
204
tools/power/acpi/os_specific/service_layers/osunixdir.c
Normal file
@ -0,0 +1,204 @@
|
||||
/******************************************************************************
|
||||
*
|
||||
* Module Name: osunixdir - Unix directory access interfaces
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2000 - 2014, Intel Corp.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification.
|
||||
* 2. Redistributions in binary form must reproduce at minimum a disclaimer
|
||||
* substantially similar to the "NO WARRANTY" disclaimer below
|
||||
* ("Disclaimer") and any redistribution must be conditioned upon
|
||||
* including a substantially similar Disclaimer requirement for further
|
||||
* binary redistribution.
|
||||
* 3. Neither the names of the above-listed copyright holders nor the names
|
||||
* of any contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* Alternatively, this software may be distributed under the terms of the
|
||||
* GNU General Public License ("GPL") version 2 as published by the Free
|
||||
* Software Foundation.
|
||||
*
|
||||
* NO WARRANTY
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
* HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
||||
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
|
||||
* IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGES.
|
||||
*/
|
||||
|
||||
#include <acpi/acpi.h>
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <dirent.h>
|
||||
#include <fnmatch.h>
|
||||
#include <ctype.h>
|
||||
#include <sys/stat.h>
|
||||
|
||||
/*
|
||||
* Allocated structure returned from os_open_directory
|
||||
*/
|
||||
typedef struct external_find_info {
|
||||
char *dir_pathname;
|
||||
DIR *dir_ptr;
|
||||
char temp_buffer[256];
|
||||
char *wildcard_spec;
|
||||
char requested_file_type;
|
||||
|
||||
} external_find_info;
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_os_open_directory
|
||||
*
|
||||
* PARAMETERS: dir_pathname - Full pathname to the directory
|
||||
* wildcard_spec - string of the form "*.c", etc.
|
||||
*
|
||||
* RETURN: A directory "handle" to be used in subsequent search operations.
|
||||
* NULL returned on failure.
|
||||
*
|
||||
* DESCRIPTION: Open a directory in preparation for a wildcard search
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
void *acpi_os_open_directory(char *dir_pathname,
|
||||
char *wildcard_spec, char requested_file_type)
|
||||
{
|
||||
struct external_find_info *external_info;
|
||||
DIR *dir;
|
||||
|
||||
/* Allocate the info struct that will be returned to the caller */
|
||||
|
||||
external_info = calloc(1, sizeof(struct external_find_info));
|
||||
if (!external_info) {
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
/* Get the directory stream */
|
||||
|
||||
dir = opendir(dir_pathname);
|
||||
if (!dir) {
|
||||
fprintf(stderr, "Cannot open directory - %s\n", dir_pathname);
|
||||
free(external_info);
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
/* Save the info in the return structure */
|
||||
|
||||
external_info->wildcard_spec = wildcard_spec;
|
||||
external_info->requested_file_type = requested_file_type;
|
||||
external_info->dir_pathname = dir_pathname;
|
||||
external_info->dir_ptr = dir;
|
||||
return (external_info);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_os_get_next_filename
|
||||
*
|
||||
* PARAMETERS: dir_handle - Created via acpi_os_open_directory
|
||||
*
|
||||
* RETURN: Next filename matched. NULL if no more matches.
|
||||
*
|
||||
* DESCRIPTION: Get the next file in the directory that matches the wildcard
|
||||
* specification.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
char *acpi_os_get_next_filename(void *dir_handle)
|
||||
{
|
||||
struct external_find_info *external_info = dir_handle;
|
||||
struct dirent *dir_entry;
|
||||
char *temp_str;
|
||||
int str_len;
|
||||
struct stat temp_stat;
|
||||
int err;
|
||||
|
||||
while ((dir_entry = readdir(external_info->dir_ptr))) {
|
||||
if (!fnmatch
|
||||
(external_info->wildcard_spec, dir_entry->d_name, 0)) {
|
||||
if (dir_entry->d_name[0] == '.') {
|
||||
continue;
|
||||
}
|
||||
|
||||
str_len = strlen(dir_entry->d_name) +
|
||||
strlen(external_info->dir_pathname) + 2;
|
||||
|
||||
temp_str = calloc(str_len, 1);
|
||||
if (!temp_str) {
|
||||
fprintf(stderr,
|
||||
"Could not allocate buffer for temporary string\n");
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
strcpy(temp_str, external_info->dir_pathname);
|
||||
strcat(temp_str, "/");
|
||||
strcat(temp_str, dir_entry->d_name);
|
||||
|
||||
err = stat(temp_str, &temp_stat);
|
||||
if (err == -1) {
|
||||
fprintf(stderr,
|
||||
"Cannot stat file (should not happen) - %s\n",
|
||||
temp_str);
|
||||
free(temp_str);
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
free(temp_str);
|
||||
|
||||
if ((S_ISDIR(temp_stat.st_mode)
|
||||
&& (external_info->requested_file_type ==
|
||||
REQUEST_DIR_ONLY))
|
||||
|| ((!S_ISDIR(temp_stat.st_mode)
|
||||
&& external_info->requested_file_type ==
|
||||
REQUEST_FILE_ONLY))) {
|
||||
|
||||
/* copy to a temp buffer because dir_entry struct is on the stack */
|
||||
|
||||
strcpy(external_info->temp_buffer,
|
||||
dir_entry->d_name);
|
||||
return (external_info->temp_buffer);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_os_close_directory
|
||||
*
|
||||
* PARAMETERS: dir_handle - Created via acpi_os_open_directory
|
||||
*
|
||||
* RETURN: None.
|
||||
*
|
||||
* DESCRIPTION: Close the open directory and cleanup.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
void acpi_os_close_directory(void *dir_handle)
|
||||
{
|
||||
struct external_find_info *external_info = dir_handle;
|
||||
|
||||
/* Close the directory and free allocations */
|
||||
|
||||
closedir(external_info->dir_ptr);
|
||||
free(dir_handle);
|
||||
}
|
151
tools/power/acpi/os_specific/service_layers/osunixmap.c
Normal file
151
tools/power/acpi/os_specific/service_layers/osunixmap.c
Normal file
@ -0,0 +1,151 @@
|
||||
/******************************************************************************
|
||||
*
|
||||
* Module Name: osunixmap - Unix OSL for file mappings
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2000 - 2014, Intel Corp.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification.
|
||||
* 2. Redistributions in binary form must reproduce at minimum a disclaimer
|
||||
* substantially similar to the "NO WARRANTY" disclaimer below
|
||||
* ("Disclaimer") and any redistribution must be conditioned upon
|
||||
* including a substantially similar Disclaimer requirement for further
|
||||
* binary redistribution.
|
||||
* 3. Neither the names of the above-listed copyright holders nor the names
|
||||
* of any contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* Alternatively, this software may be distributed under the terms of the
|
||||
* GNU General Public License ("GPL") version 2 as published by the Free
|
||||
* Software Foundation.
|
||||
*
|
||||
* NO WARRANTY
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
* HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
||||
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
|
||||
* IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGES.
|
||||
*/
|
||||
|
||||
#include "acpidump.h"
|
||||
#include <unistd.h>
|
||||
#include <sys/mman.h>
|
||||
#ifdef _free_BSD
|
||||
#include <sys/param.h>
|
||||
#endif
|
||||
|
||||
#define _COMPONENT ACPI_OS_SERVICES
|
||||
ACPI_MODULE_NAME("osunixmap")
|
||||
|
||||
#ifndef O_BINARY
|
||||
#define O_BINARY 0
|
||||
#endif
|
||||
#ifdef _free_BSD
|
||||
#define MMAP_FLAGS MAP_SHARED
|
||||
#else
|
||||
#define MMAP_FLAGS MAP_PRIVATE
|
||||
#endif
|
||||
#define SYSTEM_MEMORY "/dev/mem"
|
||||
/*******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_os_get_page_size
|
||||
*
|
||||
* PARAMETERS: None
|
||||
*
|
||||
* RETURN: Page size of the platform.
|
||||
*
|
||||
* DESCRIPTION: Obtain page size of the platform.
|
||||
*
|
||||
******************************************************************************/
|
||||
static acpi_size acpi_os_get_page_size(void)
|
||||
{
|
||||
|
||||
#ifdef PAGE_SIZE
|
||||
return PAGE_SIZE;
|
||||
#else
|
||||
return sysconf(_SC_PAGESIZE);
|
||||
#endif
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_os_map_memory
|
||||
*
|
||||
* PARAMETERS: where - Physical address of memory to be mapped
|
||||
* length - How much memory to map
|
||||
*
|
||||
* RETURN: Pointer to mapped memory. Null on error.
|
||||
*
|
||||
* DESCRIPTION: Map physical memory into local address space.
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
void *acpi_os_map_memory(acpi_physical_address where, acpi_size length)
|
||||
{
|
||||
u8 *mapped_memory;
|
||||
acpi_physical_address offset;
|
||||
acpi_size page_size;
|
||||
int fd;
|
||||
|
||||
fd = open(SYSTEM_MEMORY, O_RDONLY | O_BINARY);
|
||||
if (fd < 0) {
|
||||
fprintf(stderr, "Cannot open %s\n", SYSTEM_MEMORY);
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
/* Align the offset to use mmap */
|
||||
|
||||
page_size = acpi_os_get_page_size();
|
||||
offset = where % page_size;
|
||||
|
||||
/* Map the table header to get the length of the full table */
|
||||
|
||||
mapped_memory = mmap(NULL, (length + offset), PROT_READ, MMAP_FLAGS,
|
||||
fd, (where - offset));
|
||||
if (mapped_memory == MAP_FAILED) {
|
||||
fprintf(stderr, "Cannot map %s\n", SYSTEM_MEMORY);
|
||||
close(fd);
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
close(fd);
|
||||
return (ACPI_CAST8(mapped_memory + offset));
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_os_unmap_memory
|
||||
*
|
||||
* PARAMETERS: where - Logical address of memory to be unmapped
|
||||
* length - How much memory to unmap
|
||||
*
|
||||
* RETURN: None.
|
||||
*
|
||||
* DESCRIPTION: Delete a previously created mapping. Where and Length must
|
||||
* correspond to a previous mapping exactly.
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
void acpi_os_unmap_memory(void *where, acpi_size length)
|
||||
{
|
||||
acpi_physical_address offset;
|
||||
acpi_size page_size;
|
||||
|
||||
page_size = acpi_os_get_page_size();
|
||||
offset = (acpi_physical_address) where % page_size;
|
||||
munmap((u8 *)where - offset, (length + offset));
|
||||
}
|
@ -1,559 +0,0 @@
|
||||
/*
|
||||
* (c) Alexey Starikovskiy, Intel, 2005-2006.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification.
|
||||
* 2. Redistributions in binary form must reproduce at minimum a disclaimer
|
||||
* substantially similar to the "NO WARRANTY" disclaimer below
|
||||
* ("Disclaimer") and any redistribution must be conditioned upon
|
||||
* including a substantially similar Disclaimer requirement for further
|
||||
* binary redistribution.
|
||||
* 3. Neither the names of the above-listed copyright holders nor the names
|
||||
* of any contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* Alternatively, this software may be distributed under the terms of the
|
||||
* GNU General Public License ("GPL") version 2 as published by the Free
|
||||
* Software Foundation.
|
||||
*
|
||||
* NO WARRANTY
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
* HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
||||
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
|
||||
* IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGES.
|
||||
*/
|
||||
|
||||
#ifdef DEFINE_ALTERNATE_TYPES
|
||||
/* hack to enable building old application with new headers -lenb */
|
||||
#define acpi_fadt_descriptor acpi_table_fadt
|
||||
#define acpi_rsdp_descriptor acpi_table_rsdp
|
||||
#define DSDT_SIG ACPI_SIG_DSDT
|
||||
#define FACS_SIG ACPI_SIG_FACS
|
||||
#define FADT_SIG ACPI_SIG_FADT
|
||||
#define xfirmware_ctrl Xfacs
|
||||
#define firmware_ctrl facs
|
||||
|
||||
typedef int s32;
|
||||
typedef unsigned char u8;
|
||||
typedef unsigned short u16;
|
||||
typedef unsigned int u32;
|
||||
typedef unsigned long long u64;
|
||||
typedef long long s64;
|
||||
#endif
|
||||
|
||||
#include <sys/mman.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <fcntl.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <unistd.h>
|
||||
#include <getopt.h>
|
||||
|
||||
#include <dirent.h>
|
||||
|
||||
#include <acpi/acconfig.h>
|
||||
#include <acpi/platform/acenv.h>
|
||||
#include <acpi/actypes.h>
|
||||
#include <acpi/actbl.h>
|
||||
|
||||
static inline u8 checksum(u8 * buffer, u32 length)
|
||||
{
|
||||
u8 sum = 0, *i = buffer;
|
||||
buffer += length;
|
||||
for (; i < buffer; sum += *(i++));
|
||||
return sum;
|
||||
}
|
||||
|
||||
static unsigned long psz, addr, length;
|
||||
static int print, connect, skip;
|
||||
static u8 select_sig[4];
|
||||
|
||||
static unsigned long read_efi_systab( void )
|
||||
{
|
||||
char buffer[80];
|
||||
unsigned long addr;
|
||||
FILE *f = fopen("/sys/firmware/efi/systab", "r");
|
||||
if (f) {
|
||||
while (fgets(buffer, 80, f)) {
|
||||
if (sscanf(buffer, "ACPI20=0x%lx", &addr) == 1)
|
||||
return addr;
|
||||
}
|
||||
fclose(f);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static u8 *acpi_map_memory(unsigned long where, unsigned length)
|
||||
{
|
||||
unsigned long offset;
|
||||
u8 *there;
|
||||
int fd = open("/dev/mem", O_RDONLY);
|
||||
if (fd < 0) {
|
||||
fprintf(stderr, "acpi_os_map_memory: cannot open /dev/mem\n");
|
||||
exit(1);
|
||||
}
|
||||
offset = where % psz;
|
||||
there = mmap(NULL, length + offset, PROT_READ, MAP_PRIVATE,
|
||||
fd, where - offset);
|
||||
close(fd);
|
||||
if (there == MAP_FAILED) return 0;
|
||||
return (there + offset);
|
||||
}
|
||||
|
||||
static void acpi_unmap_memory(u8 * there, unsigned length)
|
||||
{
|
||||
unsigned long offset = (unsigned long)there % psz;
|
||||
munmap(there - offset, length + offset);
|
||||
}
|
||||
|
||||
static struct acpi_table_header *acpi_map_table(unsigned long where, char *sig)
|
||||
{
|
||||
unsigned size;
|
||||
struct acpi_table_header *tbl = (struct acpi_table_header *)
|
||||
acpi_map_memory(where, sizeof(struct acpi_table_header));
|
||||
if (!tbl || (sig && memcmp(sig, tbl->signature, 4))) return 0;
|
||||
size = tbl->length;
|
||||
acpi_unmap_memory((u8 *) tbl, sizeof(struct acpi_table_header));
|
||||
return (struct acpi_table_header *)acpi_map_memory(where, size);
|
||||
}
|
||||
|
||||
static void acpi_unmap_table(struct acpi_table_header *tbl)
|
||||
{
|
||||
acpi_unmap_memory((u8 *)tbl, tbl->length);
|
||||
}
|
||||
|
||||
static struct acpi_rsdp_descriptor *acpi_scan_for_rsdp(u8 *begin, u32 length)
|
||||
{
|
||||
struct acpi_rsdp_descriptor *rsdp;
|
||||
u8 *i, *end = begin + length;
|
||||
/* Search from given start address for the requested length */
|
||||
for (i = begin; i < end; i += ACPI_RSDP_SCAN_STEP) {
|
||||
/* The signature and checksum must both be correct */
|
||||
if (memcmp((char *)i, "RSD PTR ", 8)) continue;
|
||||
rsdp = (struct acpi_rsdp_descriptor *)i;
|
||||
/* Signature matches, check the appropriate checksum */
|
||||
if (!checksum((u8 *) rsdp, (rsdp->revision < 2) ?
|
||||
ACPI_RSDP_CHECKSUM_LENGTH :
|
||||
ACPI_RSDP_XCHECKSUM_LENGTH))
|
||||
/* Checksum valid, we have found a valid RSDP */
|
||||
return rsdp;
|
||||
}
|
||||
/* Searched entire block, no RSDP was found */
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Output data
|
||||
*/
|
||||
static void acpi_show_data(int fd, u8 * data, int size)
|
||||
{
|
||||
char buffer[256];
|
||||
int len;
|
||||
int i, remain = size;
|
||||
while (remain > 0) {
|
||||
len = snprintf(buffer, 256, " %04x:", size - remain);
|
||||
for (i = 0; i < 16 && i < remain; i++) {
|
||||
len +=
|
||||
snprintf(&buffer[len], 256 - len, " %02x", data[i]);
|
||||
}
|
||||
for (; i < 16; i++) {
|
||||
len += snprintf(&buffer[len], 256 - len, " ");
|
||||
}
|
||||
len += snprintf(&buffer[len], 256 - len, " ");
|
||||
for (i = 0; i < 16 && i < remain; i++) {
|
||||
buffer[len++] = (isprint(data[i])) ? data[i] : '.';
|
||||
}
|
||||
buffer[len++] = '\n';
|
||||
write(fd, buffer, len);
|
||||
data += 16;
|
||||
remain -= 16;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Output ACPI table
|
||||
*/
|
||||
static void acpi_show_table(int fd, struct acpi_table_header *table, unsigned long addr)
|
||||
{
|
||||
char buff[80];
|
||||
int len = snprintf(buff, 80, "%.4s @ %p\n", table->signature, (void *)addr);
|
||||
write(fd, buff, len);
|
||||
acpi_show_data(fd, (u8 *) table, table->length);
|
||||
buff[0] = '\n';
|
||||
write(fd, buff, 1);
|
||||
}
|
||||
|
||||
static void write_table(int fd, struct acpi_table_header *tbl, unsigned long addr)
|
||||
{
|
||||
static int select_done = 0;
|
||||
if (!select_sig[0]) {
|
||||
if (print) {
|
||||
acpi_show_table(fd, tbl, addr);
|
||||
} else {
|
||||
write(fd, tbl, tbl->length);
|
||||
}
|
||||
} else if (!select_done && !memcmp(select_sig, tbl->signature, 4)) {
|
||||
if (skip > 0) {
|
||||
--skip;
|
||||
return;
|
||||
}
|
||||
if (print) {
|
||||
acpi_show_table(fd, tbl, addr);
|
||||
} else {
|
||||
write(fd, tbl, tbl->length);
|
||||
}
|
||||
select_done = 1;
|
||||
}
|
||||
}
|
||||
|
||||
static void acpi_dump_FADT(int fd, struct acpi_table_header *tbl, unsigned long xaddr) {
|
||||
struct acpi_fadt_descriptor x;
|
||||
unsigned long addr;
|
||||
size_t len = sizeof(struct acpi_fadt_descriptor);
|
||||
if (len > tbl->length) len = tbl->length;
|
||||
memcpy(&x, tbl, len);
|
||||
x.header.length = len;
|
||||
if (checksum((u8 *)tbl, len)) {
|
||||
fprintf(stderr, "Wrong checksum for FADT!\n");
|
||||
}
|
||||
if (x.header.length >= 148 && x.Xdsdt) {
|
||||
addr = (unsigned long)x.Xdsdt;
|
||||
if (connect) {
|
||||
x.Xdsdt = lseek(fd, 0, SEEK_CUR);
|
||||
}
|
||||
} else if (x.header.length >= 44 && x.dsdt) {
|
||||
addr = (unsigned long)x.dsdt;
|
||||
if (connect) {
|
||||
x.dsdt = lseek(fd, 0, SEEK_CUR);
|
||||
}
|
||||
} else {
|
||||
fprintf(stderr, "No DSDT in FADT!\n");
|
||||
goto no_dsdt;
|
||||
}
|
||||
tbl = acpi_map_table(addr, DSDT_SIG);
|
||||
if (!tbl) goto no_dsdt;
|
||||
if (checksum((u8 *)tbl, tbl->length))
|
||||
fprintf(stderr, "Wrong checksum for DSDT!\n");
|
||||
write_table(fd, tbl, addr);
|
||||
acpi_unmap_table(tbl);
|
||||
no_dsdt:
|
||||
if (x.header.length >= 140 && x.xfirmware_ctrl) {
|
||||
addr = (unsigned long)x.xfirmware_ctrl;
|
||||
if (connect) {
|
||||
x.xfirmware_ctrl = lseek(fd, 0, SEEK_CUR);
|
||||
}
|
||||
} else if (x.header.length >= 40 && x.firmware_ctrl) {
|
||||
addr = (unsigned long)x.firmware_ctrl;
|
||||
if (connect) {
|
||||
x.firmware_ctrl = lseek(fd, 0, SEEK_CUR);
|
||||
}
|
||||
} else {
|
||||
fprintf(stderr, "No FACS in FADT!\n");
|
||||
goto no_facs;
|
||||
}
|
||||
tbl = acpi_map_table(addr, FACS_SIG);
|
||||
if (!tbl) goto no_facs;
|
||||
/* do not checksum FACS */
|
||||
write_table(fd, tbl, addr);
|
||||
acpi_unmap_table(tbl);
|
||||
no_facs:
|
||||
write_table(fd, (struct acpi_table_header *)&x, xaddr);
|
||||
}
|
||||
|
||||
static int acpi_dump_SDT(int fd, struct acpi_rsdp_descriptor *rsdp)
|
||||
{
|
||||
struct acpi_table_header *sdt, *tbl = 0;
|
||||
int xsdt = 1, i, num;
|
||||
char *offset;
|
||||
unsigned long addr;
|
||||
if (rsdp->revision > 1 && rsdp->xsdt_physical_address) {
|
||||
tbl = acpi_map_table(rsdp->xsdt_physical_address, "XSDT");
|
||||
}
|
||||
if (!tbl && rsdp->rsdt_physical_address) {
|
||||
xsdt = 0;
|
||||
tbl = acpi_map_table(rsdp->rsdt_physical_address, "RSDT");
|
||||
}
|
||||
if (!tbl) return 0;
|
||||
sdt = malloc(tbl->length);
|
||||
memcpy(sdt, tbl, tbl->length);
|
||||
acpi_unmap_table(tbl);
|
||||
if (checksum((u8 *)sdt, sdt->length))
|
||||
fprintf(stderr, "Wrong checksum for %s!\n", (xsdt)?"XSDT":"RSDT");
|
||||
num = (sdt->length - sizeof(struct acpi_table_header))/((xsdt)?sizeof(u64):sizeof(u32));
|
||||
offset = (char *)sdt + sizeof(struct acpi_table_header);
|
||||
for (i = 0; i < num; ++i, offset += ((xsdt) ? sizeof(u64) : sizeof(u32))) {
|
||||
addr = (xsdt) ? (unsigned long)(*(u64 *)offset):
|
||||
(unsigned long)(*(u32 *)offset);
|
||||
if (!addr) continue;
|
||||
tbl = acpi_map_table(addr, 0);
|
||||
if (!tbl) continue;
|
||||
if (!memcmp(tbl->signature, FADT_SIG, 4)) {
|
||||
acpi_dump_FADT(fd, tbl, addr);
|
||||
} else {
|
||||
if (checksum((u8 *)tbl, tbl->length))
|
||||
fprintf(stderr, "Wrong checksum for generic table!\n");
|
||||
write_table(fd, tbl, addr);
|
||||
}
|
||||
acpi_unmap_table(tbl);
|
||||
if (connect) {
|
||||
if (xsdt)
|
||||
(*(u64*)offset) = lseek(fd, 0, SEEK_CUR);
|
||||
else
|
||||
(*(u32*)offset) = lseek(fd, 0, SEEK_CUR);
|
||||
}
|
||||
}
|
||||
if (xsdt) {
|
||||
addr = (unsigned long)rsdp->xsdt_physical_address;
|
||||
if (connect) {
|
||||
rsdp->xsdt_physical_address = lseek(fd, 0, SEEK_CUR);
|
||||
}
|
||||
} else {
|
||||
addr = (unsigned long)rsdp->rsdt_physical_address;
|
||||
if (connect) {
|
||||
rsdp->rsdt_physical_address = lseek(fd, 0, SEEK_CUR);
|
||||
}
|
||||
}
|
||||
write_table(fd, sdt, addr);
|
||||
free (sdt);
|
||||
return 1;
|
||||
}
|
||||
|
||||
#define DYNAMIC_SSDT "/sys/firmware/acpi/tables/dynamic"
|
||||
|
||||
static void acpi_dump_dynamic_SSDT(int fd)
|
||||
{
|
||||
struct stat file_stat;
|
||||
char filename[256], *ptr;
|
||||
DIR *tabledir;
|
||||
struct dirent *entry;
|
||||
FILE *fp;
|
||||
int count, readcount, length;
|
||||
struct acpi_table_header table_header, *ptable;
|
||||
|
||||
if (stat(DYNAMIC_SSDT, &file_stat) == -1) {
|
||||
/* The directory doesn't exist */
|
||||
return;
|
||||
}
|
||||
tabledir = opendir(DYNAMIC_SSDT);
|
||||
if(!tabledir){
|
||||
/*can't open the directory */
|
||||
return;
|
||||
}
|
||||
|
||||
while ((entry = readdir(tabledir)) != 0){
|
||||
/* skip the file of . /.. */
|
||||
if (entry->d_name[0] == '.')
|
||||
continue;
|
||||
|
||||
sprintf(filename, "%s/%s", DYNAMIC_SSDT, entry->d_name);
|
||||
fp = fopen(filename, "r");
|
||||
if (fp == NULL) {
|
||||
fprintf(stderr, "Can't open the file of %s\n",
|
||||
filename);
|
||||
continue;
|
||||
}
|
||||
/* Read the Table header to parse the table length */
|
||||
count = fread(&table_header, 1, sizeof(struct acpi_table_header), fp);
|
||||
if (count < sizeof(table_header)) {
|
||||
/* the length is lessn than ACPI table header. skip it */
|
||||
fclose(fp);
|
||||
continue;
|
||||
}
|
||||
length = table_header.length;
|
||||
ptr = malloc(table_header.length);
|
||||
fseek(fp, 0, SEEK_SET);
|
||||
readcount = 0;
|
||||
while(!feof(fp) && readcount < length) {
|
||||
count = fread(ptr + readcount, 1, 256, fp);
|
||||
readcount += count;
|
||||
}
|
||||
fclose(fp);
|
||||
ptable = (struct acpi_table_header *) ptr;
|
||||
if (checksum((u8 *) ptable, ptable->length))
|
||||
fprintf(stderr, "Wrong checksum "
|
||||
"for dynamic SSDT table!\n");
|
||||
write_table(fd, ptable, 0);
|
||||
free(ptr);
|
||||
}
|
||||
closedir(tabledir);
|
||||
return;
|
||||
}
|
||||
|
||||
static void usage(const char *progname)
|
||||
{
|
||||
puts("Usage:");
|
||||
printf("%s [--addr 0x1234][--table DSDT][--output filename]"
|
||||
"[--binary][--length 0x456][--help]\n", progname);
|
||||
puts("\t--addr 0x1234 or -a 0x1234 -- look for tables at this physical address");
|
||||
puts("\t--table DSDT or -t DSDT -- only dump table with DSDT signature");
|
||||
puts("\t--output filename or -o filename -- redirect output from stdin to filename");
|
||||
puts("\t--binary or -b -- dump data in binary form rather than in hex-dump format");
|
||||
puts("\t--length 0x456 or -l 0x456 -- works only with --addr, dump physical memory"
|
||||
"\n\t\tregion without trying to understand it's contents");
|
||||
puts("\t--skip 2 or -s 2 -- skip 2 tables of the given name and output only 3rd one");
|
||||
puts("\t--help or -h -- this help message");
|
||||
exit(0);
|
||||
}
|
||||
|
||||
static struct option long_options[] = {
|
||||
{"addr", 1, 0, 0},
|
||||
{"table", 1, 0, 0},
|
||||
{"output", 1, 0, 0},
|
||||
{"binary", 0, 0, 0},
|
||||
{"length", 1, 0, 0},
|
||||
{"skip", 1, 0, 0},
|
||||
{"help", 0, 0, 0},
|
||||
{0, 0, 0, 0}
|
||||
};
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
int option_index, c, fd;
|
||||
u8 *raw;
|
||||
struct acpi_rsdp_descriptor rsdpx, *x = 0;
|
||||
char *filename = 0;
|
||||
char buff[80];
|
||||
memset(select_sig, 0, 4);
|
||||
print = 1;
|
||||
connect = 0;
|
||||
addr = length = 0;
|
||||
skip = 0;
|
||||
while (1) {
|
||||
option_index = 0;
|
||||
c = getopt_long(argc, argv, "a:t:o:bl:s:h",
|
||||
long_options, &option_index);
|
||||
if (c == -1)
|
||||
break;
|
||||
|
||||
switch (c) {
|
||||
case 0:
|
||||
switch (option_index) {
|
||||
case 0:
|
||||
addr = strtoul(optarg, (char **)NULL, 16);
|
||||
break;
|
||||
case 1:
|
||||
memcpy(select_sig, optarg, 4);
|
||||
break;
|
||||
case 2:
|
||||
filename = optarg;
|
||||
break;
|
||||
case 3:
|
||||
print = 0;
|
||||
break;
|
||||
case 4:
|
||||
length = strtoul(optarg, (char **)NULL, 16);
|
||||
break;
|
||||
case 5:
|
||||
skip = strtoul(optarg, (char **)NULL, 10);
|
||||
break;
|
||||
case 6:
|
||||
usage(argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
break;
|
||||
case 'a':
|
||||
addr = strtoul(optarg, (char **)NULL, 16);
|
||||
break;
|
||||
case 't':
|
||||
memcpy(select_sig, optarg, 4);
|
||||
break;
|
||||
case 'o':
|
||||
filename = optarg;
|
||||
break;
|
||||
case 'b':
|
||||
print = 0;
|
||||
break;
|
||||
case 'l':
|
||||
length = strtoul(optarg, (char **)NULL, 16);
|
||||
break;
|
||||
case 's':
|
||||
skip = strtoul(optarg, (char **)NULL, 10);
|
||||
break;
|
||||
case 'h':
|
||||
usage(argv[0]);
|
||||
exit(0);
|
||||
default:
|
||||
printf("Unknown option!\n");
|
||||
usage(argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
}
|
||||
|
||||
fd = STDOUT_FILENO;
|
||||
if (filename) {
|
||||
fd = creat(filename, S_IRUSR|S_IWUSR|S_IRGRP|S_IROTH);
|
||||
if (fd < 0)
|
||||
return fd;
|
||||
}
|
||||
|
||||
if (!select_sig[0] && !print) {
|
||||
connect = 1;
|
||||
}
|
||||
|
||||
psz = sysconf(_SC_PAGESIZE);
|
||||
if (length && addr) {
|
||||
/* We know length and address, it means we just want a memory dump */
|
||||
if (!(raw = acpi_map_memory(addr, length)))
|
||||
goto not_found;
|
||||
write(fd, raw, length);
|
||||
acpi_unmap_memory(raw, length);
|
||||
close(fd);
|
||||
return 0;
|
||||
}
|
||||
|
||||
length = sizeof(struct acpi_rsdp_descriptor);
|
||||
if (!addr) {
|
||||
addr = read_efi_systab();
|
||||
if (!addr) {
|
||||
addr = ACPI_HI_RSDP_WINDOW_BASE;
|
||||
length = ACPI_HI_RSDP_WINDOW_SIZE;
|
||||
}
|
||||
}
|
||||
|
||||
if (!(raw = acpi_map_memory(addr, length)) ||
|
||||
!(x = acpi_scan_for_rsdp(raw, length)))
|
||||
goto not_found;
|
||||
|
||||
/* Find RSDP and print all found tables */
|
||||
memcpy(&rsdpx, x, sizeof(struct acpi_rsdp_descriptor));
|
||||
acpi_unmap_memory(raw, length);
|
||||
if (connect) {
|
||||
lseek(fd, sizeof(struct acpi_rsdp_descriptor), SEEK_SET);
|
||||
}
|
||||
if (!acpi_dump_SDT(fd, &rsdpx))
|
||||
goto not_found;
|
||||
if (connect) {
|
||||
lseek(fd, 0, SEEK_SET);
|
||||
write(fd, x, (rsdpx.revision < 2) ?
|
||||
ACPI_RSDP_CHECKSUM_LENGTH : ACPI_RSDP_XCHECKSUM_LENGTH);
|
||||
} else if (!select_sig[0] || !memcmp("RSD PTR ", select_sig, 4)) {
|
||||
addr += (long)x - (long)raw;
|
||||
length = snprintf(buff, 80, "RSD PTR @ %p\n", (void *)addr);
|
||||
write(fd, buff, length);
|
||||
acpi_show_data(fd, (u8 *) & rsdpx, (rsdpx.revision < 2) ?
|
||||
ACPI_RSDP_CHECKSUM_LENGTH : ACPI_RSDP_XCHECKSUM_LENGTH);
|
||||
buff[0] = '\n';
|
||||
write(fd, buff, 1);
|
||||
}
|
||||
acpi_dump_dynamic_SSDT(fd);
|
||||
close(fd);
|
||||
return 0;
|
||||
not_found:
|
||||
close(fd);
|
||||
fprintf(stderr, "ACPI tables were not found. If you know location "
|
||||
"of RSD PTR table (from dmesg, etc), "
|
||||
"supply it with either --addr or -a option\n");
|
||||
return 1;
|
||||
}
|
131
tools/power/acpi/tools/acpidump/acpidump.h
Normal file
131
tools/power/acpi/tools/acpidump/acpidump.h
Normal file
@ -0,0 +1,131 @@
|
||||
/******************************************************************************
|
||||
*
|
||||
* Module Name: acpidump.h - Include file for acpi_dump utility
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2000 - 2014, Intel Corp.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification.
|
||||
* 2. Redistributions in binary form must reproduce at minimum a disclaimer
|
||||
* substantially similar to the "NO WARRANTY" disclaimer below
|
||||
* ("Disclaimer") and any redistribution must be conditioned upon
|
||||
* including a substantially similar Disclaimer requirement for further
|
||||
* binary redistribution.
|
||||
* 3. Neither the names of the above-listed copyright holders nor the names
|
||||
* of any contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* Alternatively, this software may be distributed under the terms of the
|
||||
* GNU General Public License ("GPL") version 2 as published by the Free
|
||||
* Software Foundation.
|
||||
*
|
||||
* NO WARRANTY
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
* HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
||||
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
|
||||
* IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGES.
|
||||
*/
|
||||
|
||||
#include <acpi/acpi.h>
|
||||
#include "accommon.h"
|
||||
#include "actables.h"
|
||||
|
||||
#include <stdio.h>
|
||||
#include <fcntl.h>
|
||||
#include <errno.h>
|
||||
#include <sys/stat.h>
|
||||
|
||||
/*
|
||||
* Global variables. Defined in main.c only, externed in all other files
|
||||
*/
|
||||
#ifdef _DECLARE_GLOBALS
|
||||
#define EXTERN
|
||||
#define INIT_GLOBAL(a,b) a=b
|
||||
#else
|
||||
#define EXTERN extern
|
||||
#define INIT_GLOBAL(a,b) a
|
||||
#endif
|
||||
|
||||
/* Globals */
|
||||
|
||||
EXTERN u8 INIT_GLOBAL(gbl_summary_mode, FALSE);
|
||||
EXTERN u8 INIT_GLOBAL(gbl_verbose_mode, FALSE);
|
||||
EXTERN u8 INIT_GLOBAL(gbl_binary_mode, FALSE);
|
||||
EXTERN u8 INIT_GLOBAL(gbl_dump_customized_tables, FALSE);
|
||||
EXTERN FILE INIT_GLOBAL(*gbl_output_file, NULL);
|
||||
EXTERN char INIT_GLOBAL(*gbl_output_filename, NULL);
|
||||
EXTERN u64 INIT_GLOBAL(gbl_rsdp_base, 0);
|
||||
|
||||
/* Globals required for use with ACPICA modules */
|
||||
|
||||
#ifdef _DECLARE_GLOBALS
|
||||
u8 acpi_gbl_enable_interpreter_slack = FALSE;
|
||||
u8 acpi_gbl_integer_byte_width = 8;
|
||||
u32 acpi_dbg_level = 0;
|
||||
u32 acpi_dbg_layer = 0;
|
||||
#endif
|
||||
|
||||
/* Action table used to defer requested options */
|
||||
|
||||
struct ap_dump_action {
|
||||
char *argument;
|
||||
u32 to_be_done;
|
||||
};
|
||||
|
||||
#define AP_MAX_ACTIONS 32
|
||||
|
||||
#define AP_DUMP_ALL_TABLES 0
|
||||
#define AP_DUMP_TABLE_BY_ADDRESS 1
|
||||
#define AP_DUMP_TABLE_BY_NAME 2
|
||||
#define AP_DUMP_TABLE_BY_FILE 3
|
||||
|
||||
#define AP_MAX_ACPI_FILES 256 /* Prevent infinite loops */
|
||||
|
||||
/* Minimum FADT sizes for various table addresses */
|
||||
|
||||
#define MIN_FADT_FOR_DSDT (ACPI_FADT_OFFSET (dsdt) + sizeof (u32))
|
||||
#define MIN_FADT_FOR_FACS (ACPI_FADT_OFFSET (facs) + sizeof (u32))
|
||||
#define MIN_FADT_FOR_XDSDT (ACPI_FADT_OFFSET (Xdsdt) + sizeof (u64))
|
||||
#define MIN_FADT_FOR_XFACS (ACPI_FADT_OFFSET (Xfacs) + sizeof (u64))
|
||||
|
||||
/*
|
||||
* apdump - Table get/dump routines
|
||||
*/
|
||||
int ap_dump_table_from_file(char *pathname);
|
||||
|
||||
int ap_dump_table_by_name(char *signature);
|
||||
|
||||
int ap_dump_table_by_address(char *ascii_address);
|
||||
|
||||
int ap_dump_all_tables(void);
|
||||
|
||||
u8 ap_is_valid_header(struct acpi_table_header *table);
|
||||
|
||||
u8 ap_is_valid_checksum(struct acpi_table_header *table);
|
||||
|
||||
u32 ap_get_table_length(struct acpi_table_header *table);
|
||||
|
||||
/*
|
||||
* apfiles - File I/O utilities
|
||||
*/
|
||||
int ap_open_output_file(char *pathname);
|
||||
|
||||
int ap_write_to_binary_file(struct acpi_table_header *table, u32 instance);
|
||||
|
||||
struct acpi_table_header *ap_get_table_from_file(char *pathname,
|
||||
u32 *file_size);
|
451
tools/power/acpi/tools/acpidump/apdump.c
Normal file
451
tools/power/acpi/tools/acpidump/apdump.c
Normal file
@ -0,0 +1,451 @@
|
||||
/******************************************************************************
|
||||
*
|
||||
* Module Name: apdump - Dump routines for ACPI tables (acpidump)
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2000 - 2014, Intel Corp.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification.
|
||||
* 2. Redistributions in binary form must reproduce at minimum a disclaimer
|
||||
* substantially similar to the "NO WARRANTY" disclaimer below
|
||||
* ("Disclaimer") and any redistribution must be conditioned upon
|
||||
* including a substantially similar Disclaimer requirement for further
|
||||
* binary redistribution.
|
||||
* 3. Neither the names of the above-listed copyright holders nor the names
|
||||
* of any contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* Alternatively, this software may be distributed under the terms of the
|
||||
* GNU General Public License ("GPL") version 2 as published by the Free
|
||||
* Software Foundation.
|
||||
*
|
||||
* NO WARRANTY
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
* HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
||||
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
|
||||
* IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGES.
|
||||
*/
|
||||
|
||||
#include "acpidump.h"
|
||||
|
||||
/* Local prototypes */
|
||||
|
||||
static int
|
||||
ap_dump_table_buffer(struct acpi_table_header *table,
|
||||
u32 instance, acpi_physical_address address);
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: ap_is_valid_header
|
||||
*
|
||||
* PARAMETERS: table - Pointer to table to be validated
|
||||
*
|
||||
* RETURN: TRUE if the header appears to be valid. FALSE otherwise
|
||||
*
|
||||
* DESCRIPTION: Check for a valid ACPI table header
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
u8 ap_is_valid_header(struct acpi_table_header *table)
|
||||
{
|
||||
|
||||
if (!ACPI_VALIDATE_RSDP_SIG(table->signature)) {
|
||||
|
||||
/* Make sure signature is all ASCII and a valid ACPI name */
|
||||
|
||||
if (!acpi_ut_valid_acpi_name(table->signature)) {
|
||||
fprintf(stderr,
|
||||
"Table signature (0x%8.8X) is invalid\n",
|
||||
*(u32 *)table->signature);
|
||||
return (FALSE);
|
||||
}
|
||||
|
||||
/* Check for minimum table length */
|
||||
|
||||
if (table->length < sizeof(struct acpi_table_header)) {
|
||||
fprintf(stderr, "Table length (0x%8.8X) is invalid\n",
|
||||
table->length);
|
||||
return (FALSE);
|
||||
}
|
||||
}
|
||||
|
||||
return (TRUE);
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: ap_is_valid_checksum
|
||||
*
|
||||
* PARAMETERS: table - Pointer to table to be validated
|
||||
*
|
||||
* RETURN: TRUE if the checksum appears to be valid. FALSE otherwise.
|
||||
*
|
||||
* DESCRIPTION: Check for a valid ACPI table checksum.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
u8 ap_is_valid_checksum(struct acpi_table_header *table)
|
||||
{
|
||||
acpi_status status;
|
||||
struct acpi_table_rsdp *rsdp;
|
||||
|
||||
if (ACPI_VALIDATE_RSDP_SIG(table->signature)) {
|
||||
/*
|
||||
* Checksum for RSDP.
|
||||
* Note: Other checksums are computed during the table dump.
|
||||
*/
|
||||
rsdp = ACPI_CAST_PTR(struct acpi_table_rsdp, table);
|
||||
status = acpi_tb_validate_rsdp(rsdp);
|
||||
} else {
|
||||
status = acpi_tb_verify_checksum(table, table->length);
|
||||
}
|
||||
|
||||
if (ACPI_FAILURE(status)) {
|
||||
fprintf(stderr, "%4.4s: Warning: wrong checksum in table\n",
|
||||
table->signature);
|
||||
}
|
||||
|
||||
return (AE_OK);
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: ap_get_table_length
|
||||
*
|
||||
* PARAMETERS: table - Pointer to the table
|
||||
*
|
||||
* RETURN: Table length
|
||||
*
|
||||
* DESCRIPTION: Obtain table length according to table signature.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
u32 ap_get_table_length(struct acpi_table_header *table)
|
||||
{
|
||||
struct acpi_table_rsdp *rsdp;
|
||||
|
||||
/* Check if table is valid */
|
||||
|
||||
if (!ap_is_valid_header(table)) {
|
||||
return (0);
|
||||
}
|
||||
|
||||
if (ACPI_VALIDATE_RSDP_SIG(table->signature)) {
|
||||
rsdp = ACPI_CAST_PTR(struct acpi_table_rsdp, table);
|
||||
return (rsdp->length);
|
||||
}
|
||||
|
||||
/* Normal ACPI table */
|
||||
|
||||
return (table->length);
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: ap_dump_table_buffer
|
||||
*
|
||||
* PARAMETERS: table - ACPI table to be dumped
|
||||
* instance - ACPI table instance no. to be dumped
|
||||
* address - Physical address of the table
|
||||
*
|
||||
* RETURN: None
|
||||
*
|
||||
* DESCRIPTION: Dump an ACPI table in standard ASCII hex format, with a
|
||||
* header that is compatible with the acpi_xtract utility.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
static int
|
||||
ap_dump_table_buffer(struct acpi_table_header *table,
|
||||
u32 instance, acpi_physical_address address)
|
||||
{
|
||||
u32 table_length;
|
||||
|
||||
table_length = ap_get_table_length(table);
|
||||
|
||||
/* Print only the header if requested */
|
||||
|
||||
if (gbl_summary_mode) {
|
||||
acpi_tb_print_table_header(address, table);
|
||||
return (0);
|
||||
}
|
||||
|
||||
/* Dump to binary file if requested */
|
||||
|
||||
if (gbl_binary_mode) {
|
||||
return (ap_write_to_binary_file(table, instance));
|
||||
}
|
||||
|
||||
/*
|
||||
* Dump the table with header for use with acpixtract utility.
|
||||
* Note: simplest to just always emit a 64-bit address. acpi_xtract
|
||||
* utility can handle this.
|
||||
*/
|
||||
printf("%4.4s @ 0x%8.8X%8.8X\n", table->signature,
|
||||
ACPI_FORMAT_UINT64(address));
|
||||
|
||||
acpi_ut_dump_buffer(ACPI_CAST_PTR(u8, table), table_length,
|
||||
DB_BYTE_DISPLAY, 0);
|
||||
printf("\n");
|
||||
return (0);
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: ap_dump_all_tables
|
||||
*
|
||||
* PARAMETERS: None
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: Get all tables from the RSDT/XSDT (or at least all of the
|
||||
* tables that we can possibly get).
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
int ap_dump_all_tables(void)
|
||||
{
|
||||
struct acpi_table_header *table;
|
||||
u32 instance = 0;
|
||||
acpi_physical_address address;
|
||||
acpi_status status;
|
||||
int table_status;
|
||||
u32 i;
|
||||
|
||||
/* Get and dump all available ACPI tables */
|
||||
|
||||
for (i = 0; i < AP_MAX_ACPI_FILES; i++) {
|
||||
status =
|
||||
acpi_os_get_table_by_index(i, &table, &instance, &address);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
|
||||
/* AE_LIMIT means that no more tables are available */
|
||||
|
||||
if (status == AE_LIMIT) {
|
||||
return (0);
|
||||
} else if (i == 0) {
|
||||
fprintf(stderr,
|
||||
"Could not get ACPI tables, %s\n",
|
||||
acpi_format_exception(status));
|
||||
return (-1);
|
||||
} else {
|
||||
fprintf(stderr,
|
||||
"Could not get ACPI table at index %u, %s\n",
|
||||
i, acpi_format_exception(status));
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
table_status = ap_dump_table_buffer(table, instance, address);
|
||||
free(table);
|
||||
|
||||
if (table_status) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* Something seriously bad happened if the loop terminates here */
|
||||
|
||||
return (-1);
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: ap_dump_table_by_address
|
||||
*
|
||||
* PARAMETERS: ascii_address - Address for requested ACPI table
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: Get an ACPI table via a physical address and dump it.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
int ap_dump_table_by_address(char *ascii_address)
|
||||
{
|
||||
acpi_physical_address address;
|
||||
struct acpi_table_header *table;
|
||||
acpi_status status;
|
||||
int table_status;
|
||||
u64 long_address;
|
||||
|
||||
/* Convert argument to an integer physical address */
|
||||
|
||||
status = acpi_ut_strtoul64(ascii_address, 0, &long_address);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
fprintf(stderr, "%s: Could not convert to a physical address\n",
|
||||
ascii_address);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
address = (acpi_physical_address) long_address;
|
||||
status = acpi_os_get_table_by_address(address, &table);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
fprintf(stderr, "Could not get table at 0x%8.8X%8.8X, %s\n",
|
||||
ACPI_FORMAT_UINT64(address),
|
||||
acpi_format_exception(status));
|
||||
return (-1);
|
||||
}
|
||||
|
||||
table_status = ap_dump_table_buffer(table, 0, address);
|
||||
free(table);
|
||||
return (table_status);
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: ap_dump_table_by_name
|
||||
*
|
||||
* PARAMETERS: signature - Requested ACPI table signature
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: Get an ACPI table via a signature and dump it. Handles
|
||||
* multiple tables with the same signature (SSDTs).
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
int ap_dump_table_by_name(char *signature)
|
||||
{
|
||||
char local_signature[ACPI_NAME_SIZE + 1];
|
||||
u32 instance;
|
||||
struct acpi_table_header *table;
|
||||
acpi_physical_address address;
|
||||
acpi_status status;
|
||||
int table_status;
|
||||
|
||||
if (strlen(signature) != ACPI_NAME_SIZE) {
|
||||
fprintf(stderr,
|
||||
"Invalid table signature [%s]: must be exactly 4 characters\n",
|
||||
signature);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
/* Table signatures are expected to be uppercase */
|
||||
|
||||
strcpy(local_signature, signature);
|
||||
acpi_ut_strupr(local_signature);
|
||||
|
||||
/* To be friendly, handle tables whose signatures do not match the name */
|
||||
|
||||
if (ACPI_COMPARE_NAME(local_signature, "FADT")) {
|
||||
strcpy(local_signature, ACPI_SIG_FADT);
|
||||
} else if (ACPI_COMPARE_NAME(local_signature, "MADT")) {
|
||||
strcpy(local_signature, ACPI_SIG_MADT);
|
||||
}
|
||||
|
||||
/* Dump all instances of this signature (to handle multiple SSDTs) */
|
||||
|
||||
for (instance = 0; instance < AP_MAX_ACPI_FILES; instance++) {
|
||||
status = acpi_os_get_table_by_name(local_signature, instance,
|
||||
&table, &address);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
|
||||
/* AE_LIMIT means that no more tables are available */
|
||||
|
||||
if (status == AE_LIMIT) {
|
||||
return (0);
|
||||
}
|
||||
|
||||
fprintf(stderr,
|
||||
"Could not get ACPI table with signature [%s], %s\n",
|
||||
local_signature, acpi_format_exception(status));
|
||||
return (-1);
|
||||
}
|
||||
|
||||
table_status = ap_dump_table_buffer(table, instance, address);
|
||||
free(table);
|
||||
|
||||
if (table_status) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* Something seriously bad happened if the loop terminates here */
|
||||
|
||||
return (-1);
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: ap_dump_table_from_file
|
||||
*
|
||||
* PARAMETERS: pathname - File containing the binary ACPI table
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: Dump an ACPI table from a binary file
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
int ap_dump_table_from_file(char *pathname)
|
||||
{
|
||||
struct acpi_table_header *table;
|
||||
u32 file_size = 0;
|
||||
int table_status = -1;
|
||||
|
||||
/* Get the entire ACPI table from the file */
|
||||
|
||||
table = ap_get_table_from_file(pathname, &file_size);
|
||||
if (!table) {
|
||||
return (-1);
|
||||
}
|
||||
|
||||
/* File must be at least as long as the table length */
|
||||
|
||||
if (table->length > file_size) {
|
||||
fprintf(stderr,
|
||||
"Table length (0x%X) is too large for input file (0x%X) %s\n",
|
||||
table->length, file_size, pathname);
|
||||
goto exit;
|
||||
}
|
||||
|
||||
if (gbl_verbose_mode) {
|
||||
fprintf(stderr,
|
||||
"Input file: %s contains table [%4.4s], 0x%X (%u) bytes\n",
|
||||
pathname, table->signature, file_size, file_size);
|
||||
}
|
||||
|
||||
table_status = ap_dump_table_buffer(table, 0, 0);
|
||||
|
||||
exit:
|
||||
free(table);
|
||||
return (table_status);
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: acpi_os* print functions
|
||||
*
|
||||
* DESCRIPTION: Used for linkage with ACPICA modules
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
void ACPI_INTERNAL_VAR_XFACE acpi_os_printf(const char *fmt, ...)
|
||||
{
|
||||
va_list args;
|
||||
|
||||
va_start(args, fmt);
|
||||
vfprintf(stdout, fmt, args);
|
||||
va_end(args);
|
||||
}
|
||||
|
||||
void acpi_os_vprintf(const char *fmt, va_list args)
|
||||
{
|
||||
vfprintf(stdout, fmt, args);
|
||||
}
|
228
tools/power/acpi/tools/acpidump/apfiles.c
Normal file
228
tools/power/acpi/tools/acpidump/apfiles.c
Normal file
@ -0,0 +1,228 @@
|
||||
/******************************************************************************
|
||||
*
|
||||
* Module Name: apfiles - File-related functions for acpidump utility
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2000 - 2014, Intel Corp.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification.
|
||||
* 2. Redistributions in binary form must reproduce at minimum a disclaimer
|
||||
* substantially similar to the "NO WARRANTY" disclaimer below
|
||||
* ("Disclaimer") and any redistribution must be conditioned upon
|
||||
* including a substantially similar Disclaimer requirement for further
|
||||
* binary redistribution.
|
||||
* 3. Neither the names of the above-listed copyright holders nor the names
|
||||
* of any contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* Alternatively, this software may be distributed under the terms of the
|
||||
* GNU General Public License ("GPL") version 2 as published by the Free
|
||||
* Software Foundation.
|
||||
*
|
||||
* NO WARRANTY
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
* HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
||||
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
|
||||
* IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGES.
|
||||
*/
|
||||
|
||||
#include "acpidump.h"
|
||||
#include "acapps.h"
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: ap_open_output_file
|
||||
*
|
||||
* PARAMETERS: pathname - Output filename
|
||||
*
|
||||
* RETURN: Open file handle
|
||||
*
|
||||
* DESCRIPTION: Open a text output file for acpidump. Checks if file already
|
||||
* exists.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
int ap_open_output_file(char *pathname)
|
||||
{
|
||||
struct stat stat_info;
|
||||
FILE *file;
|
||||
|
||||
/* If file exists, prompt for overwrite */
|
||||
|
||||
if (!stat(pathname, &stat_info)) {
|
||||
fprintf(stderr,
|
||||
"Target path already exists, overwrite? [y|n] ");
|
||||
|
||||
if (getchar() != 'y') {
|
||||
return (-1);
|
||||
}
|
||||
}
|
||||
|
||||
/* Point stdout to the file */
|
||||
|
||||
file = freopen(pathname, "w", stdout);
|
||||
if (!file) {
|
||||
perror("Could not open output file");
|
||||
return (-1);
|
||||
}
|
||||
|
||||
/* Save the file and path */
|
||||
|
||||
gbl_output_file = file;
|
||||
gbl_output_filename = pathname;
|
||||
return (0);
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: ap_write_to_binary_file
|
||||
*
|
||||
* PARAMETERS: table - ACPI table to be written
|
||||
* instance - ACPI table instance no. to be written
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: Write an ACPI table to a binary file. Builds the output
|
||||
* filename from the table signature.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
int ap_write_to_binary_file(struct acpi_table_header *table, u32 instance)
|
||||
{
|
||||
char filename[ACPI_NAME_SIZE + 16];
|
||||
char instance_str[16];
|
||||
FILE *file;
|
||||
size_t actual;
|
||||
u32 table_length;
|
||||
|
||||
/* Obtain table length */
|
||||
|
||||
table_length = ap_get_table_length(table);
|
||||
|
||||
/* Construct lower-case filename from the table local signature */
|
||||
|
||||
if (ACPI_VALIDATE_RSDP_SIG(table->signature)) {
|
||||
ACPI_MOVE_NAME(filename, ACPI_RSDP_NAME);
|
||||
} else {
|
||||
ACPI_MOVE_NAME(filename, table->signature);
|
||||
}
|
||||
filename[0] = (char)ACPI_TOLOWER(filename[0]);
|
||||
filename[1] = (char)ACPI_TOLOWER(filename[1]);
|
||||
filename[2] = (char)ACPI_TOLOWER(filename[2]);
|
||||
filename[3] = (char)ACPI_TOLOWER(filename[3]);
|
||||
filename[ACPI_NAME_SIZE] = 0;
|
||||
|
||||
/* Handle multiple SSDts - create different filenames for each */
|
||||
|
||||
if (instance > 0) {
|
||||
sprintf(instance_str, "%u", instance);
|
||||
strcat(filename, instance_str);
|
||||
}
|
||||
|
||||
strcat(filename, ACPI_TABLE_FILE_SUFFIX);
|
||||
|
||||
if (gbl_verbose_mode) {
|
||||
fprintf(stderr,
|
||||
"Writing [%4.4s] to binary file: %s 0x%X (%u) bytes\n",
|
||||
table->signature, filename, table->length,
|
||||
table->length);
|
||||
}
|
||||
|
||||
/* Open the file and dump the entire table in binary mode */
|
||||
|
||||
file = fopen(filename, "wb");
|
||||
if (!file) {
|
||||
perror("Could not open output file");
|
||||
return (-1);
|
||||
}
|
||||
|
||||
actual = fwrite(table, 1, table_length, file);
|
||||
if (actual != table_length) {
|
||||
perror("Error writing binary output file");
|
||||
fclose(file);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
fclose(file);
|
||||
return (0);
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: ap_get_table_from_file
|
||||
*
|
||||
* PARAMETERS: pathname - File containing the binary ACPI table
|
||||
* out_file_size - Where the file size is returned
|
||||
*
|
||||
* RETURN: Buffer containing the ACPI table. NULL on error.
|
||||
*
|
||||
* DESCRIPTION: Open a file and read it entirely into a new buffer
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
struct acpi_table_header *ap_get_table_from_file(char *pathname,
|
||||
u32 *out_file_size)
|
||||
{
|
||||
struct acpi_table_header *buffer = NULL;
|
||||
FILE *file;
|
||||
u32 file_size;
|
||||
size_t actual;
|
||||
|
||||
/* Must use binary mode */
|
||||
|
||||
file = fopen(pathname, "rb");
|
||||
if (!file) {
|
||||
perror("Could not open input file");
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
/* Need file size to allocate a buffer */
|
||||
|
||||
file_size = cm_get_file_size(file);
|
||||
if (file_size == ACPI_UINT32_MAX) {
|
||||
fprintf(stderr,
|
||||
"Could not get input file size: %s\n", pathname);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
/* Allocate a buffer for the entire file */
|
||||
|
||||
buffer = calloc(1, file_size);
|
||||
if (!buffer) {
|
||||
fprintf(stderr,
|
||||
"Could not allocate file buffer of size: %u\n",
|
||||
file_size);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
/* Read the entire file */
|
||||
|
||||
actual = fread(buffer, 1, file_size, file);
|
||||
if (actual != file_size) {
|
||||
fprintf(stderr, "Could not read input file: %s\n", pathname);
|
||||
free(buffer);
|
||||
buffer = NULL;
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
*out_file_size = file_size;
|
||||
|
||||
cleanup:
|
||||
fclose(file);
|
||||
return (buffer);
|
||||
}
|
340
tools/power/acpi/tools/acpidump/apmain.c
Normal file
340
tools/power/acpi/tools/acpidump/apmain.c
Normal file
@ -0,0 +1,340 @@
|
||||
/******************************************************************************
|
||||
*
|
||||
* Module Name: apmain - Main module for the acpidump utility
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2000 - 2014, Intel Corp.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification.
|
||||
* 2. Redistributions in binary form must reproduce at minimum a disclaimer
|
||||
* substantially similar to the "NO WARRANTY" disclaimer below
|
||||
* ("Disclaimer") and any redistribution must be conditioned upon
|
||||
* including a substantially similar Disclaimer requirement for further
|
||||
* binary redistribution.
|
||||
* 3. Neither the names of the above-listed copyright holders nor the names
|
||||
* of any contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* Alternatively, this software may be distributed under the terms of the
|
||||
* GNU General Public License ("GPL") version 2 as published by the Free
|
||||
* Software Foundation.
|
||||
*
|
||||
* NO WARRANTY
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
* HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
||||
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
|
||||
* IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGES.
|
||||
*/
|
||||
|
||||
#define _DECLARE_GLOBALS
|
||||
#include "acpidump.h"
|
||||
#include "acapps.h"
|
||||
|
||||
/*
|
||||
* acpidump - A portable utility for obtaining system ACPI tables and dumping
|
||||
* them in an ASCII hex format suitable for binary extraction via acpixtract.
|
||||
*
|
||||
* Obtaining the system ACPI tables is an OS-specific operation.
|
||||
*
|
||||
* This utility can be ported to any host operating system by providing a
|
||||
* module containing system-specific versions of these interfaces:
|
||||
*
|
||||
* acpi_os_get_table_by_address
|
||||
* acpi_os_get_table_by_index
|
||||
* acpi_os_get_table_by_name
|
||||
*
|
||||
* See the ACPICA Reference Guide for the exact definitions of these
|
||||
* interfaces. Also, see these ACPICA source code modules for example
|
||||
* implementations:
|
||||
*
|
||||
* source/os_specific/service_layers/oswintbl.c
|
||||
* source/os_specific/service_layers/oslinuxtbl.c
|
||||
*/
|
||||
|
||||
/* Local prototypes */
|
||||
|
||||
static void ap_display_usage(void);
|
||||
|
||||
static int ap_do_options(int argc, char **argv);
|
||||
|
||||
static void ap_insert_action(char *argument, u32 to_be_done);
|
||||
|
||||
/* Table for deferred actions from command line options */
|
||||
|
||||
struct ap_dump_action action_table[AP_MAX_ACTIONS];
|
||||
u32 current_action = 0;
|
||||
|
||||
#define AP_UTILITY_NAME "ACPI Binary Table Dump Utility"
|
||||
#define AP_SUPPORTED_OPTIONS "?a:bcf:hn:o:r:svz"
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: ap_display_usage
|
||||
*
|
||||
* DESCRIPTION: Usage message for the acpi_dump utility
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
static void ap_display_usage(void)
|
||||
{
|
||||
|
||||
ACPI_USAGE_HEADER("acpidump [options]");
|
||||
|
||||
ACPI_OPTION("-b", "Dump tables to binary files");
|
||||
ACPI_OPTION("-c", "Dump customized tables");
|
||||
ACPI_OPTION("-h -?", "This help message");
|
||||
ACPI_OPTION("-o <File>", "Redirect output to file");
|
||||
ACPI_OPTION("-r <Address>", "Dump tables from specified RSDP");
|
||||
ACPI_OPTION("-s", "Print table summaries only");
|
||||
ACPI_OPTION("-v", "Display version information");
|
||||
ACPI_OPTION("-z", "Verbose mode");
|
||||
|
||||
printf("\nTable Options:\n");
|
||||
|
||||
ACPI_OPTION("-a <Address>", "Get table via a physical address");
|
||||
ACPI_OPTION("-f <BinaryFile>", "Get table via a binary file");
|
||||
ACPI_OPTION("-n <Signature>", "Get table via a name/signature");
|
||||
|
||||
printf("\n"
|
||||
"Invocation without parameters dumps all available tables\n"
|
||||
"Multiple mixed instances of -a, -f, and -n are supported\n\n");
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: ap_insert_action
|
||||
*
|
||||
* PARAMETERS: argument - Pointer to the argument for this action
|
||||
* to_be_done - What to do to process this action
|
||||
*
|
||||
* RETURN: None. Exits program if action table becomes full.
|
||||
*
|
||||
* DESCRIPTION: Add an action item to the action table
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
static void ap_insert_action(char *argument, u32 to_be_done)
|
||||
{
|
||||
|
||||
/* Insert action and check for table overflow */
|
||||
|
||||
action_table[current_action].argument = argument;
|
||||
action_table[current_action].to_be_done = to_be_done;
|
||||
|
||||
current_action++;
|
||||
if (current_action > AP_MAX_ACTIONS) {
|
||||
fprintf(stderr, "Too many table options (max %u)\n",
|
||||
AP_MAX_ACTIONS);
|
||||
exit(-1);
|
||||
}
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: ap_do_options
|
||||
*
|
||||
* PARAMETERS: argc/argv - Standard argc/argv
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: Command line option processing. The main actions for getting
|
||||
* and dumping tables are deferred via the action table.
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
static int ap_do_options(int argc, char **argv)
|
||||
{
|
||||
int j;
|
||||
acpi_status status;
|
||||
|
||||
/* Command line options */
|
||||
|
||||
while ((j = acpi_getopt(argc, argv, AP_SUPPORTED_OPTIONS)) != EOF)
|
||||
switch (j) {
|
||||
/*
|
||||
* Global options
|
||||
*/
|
||||
case 'b': /* Dump all input tables to binary files */
|
||||
|
||||
gbl_binary_mode = TRUE;
|
||||
continue;
|
||||
|
||||
case 'c': /* Dump customized tables */
|
||||
|
||||
gbl_dump_customized_tables = TRUE;
|
||||
continue;
|
||||
|
||||
case 'h':
|
||||
case '?':
|
||||
|
||||
ap_display_usage();
|
||||
exit(0);
|
||||
|
||||
case 'o': /* Redirect output to a single file */
|
||||
|
||||
if (ap_open_output_file(acpi_gbl_optarg)) {
|
||||
exit(-1);
|
||||
}
|
||||
continue;
|
||||
|
||||
case 'r': /* Dump tables from specified RSDP */
|
||||
|
||||
status =
|
||||
acpi_ut_strtoul64(acpi_gbl_optarg, 0,
|
||||
&gbl_rsdp_base);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
fprintf(stderr,
|
||||
"%s: Could not convert to a physical address\n",
|
||||
acpi_gbl_optarg);
|
||||
exit(-1);
|
||||
}
|
||||
continue;
|
||||
|
||||
case 's': /* Print table summaries only */
|
||||
|
||||
gbl_summary_mode = TRUE;
|
||||
continue;
|
||||
|
||||
case 'v': /* Revision/version */
|
||||
|
||||
printf(ACPI_COMMON_SIGNON(AP_UTILITY_NAME));
|
||||
exit(0);
|
||||
|
||||
case 'z': /* Verbose mode */
|
||||
|
||||
gbl_verbose_mode = TRUE;
|
||||
fprintf(stderr, ACPI_COMMON_SIGNON(AP_UTILITY_NAME));
|
||||
continue;
|
||||
|
||||
/*
|
||||
* Table options
|
||||
*/
|
||||
case 'a': /* Get table by physical address */
|
||||
|
||||
ap_insert_action(acpi_gbl_optarg,
|
||||
AP_DUMP_TABLE_BY_ADDRESS);
|
||||
break;
|
||||
|
||||
case 'f': /* Get table from a file */
|
||||
|
||||
ap_insert_action(acpi_gbl_optarg,
|
||||
AP_DUMP_TABLE_BY_FILE);
|
||||
break;
|
||||
|
||||
case 'n': /* Get table by input name (signature) */
|
||||
|
||||
ap_insert_action(acpi_gbl_optarg,
|
||||
AP_DUMP_TABLE_BY_NAME);
|
||||
break;
|
||||
|
||||
default:
|
||||
|
||||
ap_display_usage();
|
||||
exit(-1);
|
||||
}
|
||||
|
||||
/* If there are no actions, this means "get/dump all tables" */
|
||||
|
||||
if (current_action == 0) {
|
||||
ap_insert_action(NULL, AP_DUMP_ALL_TABLES);
|
||||
}
|
||||
|
||||
return (0);
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* FUNCTION: main
|
||||
*
|
||||
* PARAMETERS: argc/argv - Standard argc/argv
|
||||
*
|
||||
* RETURN: Status
|
||||
*
|
||||
* DESCRIPTION: C main function for acpidump utility
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
int ACPI_SYSTEM_XFACE main(int argc, char *argv[])
|
||||
{
|
||||
int status = 0;
|
||||
struct ap_dump_action *action;
|
||||
u32 file_size;
|
||||
u32 i;
|
||||
|
||||
ACPI_DEBUG_INITIALIZE(); /* For debug version only */
|
||||
|
||||
/* Process command line options */
|
||||
|
||||
if (ap_do_options(argc, argv)) {
|
||||
return (-1);
|
||||
}
|
||||
|
||||
/* Get/dump ACPI table(s) as requested */
|
||||
|
||||
for (i = 0; i < current_action; i++) {
|
||||
action = &action_table[i];
|
||||
switch (action->to_be_done) {
|
||||
case AP_DUMP_ALL_TABLES:
|
||||
|
||||
status = ap_dump_all_tables();
|
||||
break;
|
||||
|
||||
case AP_DUMP_TABLE_BY_ADDRESS:
|
||||
|
||||
status = ap_dump_table_by_address(action->argument);
|
||||
break;
|
||||
|
||||
case AP_DUMP_TABLE_BY_NAME:
|
||||
|
||||
status = ap_dump_table_by_name(action->argument);
|
||||
break;
|
||||
|
||||
case AP_DUMP_TABLE_BY_FILE:
|
||||
|
||||
status = ap_dump_table_from_file(action->argument);
|
||||
break;
|
||||
|
||||
default:
|
||||
|
||||
fprintf(stderr,
|
||||
"Internal error, invalid action: 0x%X\n",
|
||||
action->to_be_done);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
if (status) {
|
||||
return (status);
|
||||
}
|
||||
}
|
||||
|
||||
if (gbl_output_file) {
|
||||
if (gbl_verbose_mode) {
|
||||
|
||||
/* Summary for the output file */
|
||||
|
||||
file_size = cm_get_file_size(gbl_output_file);
|
||||
fprintf(stderr,
|
||||
"Output file %s contains 0x%X (%u) bytes\n\n",
|
||||
gbl_output_filename, file_size, file_size);
|
||||
}
|
||||
|
||||
fclose(gbl_output_file);
|
||||
}
|
||||
|
||||
return (status);
|
||||
}
|
Loading…
Reference in New Issue
Block a user