xref: /illumos-gate/usr/src/common/acpica/executer/exstore.c (revision 2dc5cbd37af38054ac6aab88a3ecee22a13ed2eb)
1 /******************************************************************************
2  *
3  * Module Name: exstore - AML Interpreter object store support
4  *
5  *****************************************************************************/
6 
7 /******************************************************************************
8  *
9  * 1. Copyright Notice
10  *
11  * Some or all of this work - Copyright (c) 1999 - 2018, Intel Corp.
12  * All rights reserved.
13  *
14  * 2. License
15  *
16  * 2.1. This is your license from Intel Corp. under its intellectual property
17  * rights. You may have additional license terms from the party that provided
18  * you this software, covering your right to use that party's intellectual
19  * property rights.
20  *
21  * 2.2. Intel grants, free of charge, to any person ("Licensee") obtaining a
22  * copy of the source code appearing in this file ("Covered Code") an
23  * irrevocable, perpetual, worldwide license under Intel's copyrights in the
24  * base code distributed originally by Intel ("Original Intel Code") to copy,
25  * make derivatives, distribute, use and display any portion of the Covered
26  * Code in any form, with the right to sublicense such rights; and
27  *
28  * 2.3. Intel grants Licensee a non-exclusive and non-transferable patent
29  * license (with the right to sublicense), under only those claims of Intel
30  * patents that are infringed by the Original Intel Code, to make, use, sell,
31  * offer to sell, and import the Covered Code and derivative works thereof
32  * solely to the minimum extent necessary to exercise the above copyright
33  * license, and in no event shall the patent license extend to any additions
34  * to or modifications of the Original Intel Code. No other license or right
35  * is granted directly or by implication, estoppel or otherwise;
36  *
37  * The above copyright and patent license is granted only if the following
38  * conditions are met:
39  *
40  * 3. Conditions
41  *
42  * 3.1. Redistribution of Source with Rights to Further Distribute Source.
43  * Redistribution of source code of any substantial portion of the Covered
44  * Code or modification with rights to further distribute source must include
45  * the above Copyright Notice, the above License, this list of Conditions,
46  * and the following Disclaimer and Export Compliance provision. In addition,
47  * Licensee must cause all Covered Code to which Licensee contributes to
48  * contain a file documenting the changes Licensee made to create that Covered
49  * Code and the date of any change. Licensee must include in that file the
50  * documentation of any changes made by any predecessor Licensee. Licensee
51  * must include a prominent statement that the modification is derived,
52  * directly or indirectly, from Original Intel Code.
53  *
54  * 3.2. Redistribution of Source with no Rights to Further Distribute Source.
55  * Redistribution of source code of any substantial portion of the Covered
56  * Code or modification without rights to further distribute source must
57  * include the following Disclaimer and Export Compliance provision in the
58  * documentation and/or other materials provided with distribution. In
59  * addition, Licensee may not authorize further sublicense of source of any
60  * portion of the Covered Code, and must include terms to the effect that the
61  * license from Licensee to its licensee is limited to the intellectual
62  * property embodied in the software Licensee provides to its licensee, and
63  * not to intellectual property embodied in modifications its licensee may
64  * make.
65  *
66  * 3.3. Redistribution of Executable. Redistribution in executable form of any
67  * substantial portion of the Covered Code or modification must reproduce the
68  * above Copyright Notice, and the following Disclaimer and Export Compliance
69  * provision in the documentation and/or other materials provided with the
70  * distribution.
71  *
72  * 3.4. Intel retains all right, title, and interest in and to the Original
73  * Intel Code.
74  *
75  * 3.5. Neither the name Intel nor any other trademark owned or controlled by
76  * Intel shall be used in advertising or otherwise to promote the sale, use or
77  * other dealings in products derived from or relating to the Covered Code
78  * without prior written authorization from Intel.
79  *
80  * 4. Disclaimer and Export Compliance
81  *
82  * 4.1. INTEL MAKES NO WARRANTY OF ANY KIND REGARDING ANY SOFTWARE PROVIDED
83  * HERE. ANY SOFTWARE ORIGINATING FROM INTEL OR DERIVED FROM INTEL SOFTWARE
84  * IS PROVIDED "AS IS," AND INTEL WILL NOT PROVIDE ANY SUPPORT, ASSISTANCE,
85  * INSTALLATION, TRAINING OR OTHER SERVICES. INTEL WILL NOT PROVIDE ANY
86  * UPDATES, ENHANCEMENTS OR EXTENSIONS. INTEL SPECIFICALLY DISCLAIMS ANY
87  * IMPLIED WARRANTIES OF MERCHANTABILITY, NONINFRINGEMENT AND FITNESS FOR A
88  * PARTICULAR PURPOSE.
89  *
90  * 4.2. IN NO EVENT SHALL INTEL HAVE ANY LIABILITY TO LICENSEE, ITS LICENSEES
91  * OR ANY OTHER THIRD PARTY, FOR ANY LOST PROFITS, LOST DATA, LOSS OF USE OR
92  * COSTS OF PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, OR FOR ANY INDIRECT,
93  * SPECIAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THIS AGREEMENT, UNDER ANY
94  * CAUSE OF ACTION OR THEORY OF LIABILITY, AND IRRESPECTIVE OF WHETHER INTEL
95  * HAS ADVANCE NOTICE OF THE POSSIBILITY OF SUCH DAMAGES. THESE LIMITATIONS
96  * SHALL APPLY NOTWITHSTANDING THE FAILURE OF THE ESSENTIAL PURPOSE OF ANY
97  * LIMITED REMEDY.
98  *
99  * 4.3. Licensee shall not export, either directly or indirectly, any of this
100  * software or system incorporating such software without first obtaining any
101  * required license or other approval from the U. S. Department of Commerce or
102  * any other agency or department of the United States Government. In the
103  * event Licensee exports any such software from the United States or
104  * re-exports any such software from a foreign destination, Licensee shall
105  * ensure that the distribution and export/re-export of the software is in
106  * compliance with all laws, regulations, orders, or other restrictions of the
107  * U.S. Export Administration Regulations. Licensee agrees that neither it nor
108  * any of its subsidiaries will export/re-export any technical data, process,
109  * software, or service, directly or indirectly, to any country for which the
110  * United States government or any agency thereof requires an export license,
111  * other governmental approval, or letter of assurance, without first obtaining
112  * such license, approval or letter.
113  *
114  *****************************************************************************
115  *
116  * Alternatively, you may choose to be licensed under the terms of the
117  * following license:
118  *
119  * Redistribution and use in source and binary forms, with or without
120  * modification, are permitted provided that the following conditions
121  * are met:
122  * 1. Redistributions of source code must retain the above copyright
123  *    notice, this list of conditions, and the following disclaimer,
124  *    without modification.
125  * 2. Redistributions in binary form must reproduce at minimum a disclaimer
126  *    substantially similar to the "NO WARRANTY" disclaimer below
127  *    ("Disclaimer") and any redistribution must be conditioned upon
128  *    including a substantially similar Disclaimer requirement for further
129  *    binary redistribution.
130  * 3. Neither the names of the above-listed copyright holders nor the names
131  *    of any contributors may be used to endorse or promote products derived
132  *    from this software without specific prior written permission.
133  *
134  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
135  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
136  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
137  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
138  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
139  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
140  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
141  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
142  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
143  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
144  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
145  *
146  * Alternatively, you may choose to be licensed under the terms of the
147  * GNU General Public License ("GPL") version 2 as published by the Free
148  * Software Foundation.
149  *
150  *****************************************************************************/
151 
152 #include "acpi.h"
153 #include "accommon.h"
154 #include "acdispat.h"
155 #include "acinterp.h"
156 #include "amlcode.h"
157 #include "acnamesp.h"
158 
159 
160 #define _COMPONENT          ACPI_EXECUTER
161         ACPI_MODULE_NAME    ("exstore")
162 
163 /* Local prototypes */
164 
165 static ACPI_STATUS
166 AcpiExStoreObjectToIndex (
167     ACPI_OPERAND_OBJECT     *ValDesc,
168     ACPI_OPERAND_OBJECT     *DestDesc,
169     ACPI_WALK_STATE         *WalkState);
170 
171 static ACPI_STATUS
172 AcpiExStoreDirectToNode (
173     ACPI_OPERAND_OBJECT     *SourceDesc,
174     ACPI_NAMESPACE_NODE     *Node,
175     ACPI_WALK_STATE         *WalkState);
176 
177 
178 /*******************************************************************************
179  *
180  * FUNCTION:    AcpiExStore
181  *
182  * PARAMETERS:  *SourceDesc         - Value to be stored
183  *              *DestDesc           - Where to store it. Must be an NS node
184  *                                    or ACPI_OPERAND_OBJECT of type
185  *                                    Reference;
186  *              WalkState           - Current walk state
187  *
188  * RETURN:      Status
189  *
190  * DESCRIPTION: Store the value described by SourceDesc into the location
191  *              described by DestDesc. Called by various interpreter
192  *              functions to store the result of an operation into
193  *              the destination operand -- not just simply the actual "Store"
194  *              ASL operator.
195  *
196  ******************************************************************************/
197 
198 ACPI_STATUS
199 AcpiExStore (
200     ACPI_OPERAND_OBJECT     *SourceDesc,
201     ACPI_OPERAND_OBJECT     *DestDesc,
202     ACPI_WALK_STATE         *WalkState)
203 {
204     ACPI_STATUS             Status = AE_OK;
205     ACPI_OPERAND_OBJECT     *RefDesc = DestDesc;
206 
207 
208     ACPI_FUNCTION_TRACE_PTR (ExStore, DestDesc);
209 
210 
211     /* Validate parameters */
212 
213     if (!SourceDesc || !DestDesc)
214     {
215         ACPI_ERROR ((AE_INFO, "Null parameter"));
216         return_ACPI_STATUS (AE_AML_NO_OPERAND);
217     }
218 
219     /* DestDesc can be either a namespace node or an ACPI object */
220 
221     if (ACPI_GET_DESCRIPTOR_TYPE (DestDesc) == ACPI_DESC_TYPE_NAMED)
222     {
223         /*
224          * Dest is a namespace node,
225          * Storing an object into a Named node.
226          */
227         Status = AcpiExStoreObjectToNode (SourceDesc,
228             (ACPI_NAMESPACE_NODE *) DestDesc, WalkState,
229             ACPI_IMPLICIT_CONVERSION);
230 
231         return_ACPI_STATUS (Status);
232     }
233 
234     /* Destination object must be a Reference or a Constant object */
235 
236     switch (DestDesc->Common.Type)
237     {
238     case ACPI_TYPE_LOCAL_REFERENCE:
239 
240         break;
241 
242     case ACPI_TYPE_INTEGER:
243 
244         /* Allow stores to Constants -- a Noop as per ACPI spec */
245 
246         if (DestDesc->Common.Flags & AOPOBJ_AML_CONSTANT)
247         {
248             return_ACPI_STATUS (AE_OK);
249         }
250 
251         /*lint -fallthrough */
252 
253     default:
254 
255         /* Destination is not a Reference object */
256 
257         ACPI_ERROR ((AE_INFO,
258             "Target is not a Reference or Constant object - [%s] %p",
259             AcpiUtGetObjectTypeName (DestDesc), DestDesc));
260 
261         return_ACPI_STATUS (AE_AML_OPERAND_TYPE);
262     }
263 
264     /*
265      * Examine the Reference class. These cases are handled:
266      *
267      * 1) Store to Name (Change the object associated with a name)
268      * 2) Store to an indexed area of a Buffer or Package
269      * 3) Store to a Method Local or Arg
270      * 4) Store to the debug object
271      */
272     switch (RefDesc->Reference.Class)
273     {
274     case ACPI_REFCLASS_REFOF:
275 
276         /* Storing an object into a Name "container" */
277 
278         Status = AcpiExStoreObjectToNode (SourceDesc,
279             RefDesc->Reference.Object,
280             WalkState, ACPI_IMPLICIT_CONVERSION);
281         break;
282 
283     case ACPI_REFCLASS_INDEX:
284 
285         /* Storing to an Index (pointer into a packager or buffer) */
286 
287         Status = AcpiExStoreObjectToIndex (SourceDesc, RefDesc, WalkState);
288         break;
289 
290     case ACPI_REFCLASS_LOCAL:
291     case ACPI_REFCLASS_ARG:
292 
293         /* Store to a method local/arg  */
294 
295         Status = AcpiDsStoreObjectToLocal (RefDesc->Reference.Class,
296             RefDesc->Reference.Value, SourceDesc, WalkState);
297         break;
298 
299     case ACPI_REFCLASS_DEBUG:
300         /*
301          * Storing to the Debug object causes the value stored to be
302          * displayed and otherwise has no effect -- see ACPI Specification
303          */
304         ACPI_DEBUG_PRINT ((ACPI_DB_EXEC,
305             "**** Write to Debug Object: Object %p [%s] ****:\n\n",
306             SourceDesc, AcpiUtGetObjectTypeName (SourceDesc)));
307 
308         ACPI_DEBUG_OBJECT (SourceDesc, 0, 0);
309         break;
310 
311     default:
312 
313         ACPI_ERROR ((AE_INFO, "Unknown Reference Class 0x%2.2X",
314             RefDesc->Reference.Class));
315         ACPI_DUMP_ENTRY (RefDesc, ACPI_LV_INFO);
316 
317         Status = AE_AML_INTERNAL;
318         break;
319     }
320 
321     return_ACPI_STATUS (Status);
322 }
323 
324 
325 /*******************************************************************************
326  *
327  * FUNCTION:    AcpiExStoreObjectToIndex
328  *
329  * PARAMETERS:  *SourceDesc             - Value to be stored
330  *              *DestDesc               - Named object to receive the value
331  *              WalkState               - Current walk state
332  *
333  * RETURN:      Status
334  *
335  * DESCRIPTION: Store the object to indexed Buffer or Package element
336  *
337  ******************************************************************************/
338 
339 static ACPI_STATUS
340 AcpiExStoreObjectToIndex (
341     ACPI_OPERAND_OBJECT     *SourceDesc,
342     ACPI_OPERAND_OBJECT     *IndexDesc,
343     ACPI_WALK_STATE         *WalkState)
344 {
345     ACPI_STATUS             Status = AE_OK;
346     ACPI_OPERAND_OBJECT     *ObjDesc;
347     ACPI_OPERAND_OBJECT     *NewDesc;
348     UINT8                   Value = 0;
349     UINT32                  i;
350 
351 
352     ACPI_FUNCTION_TRACE (ExStoreObjectToIndex);
353 
354 
355     /*
356      * Destination must be a reference pointer, and
357      * must point to either a buffer or a package
358      */
359     switch (IndexDesc->Reference.TargetType)
360     {
361     case ACPI_TYPE_PACKAGE:
362         /*
363          * Storing to a package element. Copy the object and replace
364          * any existing object with the new object. No implicit
365          * conversion is performed.
366          *
367          * The object at *(IndexDesc->Reference.Where) is the
368          * element within the package that is to be modified.
369          * The parent package object is at IndexDesc->Reference.Object
370          */
371         ObjDesc = *(IndexDesc->Reference.Where);
372 
373         if (SourceDesc->Common.Type == ACPI_TYPE_LOCAL_REFERENCE &&
374             SourceDesc->Reference.Class == ACPI_REFCLASS_TABLE)
375         {
376             /* This is a DDBHandle, just add a reference to it */
377 
378             AcpiUtAddReference (SourceDesc);
379             NewDesc = SourceDesc;
380         }
381         else
382         {
383             /* Normal object, copy it */
384 
385             Status = AcpiUtCopyIobjectToIobject (
386                 SourceDesc, &NewDesc, WalkState);
387             if (ACPI_FAILURE (Status))
388             {
389                 return_ACPI_STATUS (Status);
390             }
391         }
392 
393         if (ObjDesc)
394         {
395             /* Decrement reference count by the ref count of the parent package */
396 
397             for (i = 0;
398                  i < ((ACPI_OPERAND_OBJECT *)
399                         IndexDesc->Reference.Object)->Common.ReferenceCount;
400                  i++)
401             {
402                 AcpiUtRemoveReference (ObjDesc);
403             }
404         }
405 
406         *(IndexDesc->Reference.Where) = NewDesc;
407 
408         /* Increment ref count by the ref count of the parent package-1 */
409 
410         for (i = 1;
411              i < ((ACPI_OPERAND_OBJECT *)
412                     IndexDesc->Reference.Object)->Common.ReferenceCount;
413              i++)
414         {
415             AcpiUtAddReference (NewDesc);
416         }
417 
418         break;
419 
420     case ACPI_TYPE_BUFFER_FIELD:
421         /*
422          * Store into a Buffer or String (not actually a real BufferField)
423          * at a location defined by an Index.
424          *
425          * The first 8-bit element of the source object is written to the
426          * 8-bit Buffer location defined by the Index destination object,
427          * according to the ACPI 2.0 specification.
428          */
429 
430         /*
431          * Make sure the target is a Buffer or String. An error should
432          * not happen here, since the ReferenceObject was constructed
433          * by the INDEX_OP code.
434          */
435         ObjDesc = IndexDesc->Reference.Object;
436         if ((ObjDesc->Common.Type != ACPI_TYPE_BUFFER) &&
437             (ObjDesc->Common.Type != ACPI_TYPE_STRING))
438         {
439             return_ACPI_STATUS (AE_AML_OPERAND_TYPE);
440         }
441 
442         /*
443          * The assignment of the individual elements will be slightly
444          * different for each source type.
445          */
446         switch (SourceDesc->Common.Type)
447         {
448         case ACPI_TYPE_INTEGER:
449 
450             /* Use the least-significant byte of the integer */
451 
452             Value = (UINT8) (SourceDesc->Integer.Value);
453             break;
454 
455         case ACPI_TYPE_BUFFER:
456         case ACPI_TYPE_STRING:
457 
458             /* Note: Takes advantage of common string/buffer fields */
459 
460             Value = SourceDesc->Buffer.Pointer[0];
461             break;
462 
463         default:
464 
465             /* All other types are invalid */
466 
467             ACPI_ERROR ((AE_INFO,
468                 "Source must be type [Integer/Buffer/String], found [%s]",
469                 AcpiUtGetObjectTypeName (SourceDesc)));
470             return_ACPI_STATUS (AE_AML_OPERAND_TYPE);
471         }
472 
473         /* Store the source value into the target buffer byte */
474 
475         ObjDesc->Buffer.Pointer[IndexDesc->Reference.Value] = Value;
476         break;
477 
478     default:
479         ACPI_ERROR ((AE_INFO,
480             "Target is not of type [Package/BufferField]"));
481         Status = AE_AML_TARGET_TYPE;
482         break;
483     }
484 
485     return_ACPI_STATUS (Status);
486 }
487 
488 
489 /*******************************************************************************
490  *
491  * FUNCTION:    AcpiExStoreObjectToNode
492  *
493  * PARAMETERS:  SourceDesc              - Value to be stored
494  *              Node                    - Named object to receive the value
495  *              WalkState               - Current walk state
496  *              ImplicitConversion      - Perform implicit conversion (yes/no)
497  *
498  * RETURN:      Status
499  *
500  * DESCRIPTION: Store the object to the named object.
501  *
502  * The assignment of an object to a named object is handled here.
503  * The value passed in will replace the current value (if any)
504  * with the input value.
505  *
506  * When storing into an object the data is converted to the
507  * target object type then stored in the object. This means
508  * that the target object type (for an initialized target) will
509  * not be changed by a store operation. A CopyObject can change
510  * the target type, however.
511  *
512  * The ImplicitConversion flag is set to NO/FALSE only when
513  * storing to an ArgX -- as per the rules of the ACPI spec.
514  *
515  * Assumes parameters are already validated.
516  *
517  ******************************************************************************/
518 
519 ACPI_STATUS
520 AcpiExStoreObjectToNode (
521     ACPI_OPERAND_OBJECT     *SourceDesc,
522     ACPI_NAMESPACE_NODE     *Node,
523     ACPI_WALK_STATE         *WalkState,
524     UINT8                   ImplicitConversion)
525 {
526     ACPI_STATUS             Status = AE_OK;
527     ACPI_OPERAND_OBJECT     *TargetDesc;
528     ACPI_OPERAND_OBJECT     *NewDesc;
529     ACPI_OBJECT_TYPE        TargetType;
530 
531 
532     ACPI_FUNCTION_TRACE_PTR (ExStoreObjectToNode, SourceDesc);
533 
534 
535     /* Get current type of the node, and object attached to Node */
536 
537     TargetType = AcpiNsGetType (Node);
538     TargetDesc = AcpiNsGetAttachedObject (Node);
539 
540     ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Storing %p [%s] to node %p [%s]\n",
541         SourceDesc, AcpiUtGetObjectTypeName (SourceDesc),
542         Node, AcpiUtGetTypeName (TargetType)));
543 
544     /* Only limited target types possible for everything except CopyObject */
545 
546     if (WalkState->Opcode != AML_COPY_OBJECT_OP)
547     {
548         /*
549          * Only CopyObject allows all object types to be overwritten. For
550          * TargetRef(s), there are restrictions on the object types that
551          * are allowed.
552          *
553          * Allowable operations/typing for Store:
554          *
555          * 1) Simple Store
556          *      Integer     --> Integer (Named/Local/Arg)
557          *      String      --> String  (Named/Local/Arg)
558          *      Buffer      --> Buffer  (Named/Local/Arg)
559          *      Package     --> Package (Named/Local/Arg)
560          *
561          * 2) Store with implicit conversion
562          *      Integer     --> String or Buffer  (Named)
563          *      String      --> Integer or Buffer (Named)
564          *      Buffer      --> Integer or String (Named)
565          */
566         switch (TargetType)
567         {
568         case ACPI_TYPE_PACKAGE:
569             /*
570              * Here, can only store a package to an existing package.
571              * Storing a package to a Local/Arg is OK, and handled
572              * elsewhere.
573              */
574             if (WalkState->Opcode == AML_STORE_OP)
575             {
576                 if (SourceDesc->Common.Type != ACPI_TYPE_PACKAGE)
577                 {
578                     ACPI_ERROR ((AE_INFO,
579                         "Cannot assign type [%s] to [Package] "
580                         "(source must be type Pkg)",
581                         AcpiUtGetObjectTypeName (SourceDesc)));
582 
583                     return_ACPI_STATUS (AE_AML_TARGET_TYPE);
584                 }
585                 break;
586             }
587 
588         /* Fallthrough */
589 
590         case ACPI_TYPE_DEVICE:
591         case ACPI_TYPE_EVENT:
592         case ACPI_TYPE_MUTEX:
593         case ACPI_TYPE_REGION:
594         case ACPI_TYPE_POWER:
595         case ACPI_TYPE_PROCESSOR:
596         case ACPI_TYPE_THERMAL:
597 
598             ACPI_ERROR ((AE_INFO,
599                 "Target must be [Buffer/Integer/String/Reference]"
600                 ", found [%s] (%4.4s)",
601                 AcpiUtGetTypeName (Node->Type), Node->Name.Ascii));
602 
603             return_ACPI_STATUS (AE_AML_TARGET_TYPE);
604 
605         default:
606             break;
607         }
608     }
609 
610     /*
611      * Resolve the source object to an actual value
612      * (If it is a reference object)
613      */
614     Status = AcpiExResolveObject (&SourceDesc, TargetType, WalkState);
615     if (ACPI_FAILURE (Status))
616     {
617         return_ACPI_STATUS (Status);
618     }
619 
620     /* Do the actual store operation */
621 
622     switch (TargetType)
623     {
624         /*
625          * The simple data types all support implicit source operand
626          * conversion before the store.
627          */
628     case ACPI_TYPE_INTEGER:
629     case ACPI_TYPE_STRING:
630     case ACPI_TYPE_BUFFER:
631 
632         if ((WalkState->Opcode == AML_COPY_OBJECT_OP) ||
633             !ImplicitConversion)
634         {
635             /*
636              * However, CopyObject and Stores to ArgX do not perform
637              * an implicit conversion, as per the ACPI specification.
638              * A direct store is performed instead.
639              */
640             Status = AcpiExStoreDirectToNode (SourceDesc, Node, WalkState);
641             break;
642         }
643 
644         /* Store with implicit source operand conversion support */
645 
646         Status = AcpiExStoreObjectToObject (SourceDesc, TargetDesc,
647             &NewDesc, WalkState);
648         if (ACPI_FAILURE (Status))
649         {
650             return_ACPI_STATUS (Status);
651         }
652 
653         if (NewDesc != TargetDesc)
654         {
655             /*
656              * Store the new NewDesc as the new value of the Name, and set
657              * the Name's type to that of the value being stored in it.
658              * SourceDesc reference count is incremented by AttachObject.
659              *
660              * Note: This may change the type of the node if an explicit
661              * store has been performed such that the node/object type
662              * has been changed.
663              */
664             Status = AcpiNsAttachObject (
665                 Node, NewDesc, NewDesc->Common.Type);
666 
667             ACPI_DEBUG_PRINT ((ACPI_DB_EXEC,
668                 "Store type [%s] into [%s] via Convert/Attach\n",
669                 AcpiUtGetObjectTypeName (SourceDesc),
670                 AcpiUtGetObjectTypeName (NewDesc)));
671         }
672         break;
673 
674     case ACPI_TYPE_BUFFER_FIELD:
675     case ACPI_TYPE_LOCAL_REGION_FIELD:
676     case ACPI_TYPE_LOCAL_BANK_FIELD:
677     case ACPI_TYPE_LOCAL_INDEX_FIELD:
678         /*
679          * For all fields, always write the source data to the target
680          * field. Any required implicit source operand conversion is
681          * performed in the function below as necessary. Note, field
682          * objects must retain their original type permanently.
683          */
684         Status = AcpiExWriteDataToField (SourceDesc, TargetDesc,
685             &WalkState->ResultObj);
686         break;
687 
688     default:
689         /*
690          * CopyObject operator: No conversions for all other types.
691          * Instead, directly store a copy of the source object.
692          *
693          * This is the ACPI spec-defined behavior for the CopyObject
694          * operator. (Note, for this default case, all normal
695          * Store/Target operations exited above with an error).
696          */
697         Status = AcpiExStoreDirectToNode (SourceDesc, Node, WalkState);
698         break;
699     }
700 
701     return_ACPI_STATUS (Status);
702 }
703 
704 
705 /*******************************************************************************
706  *
707  * FUNCTION:    AcpiExStoreDirectToNode
708  *
709  * PARAMETERS:  SourceDesc              - Value to be stored
710  *              Node                    - Named object to receive the value
711  *              WalkState               - Current walk state
712  *
713  * RETURN:      Status
714  *
715  * DESCRIPTION: "Store" an object directly to a node. This involves a copy
716  *              and an attach.
717  *
718  ******************************************************************************/
719 
720 static ACPI_STATUS
721 AcpiExStoreDirectToNode (
722     ACPI_OPERAND_OBJECT     *SourceDesc,
723     ACPI_NAMESPACE_NODE     *Node,
724     ACPI_WALK_STATE         *WalkState)
725 {
726     ACPI_STATUS             Status;
727     ACPI_OPERAND_OBJECT     *NewDesc;
728 
729 
730     ACPI_FUNCTION_TRACE (ExStoreDirectToNode);
731 
732 
733     ACPI_DEBUG_PRINT ((ACPI_DB_EXEC,
734         "Storing [%s] (%p) directly into node [%s] (%p)"
735         " with no implicit conversion\n",
736         AcpiUtGetObjectTypeName (SourceDesc), SourceDesc,
737         AcpiUtGetTypeName (Node->Type), Node));
738 
739     /* Copy the source object to a new object */
740 
741     Status = AcpiUtCopyIobjectToIobject (SourceDesc, &NewDesc, WalkState);
742     if (ACPI_FAILURE (Status))
743     {
744         return_ACPI_STATUS (Status);
745     }
746 
747     /* Attach the new object to the node */
748 
749     Status = AcpiNsAttachObject (Node, NewDesc, NewDesc->Common.Type);
750     AcpiUtRemoveReference (NewDesc);
751     return_ACPI_STATUS (Status);
752 }
753