📄 bm.c
字号:
/****************************************************************************** * * Module Name: bm.c * $Revision: 48 $ * *****************************************************************************//* * Copyright (C) 2000, 2001 Andrew Grover * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */#include <linux/kernel.h>#include <linux/module.h>#include <linux/init.h>#include <acpi.h>#include "bm.h"#define _COMPONENT ACPI_BUS MODULE_NAME ("bm")/**************************************************************************** * Globals ****************************************************************************/extern fadt_descriptor_rev2 acpi_fadt;/* TBD: Make dynamically sizeable. */BM_NODE_LIST node_list;/**************************************************************************** * Internal Functions ****************************************************************************//***************************************************************************** * * FUNCTION: bm_print_object * * PARAMETERS: * * RETURN: * * DESCRIPTION: * ****************************************************************************/voidbm_print_object ( acpi_handle handle){ acpi_buffer buffer; acpi_handle parent; acpi_object_type type; buffer.length = 256; buffer.pointer = acpi_os_callocate(buffer.length); if (!buffer.pointer) { return; } acpi_get_name(handle, ACPI_FULL_PATHNAME, &buffer); acpi_get_parent(handle, &parent); acpi_get_type(handle, &type); /* * TBD: Hack to get around scope identification problem. */ if (type == ACPI_TYPE_ANY) { if (ACPI_SUCCESS(acpi_get_next_object(ACPI_TYPE_ANY, handle, 0, NULL))) { type = INTERNAL_TYPE_SCOPE; } } switch (type) { case INTERNAL_TYPE_SCOPE: acpi_os_printf("SCOPE: "); break; case ACPI_TYPE_INTEGER: acpi_os_printf("SIMPLE (number): "); break; case ACPI_TYPE_STRING: acpi_os_printf("SIMPLE (string): "); break; case ACPI_TYPE_BUFFER: acpi_os_printf("SIMPLE (buffer): "); break; case ACPI_TYPE_PACKAGE: acpi_os_printf("SIMPLE (package): "); break; case ACPI_TYPE_FIELD_UNIT: acpi_os_printf("FIELD UNIT: "); break; case ACPI_TYPE_DEVICE: acpi_os_printf("DEVICE: "); break; case ACPI_TYPE_EVENT: acpi_os_printf("EVENT: "); break; case ACPI_TYPE_METHOD: acpi_os_printf("CONTROL METHOD: "); break; case ACPI_TYPE_MUTEX: acpi_os_printf("MUTEX: "); break; case ACPI_TYPE_REGION: acpi_os_printf("OPERATION REGION: "); break; case ACPI_TYPE_POWER: acpi_os_printf("POWER RESOURCE: "); break; case ACPI_TYPE_PROCESSOR: acpi_os_printf("PROCESSOR: "); break; case ACPI_TYPE_THERMAL: acpi_os_printf("THERMAL ZONE: "); break; case ACPI_TYPE_BUFFER_FIELD: acpi_os_printf("BUFFER FIELD: "); break; case ACPI_TYPE_DDB_HANDLE: acpi_os_printf("DDB HANDLE: "); break; default: acpi_os_printf("OTHER (%d): ", type); break; } acpi_os_printf("Object[%p][%s] parent[%p].\n", handle, (char*)buffer.pointer, parent); acpi_os_free(buffer.pointer);}/**************************************************************************** * * FUNCTION: bm_print_node * * PARAMETERS: * * RETURN: * * DESCRIPTION: * ****************************************************************************/voidbm_print_node ( BM_NODE *node, u32 flags){#ifdef ACPI_DEBUG acpi_buffer buffer; BM_DEVICE *device = NULL; char *type_string = NULL; PROC_NAME("bm_print_node"); if (!node) { return; } device = &(node->device); if (flags & BM_PRINT_PRESENT) { if (!BM_DEVICE_PRESENT(device)) { return; } } buffer.length = 256; buffer.pointer = acpi_os_callocate(buffer.length); if (!buffer.pointer) { return; } acpi_get_name(device->acpi_handle, ACPI_FULL_PATHNAME, &buffer); switch(device->id.type) { case BM_TYPE_SYSTEM: type_string = " System"; break; case BM_TYPE_SCOPE: type_string = " Scope"; break; case BM_TYPE_PROCESSOR: type_string = " Proc"; break; case BM_TYPE_THERMAL_ZONE: type_string = "Thermal"; break; case BM_TYPE_POWER_RESOURCE: type_string = " Power"; break; case BM_TYPE_FIXED_BUTTON: type_string = " Button"; break; case BM_TYPE_DEVICE: type_string = " Device"; break; default: type_string = "Unknown"; break; } if (!(flags & BM_PRINT_GROUP)) { ACPI_DEBUG_PRINT_RAW ((ACPI_DB_INFO, "+-------------------------------------------------------------------------------\n")); } ACPI_DEBUG_PRINT_RAW ((ACPI_DB_INFO, "| %s[%02x]:[%p] flags[%02x] hid[%s] %s\n", type_string, device->handle, device->acpi_handle, device->flags, (device->id.hid[0] ? device->id.hid : " "), (char*)buffer.pointer)); if (flags & BM_PRINT_IDENTIFICATION) { ACPI_DEBUG_PRINT_RAW ((ACPI_DB_INFO, "| identification: uid[%s] adr[%08x]\n", device->id.uid, device->id.adr)); } if (flags & BM_PRINT_LINKAGE) { ACPI_DEBUG_PRINT_RAW ((ACPI_DB_INFO, "| linkage: this[%p] parent[%p] next[%p]\n", node, node->parent, node->next)); ACPI_DEBUG_PRINT_RAW ((ACPI_DB_INFO, "| scope.head[%p] scope.tail[%p]\n", node->scope.head, node->scope.tail)); } if (flags & BM_PRINT_POWER) { ACPI_DEBUG_PRINT_RAW ((ACPI_DB_INFO, "| power: state[D%d] flags[%08x]\n", device->power.state, device->power.flags)); ACPI_DEBUG_PRINT_RAW ((ACPI_DB_INFO, "| S0[%02x] S1[%02x] S2[%02x] S3[%02x] S4[%02x] S5[%02x]\n", device->power.dx_supported[0], device->power.dx_supported[1], device->power.dx_supported[2], device->power.dx_supported[3], device->power.dx_supported[4], device->power.dx_supported[5])); } if (!(flags & BM_PRINT_GROUP)) { ACPI_DEBUG_PRINT_RAW ((ACPI_DB_INFO, "+-------------------------------------------------------------------------------\n")); } acpi_os_free(buffer.pointer);#endif /*ACPI_DEBUG*/ return;}/**************************************************************************** * * FUNCTION: bm_print_hierarchy * * PARAMETERS: * * RETURN: * * DESCRIPTION: * ****************************************************************************/voidbm_print_hierarchy (void){#ifdef ACPI_DEBUG u32 i = 0; FUNCTION_TRACE("bm_print_hierarchy"); ACPI_DEBUG_PRINT_RAW ((ACPI_DB_INFO, "+------------------------------------------------------------\n")); for (i = 0; i < node_list.count; i++) { bm_print_node(node_list.nodes[i], BM_PRINT_GROUP | BM_PRINT_PRESENT); } ACPI_DEBUG_PRINT_RAW ((ACPI_DB_INFO, "+------------------------------------------------------------\n"));#endif /*ACPI_DEBUG*/ return_VOID;}/**************************************************************************** * * FUNCTION: bm_get_status * * PARAMETERS: * * RETURN: * * DESCRIPTION: * ****************************************************************************/acpi_statusbm_get_status ( BM_DEVICE *device){ acpi_status status = AE_OK; if (!device) { return AE_BAD_PARAMETER; } device->status = BM_STATUS_UNKNOWN; /* * Dynamic Status? * --------------- * If _STA isn't present we just return the default status. */ if (!(device->flags & BM_FLAGS_DYNAMIC_STATUS)) { device->status = BM_STATUS_DEFAULT; return AE_OK; } /* * Evaluate _STA: * -------------- */ status = bm_evaluate_simple_integer(device->acpi_handle, "_STA", &(device->status)); return status;}/**************************************************************************** * * FUNCTION: bm_get_identification * * PARAMETERS: * * RETURN: * * DESCRIPTION: * ****************************************************************************/acpi_statusbm_get_identification ( BM_DEVICE *device){ acpi_status status = AE_OK; acpi_device_info info; if (!device) { return AE_BAD_PARAMETER; } if (!(device->flags & BM_FLAGS_IDENTIFIABLE)) { return AE_OK; } device->id.uid[0] = BM_UID_UNKNOWN; device->id.hid[0] = BM_HID_UNKNOWN; device->id.adr = BM_ADDRESS_UNKNOWN; /* * Get Object Info: * ---------------- * Evalute _UID, _HID, and _ADR... */ status = acpi_get_object_info(device->acpi_handle, &info); if (ACPI_FAILURE(status)) { return status; } if (info.valid & ACPI_VALID_UID) { MEMCPY((void*)device->id.uid, (void*)info.unique_id, sizeof(BM_DEVICE_UID)); } if (info.valid & ACPI_VALID_HID) { MEMCPY((void*)device->id.hid, (void*)info.hardware_id, sizeof(BM_DEVICE_HID)); } if (info.valid & ACPI_VALID_ADR) { device->id.adr = info.address; } return status;}/**************************************************************************** * * FUNCTION: bm_get_flags * * PARAMETERS: * * RETURN: * * DESCRIPTION: * ****************************************************************************/acpi_statusbm_get_flags ( BM_DEVICE *device){ acpi_handle acpi_handle = NULL; if (!device) { return AE_BAD_PARAMETER; } device->flags = BM_FLAGS_UNKNOWN; switch (device->id.type) { case BM_TYPE_DEVICE: /* * Presence of _DCK indicates a docking station. */ if (ACPI_SUCCESS(acpi_get_handle(device->acpi_handle, "_DCK", &acpi_handle))) { device->flags |= BM_FLAGS_DOCKING_STATION; } /* * Presence of _EJD and/or _EJx indicates 'ejectable'. * TBD: _EJx... */ if (ACPI_SUCCESS(acpi_get_handle(device->acpi_handle, "_EJD", &acpi_handle))) { device->flags |= BM_FLAGS_EJECTABLE; } /* * Presence of _PR0 or _PS0 indicates 'power manageable'. */ if (ACPI_SUCCESS(acpi_get_handle(device->acpi_handle, "_PR0", &acpi_handle)) || ACPI_SUCCESS(acpi_get_handle(device->acpi_handle, "_PS0", &acpi_handle))) { device->flags |= BM_FLAGS_POWER_CONTROL; } /* * Presence of _CRS indicates 'configurable'. */ if (ACPI_SUCCESS(acpi_get_handle(device->acpi_handle, "_CRS", &acpi_handle))) { device->flags |= BM_FLAGS_CONFIGURABLE; } /* Fall through to next case statement. */ case BM_TYPE_PROCESSOR: case BM_TYPE_THERMAL_ZONE: case BM_TYPE_POWER_RESOURCE: /* * Presence of _HID or _ADR indicates 'identifiable'. */ if (ACPI_SUCCESS(acpi_get_handle(device->acpi_handle, "_HID", &acpi_handle)) || ACPI_SUCCESS(acpi_get_handle(device->acpi_handle, "_ADR", &acpi_handle))) { device->flags |= BM_FLAGS_IDENTIFIABLE; } /* * Presence of _STA indicates 'dynamic status'. */ if (ACPI_SUCCESS(acpi_get_handle(device->acpi_handle, "_STA", &acpi_handle))) { device->flags |= BM_FLAGS_DYNAMIC_STATUS; } break; } return AE_OK;}/**************************************************************************** * * FUNCTION: bm_add_namespace_device * * PARAMETERS: * * RETURN: * * DESCRIPTION: * ****************************************************************************/acpi_statusbm_add_namespace_device ( acpi_handle acpi_handle, acpi_object_type acpi_type, BM_NODE *parent, BM_NODE **child){ acpi_status status = AE_OK; BM_NODE *node = NULL; BM_DEVICE *device = NULL; FUNCTION_TRACE("bm_add_namespace_device"); if (!parent || !child) { return_ACPI_STATUS(AE_BAD_PARAMETER); } if (node_list.count > BM_HANDLES_MAX) { return_ACPI_STATUS(AE_NO_MEMORY); } (*child) = NULL; /* * Create Node: * ------------ */ node = acpi_os_callocate(sizeof(BM_NODE)); if (!node) { return_ACPI_STATUS(AE_NO_MEMORY); } node->parent = parent; node->next = NULL; device = &(node->device); device->handle = node_list.count; device->acpi_handle = acpi_handle; /* * Device Type: * ------------ */ switch (acpi_type) { case INTERNAL_TYPE_SCOPE: device->id.type = BM_TYPE_SCOPE; break; case ACPI_TYPE_PROCESSOR: device->id.type = BM_TYPE_PROCESSOR; break; case ACPI_TYPE_THERMAL: device->id.type = BM_TYPE_THERMAL_ZONE; break; case ACPI_TYPE_POWER: device->id.type = BM_TYPE_POWER_RESOURCE; break; case ACPI_TYPE_DEVICE: device->id.type = BM_TYPE_DEVICE; break; } /* * Get Other Device Info: * ---------------------- * But only if this device's parent is present (which implies * this device MAY be present). */ if (BM_NODE_PRESENT(node->parent)) { /* * Device Flags */ status = bm_get_flags(device); if (ACPI_FAILURE(status)) { goto end; } /* * Device Identification */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -