⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 aslanalyze.c

📁 acpi tools for linux include acpiexec and acpixtract
💻 C
📖 第 1 页 / 共 5 页
字号:
    char                    LocalName[] = "Local0";    char                    ArgName[] = "Arg0";    ACPI_PARSE_OBJECT       *ArgNode;    ACPI_PARSE_OBJECT       *NextType;    ACPI_PARSE_OBJECT       *NextParamType;    UINT8                   ActualArgs = 0;    switch (Op->Asl.ParseOpcode)    {    case PARSEOP_METHOD:        TotalMethods++;        /* Create and init method info */        MethodInfo       = UtLocalCalloc (sizeof (ASL_METHOD_INFO));        MethodInfo->Next = WalkInfo->MethodStack;        MethodInfo->Op = Op;        WalkInfo->MethodStack = MethodInfo;        /* Get the name node, ignored here */        Next = Op->Asl.Child;        /* Get the NumArguments node */        Next = Next->Asl.Next;        MethodInfo->NumArguments = (UINT8)            (((UINT8) Next->Asl.Value.Integer) & 0x07);        /* Get the SerializeRule and SyncLevel nodes, ignored here */        Next = Next->Asl.Next;        Next = Next->Asl.Next;        ArgNode = Next;        /* Get the ReturnType node */        Next = Next->Asl.Next;        NextType = Next->Asl.Child;        while (NextType)        {            /* Get and map each of the ReturnTypes */            MethodInfo->ValidReturnTypes |= AnMapObjTypeToBtype (NextType);            NextType->Asl.ParseOpcode = PARSEOP_DEFAULT_ARG;            NextType = NextType->Asl.Next;        }        /* Get the ParameterType node */        Next = Next->Asl.Next;        NextType = Next->Asl.Child;        while (NextType)        {            if (NextType->Asl.ParseOpcode == PARSEOP_DEFAULT_ARG)            {                NextParamType = NextType->Asl.Child;                while (NextParamType)                {                    MethodInfo->ValidArgTypes[ActualArgs] |= AnMapObjTypeToBtype (NextParamType);                    NextParamType->Asl.ParseOpcode = PARSEOP_DEFAULT_ARG;                    NextParamType = NextParamType->Asl.Next;                }            }            else            {                MethodInfo->ValidArgTypes[ActualArgs] =                    AnMapObjTypeToBtype (NextType);                NextType->Asl.ParseOpcode = PARSEOP_DEFAULT_ARG;                ActualArgs++;            }            NextType = NextType->Asl.Next;        }        if ((MethodInfo->NumArguments) &&            (MethodInfo->NumArguments != ActualArgs))        {            /* error: Param list did not match number of args */        }        /* Allow numarguments == 0 for Function() */        if ((!MethodInfo->NumArguments) && (ActualArgs))        {            MethodInfo->NumArguments = ActualArgs;            ArgNode->Asl.Value.Integer |= ActualArgs;        }        /*         * Actual arguments are initialized at method entry.         * All other ArgX "registers" can be used as locals, so we         * track their initialization.         */        for (i = 0; i < MethodInfo->NumArguments; i++)        {            MethodInfo->ArgInitialized[i] = TRUE;        }        break;    case PARSEOP_METHODCALL:        if (MethodInfo &&           (Op->Asl.Node == MethodInfo->Op->Asl.Node))        {            AslError (ASL_REMARK, ASL_MSG_RECURSION, Op, Op->Asl.ExternalName);        }        break;    case PARSEOP_LOCAL0:    case PARSEOP_LOCAL1:    case PARSEOP_LOCAL2:    case PARSEOP_LOCAL3:    case PARSEOP_LOCAL4:    case PARSEOP_LOCAL5:    case PARSEOP_LOCAL6:    case PARSEOP_LOCAL7:        if (!MethodInfo)        {            /*             * Probably was an error in the method declaration,             * no additional error here             */            ACPI_WARNING ((AE_INFO, "%p, No parent method", Op));            return (AE_ERROR);        }        RegisterNumber = (Op->Asl.AmlOpcode & 0x000F);        /*         * If the local is being used as a target, mark the local         * initialized         */        if (Op->Asl.CompileFlags & NODE_IS_TARGET)        {            MethodInfo->LocalInitialized[RegisterNumber] = TRUE;        }        /*         * Otherwise, this is a reference, check if the local         * has been previously initialized.         *         * The only operator that accepts an uninitialized value is ObjectType()         */        else if ((!MethodInfo->LocalInitialized[RegisterNumber]) &&                 (Op->Asl.Parent->Asl.ParseOpcode != PARSEOP_OBJECTTYPE))        {            LocalName[strlen (LocalName) -1] = (char) (RegisterNumber + 0x30);            AslError (ASL_ERROR, ASL_MSG_LOCAL_INIT, Op, LocalName);        }        break;    case PARSEOP_ARG0:    case PARSEOP_ARG1:    case PARSEOP_ARG2:    case PARSEOP_ARG3:    case PARSEOP_ARG4:    case PARSEOP_ARG5:    case PARSEOP_ARG6:        if (!MethodInfo)        {            /*             * Probably was an error in the method declaration,             * no additional error here             */            ACPI_WARNING ((AE_INFO, "%p, No parent method", Op));            return (AE_ERROR);        }        RegisterNumber = (Op->Asl.AmlOpcode & 0x000F) - 8;        ArgName[strlen (ArgName) -1] = (char) (RegisterNumber + 0x30);        /*         * If the Arg is being used as a target, mark the local         * initialized         */        if (Op->Asl.CompileFlags & NODE_IS_TARGET)        {            MethodInfo->ArgInitialized[RegisterNumber] = TRUE;        }        /*         * Otherwise, this is a reference, check if the Arg         * has been previously initialized.         *         * The only operator that accepts an uninitialized value is ObjectType()         */        else if ((!MethodInfo->ArgInitialized[RegisterNumber]) &&                 (Op->Asl.Parent->Asl.ParseOpcode != PARSEOP_OBJECTTYPE))        {            AslError (ASL_ERROR, ASL_MSG_ARG_INIT, Op, ArgName);        }        /* Flag this arg if it is not a "real" argument to the method */        if (RegisterNumber >= MethodInfo->NumArguments)        {            AslError (ASL_REMARK, ASL_MSG_NOT_PARAMETER, Op, ArgName);        }        break;    case PARSEOP_RETURN:        if (!MethodInfo)        {            /*             * Probably was an error in the method declaration,             * no additional error here             */            ACPI_WARNING ((AE_INFO, "%p, No parent method", Op));            return (AE_ERROR);        }        /* Child indicates a return value */        if ((Op->Asl.Child) &&            (Op->Asl.Child->Asl.ParseOpcode != PARSEOP_DEFAULT_ARG))        {            MethodInfo->NumReturnWithValue++;        }        else        {            MethodInfo->NumReturnNoValue++;        }        break;    case PARSEOP_BREAK:    case PARSEOP_CONTINUE:        Next = Op->Asl.Parent;        while (Next)        {            if (Next->Asl.ParseOpcode == PARSEOP_WHILE)            {                break;            }            Next = Next->Asl.Parent;        }        if (!Next)        {            AslError (ASL_ERROR, ASL_MSG_NO_WHILE, Op, NULL);        }        break;    case PARSEOP_STALL:        /* We can range check if the argument is an integer */        if ((Op->Asl.Child->Asl.ParseOpcode == PARSEOP_INTEGER) &&            (Op->Asl.Child->Asl.Value.Integer > ACPI_UINT8_MAX))        {            AslError (ASL_ERROR, ASL_MSG_INVALID_TIME, Op, NULL);        }        break;    case PARSEOP_DEVICE:    case PARSEOP_EVENT:    case PARSEOP_MUTEX:    case PARSEOP_OPERATIONREGION:    case PARSEOP_POWERRESOURCE:    case PARSEOP_PROCESSOR:    case PARSEOP_THERMALZONE:        /*         * The first operand is a name to be created in the namespace.         * Check against the reserved list.         */        i = AnCheckForReservedName (Op, Op->Asl.NameSeg);        if (i < ACPI_VALID_RESERVED_NAME_MAX)        {            AslError (ASL_ERROR, ASL_MSG_RESERVED_USE, Op, Op->Asl.ExternalName);        }        break;    case PARSEOP_NAME:        i = AnCheckForReservedName (Op, Op->Asl.NameSeg);        if (i < ACPI_VALID_RESERVED_NAME_MAX)        {            if (ReservedMethods[i].NumArguments > 0)            {                /*                 * This reserved name must be a control method because                 * it must have arguments                 */                AslError (ASL_ERROR, ASL_MSG_RESERVED_METHOD, Op,                    "with arguments");            }            /* Typechecking for _HID */            else if (!ACPI_STRCMP (METHOD_NAME__HID, ReservedMethods[i].Name))            {                /* Examine the second operand to typecheck it */                Next = Op->Asl.Child->Asl.Next;                if ((Next->Asl.ParseOpcode != PARSEOP_INTEGER) &&                    (Next->Asl.ParseOpcode != PARSEOP_STRING_LITERAL))                {                    /* _HID must be a string or an integer */                    AslError (ASL_ERROR, ASL_MSG_RESERVED_OPERAND_TYPE, Next,                        "String or Integer");                }                if (Next->Asl.ParseOpcode == PARSEOP_STRING_LITERAL)                {                    /*                     * _HID is a string, all characters must be alphanumeric.                     * One of the things we want to catch here is the use of                     * a leading asterisk in the string.                     */                    for (i = 0; Next->Asl.Value.String[i]; i++)                    {                        if (!isalnum (Next->Asl.Value.String[i]))                        {                            AslError (ASL_ERROR, ASL_MSG_ALPHANUMERIC_STRING,                                Next, Next->Asl.Value.String);                            break;                        }                    }                }            }        }        break;    default:        break;    }    return AE_OK;}/******************************************************************************* * * FUNCTION:    AnLastStatementIsReturn * * PARAMETERS:  Op            - A method parse node * * RETURN:      TRUE if last statement is an ASL RETURN. False otherwise * * DESCRIPTION: Walk down the list of top level statements within a method *              to find the last one. Check if that last statement is in *              fact a RETURN statement. * ******************************************************************************/static BOOLEANAnLastStatementIsReturn (    ACPI_PARSE_OBJECT       *Op){    ACPI_PARSE_OBJECT       *Next;    /*     * Check if last statement is a return     */    Next = ASL_GET_CHILD_NODE (Op);    while (Next)    {        if ((!Next->Asl.Next) &&            (Next->Asl.ParseOpcode == PARSEOP_RETURN))        {            return TRUE;        }        Next = ASL_GET_PEER_NODE (Next);    }    return FALSE;}/******************************************************************************* * * FUNCTION:    AnMethodAnalysisWalkEnd * * PARAMETERS:  ASL_WALK_CALLBACK * * RETURN:      Status * * DESCRIPTION: Ascending callback for analysis walk. Complete method *              return analysis. * ******************************************************************************/ACPI_STATUSAnMethodAnalysisWalkEnd (    ACPI_PARSE_OBJECT       *Op,    UINT32                  Level,    void                    *Context){    ASL_ANALYSIS_WALK_INFO  *WalkInfo = (ASL_ANALYSIS_WALK_INFO *) Context;    ASL_METHOD_INFO         *MethodInfo = WalkInfo->MethodStack;    switch (Op->Asl.ParseOpcode)    {    case PARSEOP_METHOD:    case PARSEOP_RETURN:        if (!MethodInfo)        {            printf ("No method info for method! [%s]\n", Op->Asl.Namepath);            AslError (ASL_ERROR, ASL_MSG_COMPILER_INTERNAL, Op,                "No method info for this method");            CmCleanupAndExit ();            return (AE_AML_INTERNAL);        }        break;    default:        break;    }    switch (Op->Asl.ParseOpcode)    {    case PARSEOP_METHOD:        WalkInfo->MethodStack = MethodInfo->Next;        /*         * Check if there is no return statement at the end of the         * method AND we can actually get there -- i.e., the execution         * of the method can possibly terminate without a return statement.         */

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -