Changeset 89406 in vbox for trunk/src/VBox/Devices
- Timestamp:
- May 31, 2021 2:01:31 PM (4 years ago)
- Location:
- trunk/src/VBox/Devices
- Files:
-
- 2 deleted
- 6 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Devices/Audio/DevHda.cpp
r89379 r89406 57 57 #include "DevHdaCodec.h" 58 58 #include "DevHdaStream.h" 59 #include "DevHdaStreamMap.h"60 59 61 60 #include "AudioHlp.h" … … 4139 4138 4140 4139 /** Worker for hdaR3DbgInfoBDL. */ 4141 static void hdaR3DbgPrintBDL(PPDMDEVINS pDevIns, PHDASTATE pThis, P HDASTATER3 pThisCC, PCDBGFINFOHLP pHlp, int idxStream)4140 static void hdaR3DbgPrintBDL(PPDMDEVINS pDevIns, PHDASTATE pThis, PCDBGFINFOHLP pHlp, int idxStream) 4142 4141 { 4143 4142 const PHDASTREAM pStream = &pThis->aStreams[idxStream]; 4144 const PHDASTREAMR3 pStreamR3 = &pThisCC->aStreams[idxStream]; 4145 PCPDMAUDIOPCMPROPS pGuestProps = &pStreamR3->State.Mapping.GuestProps; 4143 PCPDMAUDIOPCMPROPS pGuestProps = &pStream->State.Cfg.Props; /** @todo We don't make a distinction any more. The mixer hides that now. */ 4146 4144 4147 4145 uint64_t const u64BaseDMA = RT_MAKE_U64(HDA_STREAM_REG(pThis, BDPL, idxStream), … … 4190 4188 } 4191 4189 pHlp->pfnPrintf(pHlp, " Total: %#RX64 bytes (%RU64), %u ms\n", cbTotal, cbTotal, 4192 PDMAudioPropsBytesToMilli( &pStreamR3->State.Mapping.GuestProps, (uint32_t)cbTotal));4190 PDMAudioPropsBytesToMilli(pGuestProps, (uint32_t)cbTotal)); 4193 4191 if (cbTotal != u32CBL) 4194 4192 pHlp->pfnPrintf(pHlp, " Warning: %#RX64 bytes does not match CBL (%#RX64)!\n", cbTotal, u32CBL); … … 4243 4241 { 4244 4242 PHDASTATE pThis = PDMDEVINS_2_DATA(pDevIns, PHDASTATE); 4245 PHDASTATER3 pThisCC = PDMDEVINS_2_DATA_CC(pDevIns, PHDASTATER3);4246 4243 int idxStream = hdaR3DbgLookupStrmIdx(pHlp, pszArgs); 4247 4244 if (idxStream != -1) 4248 hdaR3DbgPrintBDL(pDevIns, pThis, p ThisCC, pHlp, idxStream);4245 hdaR3DbgPrintBDL(pDevIns, pThis, pHlp, idxStream); 4249 4246 else 4250 4247 { 4251 4248 for (idxStream = 0; idxStream < HDA_MAX_STREAMS; ++idxStream) 4252 hdaR3DbgPrintBDL(pDevIns, pThis, p ThisCC, pHlp, idxStream);4249 hdaR3DbgPrintBDL(pDevIns, pThis, pHlp, idxStream); 4253 4250 idxStream = -1; 4254 4251 } … … 5119 5116 "The stream frequency.", "Stream%u/Cfg/Hz", idxStream); 5120 5117 PDMDevHlpSTAMRegisterF(pDevIns, &pThis->aStreams[idxStream].State.Cfg.Props.cbFrame, STAMTYPE_U8, STAMVISIBILITY_USED, STAMUNIT_BYTES, 5121 "The number of channels.", "Stream%u/Cfg/FrameSize-Host", idxStream); 5122 PDMDevHlpSTAMRegisterF(pDevIns, &pThisCC->aStreams[idxStream].State.Mapping.GuestProps.cbFrame, STAMTYPE_U8, STAMVISIBILITY_USED, STAMUNIT_BYTES, 5123 "The number of channels.", "Stream%u/Cfg/FrameSize-Guest", idxStream); 5118 "The number of channels.", "Stream%u/Cfg/FrameSize", idxStream); 5124 5119 #if 0 /** @todo this would require some callback or expansion. */ 5125 5120 PDMDevHlpSTAMRegisterF(pDevIns, &pThis->aStreams[idxStream].State.Cfg.Props.cChannelsX, STAMTYPE_U8, STAMVISIBILITY_USED, STAMUNIT_BYTES, -
trunk/src/VBox/Devices/Audio/DevHda.h
r88503 r89406 30 30 #include "DevHdaCodec.h" 31 31 #include "DevHdaStream.h" 32 #include "DevHdaStreamMap.h"33 32 34 33 #ifdef DEBUG_andy -
trunk/src/VBox/Devices/Audio/DevHdaCommon.cpp
r88300 r89406 326 326 327 327 if (RT_SUCCESS(rc)) 328 { 328 329 PDMAudioPropsInit(pProps, cbSample, true /*fSigned*/, (u16SDFMT & 0xf) + 1 /*cChannels*/, u32Hz * u32HzMult / u32HzDiv); 330 /** @todo is there anything we need to / can do about channel assignments? */ 331 } 329 332 330 333 # undef EXTRACT_VALUE -
trunk/src/VBox/Devices/Audio/DevHdaStream.cpp
r89379 r89406 168 168 LogFlowFunc(("[SD%RU8] Destroying ...\n", pStreamShared->u8SD)); 169 169 int rc2; 170 171 hdaR3StreamMapDestroy(&pStreamR3->State.Mapping);172 170 173 171 if (pStreamR3->State.pAioRegSink) … … 487 485 } 488 486 489 PDMAUDIOPCMPROPS HostProps; 490 int rc = hdaR3SDFMTToPCMProps(u16FMT, &HostProps); 491 if (RT_FAILURE(rc)) 487 /* 488 * Convert the config to PDM PCM properties and configure the stream. 489 */ 490 PPDMAUDIOSTREAMCFG pCfg = &pStreamShared->State.Cfg; 491 int rc = hdaR3SDFMTToPCMProps(u16FMT, &pCfg->Props); 492 if (RT_SUCCESS(rc)) 493 pCfg->enmDir = hdaGetDirFromSD(uSD); 494 else 492 495 { 493 496 LogRelMax(32, ("HDA: Warning: Format 0x%x for stream #%RU8 not supported\n", HDA_STREAM_REG(pThis, FMT, uSD), uSD)); … … 495 498 } 496 499 497 /* 498 * Initialize the stream mapping in any case, regardless if 499 * we support surround audio or not. This is needed to handle 500 * the supported channels within a single audio stream, e.g. mono/stereo. 501 * 502 * In other words, the stream mapping *always* knows the real 503 * number of channels in a single audio stream. 504 */ 505 /** @todo r=bird: this is not done at the wrong time. We don't have the host 506 * output side set up yet, so we cannot really do proper mapping setup. 507 * However, we really need this further down when we configure the internal DMA 508 * buffer size. For now we just assume it's all stereo on the host side. 509 * This is not compatible with microphone support. */ 510 # ifdef VBOX_WITH_AUDIO_HDA_MIC_IN 511 # error "Implement me!" 512 # endif 513 rc = hdaR3StreamMapInit(&pStreamR3->State.Mapping, 2 /*cHostChannels*/, &HostProps); 514 AssertRCReturn(rc, rc); 515 516 ASSERT_GUEST_LOGREL_MSG_RETURN( pStreamR3->State.Mapping.cbGuestFrame > 0 517 && u32CBL % pStreamR3->State.Mapping.cbGuestFrame == 0, 500 ASSERT_GUEST_LOGREL_MSG_RETURN( PDMAudioPropsFrameSize(&pCfg->Props) > 0 501 && u32CBL % PDMAudioPropsFrameSize(&pCfg->Props) == 0, 518 502 ("CBL for stream #%RU8 does not align to frame size (u32CBL=%u cbFrameSize=%u)\n", 519 uSD, u32CBL, pStreamR3->State.Mapping.cbGuestFrame),503 uSD, u32CBL, PDMAudioPropsFrameSize(&pCfg->Props)), 520 504 VERR_INVALID_PARAMETER); 521 505 … … 534 518 pStreamShared->u8FIFOW = u8FIFOW; 535 519 pStreamShared->u16FMT = u16FMT; 536 537 PPDMAUDIOSTREAMCFG pCfg = &pStreamShared->State.Cfg;538 pCfg->Props = HostProps;539 540 /* Set the stream's direction. */541 pCfg->enmDir = hdaGetDirFromSD(uSD);542 520 543 521 /* The the stream's name, based on the direction. */ … … 563 541 } 564 542 565 LogRel2(("HDA: Stream #%RU8 DMA @ 0x%x (%RU32 bytes = %RU64ms total)\n", 566 uSD, pStreamShared->u64BDLBase, pStreamShared->u32CBL, 567 PDMAudioPropsBytesToMilli(&pStreamR3->State.Mapping.GuestProps, pStreamShared->u32CBL))); 568 543 LogRel2(("HDA: Stream #%RU8 DMA @ 0x%x (%RU32 bytes = %RU64ms total)\n", uSD, pStreamShared->u64BDLBase, 544 pStreamShared->u32CBL, PDMAudioPropsBytesToMilli(&pCfg->Props, pStreamShared->u32CBL))); 569 545 570 546 /* … … 612 588 * Create a DMA timer schedule. 613 589 */ 614 rc = hdaR3StreamCreateSchedule(pStreamShared, cTransferFragments, cBufferIrqs, (uint32_t)cbTotal, 615 PDMAudioPropsMilliToBytes(&pStreamR3->State.Mapping.GuestProps, 100 /** @todo make configurable */), 590 /** @todo clean up this, pGuestProps and pHostProps are the same now. */ 591 rc = hdaR3StreamCreateSchedule(pStreamShared, cTransferFragments, cBufferIrqs, (uint32_t)cbTotal, 592 PDMAudioPropsMilliToBytes(&pCfg->Props, 100 /** @todo make configurable */), 616 593 PDMDevHlpTimerGetFreq(pDevIns, pStreamShared->hTimer), 617 & HostProps, &pStreamR3->State.Mapping.GuestProps);594 &pCfg->Props, &pCfg->Props); 618 595 if (RT_FAILURE(rc)) 619 596 return rc; … … 1384 1361 RTGCPHYS GCPhys = hdaR3StreamDmaBufGet(pStreamShared, &cbChunk); 1385 1362 1386 /* Need to diverge if the frame format differs or if we're writing silence. */ 1387 if ( !pStreamR3->State.Mapping.fMappingNeeded 1388 && !fWriteSilence) 1363 /* If we're writing silence. */ 1364 if (!fWriteSilence) 1389 1365 { 1390 1366 if (cbChunk <= cbLeft) … … 1430 1406 } 1431 1407 /* 1432 * Either we've got some initial silence to write, or we need to do1433 * channel mapping. Both producesguest output into the bounce buffer,1408 * We've got some initial silence to write, or we need to do 1409 * channel mapping. We produce guest output into the bounce buffer, 1434 1410 * which is then copied into guest memory. The bounce buffer may keep 1435 1411 * partial frames there for the next BDLE, if an BDLE isn't frame aligned. … … 1440 1416 else 1441 1417 { 1418 /** @todo clean up host/guest props distinction, they're the same now w/o the 1419 * mapping done by the mixer rather than us. */ 1420 PCPDMAUDIOPCMPROPS pGuestProps = &pStreamShared->State.Cfg.Props; 1442 1421 Assert(PDMAudioPropsIsSizeAligned(&pStreamShared->State.Cfg.Props, cbLeft)); 1443 uint32_t const cbLeftGuest = PDMAudioPropsFramesToBytes( &pStreamR3->State.Mapping.GuestProps,1422 uint32_t const cbLeftGuest = PDMAudioPropsFramesToBytes(pGuestProps, 1444 1423 PDMAudioPropsBytesToFrames(&pStreamShared->State.Cfg.Props, 1445 1424 cbLeft)); … … 1456 1435 { 1457 1436 /* Figure out how much we need to convert into the bounce buffer: */ 1458 uint32_t cbGuest = PDMAudioPropsRoundUpBytesToFrame(&pStreamR3->State.Mapping.GuestProps, cbChunk - cbBounce); 1459 uint32_t cFrames = PDMAudioPropsBytesToFrames(&pStreamR3->State.Mapping.GuestProps, 1460 RT_MIN(cbGuest, sizeof(abBounce) - cbBounce)); 1461 size_t cbBufSrc; 1462 if (!fWriteSilence) 1463 { 1464 /** @todo we could loop here to optimize buffer wrap around. Not important now though. */ 1465 void /*const*/ *pvBufSrc; 1466 RTCircBufAcquireReadBlock(pCircBuf, PDMAudioPropsFramesToBytes(&pStreamShared->State.Cfg.Props, cFrames), 1467 &pvBufSrc, &cbBufSrc); 1468 1469 uint32_t const cFramesToConvert = PDMAudioPropsBytesToFrames(&pStreamShared->State.Cfg.Props, 1470 (uint32_t)cbBufSrc); 1471 Assert(PDMAudioPropsFramesToBytes(&pStreamShared->State.Cfg.Props, cFramesToConvert) == cbBufSrc); 1472 Assert(cFramesToConvert > 0); 1473 Assert(cFramesToConvert <= cFrames); 1474 1475 pStreamR3->State.Mapping.pfnHostToGuest(&abBounce[cbBounce], pvBufSrc, cFramesToConvert, 1476 &pStreamR3->State.Mapping); 1477 Log5Func((" loop1: cbBounce=%#05x cFramesToConvert=%#05x cbBufSrc=%#x%s\n", 1478 cbBounce, cFramesToConvert, cbBufSrc, ASMMemIsZero(pvBufSrc, cbBufSrc) ? " all zero" : "")); 1479 #ifdef HDA_DEBUG_SILENCE 1480 fix me if relevant; 1481 #endif 1482 if (RT_LIKELY(!pStreamR3->Dbg.Runtime.fEnabled)) 1483 { /* likely */ } 1484 else 1485 AudioHlpFileWrite(pStreamR3->Dbg.Runtime.pFileDMARaw, pvBufSrc, cbBufSrc, 0 /* fFlags */); 1486 1487 #ifdef VBOX_WITH_DTRACE 1488 VBOXDD_HDA_STREAM_DMA_IN((uint32_t)uSD, (uint32_t)cbBufSrc, pStreamR3->State.offRead); 1489 #endif 1490 1491 pStreamR3->State.offRead += cbBufSrc; 1492 RTCircBufReleaseReadBlock(pCircBuf, cbBufSrc); 1493 1494 cFrames = cFramesToConvert; 1495 cbGuest = cbBounce + PDMAudioPropsFramesToBytes(&pStreamR3->State.Mapping.GuestProps, cFrames); 1496 } 1497 else 1498 { 1499 cbBufSrc = PDMAudioPropsFramesToBytes(&pStreamShared->State.Cfg.Props, cFrames); 1500 cbGuest = PDMAudioPropsFramesToBytes(&pStreamR3->State.Mapping.GuestProps, cFrames); 1501 PDMAudioPropsClearBuffer(&pStreamR3->State.Mapping.GuestProps, 1502 &abBounce[cbBounce], cbGuest, cFrames); 1503 cbGuest += cbBounce; 1504 } 1437 uint32_t cbGuest = PDMAudioPropsRoundUpBytesToFrame(pGuestProps, cbChunk - cbBounce); 1438 uint32_t cFrames = PDMAudioPropsBytesToFrames(pGuestProps, RT_MIN(cbGuest, sizeof(abBounce) - cbBounce)); 1439 1440 size_t cbBufSrc = PDMAudioPropsFramesToBytes(&pStreamShared->State.Cfg.Props, cFrames); 1441 cbGuest = PDMAudioPropsFramesToBytes(pGuestProps, cFrames); 1442 PDMAudioPropsClearBuffer(pGuestProps, &abBounce[cbBounce], cbGuest, cFrames); 1443 cbGuest += cbBounce; 1505 1444 1506 1445 /* Write it to the guest buffer. */ … … 1614 1553 * 1615 1554 */ 1555 #if 0 1616 1556 uint8_t abBounce[4096 + 128]; /* Most guest does at most 4KB BDLE. So, 4KB + space for a partial frame to reduce loops. */ 1617 1557 uint32_t cbBounce = 0; /* in case of incomplete frames between buffer segments */ 1558 #endif 1618 1559 PRTCIRCBUF pCircBuf = pStreamR3->State.pCircBuf; 1619 1560 uint32_t cbLeft = cbToProduce; … … 1631 1572 RTGCPHYS GCPhys = hdaR3StreamDmaBufGet(pStreamShared, &cbChunk); 1632 1573 1633 /* Need to diverge if the frame format differs. */ 1634 if ( !pStreamR3->State.Mapping.fMappingNeeded 1635 /** @todo && pStreamShared->State.fFrameAlignedBuffers */) 1574 /* Need to diverge if the BDLEs contain misaligned entries. */ 1575 #if 0 1576 if (/** @todo pStreamShared->State.fFrameAlignedBuffers */) 1577 #endif 1636 1578 { 1637 1579 if (cbChunk <= cbLeft) … … 1676 1618 } 1677 1619 } 1620 #if 0 1678 1621 /* 1679 1622 * Need to map the frame content, so we need to read the guest data … … 1686 1629 else 1687 1630 { 1631 /** @todo clean up host/guest props distinction, they're the same now w/o the 1632 * mapping done by the mixer rather than us. */ 1633 PCPDMAUDIOPCMPROPS pGuestProps = &pStreamShared->State.Cfg.Props; 1688 1634 Assert(PDMAudioPropsIsSizeAligned(&pStreamShared->State.Cfg.Props, cbLeft)); 1689 uint32_t const cbLeftGuest = PDMAudioPropsFramesToBytes( &pStreamR3->State.Mapping.GuestProps,1635 uint32_t const cbLeftGuest = PDMAudioPropsFramesToBytes(pGuestProps, 1690 1636 PDMAudioPropsBytesToFrames(&pStreamShared->State.Cfg.Props, 1691 1637 cbLeft)); … … 1708 1654 1709 1655 /* Convert the size to whole frames and a remainder. */ 1710 uint32_t cFrames = PDMAudioPropsBytesToFrames( &pStreamR3->State.Mapping.GuestProps, cbBounce);1711 uint32_t const cbRemainder = cbBounce - PDMAudioPropsFramesToBytes( &pStreamR3->State.Mapping.GuestProps, cFrames);1656 uint32_t cFrames = PDMAudioPropsBytesToFrames(pGuestProps, cbBounce); 1657 uint32_t const cbRemainder = cbBounce - PDMAudioPropsFramesToBytes(pGuestProps, cFrames); 1712 1658 Log5Func((" loop1: GCPhys=%RGp cbToRead=%#x cbBounce=%#x cFrames=%#x\n", GCPhys, cbToRead, cbBounce, cFrames)); 1713 1659 … … 1748 1694 cbLeft -= (uint32_t)cbBufDst; 1749 1695 cFrames -= cFramesToConvert; 1750 offBounce += PDMAudioPropsFramesToBytes( &pStreamR3->State.Mapping.GuestProps, cFramesToConvert);1696 offBounce += PDMAudioPropsFramesToBytes(pGuestProps, cFramesToConvert); 1751 1697 } 1752 1698 … … 1761 1707 Log5Func(("loop0: GCPhys=%RGp cbBounce=%#x cbLeft=%#x\n", GCPhys, cbBounce, cbLeft)); 1762 1708 } 1709 #endif 1763 1710 1764 1711 STAM_PROFILE_STOP(&pThis->StatOut, a); … … 1771 1718 1772 1719 Assert(cbLeft == 0); /* There shall be no break statements in the above loop, so cbLeft is always zero here! */ 1720 #if 0 1773 1721 AssertMsg(cbBounce == 0, ("%#x\n", cbBounce)); 1722 #endif 1774 1723 1775 1724 /* … … 2131 2080 STAM_REL_COUNTER_ADD(&pStreamR3->State.StatDmaFlowErrorBytes, cbSilence); 2132 2081 LogRel2(("HDA: Warning: Stream #%RU8 underrun, added %u bytes of silence (%u us)\n", pStreamShared->u8SD, 2133 cbSilence, PDMAudioPropsBytesToMicro(&pStream R3->State.Mapping.GuestProps, cbSilence)));2082 cbSilence, PDMAudioPropsBytesToMicro(&pStreamShared->State.Cfg.Props, cbSilence))); 2134 2083 } 2135 2084 } -
trunk/src/VBox/Devices/Audio/DevHdaStream.h
r89381 r89406 23 23 24 24 #include "DevHdaCommon.h" 25 #include "DevHdaStreamMap.h"26 25 27 26 … … 274 273 struct 275 274 { 276 /** This stream's data mapping. */277 HDASTREAMMAP Mapping;278 275 /** Circular buffer (FIFO) for holding DMA'ed data. */ 279 276 R3PTRTYPE(PRTCIRCBUF) pCircBuf; … … 311 308 /** Debug bits. */ 312 309 HDASTREAMDEBUG Dbg; 313 uint64_t au64Alignment[ 6];310 uint64_t au64Alignment[2+4]; 314 311 } HDASTREAMR3; 315 312 AssertCompileSizeAlignment(HDASTREAMR3, 64); -
trunk/src/VBox/Devices/Makefile.kmk
r89199 r89406 642 642 Audio/DevHdaStream.cpp \ 643 643 Audio/DevHdaStreamChannel.cpp \ 644 Audio/DevHdaStreamMap.cpp \645 644 Audio/AudioHlp.cpp \ 646 645 Audio/AudioMixBuffer.cpp \
Note:
See TracChangeset
for help on using the changeset viewer.