Changeset 89387 in vbox for trunk/src/VBox/Devices/Audio
- Timestamp:
- May 31, 2021 9:55:04 AM (4 years ago)
- svn:sync-xref-src-repo-rev:
- 144738
- Location:
- trunk/src/VBox/Devices/Audio
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Devices/Audio/AudioTest.cpp
r89383 r89387 1298 1298 * WAVE File Reader. * 1299 1299 *********************************************************************************************************************************/ 1300 1301 /** 1302 * Counts the number of set bits in @a fMask. 1303 */ 1304 static unsigned audioTestWaveCountBits(uint32_t fMask) 1305 { 1306 unsigned cBits = 0; 1307 while (fMask) 1308 { 1309 if (fMask & 1) 1310 cBits++; 1311 fMask >>= 1; 1312 } 1313 return cBits; 1314 } 1315 1300 1316 /** 1301 1317 * Opens a wave (.WAV) file for reading. … … 1304 1320 * @param pszFile The file to open. 1305 1321 * @param pWaveFile The open wave file structure to fill in on success. 1306 */ 1307 int AudioTestWaveFileOpen(const char *pszFile, PAUDIOTESTWAVEFILE pWaveFile) 1322 * @param pErrInfo Where to return addition error details on failure. 1323 */ 1324 int AudioTestWaveFileOpen(const char *pszFile, PAUDIOTESTWAVEFILE pWaveFile, PRTERRINFO pErrInfo) 1308 1325 { 1309 1326 RT_ZERO(pWaveFile->Props); … … 1311 1328 int rc = RTFileOpen(&pWaveFile->hFile, pszFile, RTFILE_O_READ | RTFILE_O_OPEN | RTFILE_O_DENY_NONE); 1312 1329 if (RT_FAILURE(rc)) 1313 return rc;1330 return RTErrInfoSet(pErrInfo, rc, "RTFileOpen failed"); 1314 1331 uint64_t cbFile = 0; 1315 1332 rc = RTFileQuerySize(pWaveFile->hFile, &cbFile); … … 1322 1339 { 1323 1340 RTRIFFHDR Hdr; 1324 RTRIFFWAVEFMTCHUNK Fmt; 1341 union 1342 { 1343 RTRIFFWAVEFMTCHUNK Fmt; 1344 RTRIFFWAVEFMTEXTCHUNK FmtExt; 1345 } u; 1325 1346 } Wave; 1326 1347 RTRIFFLIST List; … … 1335 1356 if ( uBuf.Wave.Hdr.uMagic == RTRIFFHDR_MAGIC 1336 1357 && uBuf.Wave.Hdr.uFileType == RTRIFF_FILE_TYPE_WAVE 1337 && uBuf.Wave. Fmt.Chunk.uMagic == RTRIFFWAVEFMT_MAGIC1338 && uBuf.Wave. Fmt.Chunk.cbChunk >= sizeof(uBuf.Wave.Fmt.Data))1358 && uBuf.Wave.u.Fmt.Chunk.uMagic == RTRIFFWAVEFMT_MAGIC 1359 && uBuf.Wave.u.Fmt.Chunk.cbChunk >= sizeof(uBuf.Wave.u.Fmt.Data)) 1339 1360 { 1340 1361 if (uBuf.Wave.Hdr.cbFile != cbFile - sizeof(RTRIFFCHUNK)) 1341 RT MsgWarning("%s:File size mismatch: %#x, actual %#RX64 (ignored)",1342 pszFile,uBuf.Wave.Hdr.cbFile, cbFile - sizeof(RTRIFFCHUNK));1362 RTErrInfoSetF(pErrInfo, rc, "File size mismatch: %#x, actual %#RX64 (ignored)", 1363 uBuf.Wave.Hdr.cbFile, cbFile - sizeof(RTRIFFCHUNK)); 1343 1364 rc = VERR_VFS_BOGUS_FORMAT; 1344 if (uBuf.Wave.Fmt.Data.uFormatTag != RTRIFFWAVEFMT_TAG_PCM) 1345 RTMsgError("%s: Unsupported uFormatTag value: %u (expected 1)", pszFile, uBuf.Wave.Fmt.Data.uFormatTag); 1346 else if ( uBuf.Wave.Fmt.Data.cBitsPerSample != 8 1347 && uBuf.Wave.Fmt.Data.cBitsPerSample != 16 1348 && uBuf.Wave.Fmt.Data.cBitsPerSample != 32) 1349 RTMsgError("%s: Unsupported cBitsPerSample value: %u", pszFile, uBuf.Wave.Fmt.Data.cBitsPerSample); 1350 else if ( uBuf.Wave.Fmt.Data.cChannels < 1 1351 || uBuf.Wave.Fmt.Data.cChannels >= 16) 1352 RTMsgError("%s: Unsupported cChannels value: %u (expected 1..15)", pszFile, uBuf.Wave.Fmt.Data.cChannels); 1353 else if ( uBuf.Wave.Fmt.Data.uHz < 4096 1354 || uBuf.Wave.Fmt.Data.uHz > 768000) 1355 RTMsgError("%s: Unsupported uHz value: %u (expected 4096..768000)", pszFile, uBuf.Wave.Fmt.Data.uHz); 1356 else if (uBuf.Wave.Fmt.Data.cbFrame != uBuf.Wave.Fmt.Data.cChannels * uBuf.Wave.Fmt.Data.cBitsPerSample / 8) 1357 RTMsgError("%s: Invalid cbFrame value: %u (expected %u)", pszFile, uBuf.Wave.Fmt.Data.cbFrame, 1358 uBuf.Wave.Fmt.Data.cChannels * uBuf.Wave.Fmt.Data.cBitsPerSample / 8); 1359 else if (uBuf.Wave.Fmt.Data.cbRate != uBuf.Wave.Fmt.Data.cbFrame * uBuf.Wave.Fmt.Data.uHz) 1360 RTMsgError("%s: Invalid cbRate value: %u (expected %u)", pszFile, uBuf.Wave.Fmt.Data.cbRate, 1361 uBuf.Wave.Fmt.Data.cbFrame * uBuf.Wave.Fmt.Data.uHz); 1365 if ( uBuf.Wave.u.Fmt.Data.uFormatTag != RTRIFFWAVEFMT_TAG_PCM 1366 && uBuf.Wave.u.Fmt.Data.uFormatTag != RTRIFFWAVEFMT_TAG_EXTENSIBLE) 1367 RTErrInfoSetF(pErrInfo, rc, "Unsupported uFormatTag value: %#x (expected %#x or %#x)", 1368 uBuf.Wave.u.Fmt.Data.uFormatTag, RTRIFFWAVEFMT_TAG_PCM, RTRIFFWAVEFMT_TAG_EXTENSIBLE); 1369 else if ( uBuf.Wave.u.Fmt.Data.cBitsPerSample != 8 1370 && uBuf.Wave.u.Fmt.Data.cBitsPerSample != 16 1371 /* && uBuf.Wave.u.Fmt.Data.cBitsPerSample != 24 - not supported by our stack */ 1372 && uBuf.Wave.u.Fmt.Data.cBitsPerSample != 32) 1373 RTErrInfoSetF(pErrInfo, rc, "Unsupported cBitsPerSample value: %u", uBuf.Wave.u.Fmt.Data.cBitsPerSample); 1374 else if ( uBuf.Wave.u.Fmt.Data.cChannels < 1 1375 || uBuf.Wave.u.Fmt.Data.cChannels >= 16) 1376 RTErrInfoSetF(pErrInfo, rc, "Unsupported cChannels value: %u (expected 1..15)", uBuf.Wave.u.Fmt.Data.cChannels); 1377 else if ( uBuf.Wave.u.Fmt.Data.uHz < 4096 1378 || uBuf.Wave.u.Fmt.Data.uHz > 768000) 1379 RTErrInfoSetF(pErrInfo, rc, "Unsupported uHz value: %u (expected 4096..768000)", uBuf.Wave.u.Fmt.Data.uHz); 1380 else if (uBuf.Wave.u.Fmt.Data.cbFrame != uBuf.Wave.u.Fmt.Data.cChannels * uBuf.Wave.u.Fmt.Data.cBitsPerSample / 8) 1381 RTErrInfoSetF(pErrInfo, rc, "Invalid cbFrame value: %u (expected %u)", uBuf.Wave.u.Fmt.Data.cbFrame, 1382 uBuf.Wave.u.Fmt.Data.cChannels * uBuf.Wave.u.Fmt.Data.cBitsPerSample / 8); 1383 else if (uBuf.Wave.u.Fmt.Data.cbRate != uBuf.Wave.u.Fmt.Data.cbFrame * uBuf.Wave.u.Fmt.Data.uHz) 1384 RTErrInfoSetF(pErrInfo, rc, "Invalid cbRate value: %u (expected %u)", uBuf.Wave.u.Fmt.Data.cbRate, 1385 uBuf.Wave.u.Fmt.Data.cbFrame * uBuf.Wave.u.Fmt.Data.uHz); 1386 else if ( uBuf.Wave.u.Fmt.Data.uFormatTag == RTRIFFWAVEFMT_TAG_EXTENSIBLE 1387 && uBuf.Wave.u.FmtExt.Data.cbExtra < RTRIFFWAVEFMTEXT_EXTRA_SIZE) 1388 RTErrInfoSetF(pErrInfo, rc, "Invalid cbExtra value: %#x (expected at least %#x)", 1389 uBuf.Wave.u.FmtExt.Data.cbExtra, RTRIFFWAVEFMTEXT_EXTRA_SIZE); 1390 else if ( uBuf.Wave.u.Fmt.Data.uFormatTag == RTRIFFWAVEFMT_TAG_EXTENSIBLE 1391 && audioTestWaveCountBits(uBuf.Wave.u.FmtExt.Data.fChannelMask) != uBuf.Wave.u.Fmt.Data.cChannels) 1392 RTErrInfoSetF(pErrInfo, rc, "fChannelMask does not match cChannels: %#x (%u bits set) vs %u channels", 1393 uBuf.Wave.u.FmtExt.Data.fChannelMask, 1394 audioTestWaveCountBits(uBuf.Wave.u.FmtExt.Data.fChannelMask), uBuf.Wave.u.Fmt.Data.cChannels); 1395 else if ( uBuf.Wave.u.Fmt.Data.uFormatTag == RTRIFFWAVEFMT_TAG_EXTENSIBLE 1396 && RTUuidCompareStr(&uBuf.Wave.u.FmtExt.Data.SubFormat, RTRIFFWAVEFMTEXT_SUBTYPE_PCM) != 0) 1397 RTErrInfoSetF(pErrInfo, rc, "SubFormat is not PCM: %RTuuid (expected %s)", 1398 &uBuf.Wave.u.FmtExt.Data.SubFormat, RTRIFFWAVEFMTEXT_SUBTYPE_PCM); 1362 1399 else 1363 1400 { … … 1365 1402 * Copy out the data we need from the file format structure. 1366 1403 */ 1367 PDMAudioPropsInit(&pWaveFile->Props, uBuf.Wave.Fmt.Data.cBitsPerSample / 8, true /*fSigned*/, 1368 uBuf.Wave.Fmt.Data.cChannels, uBuf.Wave.Fmt.Data.uHz); 1369 pWaveFile->offSamples = sizeof(RTRIFFHDR) + sizeof(RTRIFFCHUNK) + uBuf.Wave.Fmt.Chunk.cbChunk; 1404 PDMAudioPropsInit(&pWaveFile->Props, uBuf.Wave.u.Fmt.Data.cBitsPerSample / 8, true /*fSigned*/, 1405 uBuf.Wave.u.Fmt.Data.cChannels, uBuf.Wave.u.Fmt.Data.uHz); 1406 pWaveFile->offSamples = sizeof(RTRIFFHDR) + sizeof(RTRIFFCHUNK) + uBuf.Wave.u.Fmt.Chunk.cbChunk; 1407 1408 /* 1409 * Pick up channel assignments if present. 1410 */ 1411 if (uBuf.Wave.u.Fmt.Data.uFormatTag == RTRIFFWAVEFMT_TAG_EXTENSIBLE) 1412 { 1413 unsigned iCh = 0; 1414 for (unsigned idCh = 0; idCh < 32 && iCh < uBuf.Wave.u.Fmt.Data.cChannels; idCh++) 1415 if (uBuf.Wave.u.FmtExt.Data.fChannelMask & RT_BIT_32(idCh)) 1416 { 1417 pWaveFile->Props.aidChannels[iCh] = idCh < PDMAUDIOCHANNELID_END_STANDARD 1418 - PDMAUDIOCHANNELID_FIRST_STANDARD 1419 ? idCh + PDMAUDIOCHANNELID_END_STANDARD 1420 : PDMAUDIOCHANNELID_UNKNOWN; 1421 iCh++; 1422 } 1423 } 1370 1424 1371 1425 /* … … 1415 1469 } 1416 1470 1417 RT MsgError("%s:Bad data header: uMagic=%#x (expected %#x), cbChunk=%#x (max %#RX64, align %u)",1418 pszFile, uBuf.Data.Chunk.uMagic, RTRIFFWAVEDATACHUNK_MAGIC,1419 uBuf.Data.Chunk.cbChunk, pWaveFile->cbSamples, PDMAudioPropsFrameSize(&pWaveFile->Props));1471 RTErrInfoSetF(pErrInfo, rc, "Bad data header: uMagic=%#x (expected %#x), cbChunk=%#x (max %#RX64, align %u)", 1472 pszFile, uBuf.Data.Chunk.uMagic, RTRIFFWAVEDATACHUNK_MAGIC, 1473 uBuf.Data.Chunk.cbChunk, pWaveFile->cbSamples, PDMAudioPropsFrameSize(&pWaveFile->Props)); 1420 1474 } 1421 1475 else 1422 RT MsgError("%s: Failed to read data header: %Rrc", pszFile, rc);1476 RTErrInfoSet(pErrInfo, rc, "Failed to read data header"); 1423 1477 } 1424 1478 } 1425 1479 else 1426 RT MsgError("%s:Bad file header: uMagic=%#x (vs. %#x), uFileType=%#x (vs %#x), uFmtMagic=%#x (vs %#x) cbFmtChunk=%#x (min %#x)",1427 pszFile, uBuf.Wave.Hdr.uMagic, RTRIFFHDR_MAGIC, uBuf.Wave.Hdr.uFileType, RTRIFF_FILE_TYPE_WAVE,1428 uBuf.Wave.Fmt.Chunk.uMagic, RTRIFFWAVEFMT_MAGIC,1429 uBuf.Wave.Fmt.Chunk.cbChunk, sizeof(uBuf.Wave.Fmt.Data));1480 RTErrInfoSetF(pErrInfo, rc, "Bad file header: uMagic=%#x (vs. %#x), uFileType=%#x (vs %#x), uFmtMagic=%#x (vs %#x) cbFmtChunk=%#x (min %#x)", 1481 pszFile, uBuf.Wave.Hdr.uMagic, RTRIFFHDR_MAGIC, uBuf.Wave.Hdr.uFileType, RTRIFF_FILE_TYPE_WAVE, 1482 uBuf.Wave.u.Fmt.Chunk.uMagic, RTRIFFWAVEFMT_MAGIC, 1483 uBuf.Wave.u.Fmt.Chunk.cbChunk, sizeof(uBuf.Wave.u.Fmt.Data)); 1430 1484 } 1431 1485 else 1432 RTMsgError("%s: Failed to read file header: %Rrc", pszFile, rc);1486 rc = RTErrInfoSet(pErrInfo, rc, "Failed to read file header"); 1433 1487 } 1434 1488 else 1435 RTMsgError("%s: Failed to query file size: %Rrc", pszFile, rc);1489 rc = RTErrInfoSet(pErrInfo, rc, "Failed to query file size"); 1436 1490 1437 1491 RTFileClose(pWaveFile->hFile); -
trunk/src/VBox/Devices/Audio/AudioTest.h
r89383 r89387 342 342 void AudioTestErrorDescDestroy(PAUDIOTESTERRORDESC pErr); 343 343 344 int AudioTestWaveFileOpen(const char *pszFile, PAUDIOTESTWAVEFILE pWaveFile );344 int AudioTestWaveFileOpen(const char *pszFile, PAUDIOTESTWAVEFILE pWaveFile, PRTERRINFO pErrInfo); 345 345 int AudioTestWaveFileRead(PAUDIOTESTWAVEFILE pWaveFile, void *pvBuf, size_t cbBuf, size_t *pcbRead); 346 346 void AudioTestWaveFileClose(PAUDIOTESTWAVEFILE pWaveFile);
Note:
See TracChangeset
for help on using the changeset viewer.