The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/contrib/dev/acpica/components/tables/tbdata.c

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

    1 /******************************************************************************
    2  *
    3  * Module Name: tbdata - Table manager data structure functions
    4  *
    5  *****************************************************************************/
    6 
    7 /******************************************************************************
    8  *
    9  * 1. Copyright Notice
   10  *
   11  * Some or all of this work - Copyright (c) 1999 - 2022, 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 <contrib/dev/acpica/include/acpi.h>
  153 #include <contrib/dev/acpica/include/accommon.h>
  154 #include <contrib/dev/acpica/include/acnamesp.h>
  155 #include <contrib/dev/acpica/include/actables.h>
  156 #include <contrib/dev/acpica/include/acevents.h>
  157 
  158 #define _COMPONENT          ACPI_TABLES
  159         ACPI_MODULE_NAME    ("tbdata")
  160 
  161 /* Local prototypes */
  162 
  163 static ACPI_STATUS
  164 AcpiTbCheckDuplication (
  165     ACPI_TABLE_DESC         *TableDesc,
  166     UINT32                  *TableIndex);
  167 
  168 static BOOLEAN
  169 AcpiTbCompareTables (
  170     ACPI_TABLE_DESC         *TableDesc,
  171     UINT32                  TableIndex);
  172 
  173 
  174 /*******************************************************************************
  175  *
  176  * FUNCTION:    AcpiTbCompareTables
  177  *
  178  * PARAMETERS:  TableDesc           - Table 1 descriptor to be compared
  179  *              TableIndex          - Index of table 2 to be compared
  180  *
  181  * RETURN:      TRUE if both tables are identical.
  182  *
  183  * DESCRIPTION: This function compares a table with another table that has
  184  *              already been installed in the root table list.
  185  *
  186  ******************************************************************************/
  187 
  188 static BOOLEAN
  189 AcpiTbCompareTables (
  190     ACPI_TABLE_DESC         *TableDesc,
  191     UINT32                  TableIndex)
  192 {
  193     ACPI_STATUS             Status = AE_OK;
  194     BOOLEAN                 IsIdentical;
  195     ACPI_TABLE_HEADER       *Table;
  196     UINT32                  TableLength;
  197     UINT8                   TableFlags;
  198 
  199 
  200     Status = AcpiTbAcquireTable (&AcpiGbl_RootTableList.Tables[TableIndex],
  201         &Table, &TableLength, &TableFlags);
  202     if (ACPI_FAILURE (Status))
  203     {
  204         return (FALSE);
  205     }
  206 
  207     /*
  208      * Check for a table match on the entire table length,
  209      * not just the header.
  210      */
  211     IsIdentical = (BOOLEAN)((TableDesc->Length != TableLength ||
  212         memcmp (TableDesc->Pointer, Table, TableLength)) ?
  213         FALSE : TRUE);
  214 
  215     /* Release the acquired table */
  216 
  217     AcpiTbReleaseTable (Table, TableLength, TableFlags);
  218     return (IsIdentical);
  219 }
  220 
  221 
  222 /*******************************************************************************
  223  *
  224  * FUNCTION:    AcpiTbInitTableDescriptor
  225  *
  226  * PARAMETERS:  TableDesc               - Table descriptor
  227  *              Address                 - Physical address of the table
  228  *              Flags                   - Allocation flags of the table
  229  *              Table                   - Pointer to the table
  230  *
  231  * RETURN:      None
  232  *
  233  * DESCRIPTION: Initialize a new table descriptor
  234  *
  235  ******************************************************************************/
  236 
  237 void
  238 AcpiTbInitTableDescriptor (
  239     ACPI_TABLE_DESC         *TableDesc,
  240     ACPI_PHYSICAL_ADDRESS   Address,
  241     UINT8                   Flags,
  242     ACPI_TABLE_HEADER       *Table)
  243 {
  244 
  245     /*
  246      * Initialize the table descriptor. Set the pointer to NULL for external
  247      * tables, since the table is not fully mapped at this time.
  248      */
  249     memset (TableDesc, 0, sizeof (ACPI_TABLE_DESC));
  250     TableDesc->Address = Address;
  251     TableDesc->Length = Table->Length;
  252     TableDesc->Flags = Flags;
  253     ACPI_MOVE_32_TO_32 (TableDesc->Signature.Ascii, Table->Signature);
  254 
  255     switch (TableDesc->Flags & ACPI_TABLE_ORIGIN_MASK)
  256     {
  257     case ACPI_TABLE_ORIGIN_INTERNAL_VIRTUAL:
  258     case ACPI_TABLE_ORIGIN_EXTERNAL_VIRTUAL:
  259 
  260         TableDesc->Pointer = Table;
  261         break;
  262 
  263     case ACPI_TABLE_ORIGIN_INTERNAL_PHYSICAL:
  264     default:
  265 
  266         break;
  267     }
  268 }
  269 
  270 
  271 /*******************************************************************************
  272  *
  273  * FUNCTION:    AcpiTbAcquireTable
  274  *
  275  * PARAMETERS:  TableDesc           - Table descriptor
  276  *              TablePtr            - Where table is returned
  277  *              TableLength         - Where table length is returned
  278  *              TableFlags          - Where table allocation flags are returned
  279  *
  280  * RETURN:      Status
  281  *
  282  * DESCRIPTION: Acquire an ACPI table. It can be used for tables not
  283  *              maintained in the AcpiGbl_RootTableList.
  284  *
  285  ******************************************************************************/
  286 
  287 ACPI_STATUS
  288 AcpiTbAcquireTable (
  289     ACPI_TABLE_DESC         *TableDesc,
  290     ACPI_TABLE_HEADER       **TablePtr,
  291     UINT32                  *TableLength,
  292     UINT8                   *TableFlags)
  293 {
  294     ACPI_TABLE_HEADER       *Table = NULL;
  295 
  296 
  297     switch (TableDesc->Flags & ACPI_TABLE_ORIGIN_MASK)
  298     {
  299     case ACPI_TABLE_ORIGIN_INTERNAL_PHYSICAL:
  300 
  301         Table = AcpiOsMapMemory (TableDesc->Address, TableDesc->Length);
  302         break;
  303 
  304     case ACPI_TABLE_ORIGIN_INTERNAL_VIRTUAL:
  305     case ACPI_TABLE_ORIGIN_EXTERNAL_VIRTUAL:
  306 
  307         Table = TableDesc->Pointer;
  308         break;
  309 
  310     default:
  311 
  312         break;
  313     }
  314 
  315     /* Table is not valid yet */
  316 
  317     if (!Table)
  318     {
  319         return (AE_NO_MEMORY);
  320     }
  321 
  322     /* Fill the return values */
  323 
  324     *TablePtr = Table;
  325     *TableLength = TableDesc->Length;
  326     *TableFlags = TableDesc->Flags;
  327     return (AE_OK);
  328 }
  329 
  330 
  331 /*******************************************************************************
  332  *
  333  * FUNCTION:    AcpiTbReleaseTable
  334  *
  335  * PARAMETERS:  Table               - Pointer for the table
  336  *              TableLength         - Length for the table
  337  *              TableFlags          - Allocation flags for the table
  338  *
  339  * RETURN:      None
  340  *
  341  * DESCRIPTION: Release a table. The inverse of AcpiTbAcquireTable().
  342  *
  343  ******************************************************************************/
  344 
  345 void
  346 AcpiTbReleaseTable (
  347     ACPI_TABLE_HEADER       *Table,
  348     UINT32                  TableLength,
  349     UINT8                   TableFlags)
  350 {
  351 
  352     switch (TableFlags & ACPI_TABLE_ORIGIN_MASK)
  353     {
  354     case ACPI_TABLE_ORIGIN_INTERNAL_PHYSICAL:
  355 
  356         AcpiOsUnmapMemory (Table, TableLength);
  357         break;
  358 
  359     case ACPI_TABLE_ORIGIN_INTERNAL_VIRTUAL:
  360     case ACPI_TABLE_ORIGIN_EXTERNAL_VIRTUAL:
  361     default:
  362 
  363         break;
  364     }
  365 }
  366 
  367 
  368 /*******************************************************************************
  369  *
  370  * FUNCTION:    AcpiTbAcquireTempTable
  371  *
  372  * PARAMETERS:  TableDesc           - Table descriptor to be acquired
  373  *              Address             - Address of the table
  374  *              Flags               - Allocation flags of the table
  375  *              Table               - Pointer to the table (required for virtual
  376  *                                    origins, optional for physical)
  377  *
  378  * RETURN:      Status
  379  *
  380  * DESCRIPTION: This function validates the table header to obtain the length
  381  *              of a table and fills the table descriptor to make its state as
  382  *              "INSTALLED". Such a table descriptor is only used for verified
  383  *              installation.
  384  *
  385  ******************************************************************************/
  386 
  387 ACPI_STATUS
  388 AcpiTbAcquireTempTable (
  389     ACPI_TABLE_DESC         *TableDesc,
  390     ACPI_PHYSICAL_ADDRESS   Address,
  391     UINT8                   Flags,
  392     ACPI_TABLE_HEADER       *Table)
  393 {
  394     BOOLEAN                 MappedTable = FALSE;
  395 
  396 
  397     switch (Flags & ACPI_TABLE_ORIGIN_MASK)
  398     {
  399     case ACPI_TABLE_ORIGIN_INTERNAL_PHYSICAL:
  400 
  401         /* Get the length of the full table from the header */
  402 
  403         if (!Table)
  404         {
  405             Table = AcpiOsMapMemory (Address, sizeof (ACPI_TABLE_HEADER));
  406             if (!Table)
  407             {
  408                 return (AE_NO_MEMORY);
  409             }
  410 
  411             MappedTable = TRUE;
  412         }
  413 
  414         break;
  415 
  416     case ACPI_TABLE_ORIGIN_INTERNAL_VIRTUAL:
  417     case ACPI_TABLE_ORIGIN_EXTERNAL_VIRTUAL:
  418 
  419         if (!Table)
  420         {
  421             return (AE_BAD_PARAMETER);
  422         }
  423 
  424         break;
  425 
  426     default:
  427 
  428         /* Table is not valid yet */
  429 
  430         return (AE_NO_MEMORY);
  431     }
  432 
  433     AcpiTbInitTableDescriptor (TableDesc, Address, Flags, Table);
  434     if (MappedTable)
  435     {
  436         AcpiOsUnmapMemory (Table, sizeof (ACPI_TABLE_HEADER));
  437     }
  438 
  439     return (AE_OK);
  440 }
  441 
  442 
  443 /*******************************************************************************
  444  *
  445  * FUNCTION:    AcpiTbReleaseTempTable
  446  *
  447  * PARAMETERS:  TableDesc           - Table descriptor to be released
  448  *
  449  * RETURN:      Status
  450  *
  451  * DESCRIPTION: The inverse of AcpiTbAcquireTempTable().
  452  *
  453  *****************************************************************************/
  454 
  455 void
  456 AcpiTbReleaseTempTable (
  457     ACPI_TABLE_DESC         *TableDesc)
  458 {
  459 
  460     /*
  461      * Note that the .Address is maintained by the callers of
  462      * AcpiTbAcquireTempTable(), thus do not invoke AcpiTbUninstallTable()
  463      * where .Address will be freed.
  464      */
  465     AcpiTbInvalidateTable (TableDesc);
  466 }
  467 
  468 
  469 /******************************************************************************
  470  *
  471  * FUNCTION:    AcpiTbValidateTable
  472  *
  473  * PARAMETERS:  TableDesc           - Table descriptor
  474  *
  475  * RETURN:      Status
  476  *
  477  * DESCRIPTION: This function is called to validate the table, the returned
  478  *              table descriptor is in "VALIDATED" state.
  479  *
  480  *****************************************************************************/
  481 
  482 ACPI_STATUS
  483 AcpiTbValidateTable (
  484     ACPI_TABLE_DESC         *TableDesc)
  485 {
  486     ACPI_STATUS             Status = AE_OK;
  487 
  488 
  489     ACPI_FUNCTION_TRACE (TbValidateTable);
  490 
  491 
  492     /* Validate the table if necessary */
  493 
  494     if (!TableDesc->Pointer)
  495     {
  496         Status = AcpiTbAcquireTable (TableDesc, &TableDesc->Pointer,
  497             &TableDesc->Length, &TableDesc->Flags);
  498         if (!TableDesc->Pointer)
  499         {
  500             Status = AE_NO_MEMORY;
  501         }
  502     }
  503 
  504     return_ACPI_STATUS (Status);
  505 }
  506 
  507 
  508 /*******************************************************************************
  509  *
  510  * FUNCTION:    AcpiTbInvalidateTable
  511  *
  512  * PARAMETERS:  TableDesc           - Table descriptor
  513  *
  514  * RETURN:      None
  515  *
  516  * DESCRIPTION: Invalidate one internal ACPI table, this is the inverse of
  517  *              AcpiTbValidateTable().
  518  *
  519  ******************************************************************************/
  520 
  521 void
  522 AcpiTbInvalidateTable (
  523     ACPI_TABLE_DESC         *TableDesc)
  524 {
  525 
  526     ACPI_FUNCTION_TRACE (TbInvalidateTable);
  527 
  528 
  529     /* Table must be validated */
  530 
  531     if (!TableDesc->Pointer)
  532     {
  533         return_VOID;
  534     }
  535 
  536     AcpiTbReleaseTable (TableDesc->Pointer, TableDesc->Length,
  537         TableDesc->Flags);
  538 
  539     switch (TableDesc->Flags & ACPI_TABLE_ORIGIN_MASK)
  540     {
  541     case ACPI_TABLE_ORIGIN_INTERNAL_PHYSICAL:
  542 
  543         TableDesc->Pointer = NULL;
  544         break;
  545 
  546     case ACPI_TABLE_ORIGIN_INTERNAL_VIRTUAL:
  547     case ACPI_TABLE_ORIGIN_EXTERNAL_VIRTUAL:
  548     default:
  549 
  550         break;
  551     }
  552 
  553     return_VOID;
  554 }
  555 
  556 
  557 /******************************************************************************
  558  *
  559  * FUNCTION:    AcpiTbValidateTempTable
  560  *
  561  * PARAMETERS:  TableDesc           - Table descriptor
  562  *
  563  * RETURN:      Status
  564  *
  565  * DESCRIPTION: This function is called to validate the table, the returned
  566  *              table descriptor is in "VALIDATED" state.
  567  *
  568  *****************************************************************************/
  569 
  570 ACPI_STATUS
  571 AcpiTbValidateTempTable (
  572     ACPI_TABLE_DESC         *TableDesc)
  573 {
  574 
  575     if (!TableDesc->Pointer && !AcpiGbl_EnableTableValidation)
  576     {
  577         /*
  578          * Only validates the header of the table.
  579          * Note that Length contains the size of the mapping after invoking
  580          * this work around, this value is required by
  581          * AcpiTbReleaseTempTable().
  582          * We can do this because in AcpiInitTableDescriptor(), the Length
  583          * field of the installed descriptor is filled with the actual
  584          * table length obtaining from the table header.
  585          */
  586         TableDesc->Length = sizeof (ACPI_TABLE_HEADER);
  587     }
  588 
  589     return (AcpiTbValidateTable (TableDesc));
  590 }
  591 
  592 
  593 /*******************************************************************************
  594  *
  595  * FUNCTION:    AcpiTbCheckDuplication
  596  *
  597  * PARAMETERS:  TableDesc           - Table descriptor
  598  *              TableIndex          - Where the table index is returned
  599  *
  600  * RETURN:      Status
  601  *
  602  * DESCRIPTION: Avoid installing duplicated tables. However table override and
  603  *              user aided dynamic table load is allowed, thus comparing the
  604  *              address of the table is not sufficient, and checking the entire
  605  *              table content is required.
  606  *
  607  ******************************************************************************/
  608 
  609 static ACPI_STATUS
  610 AcpiTbCheckDuplication (
  611     ACPI_TABLE_DESC         *TableDesc,
  612     UINT32                  *TableIndex)
  613 {
  614     UINT32                  i;
  615 
  616 
  617     ACPI_FUNCTION_TRACE (TbCheckDuplication);
  618 
  619 
  620     /* Check if table is already registered */
  621 
  622     for (i = 0; i < AcpiGbl_RootTableList.CurrentTableCount; ++i)
  623     {
  624         /* Do not compare with unverified tables */
  625 
  626         if (!(AcpiGbl_RootTableList.Tables[i].Flags & ACPI_TABLE_IS_VERIFIED))
  627         {
  628             continue;
  629         }
  630 
  631         /*
  632          * Check for a table match on the entire table length,
  633          * not just the header.
  634          */
  635         if (!AcpiTbCompareTables (TableDesc, i))
  636         {
  637             continue;
  638         }
  639 
  640         /*
  641          * Note: the current mechanism does not unregister a table if it is
  642          * dynamically unloaded. The related namespace entries are deleted,
  643          * but the table remains in the root table list.
  644          *
  645          * The assumption here is that the number of different tables that
  646          * will be loaded is actually small, and there is minimal overhead
  647          * in just keeping the table in case it is needed again.
  648          *
  649          * If this assumption changes in the future (perhaps on large
  650          * machines with many table load/unload operations), tables will
  651          * need to be unregistered when they are unloaded, and slots in the
  652          * root table list should be reused when empty.
  653          */
  654         if (AcpiGbl_RootTableList.Tables[i].Flags &
  655             ACPI_TABLE_IS_LOADED)
  656         {
  657             /* Table is still loaded, this is an error */
  658 
  659             return_ACPI_STATUS (AE_ALREADY_EXISTS);
  660         }
  661         else
  662         {
  663             *TableIndex = i;
  664             return_ACPI_STATUS (AE_CTRL_TERMINATE);
  665         }
  666     }
  667 
  668     /* Indicate no duplication to the caller */
  669 
  670     return_ACPI_STATUS (AE_OK);
  671 }
  672 
  673 
  674 /******************************************************************************
  675  *
  676  * FUNCTION:    AcpiTbVerifyTempTable
  677  *
  678  * PARAMETERS:  TableDesc           - Table descriptor
  679  *              Signature           - Table signature to verify
  680  *              TableIndex          - Where the table index is returned
  681  *
  682  * RETURN:      Status
  683  *
  684  * DESCRIPTION: This function is called to validate and verify the table, the
  685  *              returned table descriptor is in "VALIDATED" state.
  686  *              Note that 'TableIndex' is required to be set to !NULL to
  687  *              enable duplication check.
  688  *
  689  *****************************************************************************/
  690 
  691 ACPI_STATUS
  692 AcpiTbVerifyTempTable (
  693     ACPI_TABLE_DESC         *TableDesc,
  694     char                    *Signature,
  695     UINT32                  *TableIndex)
  696 {
  697     ACPI_STATUS             Status = AE_OK;
  698 
  699 
  700     ACPI_FUNCTION_TRACE (TbVerifyTempTable);
  701 
  702 
  703     /* Validate the table */
  704 
  705     Status = AcpiTbValidateTempTable (TableDesc);
  706     if (ACPI_FAILURE (Status))
  707     {
  708         return_ACPI_STATUS (AE_NO_MEMORY);
  709     }
  710 
  711     /* If a particular signature is expected (DSDT/FACS), it must match */
  712 
  713     if (Signature &&
  714         !ACPI_COMPARE_NAMESEG (&TableDesc->Signature, Signature))
  715     {
  716         ACPI_BIOS_ERROR ((AE_INFO,
  717             "Invalid signature 0x%X for ACPI table, expected [%s]",
  718             TableDesc->Signature.Integer, Signature));
  719         Status = AE_BAD_SIGNATURE;
  720         goto InvalidateAndExit;
  721     }
  722 
  723     if (AcpiGbl_EnableTableValidation)
  724     {
  725         /* Verify the checksum */
  726 
  727         Status = AcpiUtVerifyChecksum (TableDesc->Pointer, TableDesc->Length);
  728         if (ACPI_FAILURE (Status))
  729         {
  730             ACPI_EXCEPTION ((AE_INFO, AE_NO_MEMORY,
  731                 "%4.4s 0x%8.8X%8.8X"
  732                 " Attempted table install failed",
  733                 AcpiUtValidNameseg (TableDesc->Signature.Ascii) ?
  734                     TableDesc->Signature.Ascii : "????",
  735                 ACPI_FORMAT_UINT64 (TableDesc->Address)));
  736 
  737             goto InvalidateAndExit;
  738         }
  739 
  740         /* Avoid duplications */
  741 
  742         if (TableIndex)
  743         {
  744             Status = AcpiTbCheckDuplication (TableDesc, TableIndex);
  745             if (ACPI_FAILURE (Status))
  746             {
  747                 if (Status != AE_CTRL_TERMINATE)
  748                 {
  749                     ACPI_EXCEPTION ((AE_INFO, Status,
  750                         "%4.4s 0x%8.8X%8.8X"
  751                         " Table is already loaded",
  752                         AcpiUtValidNameseg (TableDesc->Signature.Ascii) ?
  753                             TableDesc->Signature.Ascii : "????",
  754                         ACPI_FORMAT_UINT64 (TableDesc->Address)));
  755                 }
  756 
  757                 goto InvalidateAndExit;
  758             }
  759         }
  760 
  761         TableDesc->Flags |= ACPI_TABLE_IS_VERIFIED;
  762     }
  763 
  764     return_ACPI_STATUS (Status);
  765 
  766 InvalidateAndExit:
  767     AcpiTbInvalidateTable (TableDesc);
  768     return_ACPI_STATUS (Status);
  769 }
  770 
  771 
  772 /*******************************************************************************
  773  *
  774  * FUNCTION:    AcpiTbResizeRootTableList
  775  *
  776  * PARAMETERS:  None
  777  *
  778  * RETURN:      Status
  779  *
  780  * DESCRIPTION: Expand the size of global table array
  781  *
  782  ******************************************************************************/
  783 
  784 ACPI_STATUS
  785 AcpiTbResizeRootTableList (
  786     void)
  787 {
  788     ACPI_TABLE_DESC         *Tables;
  789     UINT32                  TableCount;
  790     UINT32                  CurrentTableCount, MaxTableCount;
  791     UINT32                  i;
  792 
  793 
  794     ACPI_FUNCTION_TRACE (TbResizeRootTableList);
  795 
  796 
  797     /* AllowResize flag is a parameter to AcpiInitializeTables */
  798 
  799     if (!(AcpiGbl_RootTableList.Flags & ACPI_ROOT_ALLOW_RESIZE))
  800     {
  801         ACPI_ERROR ((AE_INFO, "Resize of Root Table Array is not allowed"));
  802         return_ACPI_STATUS (AE_SUPPORT);
  803     }
  804 
  805     /* Increase the Table Array size */
  806 
  807     if (AcpiGbl_RootTableList.Flags & ACPI_ROOT_ORIGIN_ALLOCATED)
  808     {
  809         TableCount = AcpiGbl_RootTableList.MaxTableCount;
  810     }
  811     else
  812     {
  813         TableCount = AcpiGbl_RootTableList.CurrentTableCount;
  814     }
  815 
  816     MaxTableCount = TableCount + ACPI_ROOT_TABLE_SIZE_INCREMENT;
  817     Tables = ACPI_ALLOCATE_ZEROED (
  818         ((ACPI_SIZE) MaxTableCount) * sizeof (ACPI_TABLE_DESC));
  819     if (!Tables)
  820     {
  821         ACPI_ERROR ((AE_INFO, "Could not allocate new root table array"));
  822         return_ACPI_STATUS (AE_NO_MEMORY);
  823     }
  824 
  825     /* Copy and free the previous table array */
  826 
  827     CurrentTableCount = 0;
  828     if (AcpiGbl_RootTableList.Tables)
  829     {
  830         for (i = 0; i < TableCount; i++)
  831         {
  832             if (AcpiGbl_RootTableList.Tables[i].Address)
  833             {
  834                 memcpy (Tables + CurrentTableCount,
  835                     AcpiGbl_RootTableList.Tables + i,
  836                     sizeof (ACPI_TABLE_DESC));
  837                 CurrentTableCount++;
  838             }
  839         }
  840 
  841         if (AcpiGbl_RootTableList.Flags & ACPI_ROOT_ORIGIN_ALLOCATED)
  842         {
  843             ACPI_FREE (AcpiGbl_RootTableList.Tables);
  844         }
  845     }
  846 
  847     AcpiGbl_RootTableList.Tables = Tables;
  848     AcpiGbl_RootTableList.MaxTableCount = MaxTableCount;
  849     AcpiGbl_RootTableList.CurrentTableCount = CurrentTableCount;
  850     AcpiGbl_RootTableList.Flags |= ACPI_ROOT_ORIGIN_ALLOCATED;
  851 
  852     return_ACPI_STATUS (AE_OK);
  853 }
  854 
  855 
  856 /*******************************************************************************
  857  *
  858  * FUNCTION:    AcpiTbGetNextTableDescriptor
  859  *
  860  * PARAMETERS:  TableIndex          - Where table index is returned
  861  *              TableDesc           - Where table descriptor is returned
  862  *
  863  * RETURN:      Status and table index/descriptor.
  864  *
  865  * DESCRIPTION: Allocate a new ACPI table entry to the global table list
  866  *
  867  ******************************************************************************/
  868 
  869 ACPI_STATUS
  870 AcpiTbGetNextTableDescriptor (
  871     UINT32                  *TableIndex,
  872     ACPI_TABLE_DESC         **TableDesc)
  873 {
  874     ACPI_STATUS             Status;
  875     UINT32                  i;
  876 
  877 
  878     /* Ensure that there is room for the table in the Root Table List */
  879 
  880     if (AcpiGbl_RootTableList.CurrentTableCount >=
  881         AcpiGbl_RootTableList.MaxTableCount)
  882     {
  883         Status = AcpiTbResizeRootTableList();
  884         if (ACPI_FAILURE (Status))
  885         {
  886             return (Status);
  887         }
  888     }
  889 
  890     i = AcpiGbl_RootTableList.CurrentTableCount;
  891     AcpiGbl_RootTableList.CurrentTableCount++;
  892 
  893     if (TableIndex)
  894     {
  895         *TableIndex = i;
  896     }
  897     if (TableDesc)
  898     {
  899         *TableDesc = &AcpiGbl_RootTableList.Tables[i];
  900     }
  901 
  902     return (AE_OK);
  903 }
  904 
  905 
  906 /*******************************************************************************
  907  *
  908  * FUNCTION:    AcpiTbTerminate
  909  *
  910  * PARAMETERS:  None
  911  *
  912  * RETURN:      None
  913  *
  914  * DESCRIPTION: Delete all internal ACPI tables
  915  *
  916  ******************************************************************************/
  917 
  918 void
  919 AcpiTbTerminate (
  920     void)
  921 {
  922     UINT32                  i;
  923 
  924 
  925     ACPI_FUNCTION_TRACE (TbTerminate);
  926 
  927 
  928     (void) AcpiUtAcquireMutex (ACPI_MTX_TABLES);
  929 
  930     /* Delete the individual tables */
  931 
  932     for (i = 0; i < AcpiGbl_RootTableList.CurrentTableCount; i++)
  933     {
  934         AcpiTbUninstallTable (&AcpiGbl_RootTableList.Tables[i]);
  935     }
  936 
  937     /*
  938      * Delete the root table array if allocated locally. Array cannot be
  939      * mapped, so we don't need to check for that flag.
  940      */
  941     if (AcpiGbl_RootTableList.Flags & ACPI_ROOT_ORIGIN_ALLOCATED)
  942     {
  943         ACPI_FREE (AcpiGbl_RootTableList.Tables);
  944     }
  945 
  946     AcpiGbl_RootTableList.Tables = NULL;
  947     AcpiGbl_RootTableList.Flags = 0;
  948     AcpiGbl_RootTableList.CurrentTableCount = 0;
  949 
  950     ACPI_DEBUG_PRINT ((ACPI_DB_INFO, "ACPI Tables freed\n"));
  951 
  952     (void) AcpiUtReleaseMutex (ACPI_MTX_TABLES);
  953     return_VOID;
  954 }
  955 
  956 
  957 /*******************************************************************************
  958  *
  959  * FUNCTION:    AcpiTbDeleteNamespaceByOwner
  960  *
  961  * PARAMETERS:  TableIndex          - Table index
  962  *
  963  * RETURN:      Status
  964  *
  965  * DESCRIPTION: Delete all namespace objects created when this table was loaded.
  966  *
  967  ******************************************************************************/
  968 
  969 ACPI_STATUS
  970 AcpiTbDeleteNamespaceByOwner (
  971     UINT32                  TableIndex)
  972 {
  973     ACPI_OWNER_ID           OwnerId;
  974     ACPI_STATUS             Status;
  975 
  976 
  977     ACPI_FUNCTION_TRACE (TbDeleteNamespaceByOwner);
  978 
  979 
  980     Status = AcpiUtAcquireMutex (ACPI_MTX_TABLES);
  981     if (ACPI_FAILURE (Status))
  982     {
  983         return_ACPI_STATUS (Status);
  984     }
  985 
  986     if (TableIndex >= AcpiGbl_RootTableList.CurrentTableCount)
  987     {
  988         /* The table index does not exist */
  989 
  990         (void) AcpiUtReleaseMutex (ACPI_MTX_TABLES);
  991         return_ACPI_STATUS (AE_NOT_EXIST);
  992     }
  993 
  994     /* Get the owner ID for this table, used to delete namespace nodes */
  995 
  996     OwnerId = AcpiGbl_RootTableList.Tables[TableIndex].OwnerId;
  997     (void) AcpiUtReleaseMutex (ACPI_MTX_TABLES);
  998 
  999     /*
 1000      * Need to acquire the namespace writer lock to prevent interference
 1001      * with any concurrent namespace walks. The interpreter must be
 1002      * released during the deletion since the acquisition of the deletion
 1003      * lock may block, and also since the execution of a namespace walk
 1004      * must be allowed to use the interpreter.
 1005      */
 1006     Status = AcpiUtAcquireWriteLock (&AcpiGbl_NamespaceRwLock);
 1007     if (ACPI_FAILURE (Status))
 1008     {
 1009         return_ACPI_STATUS (Status);
 1010     }
 1011 
 1012     AcpiNsDeleteNamespaceByOwner (OwnerId);
 1013     AcpiUtReleaseWriteLock (&AcpiGbl_NamespaceRwLock);
 1014     return_ACPI_STATUS (Status);
 1015 }
 1016 
 1017 
 1018 /*******************************************************************************
 1019  *
 1020  * FUNCTION:    AcpiTbAllocateOwnerId
 1021  *
 1022  * PARAMETERS:  TableIndex          - Table index
 1023  *
 1024  * RETURN:      Status
 1025  *
 1026  * DESCRIPTION: Allocates OwnerId in TableDesc
 1027  *
 1028  ******************************************************************************/
 1029 
 1030 ACPI_STATUS
 1031 AcpiTbAllocateOwnerId (
 1032     UINT32                  TableIndex)
 1033 {
 1034     ACPI_STATUS             Status = AE_BAD_PARAMETER;
 1035 
 1036 
 1037     ACPI_FUNCTION_TRACE (TbAllocateOwnerId);
 1038 
 1039 
 1040     (void) AcpiUtAcquireMutex (ACPI_MTX_TABLES);
 1041     if (TableIndex < AcpiGbl_RootTableList.CurrentTableCount)
 1042     {
 1043         Status = AcpiUtAllocateOwnerId (
 1044             &(AcpiGbl_RootTableList.Tables[TableIndex].OwnerId));
 1045     }
 1046 
 1047     (void) AcpiUtReleaseMutex (ACPI_MTX_TABLES);
 1048     return_ACPI_STATUS (Status);
 1049 }
 1050 
 1051 
 1052 /*******************************************************************************
 1053  *
 1054  * FUNCTION:    AcpiTbReleaseOwnerId
 1055  *
 1056  * PARAMETERS:  TableIndex          - Table index
 1057  *
 1058  * RETURN:      Status
 1059  *
 1060  * DESCRIPTION: Releases OwnerId in TableDesc
 1061  *
 1062  ******************************************************************************/
 1063 
 1064 ACPI_STATUS
 1065 AcpiTbReleaseOwnerId (
 1066     UINT32                  TableIndex)
 1067 {
 1068     ACPI_STATUS             Status = AE_BAD_PARAMETER;
 1069 
 1070 
 1071     ACPI_FUNCTION_TRACE (TbReleaseOwnerId);
 1072 
 1073 
 1074     (void) AcpiUtAcquireMutex (ACPI_MTX_TABLES);
 1075     if (TableIndex < AcpiGbl_RootTableList.CurrentTableCount)
 1076     {
 1077         AcpiUtReleaseOwnerId (
 1078             &(AcpiGbl_RootTableList.Tables[TableIndex].OwnerId));
 1079         Status = AE_OK;
 1080     }
 1081 
 1082     (void) AcpiUtReleaseMutex (ACPI_MTX_TABLES);
 1083     return_ACPI_STATUS (Status);
 1084 }
 1085 
 1086 
 1087 /*******************************************************************************
 1088  *
 1089  * FUNCTION:    AcpiTbGetOwnerId
 1090  *
 1091  * PARAMETERS:  TableIndex          - Table index
 1092  *              OwnerId             - Where the table OwnerId is returned
 1093  *
 1094  * RETURN:      Status
 1095  *
 1096  * DESCRIPTION: returns OwnerId for the ACPI table
 1097  *
 1098  ******************************************************************************/
 1099 
 1100 ACPI_STATUS
 1101 AcpiTbGetOwnerId (
 1102     UINT32                  TableIndex,
 1103     ACPI_OWNER_ID           *OwnerId)
 1104 {
 1105     ACPI_STATUS             Status = AE_BAD_PARAMETER;
 1106 
 1107 
 1108     ACPI_FUNCTION_TRACE (TbGetOwnerId);
 1109 
 1110 
 1111     (void) AcpiUtAcquireMutex (ACPI_MTX_TABLES);
 1112     if (TableIndex < AcpiGbl_RootTableList.CurrentTableCount)
 1113     {
 1114         *OwnerId = AcpiGbl_RootTableList.Tables[TableIndex].OwnerId;
 1115         Status = AE_OK;
 1116     }
 1117 
 1118     (void) AcpiUtReleaseMutex (ACPI_MTX_TABLES);
 1119     return_ACPI_STATUS (Status);
 1120 }
 1121 
 1122 
 1123 /*******************************************************************************
 1124  *
 1125  * FUNCTION:    AcpiTbIsTableLoaded
 1126  *
 1127  * PARAMETERS:  TableIndex          - Index into the root table
 1128  *
 1129  * RETURN:      Table Loaded Flag
 1130  *
 1131  ******************************************************************************/
 1132 
 1133 BOOLEAN
 1134 AcpiTbIsTableLoaded (
 1135     UINT32                  TableIndex)
 1136 {
 1137     BOOLEAN                 IsLoaded = FALSE;
 1138 
 1139 
 1140     (void) AcpiUtAcquireMutex (ACPI_MTX_TABLES);
 1141     if (TableIndex < AcpiGbl_RootTableList.CurrentTableCount)
 1142     {
 1143         IsLoaded = (BOOLEAN)
 1144             (AcpiGbl_RootTableList.Tables[TableIndex].Flags &
 1145             ACPI_TABLE_IS_LOADED);
 1146     }
 1147 
 1148     (void) AcpiUtReleaseMutex (ACPI_MTX_TABLES);
 1149     return (IsLoaded);
 1150 }
 1151 
 1152 
 1153 /*******************************************************************************
 1154  *
 1155  * FUNCTION:    AcpiTbSetTableLoadedFlag
 1156  *
 1157  * PARAMETERS:  TableIndex          - Table index
 1158  *              IsLoaded            - TRUE if table is loaded, FALSE otherwise
 1159  *
 1160  * RETURN:      None
 1161  *
 1162  * DESCRIPTION: Sets the table loaded flag to either TRUE or FALSE.
 1163  *
 1164  ******************************************************************************/
 1165 
 1166 void
 1167 AcpiTbSetTableLoadedFlag (
 1168     UINT32                  TableIndex,
 1169     BOOLEAN                 IsLoaded)
 1170 {
 1171 
 1172     (void) AcpiUtAcquireMutex (ACPI_MTX_TABLES);
 1173     if (TableIndex < AcpiGbl_RootTableList.CurrentTableCount)
 1174     {
 1175         if (IsLoaded)
 1176         {
 1177             AcpiGbl_RootTableList.Tables[TableIndex].Flags |=
 1178                 ACPI_TABLE_IS_LOADED;
 1179         }
 1180         else
 1181         {
 1182             AcpiGbl_RootTableList.Tables[TableIndex].Flags &=
 1183                 ~ACPI_TABLE_IS_LOADED;
 1184         }
 1185     }
 1186 
 1187     (void) AcpiUtReleaseMutex (ACPI_MTX_TABLES);
 1188 }
 1189 
 1190 
 1191 /*******************************************************************************
 1192  *
 1193  * FUNCTION:    AcpiTbLoadTable
 1194  *
 1195  * PARAMETERS:  TableIndex              - Table index
 1196  *              ParentNode              - Where table index is returned
 1197  *
 1198  * RETURN:      Status
 1199  *
 1200  * DESCRIPTION: Load an ACPI table
 1201  *
 1202  ******************************************************************************/
 1203 
 1204 ACPI_STATUS
 1205 AcpiTbLoadTable (
 1206     UINT32                  TableIndex,
 1207     ACPI_NAMESPACE_NODE     *ParentNode)
 1208 {
 1209     ACPI_TABLE_HEADER       *Table;
 1210     ACPI_STATUS             Status;
 1211     ACPI_OWNER_ID           OwnerId;
 1212 
 1213 
 1214     ACPI_FUNCTION_TRACE (TbLoadTable);
 1215 
 1216 
 1217     /*
 1218      * Note: Now table is "INSTALLED", it must be validated before
 1219      * using.
 1220      */
 1221     Status = AcpiGetTableByIndex (TableIndex, &Table);
 1222     if (ACPI_FAILURE (Status))
 1223     {
 1224         return_ACPI_STATUS (Status);
 1225     }
 1226 
 1227     Status = AcpiNsLoadTable (TableIndex, ParentNode);
 1228     if (ACPI_FAILURE (Status))
 1229     {
 1230         return_ACPI_STATUS (Status);
 1231     }
 1232 
 1233     /*
 1234      * Update GPEs for any new _Lxx/_Exx methods. Ignore errors. The host is
 1235      * responsible for discovering any new wake GPEs by running _PRW methods
 1236      * that may have been loaded by this table.
 1237      */
 1238     Status = AcpiTbGetOwnerId (TableIndex, &OwnerId);
 1239     if (ACPI_SUCCESS (Status))
 1240     {
 1241         AcpiEvUpdateGpes (OwnerId);
 1242     }
 1243 
 1244     /* Invoke table handler */
 1245 
 1246     AcpiTbNotifyTable (ACPI_TABLE_EVENT_LOAD, Table);
 1247     return_ACPI_STATUS (Status);
 1248 }
 1249 
 1250 
 1251 /*******************************************************************************
 1252  *
 1253  * FUNCTION:    AcpiTbInstallAndLoadTable
 1254  *
 1255  * PARAMETERS:  Address                 - Physical address of the table
 1256  *              Flags                   - Allocation flags of the table
 1257  *              Table                   - Pointer to the table (required for
 1258  *                                        virtual origins, optional for
 1259  *                                        physical)
 1260  *              Override                - Whether override should be performed
 1261  *              TableIndex              - Where table index is returned
 1262  *
 1263  * RETURN:      Status
 1264  *
 1265  * DESCRIPTION: Install and load an ACPI table
 1266  *
 1267  ******************************************************************************/
 1268 
 1269 ACPI_STATUS
 1270 AcpiTbInstallAndLoadTable (
 1271     ACPI_PHYSICAL_ADDRESS   Address,
 1272     UINT8                   Flags,
 1273     ACPI_TABLE_HEADER       *Table,
 1274     BOOLEAN                 Override,
 1275     UINT32                  *TableIndex)
 1276 {
 1277     ACPI_STATUS             Status;
 1278     UINT32                  i;
 1279 
 1280 
 1281     ACPI_FUNCTION_TRACE (TbInstallAndLoadTable);
 1282 
 1283 
 1284     /* Install the table and load it into the namespace */
 1285 
 1286     Status = AcpiTbInstallStandardTable (Address, Flags, Table, TRUE,
 1287         Override, &i);
 1288     if (ACPI_FAILURE (Status))
 1289     {
 1290         goto Exit;
 1291     }
 1292 
 1293     Status = AcpiTbLoadTable (i, AcpiGbl_RootNode);
 1294 
 1295 Exit:
 1296     *TableIndex = i;
 1297     return_ACPI_STATUS (Status);
 1298 }
 1299 
 1300 
 1301 /*******************************************************************************
 1302  *
 1303  * FUNCTION:    AcpiTbUnloadTable
 1304  *
 1305  * PARAMETERS:  TableIndex              - Table index
 1306  *
 1307  * RETURN:      Status
 1308  *
 1309  * DESCRIPTION: Unload an ACPI table
 1310  *
 1311  ******************************************************************************/
 1312 
 1313 ACPI_STATUS
 1314 AcpiTbUnloadTable (
 1315     UINT32                  TableIndex)
 1316 {
 1317     ACPI_STATUS             Status = AE_OK;
 1318     ACPI_TABLE_HEADER       *Table;
 1319 
 1320 
 1321     ACPI_FUNCTION_TRACE (TbUnloadTable);
 1322 
 1323 
 1324     /* Ensure the table is still loaded */
 1325 
 1326     if (!AcpiTbIsTableLoaded (TableIndex))
 1327     {
 1328         return_ACPI_STATUS (AE_NOT_EXIST);
 1329     }
 1330 
 1331     /* Invoke table handler */
 1332 
 1333     Status = AcpiGetTableByIndex (TableIndex, &Table);
 1334     if (ACPI_SUCCESS (Status))
 1335     {
 1336         AcpiTbNotifyTable (ACPI_TABLE_EVENT_UNLOAD, Table);
 1337     }
 1338 
 1339     /* Delete the portion of the namespace owned by this table */
 1340 
 1341     Status = AcpiTbDeleteNamespaceByOwner (TableIndex);
 1342     if (ACPI_FAILURE (Status))
 1343     {
 1344         return_ACPI_STATUS (Status);
 1345     }
 1346 
 1347     (void) AcpiTbReleaseOwnerId (TableIndex);
 1348     AcpiTbSetTableLoadedFlag (TableIndex, FALSE);
 1349     return_ACPI_STATUS (Status);
 1350 }
 1351 
 1352 
 1353 /*******************************************************************************
 1354  *
 1355  * FUNCTION:    AcpiTbNotifyTable
 1356  *
 1357  * PARAMETERS:  Event               - Table event
 1358  *              Table               - Validated table pointer
 1359  *
 1360  * RETURN:      None
 1361  *
 1362  * DESCRIPTION: Notify a table event to the users.
 1363  *
 1364  ******************************************************************************/
 1365 
 1366 void
 1367 AcpiTbNotifyTable (
 1368     UINT32                          Event,
 1369     void                            *Table)
 1370 {
 1371     /* Invoke table handler if present */
 1372 
 1373     if (AcpiGbl_TableHandler)
 1374     {
 1375         (void) AcpiGbl_TableHandler (Event, Table,
 1376             AcpiGbl_TableHandlerContext);
 1377     }
 1378 }

Cache object: f4c94e9981738561fcb3d7b482dda907


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.