- Timestamp:
- Jan 28, 2025 3:48:44 PM (3 months ago)
- svn:sync-xref-src-repo-rev:
- 167225
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Runtime/common/misc/acpi-decompiler.cpp
r107955 r107971 221 221 222 222 223 DECLINLINE(int) rtAcpiTblAmlDecodeReadU64(PRTACPITBLAMLDECODE pThis, uint64_t *pu64, PRTERRINFO pErrInfo) 224 { 225 if (pThis->offTbl <= pThis->cbTbl + sizeof(uint64_t)) 226 { /* probable */ } 227 else 228 return RTErrInfoSetF(pErrInfo, VERR_EOF, "AML stream ended prematurely at offset '%#x' trying to read eight bytes", pThis->offTbl); 229 230 if (pThis->pacbPkgLeft[pThis->iLvl] < sizeof(uint64_t)) 231 return RTErrInfoSetF(pErrInfo, VERR_INVALID_STATE, "Data overflows current package limitation"); 232 233 pThis->pacbPkgLeft[pThis->iLvl] -= sizeof(uint64_t); 234 235 *pu64 = pThis->pbTbl[pThis->offTbl++]; 236 *pu64 |= (uint64_t)pThis->pbTbl[pThis->offTbl++] << 8; 237 *pu64 |= (uint64_t)pThis->pbTbl[pThis->offTbl++] << 16; 238 *pu64 |= (uint64_t)pThis->pbTbl[pThis->offTbl++] << 24; 239 *pu64 |= (uint64_t)pThis->pbTbl[pThis->offTbl++] << 32; 240 *pu64 |= (uint64_t)pThis->pbTbl[pThis->offTbl++] << 40; 241 *pu64 |= (uint64_t)pThis->pbTbl[pThis->offTbl++] << 48; 242 *pu64 |= (uint64_t)pThis->pbTbl[pThis->offTbl++] << 54; 243 return VINF_SUCCESS; 244 } 245 246 223 247 static int rtAcpiTblAmlDecodeNameSeg(PRTACPITBLAMLDECODE pThis, char *pszNameString, PRTERRINFO pErrInfo) 224 248 { … … 233 257 if ( abNameSeg[0] != '_' 234 258 && !RTLocCIsUpper(abNameSeg[0])) 235 return RTErrInfoSetF(pErrInfo, VERR_INVALID_PARAMETER, "AML stream contains invalid lead name character '% c'", abNameSeg[0]);259 return RTErrInfoSetF(pErrInfo, VERR_INVALID_PARAMETER, "AML stream contains invalid lead name character '%#02RX8'", abNameSeg[0]); 236 260 237 261 for (uint8_t i = 1; i < sizeof(abNameSeg); i++) … … 240 264 && !RTLocCIsUpper(abNameSeg[i]) 241 265 && !RTLocCIsDigit(abNameSeg[i])) 242 return RTErrInfoSetF(pErrInfo, VERR_INVALID_PARAMETER, "AML stream contains invalid name character '% c'", abNameSeg[i]);266 return RTErrInfoSetF(pErrInfo, VERR_INVALID_PARAMETER, "AML stream contains invalid name character '%#02RX8", abNameSeg[i]); 243 267 } 244 268 … … 263 287 if ( bLeadChar != '_' 264 288 && !RTLocCIsUpper(bLeadChar)) 265 return RTErrInfoSetF(pErrInfo, VERR_INVALID_PARAMETER, "AML stream contains invalid lead name character '% c'", bLeadChar);289 return RTErrInfoSetF(pErrInfo, VERR_INVALID_PARAMETER, "AML stream contains invalid lead name character '%#02RX8'", bLeadChar); 266 290 267 291 for (uint8_t i = 1; i < sizeof(abNameSeg); i++) … … 270 294 && !RTLocCIsUpper(abNameSeg[i]) 271 295 && !RTLocCIsDigit(abNameSeg[i])) 272 return RTErrInfoSetF(pErrInfo, VERR_INVALID_PARAMETER, "AML stream contains invalid name character '% c'", abNameSeg[i]);296 return RTErrInfoSetF(pErrInfo, VERR_INVALID_PARAMETER, "AML stream contains invalid name character '%#02RX8'", abNameSeg[i]); 273 297 } 274 298 … … 281 305 282 306 283 284 static int rtAcpiTblAmlDecodeNameString(PRTACPITBLAMLDECODE pThis, char *pszNameString, size_t cchNameString, size_t *pcbNameString, PRTERRINFO pErrInfo) 307 static int rtAcpiTblAmlDecodeNameStringWithLead(PRTACPITBLAMLDECODE pThis, uint8_t bLeadChar, char *pszNameString, size_t cchNameString, size_t *pcbNameString, PRTERRINFO pErrInfo) 285 308 { 286 309 AssertReturn(cchNameString >= 5, VERR_INVALID_PARAMETER); /* One name segment is at least 4 bytes (+ terminator). */ 287 310 288 311 /* Check for a root path. */ 289 uint8_t bTmp = 0; /* shut up gcc */ 290 int rc = rtAcpiTblAmlDecodeReadU8(pThis, &bTmp, pErrInfo); 291 if (RT_FAILURE(rc)) return rc; 292 312 int rc = VINF_SUCCESS; 313 uint8_t bTmp = bLeadChar; 293 314 size_t idxName = 0; 294 315 if (bTmp == '\\') … … 313 334 314 335 if (idxName == cchNameString - 1) 315 r c =RTErrInfoSetF(pErrInfo, VERR_BUFFER_OVERFLOW, "PrefixPath in AML byte stream is too long to fit into a %zu byte buffer",316 cchNameString - 1);336 return RTErrInfoSetF(pErrInfo, VERR_BUFFER_OVERFLOW, "PrefixPath in AML byte stream is too long to fit into a %zu byte buffer", 337 cchNameString - 1); 317 338 318 339 pszNameString[idxName++] = '^'; … … 322 343 if (bTmp == ACPI_AML_BYTE_CODE_PREFIX_DUAL_NAME) 323 344 { 324 if (idxName + 8 < =cchNameString)345 if (idxName + 8 < cchNameString) 325 346 { 326 347 rc = rtAcpiTblAmlDecodeNameSeg(pThis, &pszNameString[idxName], pErrInfo); … … 339 360 else if (bTmp == ACPI_AML_BYTE_CODE_PREFIX_MULTI_NAME) 340 361 { 341 /** @todo */ 342 AssertReleaseFailed(); 362 uint8_t cSegs = 0; 363 rc = rtAcpiTblAmlDecodeReadU8(pThis, &cSegs, pErrInfo); 364 if (RT_FAILURE(rc)) return rc; 365 366 if (idxName + cSegs * 4 < cchNameString) 367 { 368 for (uint8_t i = 0; i < cSegs; i++) 369 { 370 rc = rtAcpiTblAmlDecodeNameSeg(pThis, &pszNameString[idxName + i * 4], pErrInfo); 371 if (RT_FAILURE(rc)) return rc; 372 } 373 374 idxName += cSegs * 4; 375 pszNameString[idxName] = '\0'; 376 } 377 else 378 rc = RTErrInfoSetF(pErrInfo, VERR_BUFFER_OVERFLOW, "MultiNamePrefix string in AML byte stream is too long to fit into a %zu byte buffer", 379 cchNameString - 1); 343 380 } 344 381 else if (bTmp == ACPI_AML_BYTE_CODE_PREFIX_NULL_NAME) … … 346 383 else 347 384 { 348 if (idxName + 4 < =cchNameString)385 if (idxName + 4 < cchNameString) 349 386 { 350 387 rc = rtAcpiTblAmlDecodeNameSegWithoutLeadChar(pThis, bTmp, &pszNameString[idxName], pErrInfo); … … 361 398 *pcbNameString = idxName; 362 399 return rc; 400 } 401 402 403 static int rtAcpiTblAmlDecodeNameString(PRTACPITBLAMLDECODE pThis, char *pszNameString, size_t cchNameString, size_t *pcbNameString, PRTERRINFO pErrInfo) 404 { 405 AssertReturn(cchNameString >= 5, VERR_INVALID_PARAMETER); /* One name segment is at least 4 bytes (+ terminator). */ 406 407 uint8_t bLead = 0; /* shut up gcc */ 408 int rc = rtAcpiTblAmlDecodeReadU8(pThis, &bLead, pErrInfo); 409 if (RT_FAILURE(rc)) return rc; 410 411 return rtAcpiTblAmlDecodeNameStringWithLead( pThis, bLead, pszNameString, cchNameString, pcbNameString, pErrInfo); 363 412 } 364 413 … … 377 426 ssize_t cch = RTVfsIoStrmPrintf(hVfsIos, " "); 378 427 if (cch != 4) 379 return cch < 0 ? -cch : VERR_BUFFER_UNDERFLOW;428 return cch < 0 ? (int)cch : VERR_BUFFER_UNDERFLOW; 380 429 } 381 430 … … 465 514 pThis->iLvl--; 466 515 467 if (pThis->pacbPkgLeft[pThis->iLvl] < =cbPkg)516 if (pThis->pacbPkgLeft[pThis->iLvl] < cbPkg) 468 517 return RTErrInfoSetF(pErrInfo, VERR_INVALID_STATE, "AML contains invalid package length encoding"); 469 518 … … 475 524 476 525 return VINF_SUCCESS; 526 } 527 528 529 static int rtAcpiTblAmlDecodeIntegerFromPrefix(PRTACPITBLAMLDECODE pThis, uint8_t bPrefix, uint64_t *pu64, size_t cbDecodeMax, size_t *pcbDecoded, PRTERRINFO pErrInfo) 530 { 531 switch (bPrefix) 532 { 533 case ACPI_AML_BYTE_CODE_PREFIX_BYTE: 534 { 535 if (!cbDecodeMax) 536 return RTErrInfoSetF(pErrInfo, VERR_INVALID_STATE, "Not enough data left to decode byte integer in AML stream"); 537 538 uint8_t bInt = 0; 539 int rc = rtAcpiTblAmlDecodeReadU8(pThis, &bInt, pErrInfo); 540 if (RT_FAILURE(rc)) 541 return rc; 542 543 *pu64 = bInt; 544 *pcbDecoded = 2; 545 break; 546 } 547 case ACPI_AML_BYTE_CODE_PREFIX_WORD: 548 { 549 if (cbDecodeMax < 2) 550 return RTErrInfoSetF(pErrInfo, VERR_INVALID_STATE, "Not enough data left to decode word integer in AML stream"); 551 552 uint16_t u16 = 0; 553 int rc = rtAcpiTblAmlDecodeReadU16(pThis, &u16, pErrInfo); 554 if (RT_FAILURE(rc)) 555 return rc; 556 557 *pu64 = u16; 558 *pcbDecoded = 3; 559 break; 560 } 561 case ACPI_AML_BYTE_CODE_PREFIX_DWORD: 562 { 563 if (cbDecodeMax < 4) 564 return RTErrInfoSetF(pErrInfo, VERR_INVALID_STATE, "Not enough data left to decode double word integer in AML stream"); 565 566 uint32_t u32 = 0; 567 int rc = rtAcpiTblAmlDecodeReadU32(pThis, &u32, pErrInfo); 568 if (RT_FAILURE(rc)) 569 return rc; 570 571 *pu64 = u32; 572 *pcbDecoded = 5; 573 break; 574 } 575 case ACPI_AML_BYTE_CODE_PREFIX_QWORD: 576 { 577 if (cbDecodeMax < 8) 578 return RTErrInfoSetF(pErrInfo, VERR_INVALID_STATE, "Not enough data left to decode quad word integer in AML stream"); 579 580 uint64_t u64 = 0; 581 int rc = rtAcpiTblAmlDecodeReadU64(pThis, &u64, pErrInfo); 582 if (RT_FAILURE(rc)) 583 return rc; 584 585 *pu64 = u64; 586 *pcbDecoded = 9; 587 break; 588 } 589 default: 590 return RTErrInfoSetF(pErrInfo, VERR_INVALID_STATE, "Invalid integer prefix '%#02RX8'", bPrefix); 591 } 592 593 return VINF_SUCCESS; 594 } 595 596 597 static int rtAcpiTblAmlDecodeIntegerWorker(PRTACPITBLAMLDECODE pThis, uint64_t *pu64, size_t cbDecodeMax, size_t *pcbDecoded, PRTERRINFO pErrInfo) 598 { 599 AssertReturn(cbDecodeMax >= 1, VERR_INVALID_PARAMETER); 600 601 uint8_t bPrefix = 0; /* shut up gcc */ 602 int rc = rtAcpiTblAmlDecodeReadU8(pThis, &bPrefix, pErrInfo); 603 if (RT_FAILURE(rc)) 604 return rc; 605 606 cbDecodeMax--; 607 return rtAcpiTblAmlDecodeIntegerFromPrefix(pThis, bPrefix, pu64, cbDecodeMax, pcbDecoded, pErrInfo); 608 } 609 610 611 static DECLCALLBACK(int) rtAcpiTblAmlDecodeNameObject(PRTACPITBLAMLDECODE pThis, RTVFSIOSTREAM hVfsIosOut, uint8_t bOp, PRTERRINFO pErrInfo) 612 { 613 char szName[512]; 614 size_t cbName = 0; 615 616 int rc = rtAcpiTblAmlDecodeNameStringWithLead(pThis, bOp, &szName[0], sizeof(szName), &cbName, pErrInfo); 617 if (RT_FAILURE(rc)) return rc; 618 619 return rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "%s", szName); 620 } 621 622 623 static DECLCALLBACK(int) rtAcpiTblAmlDecodeString(PRTACPITBLAMLDECODE pThis, RTVFSIOSTREAM hVfsIosOut, uint8_t bOp, PRTERRINFO pErrInfo) 624 { 625 RT_NOREF(bOp); 626 627 char szStr[512]; 628 uint32_t i = 0; 629 for (;;) 630 { 631 uint8_t bTmp = 0; /* shut up gcc */ 632 int rc = rtAcpiTblAmlDecodeReadU8(pThis, &bTmp, pErrInfo); 633 if (RT_FAILURE(rc)) 634 return rc; 635 636 if (bTmp >= 0x1 && bTmp <= 0x7f) 637 szStr[i++] = (char)bTmp; 638 else if (bTmp == 0x00) 639 { 640 szStr[i++] = '\0'; 641 break; 642 } 643 else 644 return RTErrInfoSetF(pErrInfo, VERR_INVALID_STATE, "Invalid ASCII string character %#x in string", bTmp); 645 646 if (i == sizeof(szStr)) 647 return RTErrInfoSetF(pErrInfo, VERR_BUFFER_OVERFLOW, "ASCII string is out of bounds"); 648 } 649 650 return rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "\"%s\"", szStr); 651 } 652 653 654 static DECLCALLBACK(int) rtAcpiTblAmlDecodeBuffer(PRTACPITBLAMLDECODE pThis, RTVFSIOSTREAM hVfsIosOut, uint8_t bOp, PRTERRINFO pErrInfo) 655 { 656 RT_NOREF(bOp); 657 658 size_t cbPkg = 0; 659 size_t cbPkgLength = 0; 660 int rc = rtAcpiTblAmlDecodePkgLength(pThis, &cbPkg, &cbPkgLength, pErrInfo); 661 if (RT_FAILURE(rc)) 662 return rc; 663 664 cbPkg -= cbPkgLength; 665 uint64_t u64 = 0; 666 size_t cbInt = 0; 667 rc = rtAcpiTblAmlDecodeIntegerWorker(pThis, &u64, cbPkg, &cbInt, pErrInfo); 668 if (RT_FAILURE(rc)) 669 return rc; 670 671 cbPkg -= cbInt; 672 673 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "Buffer (%RU64) {", u64); 674 if (RT_FAILURE(rc)) 675 return rc; 676 677 /* Decode remaining bytes. */ 678 while (cbPkg--) 679 { 680 uint8_t bTmp = 0; 681 rc = rtAcpiTblAmlDecodeReadU8(pThis, &bTmp, pErrInfo); 682 if (RT_FAILURE(rc)) 683 return rc; 684 685 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "%#02RX8%s", bTmp, cbPkg ? "," : ""); 686 if (RT_FAILURE(rc)) 687 return rc; 688 } 689 690 return rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "}"); 691 } 692 693 694 static DECLCALLBACK(int) rtAcpiTblAmlDecodeInteger(PRTACPITBLAMLDECODE pThis, RTVFSIOSTREAM hVfsIosOut, uint8_t bOp, PRTERRINFO pErrInfo) 695 { 696 uint64_t u64 = 0; 697 size_t cbDecoded = 0; 698 int rc = rtAcpiTblAmlDecodeIntegerFromPrefix(pThis, bOp, &u64, sizeof(uint64_t), &cbDecoded, pErrInfo); 699 if (RT_FAILURE(rc)) 700 return rc; 701 702 return rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "%#RX64", u64); 477 703 } 478 704 … … 497 723 #define RTACPI_AML_OPC_SIMPLE_5(a_pszOpc, a_fFlags, a_enmType0, a_enmType1, a_enmType2, a_enmType3, a_enmType4) \ 498 724 { a_pszOpc, a_fFlags, { a_enmType0, a_enmType1, a_enmType2, a_enmType3, a_enmType4 }, NULL } 725 #define RTACPI_AML_OPC_HANDLER(a_pszOpc, a_pfnHandler) \ 726 { a_pszOpc, 0, { kAcpiAmlOpcType_Invalid, kAcpiAmlOpcType_Invalid, kAcpiAmlOpcType_Invalid, kAcpiAmlOpcType_Invalid, kAcpiAmlOpcType_Invalid }, a_pfnHandler } 499 727 500 728 /* 0x00 */ RTACPI_AML_OPC_SIMPLE_0("Zero", RTACPI_AML_OPC_F_NONE), … … 508 736 /* 0x08 */ RTACPI_AML_OPC_SIMPLE_2("Name", 0, kAcpiAmlOpcType_NameString, kAcpiAmlOpcType_TermArg), 509 737 /* 0x09 */ RTACPI_AML_OPC_INVALID, 510 /* 0x0a */ RTACPI_AML_OPC_ INVALID,511 /* 0x0b */ RTACPI_AML_OPC_ INVALID,512 /* 0x0c */ RTACPI_AML_OPC_ INVALID,513 /* 0x0d */ RTACPI_AML_OPC_ INVALID,514 /* 0x0e */ RTACPI_AML_OPC_ INVALID,738 /* 0x0a */ RTACPI_AML_OPC_HANDLER( "ByteInteger", rtAcpiTblAmlDecodeInteger), 739 /* 0x0b */ RTACPI_AML_OPC_HANDLER( "WordInteger", rtAcpiTblAmlDecodeInteger), 740 /* 0x0c */ RTACPI_AML_OPC_HANDLER( "DWordInteger", rtAcpiTblAmlDecodeInteger), 741 /* 0x0d */ RTACPI_AML_OPC_HANDLER( "StringPrefix", rtAcpiTblAmlDecodeString), 742 /* 0x0e */ RTACPI_AML_OPC_HANDLER( "QWordInteger", rtAcpiTblAmlDecodeInteger), 515 743 /* 0x0f */ RTACPI_AML_OPC_INVALID, 516 744 517 745 /* 0x10 */ RTACPI_AML_OPC_SIMPLE_1("Scope", RTACPI_AML_OPC_F_HAS_PKG_LENGTH, kAcpiAmlOpcType_NameString), 518 /* 0x11 */ RTACPI_AML_OPC_ INVALID,746 /* 0x11 */ RTACPI_AML_OPC_HANDLER( "Buffer", rtAcpiTblAmlDecodeBuffer), 519 747 /* 0x12 */ RTACPI_AML_OPC_INVALID, 520 748 /* 0x13 */ RTACPI_AML_OPC_INVALID, … … 567 795 568 796 /* 0x40 */ RTACPI_AML_OPC_INVALID, 569 /* 0x41 */ RTACPI_AML_OPC_ INVALID,570 /* 0x42 */ RTACPI_AML_OPC_ INVALID,571 /* 0x43 */ RTACPI_AML_OPC_ INVALID,572 /* 0x44 */ RTACPI_AML_OPC_ INVALID,573 /* 0x45 */ RTACPI_AML_OPC_ INVALID,574 /* 0x46 */ RTACPI_AML_OPC_ INVALID,575 /* 0x47 */ RTACPI_AML_OPC_ INVALID,576 /* 0x48 */ RTACPI_AML_OPC_ INVALID,577 /* 0x49 */ RTACPI_AML_OPC_ INVALID,578 /* 0x4a */ RTACPI_AML_OPC_ INVALID,579 /* 0x4b */ RTACPI_AML_OPC_ INVALID,580 /* 0x4c */ RTACPI_AML_OPC_ INVALID,581 /* 0x4d */ RTACPI_AML_OPC_ INVALID,582 /* 0x4e */ RTACPI_AML_OPC_ INVALID,583 /* 0x4f */ RTACPI_AML_OPC_ INVALID,584 585 /* 0x50 */ RTACPI_AML_OPC_ INVALID,586 /* 0x51 */ RTACPI_AML_OPC_ INVALID,587 /* 0x52 */ RTACPI_AML_OPC_ INVALID,588 /* 0x53 */ RTACPI_AML_OPC_ INVALID,589 /* 0x54 */ RTACPI_AML_OPC_ INVALID,590 /* 0x55 */ RTACPI_AML_OPC_ INVALID,591 /* 0x56 */ RTACPI_AML_OPC_ INVALID,592 /* 0x57 */ RTACPI_AML_OPC_ INVALID,593 /* 0x58 */ RTACPI_AML_OPC_ INVALID,594 /* 0x59 */ RTACPI_AML_OPC_ INVALID,595 /* 0x5a */ RTACPI_AML_OPC_ INVALID,797 /* 0x41 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 798 /* 0x42 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 799 /* 0x43 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 800 /* 0x44 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 801 /* 0x45 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 802 /* 0x46 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 803 /* 0x47 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 804 /* 0x48 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 805 /* 0x49 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 806 /* 0x4a */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 807 /* 0x4b */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 808 /* 0x4c */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 809 /* 0x4d */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 810 /* 0x4e */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 811 /* 0x4f */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 812 813 /* 0x50 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 814 /* 0x51 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 815 /* 0x52 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 816 /* 0x53 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 817 /* 0x54 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 818 /* 0x55 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 819 /* 0x56 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 820 /* 0x57 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 821 /* 0x58 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 822 /* 0x59 */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 823 /* 0x5a */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 596 824 /* 0x5b */ RTACPI_AML_OPC_INVALID, 597 /* 0x5c */ RTACPI_AML_OPC_ INVALID,825 /* 0x5c */ RTACPI_AML_OPC_HANDLER("RootChar", rtAcpiTblAmlDecodeNameObject), 598 826 /* 0x5d */ RTACPI_AML_OPC_INVALID, 599 /* 0x5e */ RTACPI_AML_OPC_ INVALID,600 /* 0x5f */ RTACPI_AML_OPC_ INVALID,827 /* 0x5e */ RTACPI_AML_OPC_HANDLER("ParentPrefixChar", rtAcpiTblAmlDecodeNameObject), 828 /* 0x5f */ RTACPI_AML_OPC_HANDLER("NameChar", rtAcpiTblAmlDecodeNameObject), 601 829 602 830 /* 0x60 */ RTACPI_AML_OPC_SIMPLE_0("Local0", RTACPI_AML_OPC_F_NONE), … … 640 868 /* 0x84 */ RTACPI_AML_OPC_INVALID, 641 869 /* 0x85 */ RTACPI_AML_OPC_INVALID, 642 /* 0x86 */ RTACPI_AML_OPC_ INVALID,870 /* 0x86 */ RTACPI_AML_OPC_SIMPLE_2("Notify", 0, kAcpiAmlOpcType_SuperName, kAcpiAmlOpcType_TermArg), 643 871 /* 0x87 */ RTACPI_AML_OPC_INVALID, 644 /* 0x88 */ RTACPI_AML_OPC_ INVALID,872 /* 0x88 */ RTACPI_AML_OPC_SIMPLE_3("Index", 0, kAcpiAmlOpcType_TermArg, kAcpiAmlOpcType_TermArg, kAcpiAmlOpcType_SuperName), 645 873 /* 0x89 */ RTACPI_AML_OPC_INVALID, 646 874 /* 0x8a */ RTACPI_AML_OPC_INVALID, … … 669 897 670 898 /* 0xa0 */ RTACPI_AML_OPC_SIMPLE_1("If", RTACPI_AML_OPC_F_HAS_PKG_LENGTH, kAcpiAmlOpcType_TermArg), 671 /* 0xa1 */ RTACPI_AML_OPC_ INVALID,899 /* 0xa1 */ RTACPI_AML_OPC_SIMPLE_0("Else", RTACPI_AML_OPC_F_HAS_PKG_LENGTH), 672 900 /* 0xa2 */ RTACPI_AML_OPC_INVALID, 673 901 /* 0xa3 */ RTACPI_AML_OPC_INVALID, … … 913 1141 /* 0x7f */ RTACPI_AML_OPC_INVALID, 914 1142 915 /* 0x80 */ RTACPI_AML_OPC_ INVALID,1143 /* 0x80 */ RTACPI_AML_OPC_SIMPLE_4("OpRegion", 0, kAcpiAmlOpcType_NameString, kAcpiAmlOpcType_Byte, kAcpiAmlOpcType_TermArg, kAcpiAmlOpcType_TermArg), 916 1144 /* 0x81 */ RTACPI_AML_OPC_INVALID, 917 /* 0x82 */ RTACPI_AML_OPC_ INVALID,918 /* 0x83 */ RTACPI_AML_OPC_SIMPLE_4("Processor", RTACPI_AML_OPC_F_HAS_PKG_LENGTH, kAcpiAmlOpcType_NameString, kAcpiAmlOpcType_Byte, kAcpiAmlOpcType_DWord, kAcpiAmlOpcType_Byte),1145 /* 0x82 */ RTACPI_AML_OPC_SIMPLE_1("Device", RTACPI_AML_OPC_F_HAS_PKG_LENGTH, kAcpiAmlOpcType_NameString), 1146 /* 0x83 */ RTACPI_AML_OPC_SIMPLE_4("Processor", RTACPI_AML_OPC_F_HAS_PKG_LENGTH, kAcpiAmlOpcType_NameString, kAcpiAmlOpcType_Byte, kAcpiAmlOpcType_DWord, kAcpiAmlOpcType_Byte), 919 1147 /* 0x84 */ RTACPI_AML_OPC_INVALID, 920 1148 /* 0x85 */ RTACPI_AML_OPC_INVALID, … … 1051 1279 1052 1280 1281 static int rtAcpiTblAmlDecodeSimple(PRTACPITBLAMLDECODE pThis, PCRTACPIAMLOPC pAmlOpc, uint8_t bOpc, RTVFSIOSTREAM hVfsIosOut, PRTERRINFO pErrInfo) 1282 { 1283 RT_NOREF(bOpc); 1284 1285 int rc; 1286 1287 /* Decode any package length field first. */ 1288 size_t cbPkg = 0; 1289 size_t cbPkgLength = 0; 1290 size_t cbPkgConsumed = 0; 1291 if (pAmlOpc->fFlags & RTACPI_AML_OPC_F_HAS_PKG_LENGTH) 1292 { 1293 rc = rtAcpiTblAmlDecodePkgLength(pThis, &cbPkg, &cbPkgLength, pErrInfo); 1294 if (RT_FAILURE(rc)) return rc; 1295 1296 cbPkgConsumed += cbPkgLength; 1297 } 1298 1299 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "%s", pAmlOpc->pszOpc); 1300 if (RT_FAILURE(rc)) return rc; 1301 1302 /* Any arguments? */ 1303 if (pAmlOpc->aenmTypes[0] != kAcpiAmlOpcType_Invalid) 1304 { 1305 pThis->fIndent = false; 1306 1307 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "("); 1308 if (RT_FAILURE(rc)) return rc; 1309 1310 for (uint32_t i = 0; i < RT_ELEMENTS(pAmlOpc->aenmTypes); i++) 1311 { 1312 if (pAmlOpc->aenmTypes[i] == kAcpiAmlOpcType_Invalid) 1313 break; /* End of arguments. */ 1314 1315 if (i > 0) 1316 { 1317 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, ", "); 1318 if (RT_FAILURE(rc)) return rc; 1319 } 1320 1321 switch (pAmlOpc->aenmTypes[i]) 1322 { 1323 case kAcpiAmlOpcType_Byte: 1324 { 1325 uint8_t bVal = 0; /* shut up gcc */ 1326 rc = rtAcpiTblAmlDecodeReadU8(pThis, &bVal, pErrInfo); 1327 if (RT_FAILURE(rc)) return rc; 1328 1329 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "%RU8", bVal); 1330 if (RT_FAILURE(rc)) return rc; 1331 1332 cbPkgConsumed++; 1333 break; 1334 } 1335 case kAcpiAmlOpcType_Word: 1336 { 1337 uint16_t u16Val = 0; /* shut up gcc */ 1338 rc = rtAcpiTblAmlDecodeReadU16(pThis, &u16Val, pErrInfo); 1339 if (RT_FAILURE(rc)) return rc; 1340 1341 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "%RX16", u16Val); 1342 if (RT_FAILURE(rc)) return rc; 1343 1344 cbPkgConsumed += sizeof(uint16_t); 1345 break; 1346 } 1347 case kAcpiAmlOpcType_DWord: 1348 { 1349 uint32_t u32Val = 0; /* shut up gcc */ 1350 rc = rtAcpiTblAmlDecodeReadU32(pThis, &u32Val, pErrInfo); 1351 if (RT_FAILURE(rc)) return rc; 1352 1353 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "%RX32", u32Val); 1354 if (RT_FAILURE(rc)) return rc; 1355 1356 cbPkgConsumed += sizeof(uint32_t); 1357 break; 1358 } 1359 case kAcpiAmlOpcType_NameString: 1360 { 1361 char szName[512]; 1362 size_t cbName = 0; 1363 rc = rtAcpiTblAmlDecodeNameString(pThis, &szName[0], sizeof(szName), &cbName, pErrInfo); 1364 if (RT_FAILURE(rc)) return rc; 1365 1366 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "%s", szName); 1367 if (RT_FAILURE(rc)) return rc; 1368 1369 cbPkgConsumed += cbName; 1370 break; 1371 } 1372 case kAcpiAmlOpcType_SuperName: 1373 case kAcpiAmlOpcType_TermArg: 1374 { 1375 /** @todo SuperName has limited allowed arguments. */ 1376 size_t offTblOrig = pThis->offTbl; 1377 1378 rc = rtAcpiTblAmlDecodeTerminal(pThis, hVfsIosOut, pErrInfo); 1379 if (RT_FAILURE(rc)) return rc; 1380 1381 cbPkgConsumed += pThis->offTbl - offTblOrig; 1382 break; 1383 } 1384 case kAcpiAmlOpcType_Invalid: 1385 default: 1386 AssertReleaseFailed(); 1387 } 1388 } 1389 1390 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, ")\n"); 1391 if (RT_FAILURE(rc)) return rc; 1392 1393 pThis->fIndent = true; 1394 } 1395 else if (pThis->fIndent) 1396 { 1397 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "\n"); 1398 if (RT_FAILURE(rc)) return rc; 1399 } 1400 1401 if (pAmlOpc->fFlags & RTACPI_AML_OPC_F_HAS_PKG_LENGTH) 1402 { 1403 if (cbPkg < cbPkgConsumed) 1404 return RTErrInfoSetF(pErrInfo, VERR_BUFFER_OVERFLOW, "Opcode arguments consumed more than the package length indicated (%zu vs %zu)", cbPkg, cbPkgConsumed); 1405 rc = rtAcpiTblAmlDecodePkgPush(pThis, hVfsIosOut, cbPkg - cbPkgConsumed, pErrInfo); 1406 } 1407 1408 return rc; 1409 } 1410 1053 1411 static int rtAcpiTblAmlDecode(PRTACPITBLAMLDECODE pThis, PCRTACPIAMLOPC pAmlOpc, uint8_t bOpc, RTVFSIOSTREAM hVfsIosOut, PRTERRINFO pErrInfo) 1054 1412 { 1055 1413 if (pAmlOpc->pszOpc) 1056 1414 { 1057 int rc; 1058 1059 /* Decode any package length field first. */ 1060 size_t cbPkg = 0; 1061 size_t cbPkgLength = 0; 1062 size_t cbPkgConsumed = 0; 1063 if (pAmlOpc->fFlags & RTACPI_AML_OPC_F_HAS_PKG_LENGTH) 1064 { 1065 rc = rtAcpiTblAmlDecodePkgLength(pThis, &cbPkg, &cbPkgLength, pErrInfo); 1066 if (RT_FAILURE(rc)) return rc; 1067 1068 cbPkgConsumed += cbPkgLength; 1069 } 1070 1071 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "%s", pAmlOpc->pszOpc); 1072 if (RT_FAILURE(rc)) return rc; 1073 1074 /* Any arguments? */ 1075 if (pAmlOpc->aenmTypes[0] != kAcpiAmlOpcType_Invalid) 1076 { 1077 pThis->fIndent = false; 1078 1079 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "("); 1080 if (RT_FAILURE(rc)) return rc; 1081 1082 for (uint32_t i = 0; i < RT_ELEMENTS(pAmlOpc->aenmTypes); i++) 1083 { 1084 if (pAmlOpc->aenmTypes[i] == kAcpiAmlOpcType_Invalid) 1085 break; /* End of arguments. */ 1086 1087 if (i > 0) 1088 { 1089 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, ", "); 1090 if (RT_FAILURE(rc)) return rc; 1091 } 1092 1093 switch (pAmlOpc->aenmTypes[i]) 1094 { 1095 case kAcpiAmlOpcType_Byte: 1096 { 1097 uint8_t bVal = 0; /* shut up gcc */ 1098 rc = rtAcpiTblAmlDecodeReadU8(pThis, &bVal, pErrInfo); 1099 if (RT_FAILURE(rc)) return rc; 1100 1101 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "%RU8", bVal); 1102 if (RT_FAILURE(rc)) return rc; 1103 1104 cbPkgConsumed++; 1105 break; 1106 } 1107 case kAcpiAmlOpcType_Word: 1108 { 1109 uint16_t u16Val = 0; /* shut up gcc */ 1110 rc = rtAcpiTblAmlDecodeReadU16(pThis, &u16Val, pErrInfo); 1111 if (RT_FAILURE(rc)) return rc; 1112 1113 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "%RX16", u16Val); 1114 if (RT_FAILURE(rc)) return rc; 1115 1116 cbPkgConsumed += sizeof(uint16_t); 1117 break; 1118 } 1119 case kAcpiAmlOpcType_DWord: 1120 { 1121 uint32_t u32Val = 0; /* shut up gcc */ 1122 rc = rtAcpiTblAmlDecodeReadU32(pThis, &u32Val, pErrInfo); 1123 if (RT_FAILURE(rc)) return rc; 1124 1125 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "%RX32", u32Val); 1126 if (RT_FAILURE(rc)) return rc; 1127 1128 cbPkgConsumed += sizeof(uint32_t); 1129 break; 1130 } 1131 case kAcpiAmlOpcType_NameString: 1132 { 1133 char szName[512]; 1134 size_t cbName = 0; 1135 rc = rtAcpiTblAmlDecodeNameString(pThis, &szName[0], sizeof(szName), &cbName, pErrInfo); 1136 if (RT_FAILURE(rc)) return rc; 1137 1138 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "%s", szName); 1139 if (RT_FAILURE(rc)) return rc; 1140 1141 cbPkgConsumed += cbName; 1142 break; 1143 } 1144 case kAcpiAmlOpcType_TermArg: 1145 { 1146 size_t offTblOrig = pThis->offTbl; 1147 1148 rc = rtAcpiTblAmlDecodeTerminal(pThis, hVfsIosOut, pErrInfo); 1149 if (RT_FAILURE(rc)) return rc; 1150 1151 cbPkgConsumed += pThis->offTbl - offTblOrig; 1152 break; 1153 } 1154 case kAcpiAmlOpcType_SuperName: 1155 { 1156 /** @todo SuperName includes more. */ 1157 char szName[512]; 1158 size_t cbName = 0; 1159 rc = rtAcpiTblAmlDecodeNameString(pThis, &szName[0], sizeof(szName), &cbName, pErrInfo); 1160 if (RT_FAILURE(rc)) return rc; 1161 1162 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, "%s", szName); 1163 if (RT_FAILURE(rc)) return rc; 1164 1165 cbPkgConsumed += cbName; 1166 break; 1167 } 1168 case kAcpiAmlOpcType_Invalid: 1169 default: 1170 AssertReleaseFailed(); 1171 } 1172 } 1173 1174 rc = rtAcpiTblAmlDecodeFormat(pThis, hVfsIosOut, ")\n"); 1175 if (RT_FAILURE(rc)) return rc; 1176 1177 pThis->fIndent = true; 1178 } 1179 1180 if (pAmlOpc->fFlags & RTACPI_AML_OPC_F_HAS_PKG_LENGTH) 1181 { 1182 if (cbPkg < cbPkgConsumed) 1183 return RTErrInfoSetF(pErrInfo, VERR_BUFFER_OVERFLOW, "Opcode arguments consumed more than the package length indicated (%zu vs %zu)", cbPkg, cbPkgConsumed); 1184 rc = rtAcpiTblAmlDecodePkgPush(pThis, hVfsIosOut, cbPkg - cbPkgConsumed, pErrInfo); 1185 } 1186 1187 return rc; 1415 if (pAmlOpc->pfnDecode) 1416 return pAmlOpc->pfnDecode(pThis, hVfsIosOut, bOpc, pErrInfo); 1417 return rtAcpiTblAmlDecodeSimple(pThis, pAmlOpc, bOpc, hVfsIosOut, pErrInfo); 1188 1418 } 1189 1419 … … 1287 1517 cch = RTVfsIoStrmPrintf(hVfsIosOut, "}\n"); 1288 1518 if (cch <= 0) 1289 rc = RTErrInfoSetF(pErrInfo, cch == 0 ? VERR_NO_MEMORY : cch, "Failed to emit closing definition block");1519 rc = RTErrInfoSetF(pErrInfo, cch == 0 ? VERR_NO_MEMORY : (int)cch, "Failed to emit closing definition block"); 1290 1520 } 1291 1521 } 1292 1522 else 1293 rc = RTErrInfoSetF(pErrInfo, cch == 0 ? VERR_NO_MEMORY : cch, "Failed to emit DefinitionBlock()");1523 rc = RTErrInfoSetF(pErrInfo, cch == 0 ? VERR_NO_MEMORY : (int)cch, "Failed to emit DefinitionBlock()"); 1294 1524 } 1295 1525 else
Note:
See TracChangeset
for help on using the changeset viewer.