xref: /OK3568_Linux_fs/kernel/drivers/acpi/acpica/nsconvert.c (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun // SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0
2*4882a593Smuzhiyun /******************************************************************************
3*4882a593Smuzhiyun  *
4*4882a593Smuzhiyun  * Module Name: nsconvert - Object conversions for objects returned by
5*4882a593Smuzhiyun  *                          predefined methods
6*4882a593Smuzhiyun  *
7*4882a593Smuzhiyun  * Copyright (C) 2000 - 2020, Intel Corp.
8*4882a593Smuzhiyun  *
9*4882a593Smuzhiyun  *****************************************************************************/
10*4882a593Smuzhiyun 
11*4882a593Smuzhiyun #include <acpi/acpi.h>
12*4882a593Smuzhiyun #include "accommon.h"
13*4882a593Smuzhiyun #include "acnamesp.h"
14*4882a593Smuzhiyun #include "acinterp.h"
15*4882a593Smuzhiyun #include "acpredef.h"
16*4882a593Smuzhiyun #include "amlresrc.h"
17*4882a593Smuzhiyun 
18*4882a593Smuzhiyun #define _COMPONENT          ACPI_NAMESPACE
19*4882a593Smuzhiyun ACPI_MODULE_NAME("nsconvert")
20*4882a593Smuzhiyun 
21*4882a593Smuzhiyun /*******************************************************************************
22*4882a593Smuzhiyun  *
23*4882a593Smuzhiyun  * FUNCTION:    acpi_ns_convert_to_integer
24*4882a593Smuzhiyun  *
25*4882a593Smuzhiyun  * PARAMETERS:  original_object     - Object to be converted
26*4882a593Smuzhiyun  *              return_object       - Where the new converted object is returned
27*4882a593Smuzhiyun  *
28*4882a593Smuzhiyun  * RETURN:      Status. AE_OK if conversion was successful.
29*4882a593Smuzhiyun  *
30*4882a593Smuzhiyun  * DESCRIPTION: Attempt to convert a String/Buffer object to an Integer.
31*4882a593Smuzhiyun  *
32*4882a593Smuzhiyun  ******************************************************************************/
33*4882a593Smuzhiyun acpi_status
acpi_ns_convert_to_integer(union acpi_operand_object * original_object,union acpi_operand_object ** return_object)34*4882a593Smuzhiyun acpi_ns_convert_to_integer(union acpi_operand_object *original_object,
35*4882a593Smuzhiyun 			   union acpi_operand_object **return_object)
36*4882a593Smuzhiyun {
37*4882a593Smuzhiyun 	union acpi_operand_object *new_object;
38*4882a593Smuzhiyun 	acpi_status status;
39*4882a593Smuzhiyun 	u64 value = 0;
40*4882a593Smuzhiyun 	u32 i;
41*4882a593Smuzhiyun 
42*4882a593Smuzhiyun 	switch (original_object->common.type) {
43*4882a593Smuzhiyun 	case ACPI_TYPE_STRING:
44*4882a593Smuzhiyun 
45*4882a593Smuzhiyun 		/* String-to-Integer conversion */
46*4882a593Smuzhiyun 
47*4882a593Smuzhiyun 		status =
48*4882a593Smuzhiyun 		    acpi_ut_strtoul64(original_object->string.pointer, &value);
49*4882a593Smuzhiyun 		if (ACPI_FAILURE(status)) {
50*4882a593Smuzhiyun 			return (status);
51*4882a593Smuzhiyun 		}
52*4882a593Smuzhiyun 		break;
53*4882a593Smuzhiyun 
54*4882a593Smuzhiyun 	case ACPI_TYPE_BUFFER:
55*4882a593Smuzhiyun 
56*4882a593Smuzhiyun 		/* Buffer-to-Integer conversion. Max buffer size is 64 bits. */
57*4882a593Smuzhiyun 
58*4882a593Smuzhiyun 		if (original_object->buffer.length > 8) {
59*4882a593Smuzhiyun 			return (AE_AML_OPERAND_TYPE);
60*4882a593Smuzhiyun 		}
61*4882a593Smuzhiyun 
62*4882a593Smuzhiyun 		/* Extract each buffer byte to create the integer */
63*4882a593Smuzhiyun 
64*4882a593Smuzhiyun 		for (i = 0; i < original_object->buffer.length; i++) {
65*4882a593Smuzhiyun 			value |= ((u64)
66*4882a593Smuzhiyun 				  original_object->buffer.pointer[i] << (i *
67*4882a593Smuzhiyun 									 8));
68*4882a593Smuzhiyun 		}
69*4882a593Smuzhiyun 		break;
70*4882a593Smuzhiyun 
71*4882a593Smuzhiyun 	default:
72*4882a593Smuzhiyun 
73*4882a593Smuzhiyun 		return (AE_AML_OPERAND_TYPE);
74*4882a593Smuzhiyun 	}
75*4882a593Smuzhiyun 
76*4882a593Smuzhiyun 	new_object = acpi_ut_create_integer_object(value);
77*4882a593Smuzhiyun 	if (!new_object) {
78*4882a593Smuzhiyun 		return (AE_NO_MEMORY);
79*4882a593Smuzhiyun 	}
80*4882a593Smuzhiyun 
81*4882a593Smuzhiyun 	*return_object = new_object;
82*4882a593Smuzhiyun 	return (AE_OK);
83*4882a593Smuzhiyun }
84*4882a593Smuzhiyun 
85*4882a593Smuzhiyun /*******************************************************************************
86*4882a593Smuzhiyun  *
87*4882a593Smuzhiyun  * FUNCTION:    acpi_ns_convert_to_string
88*4882a593Smuzhiyun  *
89*4882a593Smuzhiyun  * PARAMETERS:  original_object     - Object to be converted
90*4882a593Smuzhiyun  *              return_object       - Where the new converted object is returned
91*4882a593Smuzhiyun  *
92*4882a593Smuzhiyun  * RETURN:      Status. AE_OK if conversion was successful.
93*4882a593Smuzhiyun  *
94*4882a593Smuzhiyun  * DESCRIPTION: Attempt to convert a Integer/Buffer object to a String.
95*4882a593Smuzhiyun  *
96*4882a593Smuzhiyun  ******************************************************************************/
97*4882a593Smuzhiyun 
98*4882a593Smuzhiyun acpi_status
acpi_ns_convert_to_string(union acpi_operand_object * original_object,union acpi_operand_object ** return_object)99*4882a593Smuzhiyun acpi_ns_convert_to_string(union acpi_operand_object *original_object,
100*4882a593Smuzhiyun 			  union acpi_operand_object **return_object)
101*4882a593Smuzhiyun {
102*4882a593Smuzhiyun 	union acpi_operand_object *new_object;
103*4882a593Smuzhiyun 	acpi_size length;
104*4882a593Smuzhiyun 	acpi_status status;
105*4882a593Smuzhiyun 
106*4882a593Smuzhiyun 	switch (original_object->common.type) {
107*4882a593Smuzhiyun 	case ACPI_TYPE_INTEGER:
108*4882a593Smuzhiyun 		/*
109*4882a593Smuzhiyun 		 * Integer-to-String conversion. Commonly, convert
110*4882a593Smuzhiyun 		 * an integer of value 0 to a NULL string. The last element of
111*4882a593Smuzhiyun 		 * _BIF and _BIX packages occasionally need this fix.
112*4882a593Smuzhiyun 		 */
113*4882a593Smuzhiyun 		if (original_object->integer.value == 0) {
114*4882a593Smuzhiyun 
115*4882a593Smuzhiyun 			/* Allocate a new NULL string object */
116*4882a593Smuzhiyun 
117*4882a593Smuzhiyun 			new_object = acpi_ut_create_string_object(0);
118*4882a593Smuzhiyun 			if (!new_object) {
119*4882a593Smuzhiyun 				return (AE_NO_MEMORY);
120*4882a593Smuzhiyun 			}
121*4882a593Smuzhiyun 		} else {
122*4882a593Smuzhiyun 			status = acpi_ex_convert_to_string(original_object,
123*4882a593Smuzhiyun 							   &new_object,
124*4882a593Smuzhiyun 							   ACPI_IMPLICIT_CONVERT_HEX);
125*4882a593Smuzhiyun 			if (ACPI_FAILURE(status)) {
126*4882a593Smuzhiyun 				return (status);
127*4882a593Smuzhiyun 			}
128*4882a593Smuzhiyun 		}
129*4882a593Smuzhiyun 		break;
130*4882a593Smuzhiyun 
131*4882a593Smuzhiyun 	case ACPI_TYPE_BUFFER:
132*4882a593Smuzhiyun 		/*
133*4882a593Smuzhiyun 		 * Buffer-to-String conversion. Use a to_string
134*4882a593Smuzhiyun 		 * conversion, no transform performed on the buffer data. The best
135*4882a593Smuzhiyun 		 * example of this is the _BIF method, where the string data from
136*4882a593Smuzhiyun 		 * the battery is often (incorrectly) returned as buffer object(s).
137*4882a593Smuzhiyun 		 */
138*4882a593Smuzhiyun 		length = 0;
139*4882a593Smuzhiyun 		while ((length < original_object->buffer.length) &&
140*4882a593Smuzhiyun 		       (original_object->buffer.pointer[length])) {
141*4882a593Smuzhiyun 			length++;
142*4882a593Smuzhiyun 		}
143*4882a593Smuzhiyun 
144*4882a593Smuzhiyun 		/* Allocate a new string object */
145*4882a593Smuzhiyun 
146*4882a593Smuzhiyun 		new_object = acpi_ut_create_string_object(length);
147*4882a593Smuzhiyun 		if (!new_object) {
148*4882a593Smuzhiyun 			return (AE_NO_MEMORY);
149*4882a593Smuzhiyun 		}
150*4882a593Smuzhiyun 
151*4882a593Smuzhiyun 		/*
152*4882a593Smuzhiyun 		 * Copy the raw buffer data with no transform. String is already NULL
153*4882a593Smuzhiyun 		 * terminated at Length+1.
154*4882a593Smuzhiyun 		 */
155*4882a593Smuzhiyun 		memcpy(new_object->string.pointer,
156*4882a593Smuzhiyun 		       original_object->buffer.pointer, length);
157*4882a593Smuzhiyun 		break;
158*4882a593Smuzhiyun 
159*4882a593Smuzhiyun 	default:
160*4882a593Smuzhiyun 
161*4882a593Smuzhiyun 		return (AE_AML_OPERAND_TYPE);
162*4882a593Smuzhiyun 	}
163*4882a593Smuzhiyun 
164*4882a593Smuzhiyun 	*return_object = new_object;
165*4882a593Smuzhiyun 	return (AE_OK);
166*4882a593Smuzhiyun }
167*4882a593Smuzhiyun 
168*4882a593Smuzhiyun /*******************************************************************************
169*4882a593Smuzhiyun  *
170*4882a593Smuzhiyun  * FUNCTION:    acpi_ns_convert_to_buffer
171*4882a593Smuzhiyun  *
172*4882a593Smuzhiyun  * PARAMETERS:  original_object     - Object to be converted
173*4882a593Smuzhiyun  *              return_object       - Where the new converted object is returned
174*4882a593Smuzhiyun  *
175*4882a593Smuzhiyun  * RETURN:      Status. AE_OK if conversion was successful.
176*4882a593Smuzhiyun  *
177*4882a593Smuzhiyun  * DESCRIPTION: Attempt to convert a Integer/String/Package object to a Buffer.
178*4882a593Smuzhiyun  *
179*4882a593Smuzhiyun  ******************************************************************************/
180*4882a593Smuzhiyun 
181*4882a593Smuzhiyun acpi_status
acpi_ns_convert_to_buffer(union acpi_operand_object * original_object,union acpi_operand_object ** return_object)182*4882a593Smuzhiyun acpi_ns_convert_to_buffer(union acpi_operand_object *original_object,
183*4882a593Smuzhiyun 			  union acpi_operand_object **return_object)
184*4882a593Smuzhiyun {
185*4882a593Smuzhiyun 	union acpi_operand_object *new_object;
186*4882a593Smuzhiyun 	acpi_status status;
187*4882a593Smuzhiyun 	union acpi_operand_object **elements;
188*4882a593Smuzhiyun 	u32 *dword_buffer;
189*4882a593Smuzhiyun 	u32 count;
190*4882a593Smuzhiyun 	u32 i;
191*4882a593Smuzhiyun 
192*4882a593Smuzhiyun 	switch (original_object->common.type) {
193*4882a593Smuzhiyun 	case ACPI_TYPE_INTEGER:
194*4882a593Smuzhiyun 		/*
195*4882a593Smuzhiyun 		 * Integer-to-Buffer conversion.
196*4882a593Smuzhiyun 		 * Convert the Integer to a packed-byte buffer. _MAT and other
197*4882a593Smuzhiyun 		 * objects need this sometimes, if a read has been performed on a
198*4882a593Smuzhiyun 		 * Field object that is less than or equal to the global integer
199*4882a593Smuzhiyun 		 * size (32 or 64 bits).
200*4882a593Smuzhiyun 		 */
201*4882a593Smuzhiyun 		status =
202*4882a593Smuzhiyun 		    acpi_ex_convert_to_buffer(original_object, &new_object);
203*4882a593Smuzhiyun 		if (ACPI_FAILURE(status)) {
204*4882a593Smuzhiyun 			return (status);
205*4882a593Smuzhiyun 		}
206*4882a593Smuzhiyun 		break;
207*4882a593Smuzhiyun 
208*4882a593Smuzhiyun 	case ACPI_TYPE_STRING:
209*4882a593Smuzhiyun 
210*4882a593Smuzhiyun 		/* String-to-Buffer conversion. Simple data copy */
211*4882a593Smuzhiyun 
212*4882a593Smuzhiyun 		new_object = acpi_ut_create_buffer_object
213*4882a593Smuzhiyun 		    (original_object->string.length);
214*4882a593Smuzhiyun 		if (!new_object) {
215*4882a593Smuzhiyun 			return (AE_NO_MEMORY);
216*4882a593Smuzhiyun 		}
217*4882a593Smuzhiyun 
218*4882a593Smuzhiyun 		memcpy(new_object->buffer.pointer,
219*4882a593Smuzhiyun 		       original_object->string.pointer,
220*4882a593Smuzhiyun 		       original_object->string.length);
221*4882a593Smuzhiyun 		break;
222*4882a593Smuzhiyun 
223*4882a593Smuzhiyun 	case ACPI_TYPE_PACKAGE:
224*4882a593Smuzhiyun 		/*
225*4882a593Smuzhiyun 		 * This case is often seen for predefined names that must return a
226*4882a593Smuzhiyun 		 * Buffer object with multiple DWORD integers within. For example,
227*4882a593Smuzhiyun 		 * _FDE and _GTM. The Package can be converted to a Buffer.
228*4882a593Smuzhiyun 		 */
229*4882a593Smuzhiyun 
230*4882a593Smuzhiyun 		/* All elements of the Package must be integers */
231*4882a593Smuzhiyun 
232*4882a593Smuzhiyun 		elements = original_object->package.elements;
233*4882a593Smuzhiyun 		count = original_object->package.count;
234*4882a593Smuzhiyun 
235*4882a593Smuzhiyun 		for (i = 0; i < count; i++) {
236*4882a593Smuzhiyun 			if ((!*elements) ||
237*4882a593Smuzhiyun 			    ((*elements)->common.type != ACPI_TYPE_INTEGER)) {
238*4882a593Smuzhiyun 				return (AE_AML_OPERAND_TYPE);
239*4882a593Smuzhiyun 			}
240*4882a593Smuzhiyun 			elements++;
241*4882a593Smuzhiyun 		}
242*4882a593Smuzhiyun 
243*4882a593Smuzhiyun 		/* Create the new buffer object to replace the Package */
244*4882a593Smuzhiyun 
245*4882a593Smuzhiyun 		new_object = acpi_ut_create_buffer_object(ACPI_MUL_4(count));
246*4882a593Smuzhiyun 		if (!new_object) {
247*4882a593Smuzhiyun 			return (AE_NO_MEMORY);
248*4882a593Smuzhiyun 		}
249*4882a593Smuzhiyun 
250*4882a593Smuzhiyun 		/* Copy the package elements (integers) to the buffer as DWORDs */
251*4882a593Smuzhiyun 
252*4882a593Smuzhiyun 		elements = original_object->package.elements;
253*4882a593Smuzhiyun 		dword_buffer = ACPI_CAST_PTR(u32, new_object->buffer.pointer);
254*4882a593Smuzhiyun 
255*4882a593Smuzhiyun 		for (i = 0; i < count; i++) {
256*4882a593Smuzhiyun 			*dword_buffer = (u32)(*elements)->integer.value;
257*4882a593Smuzhiyun 			dword_buffer++;
258*4882a593Smuzhiyun 			elements++;
259*4882a593Smuzhiyun 		}
260*4882a593Smuzhiyun 		break;
261*4882a593Smuzhiyun 
262*4882a593Smuzhiyun 	default:
263*4882a593Smuzhiyun 
264*4882a593Smuzhiyun 		return (AE_AML_OPERAND_TYPE);
265*4882a593Smuzhiyun 	}
266*4882a593Smuzhiyun 
267*4882a593Smuzhiyun 	*return_object = new_object;
268*4882a593Smuzhiyun 	return (AE_OK);
269*4882a593Smuzhiyun }
270*4882a593Smuzhiyun 
271*4882a593Smuzhiyun /*******************************************************************************
272*4882a593Smuzhiyun  *
273*4882a593Smuzhiyun  * FUNCTION:    acpi_ns_convert_to_unicode
274*4882a593Smuzhiyun  *
275*4882a593Smuzhiyun  * PARAMETERS:  scope               - Namespace node for the method/object
276*4882a593Smuzhiyun  *              original_object     - ASCII String Object to be converted
277*4882a593Smuzhiyun  *              return_object       - Where the new converted object is returned
278*4882a593Smuzhiyun  *
279*4882a593Smuzhiyun  * RETURN:      Status. AE_OK if conversion was successful.
280*4882a593Smuzhiyun  *
281*4882a593Smuzhiyun  * DESCRIPTION: Attempt to convert a String object to a Unicode string Buffer.
282*4882a593Smuzhiyun  *
283*4882a593Smuzhiyun  ******************************************************************************/
284*4882a593Smuzhiyun 
285*4882a593Smuzhiyun acpi_status
acpi_ns_convert_to_unicode(struct acpi_namespace_node * scope,union acpi_operand_object * original_object,union acpi_operand_object ** return_object)286*4882a593Smuzhiyun acpi_ns_convert_to_unicode(struct acpi_namespace_node *scope,
287*4882a593Smuzhiyun 			   union acpi_operand_object *original_object,
288*4882a593Smuzhiyun 			   union acpi_operand_object **return_object)
289*4882a593Smuzhiyun {
290*4882a593Smuzhiyun 	union acpi_operand_object *new_object;
291*4882a593Smuzhiyun 	char *ascii_string;
292*4882a593Smuzhiyun 	u16 *unicode_buffer;
293*4882a593Smuzhiyun 	u32 unicode_length;
294*4882a593Smuzhiyun 	u32 i;
295*4882a593Smuzhiyun 
296*4882a593Smuzhiyun 	if (!original_object) {
297*4882a593Smuzhiyun 		return (AE_OK);
298*4882a593Smuzhiyun 	}
299*4882a593Smuzhiyun 
300*4882a593Smuzhiyun 	/* If a Buffer was returned, it must be at least two bytes long */
301*4882a593Smuzhiyun 
302*4882a593Smuzhiyun 	if (original_object->common.type == ACPI_TYPE_BUFFER) {
303*4882a593Smuzhiyun 		if (original_object->buffer.length < 2) {
304*4882a593Smuzhiyun 			return (AE_AML_OPERAND_VALUE);
305*4882a593Smuzhiyun 		}
306*4882a593Smuzhiyun 
307*4882a593Smuzhiyun 		*return_object = NULL;
308*4882a593Smuzhiyun 		return (AE_OK);
309*4882a593Smuzhiyun 	}
310*4882a593Smuzhiyun 
311*4882a593Smuzhiyun 	/*
312*4882a593Smuzhiyun 	 * The original object is an ASCII string. Convert this string to
313*4882a593Smuzhiyun 	 * a unicode buffer.
314*4882a593Smuzhiyun 	 */
315*4882a593Smuzhiyun 	ascii_string = original_object->string.pointer;
316*4882a593Smuzhiyun 	unicode_length = (original_object->string.length * 2) + 2;
317*4882a593Smuzhiyun 
318*4882a593Smuzhiyun 	/* Create a new buffer object for the Unicode data */
319*4882a593Smuzhiyun 
320*4882a593Smuzhiyun 	new_object = acpi_ut_create_buffer_object(unicode_length);
321*4882a593Smuzhiyun 	if (!new_object) {
322*4882a593Smuzhiyun 		return (AE_NO_MEMORY);
323*4882a593Smuzhiyun 	}
324*4882a593Smuzhiyun 
325*4882a593Smuzhiyun 	unicode_buffer = ACPI_CAST_PTR(u16, new_object->buffer.pointer);
326*4882a593Smuzhiyun 
327*4882a593Smuzhiyun 	/* Convert ASCII to Unicode */
328*4882a593Smuzhiyun 
329*4882a593Smuzhiyun 	for (i = 0; i < original_object->string.length; i++) {
330*4882a593Smuzhiyun 		unicode_buffer[i] = (u16)ascii_string[i];
331*4882a593Smuzhiyun 	}
332*4882a593Smuzhiyun 
333*4882a593Smuzhiyun 	*return_object = new_object;
334*4882a593Smuzhiyun 	return (AE_OK);
335*4882a593Smuzhiyun }
336*4882a593Smuzhiyun 
337*4882a593Smuzhiyun /*******************************************************************************
338*4882a593Smuzhiyun  *
339*4882a593Smuzhiyun  * FUNCTION:    acpi_ns_convert_to_resource
340*4882a593Smuzhiyun  *
341*4882a593Smuzhiyun  * PARAMETERS:  scope               - Namespace node for the method/object
342*4882a593Smuzhiyun  *              original_object     - Object to be converted
343*4882a593Smuzhiyun  *              return_object       - Where the new converted object is returned
344*4882a593Smuzhiyun  *
345*4882a593Smuzhiyun  * RETURN:      Status. AE_OK if conversion was successful
346*4882a593Smuzhiyun  *
347*4882a593Smuzhiyun  * DESCRIPTION: Attempt to convert a Integer object to a resource_template
348*4882a593Smuzhiyun  *              Buffer.
349*4882a593Smuzhiyun  *
350*4882a593Smuzhiyun  ******************************************************************************/
351*4882a593Smuzhiyun 
352*4882a593Smuzhiyun acpi_status
acpi_ns_convert_to_resource(struct acpi_namespace_node * scope,union acpi_operand_object * original_object,union acpi_operand_object ** return_object)353*4882a593Smuzhiyun acpi_ns_convert_to_resource(struct acpi_namespace_node *scope,
354*4882a593Smuzhiyun 			    union acpi_operand_object *original_object,
355*4882a593Smuzhiyun 			    union acpi_operand_object **return_object)
356*4882a593Smuzhiyun {
357*4882a593Smuzhiyun 	union acpi_operand_object *new_object;
358*4882a593Smuzhiyun 	u8 *buffer;
359*4882a593Smuzhiyun 
360*4882a593Smuzhiyun 	/*
361*4882a593Smuzhiyun 	 * We can fix the following cases for an expected resource template:
362*4882a593Smuzhiyun 	 * 1. No return value (interpreter slack mode is disabled)
363*4882a593Smuzhiyun 	 * 2. A "Return (Zero)" statement
364*4882a593Smuzhiyun 	 * 3. A "Return empty buffer" statement
365*4882a593Smuzhiyun 	 *
366*4882a593Smuzhiyun 	 * We will return a buffer containing a single end_tag
367*4882a593Smuzhiyun 	 * resource descriptor.
368*4882a593Smuzhiyun 	 */
369*4882a593Smuzhiyun 	if (original_object) {
370*4882a593Smuzhiyun 		switch (original_object->common.type) {
371*4882a593Smuzhiyun 		case ACPI_TYPE_INTEGER:
372*4882a593Smuzhiyun 
373*4882a593Smuzhiyun 			/* We can only repair an Integer==0 */
374*4882a593Smuzhiyun 
375*4882a593Smuzhiyun 			if (original_object->integer.value) {
376*4882a593Smuzhiyun 				return (AE_AML_OPERAND_TYPE);
377*4882a593Smuzhiyun 			}
378*4882a593Smuzhiyun 			break;
379*4882a593Smuzhiyun 
380*4882a593Smuzhiyun 		case ACPI_TYPE_BUFFER:
381*4882a593Smuzhiyun 
382*4882a593Smuzhiyun 			if (original_object->buffer.length) {
383*4882a593Smuzhiyun 
384*4882a593Smuzhiyun 				/* Additional checks can be added in the future */
385*4882a593Smuzhiyun 
386*4882a593Smuzhiyun 				*return_object = NULL;
387*4882a593Smuzhiyun 				return (AE_OK);
388*4882a593Smuzhiyun 			}
389*4882a593Smuzhiyun 			break;
390*4882a593Smuzhiyun 
391*4882a593Smuzhiyun 		case ACPI_TYPE_STRING:
392*4882a593Smuzhiyun 		default:
393*4882a593Smuzhiyun 
394*4882a593Smuzhiyun 			return (AE_AML_OPERAND_TYPE);
395*4882a593Smuzhiyun 		}
396*4882a593Smuzhiyun 	}
397*4882a593Smuzhiyun 
398*4882a593Smuzhiyun 	/* Create the new buffer object for the resource descriptor */
399*4882a593Smuzhiyun 
400*4882a593Smuzhiyun 	new_object = acpi_ut_create_buffer_object(2);
401*4882a593Smuzhiyun 	if (!new_object) {
402*4882a593Smuzhiyun 		return (AE_NO_MEMORY);
403*4882a593Smuzhiyun 	}
404*4882a593Smuzhiyun 
405*4882a593Smuzhiyun 	buffer = ACPI_CAST_PTR(u8, new_object->buffer.pointer);
406*4882a593Smuzhiyun 
407*4882a593Smuzhiyun 	/* Initialize the Buffer with a single end_tag descriptor */
408*4882a593Smuzhiyun 
409*4882a593Smuzhiyun 	buffer[0] = (ACPI_RESOURCE_NAME_END_TAG | ASL_RDESC_END_TAG_SIZE);
410*4882a593Smuzhiyun 	buffer[1] = 0x00;
411*4882a593Smuzhiyun 
412*4882a593Smuzhiyun 	*return_object = new_object;
413*4882a593Smuzhiyun 	return (AE_OK);
414*4882a593Smuzhiyun }
415*4882a593Smuzhiyun 
416*4882a593Smuzhiyun /*******************************************************************************
417*4882a593Smuzhiyun  *
418*4882a593Smuzhiyun  * FUNCTION:    acpi_ns_convert_to_reference
419*4882a593Smuzhiyun  *
420*4882a593Smuzhiyun  * PARAMETERS:  scope               - Namespace node for the method/object
421*4882a593Smuzhiyun  *              original_object     - Object to be converted
422*4882a593Smuzhiyun  *              return_object       - Where the new converted object is returned
423*4882a593Smuzhiyun  *
424*4882a593Smuzhiyun  * RETURN:      Status. AE_OK if conversion was successful
425*4882a593Smuzhiyun  *
426*4882a593Smuzhiyun  * DESCRIPTION: Attempt to convert a Integer object to a object_reference.
427*4882a593Smuzhiyun  *              Buffer.
428*4882a593Smuzhiyun  *
429*4882a593Smuzhiyun  ******************************************************************************/
430*4882a593Smuzhiyun 
431*4882a593Smuzhiyun acpi_status
acpi_ns_convert_to_reference(struct acpi_namespace_node * scope,union acpi_operand_object * original_object,union acpi_operand_object ** return_object)432*4882a593Smuzhiyun acpi_ns_convert_to_reference(struct acpi_namespace_node *scope,
433*4882a593Smuzhiyun 			     union acpi_operand_object *original_object,
434*4882a593Smuzhiyun 			     union acpi_operand_object **return_object)
435*4882a593Smuzhiyun {
436*4882a593Smuzhiyun 	union acpi_operand_object *new_object = NULL;
437*4882a593Smuzhiyun 	acpi_status status;
438*4882a593Smuzhiyun 	struct acpi_namespace_node *node;
439*4882a593Smuzhiyun 	union acpi_generic_state scope_info;
440*4882a593Smuzhiyun 	char *name;
441*4882a593Smuzhiyun 
442*4882a593Smuzhiyun 	ACPI_FUNCTION_NAME(ns_convert_to_reference);
443*4882a593Smuzhiyun 
444*4882a593Smuzhiyun 	/* Convert path into internal presentation */
445*4882a593Smuzhiyun 
446*4882a593Smuzhiyun 	status =
447*4882a593Smuzhiyun 	    acpi_ns_internalize_name(original_object->string.pointer, &name);
448*4882a593Smuzhiyun 	if (ACPI_FAILURE(status)) {
449*4882a593Smuzhiyun 		return_ACPI_STATUS(status);
450*4882a593Smuzhiyun 	}
451*4882a593Smuzhiyun 
452*4882a593Smuzhiyun 	/* Find the namespace node */
453*4882a593Smuzhiyun 
454*4882a593Smuzhiyun 	scope_info.scope.node =
455*4882a593Smuzhiyun 	    ACPI_CAST_PTR(struct acpi_namespace_node, scope);
456*4882a593Smuzhiyun 	status =
457*4882a593Smuzhiyun 	    acpi_ns_lookup(&scope_info, name, ACPI_TYPE_ANY, ACPI_IMODE_EXECUTE,
458*4882a593Smuzhiyun 			   ACPI_NS_SEARCH_PARENT | ACPI_NS_DONT_OPEN_SCOPE,
459*4882a593Smuzhiyun 			   NULL, &node);
460*4882a593Smuzhiyun 	if (ACPI_FAILURE(status)) {
461*4882a593Smuzhiyun 
462*4882a593Smuzhiyun 		/* Check if we are resolving a named reference within a package */
463*4882a593Smuzhiyun 
464*4882a593Smuzhiyun 		ACPI_ERROR_NAMESPACE(&scope_info,
465*4882a593Smuzhiyun 				     original_object->string.pointer, status);
466*4882a593Smuzhiyun 		goto error_exit;
467*4882a593Smuzhiyun 	}
468*4882a593Smuzhiyun 
469*4882a593Smuzhiyun 	/* Create and init a new internal ACPI object */
470*4882a593Smuzhiyun 
471*4882a593Smuzhiyun 	new_object = acpi_ut_create_internal_object(ACPI_TYPE_LOCAL_REFERENCE);
472*4882a593Smuzhiyun 	if (!new_object) {
473*4882a593Smuzhiyun 		status = AE_NO_MEMORY;
474*4882a593Smuzhiyun 		goto error_exit;
475*4882a593Smuzhiyun 	}
476*4882a593Smuzhiyun 	new_object->reference.node = node;
477*4882a593Smuzhiyun 	new_object->reference.object = node->object;
478*4882a593Smuzhiyun 	new_object->reference.class = ACPI_REFCLASS_NAME;
479*4882a593Smuzhiyun 
480*4882a593Smuzhiyun 	/*
481*4882a593Smuzhiyun 	 * Increase reference of the object if needed (the object is likely a
482*4882a593Smuzhiyun 	 * null for device nodes).
483*4882a593Smuzhiyun 	 */
484*4882a593Smuzhiyun 	acpi_ut_add_reference(node->object);
485*4882a593Smuzhiyun 
486*4882a593Smuzhiyun error_exit:
487*4882a593Smuzhiyun 	ACPI_FREE(name);
488*4882a593Smuzhiyun 	*return_object = new_object;
489*4882a593Smuzhiyun 	return (status);
490*4882a593Smuzhiyun }
491