Changeset 108234 in vbox
- Timestamp:
- Feb 16, 2025 2:20:28 PM (2 months ago)
- svn:sync-xref-src-repo-rev:
- 167555
- Location:
- trunk/src/VBox/Runtime
- Files:
-
- 4 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Runtime/common/acpi/acpi-ast.cpp
r108230 r108234 92 92 93 93 94 DECLHIDDEN(int) rtAcpiAstNodeTransform(PRTACPIASTNODE pAstNd, PRTERRINFO pErrInfo)95 {96 #if 097 /* Walk all arguments containing AST nodes first. */98 for (uint8_t i = 0; i < pAstNd->cArgs; i++)99 {100 if ( pAstNd->aArgs[i].enmType == kAcpiAstArgType_AstNode101 && pAstNd->aArgs[i].u.pAstNd)102 {103 int rc = rtAcpiAstNodeTransform(pAstNd->aArgs[i].u.pAstNd, pErrInfo);104 if (RT_FAILURE(rc))105 return rc;106 }107 }108 109 if (pAstNd->fFlags & RTACPI_AST_NODE_F_NEW_SCOPE)110 {111 PRTACPIASTNODE pIt/*, pItPrev*/;112 /* Do transformations on the nodes first. */113 RTListForEach(&pAstNd->LstScopeNodes, pIt, RTACPIASTNODE, NdAst)114 {115 int rc = rtAcpiAstNodeTransform(pIt, pErrInfo);116 if (RT_FAILURE(rc))117 return rc;118 }119 120 /* Now do transformations on our level. */121 RTListForEachReverseSafe(&pAstNd->LstScopeNodes, pIt, pItPrev, RTACPIASTNODE, NdAst)122 {123 /*124 * If there is an If AST node followed by Else we move the Else branch as the last125 * statement in the If because when emitting to AML the Else is enclosed in the If126 * package.127 */128 if ( pIt->enmOp == kAcpiAstNodeOp_Else129 && pItPrev130 && pItPrev->enmOp == kAcpiAstNodeOp_If)131 {132 RTListNodeRemove(&pIt->NdAst);133 RTListAppend(&pItPrev->LstScopeNodes, &pIt->NdAst);134 }135 }136 }137 #else138 RT_NOREF(pAstNd, pErrInfo);139 #endif140 141 return VINF_SUCCESS;142 }143 144 145 94 /** 146 95 * Evaluates the given AST node to an integer if possible. 147 96 * 148 97 * @returns IPRT status code. 149 * @param pAstNd The AST node to evaluate. 150 * @param pNsRoot The namespace root this AST belongs to. 151 * @param pu64 Where to store the integer on success. 98 * @param pAstNd The AST node to evaluate. 99 * @param pNsRoot The namespace root this AST belongs to. 100 * @param fResolveIdentifiers Flag whether to try resolving identifiers to constant integers. 101 * @param pu64 Where to store the integer on success. 152 102 */ 153 static int rtAcpiAstNodeEvaluateToInteger(PCRTACPIASTNODE pAstNd, PRTACPINSROOT pNsRoot, uint64_t *pu64)103 static int rtAcpiAstNodeEvaluateToInteger(PCRTACPIASTNODE pAstNd, PRTACPINSROOT pNsRoot, bool fResolveIdentifiers, uint64_t *pu64) 154 104 { 155 105 /* Easy way out?. */ … … 172 122 } 173 123 174 if (pAstNd->enmOp == kAcpiAstNodeOp_Identifier) 124 if ( pAstNd->enmOp == kAcpiAstNodeOp_Identifier 125 && fResolveIdentifiers) 175 126 { 176 127 /* Look it up in the namespace and use the result. */ … … 178 129 if (!pNsEntry) 179 130 return VERR_NOT_FOUND; 180 181 *pu64 = pNsEntry->offBits; 131 if (pNsEntry->enmType != kAcpiNsEntryType_ResourceField) 132 return VERR_NOT_SUPPORTED; 133 134 *pu64 = pNsEntry->RsrcFld.offBits; 182 135 return VINF_SUCCESS; 183 136 } … … 185 138 /** @todo */ 186 139 return VERR_NOT_IMPLEMENTED; 140 } 141 142 143 DECLHIDDEN(int) rtAcpiAstNodeTransform(PRTACPIASTNODE pAstNd, PRTACPINSROOT pNsRoot, PRTERRINFO pErrInfo) 144 { 145 /* Walk all arguments containing AST nodes first. */ 146 for (uint8_t i = 0; i < pAstNd->cArgs; i++) 147 { 148 if ( pAstNd->aArgs[i].enmType == kAcpiAstArgType_AstNode 149 && pAstNd->aArgs[i].u.pAstNd) 150 { 151 int rc = rtAcpiAstNodeTransform(pAstNd->aArgs[i].u.pAstNd, pNsRoot, pErrInfo); 152 if (RT_FAILURE(rc)) 153 return rc; 154 } 155 } 156 157 if (pAstNd->fFlags & RTACPI_AST_NODE_F_NEW_SCOPE) 158 { 159 PRTACPIASTNODE pIt/*, pItPrev*/; 160 /* Do transformations on the nodes first. */ 161 RTListForEach(&pAstNd->LstScopeNodes, pIt, RTACPIASTNODE, NdAst) 162 { 163 int rc = rtAcpiAstNodeTransform(pIt, pNsRoot, pErrInfo); 164 if (RT_FAILURE(rc)) 165 return rc; 166 } 167 } 168 169 /* Now do optimizations we can do here. */ 170 switch (pAstNd->enmOp) 171 { 172 case kAcpiAstNodeOp_ShiftLeft: 173 { 174 /* 175 * If both arguments evaluate to constant integers we can convert this 176 * to the final result. 177 */ 178 /** @todo Skips the 3 operand variant (no target), check what iasl is doing here. */ 179 if (!pAstNd->aArgs[2].u.pAstNd) 180 { 181 uint64_t u64ValToShift = 0; 182 uint64_t u64ValShift = 0; 183 int rc = rtAcpiAstNodeEvaluateToInteger(pAstNd->aArgs[0].u.pAstNd, pNsRoot, false /*fResolveIdentifiers*/, &u64ValToShift); 184 if (RT_SUCCESS(rc)) 185 rc = rtAcpiAstNodeEvaluateToInteger(pAstNd->aArgs[1].u.pAstNd, pNsRoot, false /*fResolveIdentifiers*/, &u64ValShift); 186 if ( RT_SUCCESS(rc) 187 && u64ValShift <= 63) 188 { 189 /** @todo Check overflow handling. */ 190 rtAcpiAstNodeFree(pAstNd->aArgs[0].u.pAstNd); 191 rtAcpiAstNodeFree(pAstNd->aArgs[1].u.pAstNd); 192 193 pAstNd->aArgs[0].u.pAstNd = NULL; 194 pAstNd->aArgs[1].u.pAstNd = NULL; 195 pAstNd->cArgs = 0; 196 pAstNd->enmOp = kAcpiAstNodeOp_Number; 197 pAstNd->u64 = u64ValToShift << u64ValShift; 198 } 199 } 200 break; 201 } 202 default: 203 break; 204 } 205 206 return VINF_SUCCESS; 187 207 } 188 208 … … 548 568 { 549 569 /* Try resolving to a constant expression. */ 550 rc = rtAcpiAstNodeEvaluateToInteger(pAstNd->aArgs[0].u.pAstNd, pNsRoot, &cElems);570 rc = rtAcpiAstNodeEvaluateToInteger(pAstNd->aArgs[0].u.pAstNd, pNsRoot, true /*fResolveIdentifiers*/, &cElems); 551 571 if (RT_FAILURE(rc)) 552 572 break; … … 615 635 /* Try resolving to a constant expression. */ 616 636 uint64_t u64 = 0; 617 rc = rtAcpiAstNodeEvaluateToInteger(pIt, pNsRoot, &u64);637 rc = rtAcpiAstNodeEvaluateToInteger(pIt, pNsRoot, true /*fResolveIdentifiers*/, &u64); 618 638 if (RT_FAILURE(rc)) 619 639 break; … … 832 852 else 833 853 { 834 rc = rtAcpiAstNodeEvaluateToInteger(pAstNd->aArgs[1].u.pAstNd, pNsRoot, &off);854 rc = rtAcpiAstNodeEvaluateToInteger(pAstNd->aArgs[1].u.pAstNd, pNsRoot, true /*fResolveIdentifiers*/, &off); 835 855 off = pAstNd->enmOp == kAcpiAstNodeOp_CreateBitField ? off : off / 8; 836 856 } -
trunk/src/VBox/Runtime/common/acpi/acpi-compiler.cpp
r108230 r108234 2989 2989 { 2990 2990 /* 2. - Optimize AST (constant folding, etc). */ 2991 PRTACPIASTNODE pIt; 2992 RTListForEach(&pThis->LstStmts, pIt, RTACPIASTNODE, NdAst) 2993 { 2994 rc = rtAcpiAstNodeTransform(pIt, pThis->pNs, pErrInfo); 2995 if (RT_FAILURE(rc)) 2996 break; 2997 } 2991 2998 2992 2999 /* 3. - Traverse AST and output table. */ … … 3012 3019 if (RT_SUCCESS(rc)) 3013 3020 { 3014 PRTACPIASTNODEpIt;3021 pIt; 3015 3022 RTListForEach(&pThis->LstStmts, pIt, RTACPIASTNODE, NdAst) 3016 3023 { 3017 rc = rtAcpiAstNodeTransform(pIt, pErrInfo);3018 if (RT_FAILURE(rc))3019 break;3020 3021 3024 rc = rtAcpiAstDumpToTbl(pIt, pThis->pNs, pThis->hAcpiTbl); 3022 3025 if (RT_FAILURE(rc)) -
trunk/src/VBox/Runtime/common/acpi/acpi-ns.cpp
r108230 r108234 231 231 * @returns IPRT status code. 232 232 * @param pNsRoot The namespace to add the new entry to. 233 * @param enmType The type of the namespace entry. 233 234 * @param pszNameString The namestring to add. 234 235 * @param fSwitchTo Flag whether to switch to the new entry. … … 236 237 * @param ppNsEntry Where to store the pointer to the created entry on success. 237 238 */ 238 static int rtAcpiNsAddEntryWorker(PRTACPINSROOT pNsRoot, const char *pszNameString, bool fSwitchTo, bool fIgnoreExisting, PRTACPINSENTRY *ppNsEntry)239 static int rtAcpiNsAddEntryWorker(PRTACPINSROOT pNsRoot, RTACPINSENTRYTYPE enmType, const char *pszNameString, bool fSwitchTo, bool fIgnoreExisting, PRTACPINSENTRY *ppNsEntry) 239 240 { 240 241 AssertReturn( !fSwitchTo … … 263 264 if (pNsEntry) 264 265 { 266 pNsEntry->enmType = enmType; 265 267 pNsEntry->pParent = pNsEntryParent; 266 268 RTListInit(&pNsEntry->LstNsEntries); … … 340 342 { 341 343 PRTACPINSENTRY pNsEntry = NULL; 342 int rc = rtAcpiNsAddEntryWorker(pNsRoot, pszNameString, fSwitchTo, false /*fIgnoreExisting*/, &pNsEntry);344 int rc = rtAcpiNsAddEntryWorker(pNsRoot, kAcpiNsEntryType_AstNode, pszNameString, fSwitchTo, false /*fIgnoreExisting*/, &pNsEntry); 343 345 if (rc == VERR_ALREADY_EXISTS) 344 346 rc = VINF_SUCCESS; 345 347 if (RT_SUCCESS(rc)) 346 {347 pNsEntry->fAstNd = true;348 348 pNsEntry->pAstNd = pAstNd; 349 }350 349 351 350 return rc; … … 356 355 { 357 356 PRTACPINSENTRY pNsEntry = NULL; 358 int rc = rtAcpiNsAddEntryWorker(pNsRoot, pszNameString, false /*fSwitchTo*/, true /*fIgnoreExisting*/, &pNsEntry);357 int rc = rtAcpiNsAddEntryWorker(pNsRoot, kAcpiNsEntryType_ResourceField, pszNameString, false /*fSwitchTo*/, true /*fIgnoreExisting*/, &pNsEntry); 359 358 if (RT_SUCCESS(rc)) 360 359 { 361 pNsEntry->fAstNd = false; 362 pNsEntry->pAstNd = NULL; 363 pNsEntry->offBits = offBits; 364 pNsEntry->cBits = cBits; 360 pNsEntry->RsrcFld.offBits = offBits; 361 pNsEntry->RsrcFld.cBits = cBits; 365 362 } 366 363 … … 372 369 { 373 370 PRTACPINSENTRY pNsEntry = NULL; 374 int rc = rtAcpiNsAddEntryWorker(pNsRoot, pszNameString, false /*fSwitchTo*/, false /*fIgnoreExisting*/, &pNsEntry);371 int rc = rtAcpiNsAddEntryWorker(pNsRoot, kAcpiNsEntryType_External, pszNameString, false /*fSwitchTo*/, false /*fIgnoreExisting*/, &pNsEntry); 375 372 if (RT_SUCCESS(rc)) 376 {377 pNsEntry->fAstNd = false;378 373 pNsEntry->pExternal = pExternal; 379 }380 374 381 375 return rc; -
trunk/src/VBox/Runtime/include/internal/acpi.h
r108230 r108234 79 79 80 80 /** 81 * ACPI namespace entry type. 82 */ 83 typedef enum RTACPINSENTRYTYPE 84 { 85 /** Invalid type. */ 86 kAcpiNsEntryType_Invalid = 0, 87 /** Namespace entry points to an AST node. */ 88 kAcpiNsEntryType_AstNode, 89 /** Namesapce entry points to an external declaration. */ 90 kAcpiNsEntryType_External, 91 /** Namespace entry is a resource field containing an offset and number of bits. */ 92 kAcpiNsEntryType_ResourceField, 93 /** 32bit hack. */ 94 kAcpiNsEntryType_32Bit_Hack = 0x7fffffff 95 } RTACPINSENTRYTYPE; 96 97 98 /** 81 99 * An ACPI namespace entry. 82 100 */ … … 89 107 /** The name segment identifying the entry. */ 90 108 char achNameSeg[4]; 91 /** Flag whether this points to an AST node or an external. */92 bool fAstNd;109 /** Namespace entry type.. */ 110 RTACPINSENTRYTYPE enmType; 93 111 /** Type dependent data. */ 94 112 union … … 98 116 /** Pointer to the external declaration. */ 99 117 PCRTACPIASLEXTERNAL pExternal; 118 /** Resource field data. */ 119 struct 120 { 121 /** Bit offset for resource fields. */ 122 uint32_t offBits; 123 /** Bit count for resource fields. */ 124 uint32_t cBits; 125 } RsrcFld; 100 126 }; 101 /** Bit offset for resource fields. */102 uint32_t offBits;103 /** Bit count for resource fields. */104 uint32_t cBits;105 127 /** List of namespace entries below this entry. */ 106 128 RTLISTANCHOR LstNsEntries; … … 347 369 * @returns IPRT status. 348 370 * @param pAstNd The AST node to transform. 371 * @param pNsRoot The namespace root. 349 372 * @param pErrInfo Some additional error information on failure. 350 * 351 * @note This currently only implements merging if ... else ... nodes but can be extended to 352 * also do some optimizations and proper checking. 353 */ 354 DECLHIDDEN(int) rtAcpiAstNodeTransform(PRTACPIASTNODE pAstNd, PRTERRINFO pErrInfo); 373 */ 374 DECLHIDDEN(int) rtAcpiAstNodeTransform(PRTACPIASTNODE pAstNd, PRTACPINSROOT pNsRoot, PRTERRINFO pErrInfo); 355 375 356 376
Note:
See TracChangeset
for help on using the changeset viewer.