patch-2.4.0-prerelease linux/drivers/acpi/namespace/nsutils.c
Next file: linux/drivers/acpi/namespace/nsxfname.c
Previous file: linux/drivers/acpi/namespace/nssearch.c
Back to the patch index
Back to the overall index
- Lines: 355
- Date:
Fri Dec 29 14:07:21 2000
- Orig file:
v2.4.0-test12/linux/drivers/acpi/namespace/nsutils.c
- Orig date:
Sun Oct 8 10:50:15 2000
diff -u --recursive --new-file v2.4.0-test12/linux/drivers/acpi/namespace/nsutils.c linux/drivers/acpi/namespace/nsutils.c
@@ -2,7 +2,7 @@
*
* Module Name: nsutils - Utilities for accessing ACPI namespace, accessing
* parents and siblings and Scope manipulation
- * $Revision: 69 $
+ * $Revision: 74 $
*
*****************************************************************************/
@@ -93,7 +93,7 @@
{
if (!handle) {
- REPORT_WARNING ("Ns_get_type: Null handle");
+ REPORT_WARNING (("Ns_get_type: Null handle\n"));
return (ACPI_TYPE_ANY);
}
@@ -120,7 +120,7 @@
if (!acpi_cm_valid_object_type (type)) {
/* Type code out of range */
- REPORT_WARNING ("Ns_local: Invalid Object Type");
+ REPORT_WARNING (("Ns_local: Invalid Object Type\n"));
return (NSP_NORMAL);
}
@@ -150,9 +150,10 @@
{
NATIVE_CHAR *result = NULL;
NATIVE_CHAR *internal_name;
- u32 num_segments;
+ u32 num_segments = 0;
u8 fully_qualified = FALSE;
u32 i;
+ u32 num_carats = 0;
if ((!external_name) ||
@@ -178,6 +179,16 @@
external_name++;
}
+ else {
+ /*
+ * Handle Carat prefixes
+ */
+
+ while (*external_name == '^') {
+ num_carats++;
+ external_name++;
+ }
+ }
/*
* Determine the number of ACPI name "segments" by counting
@@ -186,17 +197,19 @@
* + 1, and zero separators is ok.
*/
- num_segments = 1;
- for (i = 0; external_name[i]; i++) {
- if (acpi_ns_valid_path_separator (external_name[i])) {
- num_segments++;
+ if (*external_name) {
+ num_segments = 1;
+ for (i = 0; external_name[i]; i++) {
+ if (acpi_ns_valid_path_separator (external_name[i])) {
+ num_segments++;
+ }
}
}
/* We need a segment to store the internal version of the name */
- internal_name = acpi_cm_callocate ((ACPI_NAME_SIZE * num_segments) + 4);
+ internal_name = acpi_cm_callocate ((ACPI_NAME_SIZE * num_segments) + 4 + num_carats);
if (!internal_name) {
return (AE_NO_MEMORY);
}
@@ -206,14 +219,49 @@
if (fully_qualified) {
internal_name[0] = '\\';
- internal_name[1] = AML_MULTI_NAME_PREFIX_OP;
- internal_name[2] = (char) num_segments;
- result = &internal_name[3];
+
+ if (num_segments <= 1) {
+ result = &internal_name[1];
+ }
+ else if (num_segments == 2) {
+ internal_name[1] = AML_DUAL_NAME_PREFIX;
+ result = &internal_name[2];
+ }
+ else {
+ internal_name[1] = AML_MULTI_NAME_PREFIX_OP;
+ internal_name[2] = (char) num_segments;
+ result = &internal_name[3];
+ }
+
}
+
else {
- internal_name[0] = AML_MULTI_NAME_PREFIX_OP;
- internal_name[1] = (char) num_segments;
- result = &internal_name[2];
+ /*
+ * Not fully qualified.
+ * Handle Carats first, then append the name segments
+ */
+
+ i = 0;
+ if (num_carats) {
+ for (i = 0; i < num_carats; i++) {
+ internal_name[i] = '^';
+ }
+ }
+
+ if (num_segments == 1) {
+ result = &internal_name[i];
+ }
+
+ else if (num_segments == 2) {
+ internal_name[i] = AML_DUAL_NAME_PREFIX;
+ result = &internal_name[i+1];
+ }
+
+ else {
+ internal_name[i] = AML_MULTI_NAME_PREFIX_OP;
+ internal_name[i+1] = (char) num_segments;
+ result = &internal_name[i+2];
+ }
}
@@ -271,6 +319,157 @@
/****************************************************************************
*
+ * FUNCTION: Acpi_ns_externalize_name
+ *
+ * PARAMETERS: *Internal_name - Internal representation of name
+ * **Converted_name - Where to return the resulting
+ * external representation of name
+ *
+ * RETURN: Status
+ *
+ * DESCRIPTION: Convert internal name (e.g. 5c 2f 02 5f 50 52 5f 43 50 55 30)
+ * to its external form (e.g. "\_PR_.CPU0")
+ *
+ ****************************************************************************/
+
+ACPI_STATUS
+acpi_ns_externalize_name (
+ u32 internal_name_length,
+ char *internal_name,
+ u32 *converted_name_length,
+ char **converted_name)
+{
+ u32 prefix_length = 0;
+ u32 names_index = 0;
+ u32 names_count = 0;
+ u32 i = 0;
+ u32 j = 0;
+
+
+ if (!internal_name_length ||
+ !internal_name ||
+ !converted_name_length ||
+ !converted_name)
+ {
+ return (AE_BAD_PARAMETER);
+ }
+
+
+ /*
+ * Check for a prefix (one '\' | one or more '^').
+ */
+ switch (internal_name[0])
+ {
+ case '\\':
+ prefix_length = 1;
+ break;
+
+ case '^':
+ for (i = 0; i < internal_name_length; i++) {
+ if (internal_name[i] != '^') {
+ prefix_length = i + 1;
+ }
+ }
+
+ if (i == internal_name_length) {
+ prefix_length = i;
+ }
+
+ break;
+ }
+
+ /*
+ * Check for object names. Note that there could be 0-255 of these
+ * 4-byte elements.
+ */
+ if (prefix_length < internal_name_length) {
+ switch (internal_name[prefix_length])
+ {
+
+ /* <count> 4-byte names */
+
+ case AML_MULTI_NAME_PREFIX_OP:
+ names_index = prefix_length + 2;
+ names_count = (u32) internal_name[prefix_length + 1];
+ break;
+
+
+ /* two 4-byte names */
+
+ case AML_DUAL_NAME_PREFIX:
+ names_index = prefix_length + 1;
+ names_count = 2;
+ break;
+
+
+ /* Null_name */
+
+ case 0:
+ names_index = 0;
+ names_count = 0;
+ break;
+
+
+ /* one 4-byte name */
+
+ default:
+ names_index = prefix_length;
+ names_count = 1;
+ break;
+ }
+ }
+
+ /*
+ * Calculate the length of Converted_name, which equals the length
+ * of the prefix, length of all object names, length of any required
+ * punctuation ('.') between object names, plus the NULL terminator.
+ */
+ *converted_name_length = prefix_length + (4 * names_count) +
+ ((names_count > 0) ? (names_count - 1) : 0) + 1;
+
+ /*
+ * Check to see if we're still in bounds. If not, there's a problem
+ * with Internal_name (invalid format).
+ */
+ if (*converted_name_length > internal_name_length) {
+ REPORT_ERROR (("Ns_externalize_name: Invalid internal name\n"));
+ return (AE_BAD_PATHNAME);
+ }
+
+ /*
+ * Build Converted_name...
+ */
+
+ (*converted_name) = acpi_cm_callocate (*converted_name_length);
+ if (!(*converted_name)) {
+ return (AE_NO_MEMORY);
+ }
+
+ j = 0;
+
+ for (i = 0; i < prefix_length; i++) {
+ (*converted_name)[j++] = internal_name[i];
+ }
+
+ if (names_count > 0) {
+ for (i = 0; i < names_count; i++) {
+ if (i > 0) {
+ (*converted_name)[j++] = '.';
+ }
+
+ (*converted_name)[j++] = internal_name[names_index++];
+ (*converted_name)[j++] = internal_name[names_index++];
+ (*converted_name)[j++] = internal_name[names_index++];
+ (*converted_name)[j++] = internal_name[names_index++];
+ }
+ }
+
+ return (AE_OK);
+}
+
+
+/****************************************************************************
+ *
* FUNCTION: Acpi_ns_convert_handle_to_entry
*
* PARAMETERS: Handle - Handle to be converted to an Node
@@ -425,7 +624,7 @@
if (!acpi_cm_valid_object_type (type)) {
/* type code out of range */
- REPORT_WARNING ("Ns_opens_scope: Invalid Object Type");
+ REPORT_WARNING (("Ns_opens_scope: Invalid Object Type\n"));
return (NSP_NORMAL);
}
@@ -464,8 +663,6 @@
NATIVE_CHAR *internal_path = NULL;
- scope_info.scope.node = start_node;
-
/* Ensure that the namespace has been initialized */
if (!acpi_gbl_root_node) {
@@ -487,19 +684,9 @@
acpi_cm_acquire_mutex (ACPI_MTX_NAMESPACE);
- /* NS_ALL means start from the root */
-
- if (NS_ALL == scope_info.scope.node) {
- scope_info.scope.node = acpi_gbl_root_node;
- }
+ /* Setup lookup scope (search starting point) */
- else {
- scope_info.scope.node = start_node;
- if (!scope_info.scope.node) {
- status = AE_BAD_PARAMETER;
- goto unlock_and_exit;
- }
- }
+ scope_info.scope.node = start_node;
/* Lookup the name in the namespace */
@@ -510,8 +697,6 @@
-unlock_and_exit:
-
acpi_cm_release_mutex (ACPI_MTX_NAMESPACE);
/* Cleanup */
@@ -578,6 +763,10 @@
ACPI_NAMESPACE_NODE *node)
{
+
+ if (!node) {
+ return (NULL);
+ }
/*
* Walk to the end of this peer list.
FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen (who was at: slshen@lbl.gov)