- Timestamp:
- Jul 6, 2021 4:29:39 PM (4 years ago)
- svn:sync-xref-src-repo-rev:
- 145566
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Devices/Audio/AudioTest.cpp
r90048 r90071 215 215 * Internal Functions * 216 216 *********************************************************************************************************************************/ 217 static int audioTestObjClose Internal(PAUDIOTESTOBJINT pObj);217 static int audioTestObjClose(PAUDIOTESTOBJINT pObj); 218 218 static void audioTestObjFinalize(PAUDIOTESTOBJINT pObj); 219 static void audioTestObjInit(PAUDIOTESTOBJINT pObj); 219 220 220 221 … … 827 828 * 828 829 * @returns VBox status code. 829 * @param p hObj Object handle to get value for.830 * @param pObj Object handle to get value for. 830 831 * @param pszKey Key to get value from. 831 832 * @param pszVal Where to return the value on success. 832 833 * @param cbVal Size (in bytes) of \a pszVal. 833 834 */ 834 static int audioTestObjGetStr(PAUDIOTESTOBJINT p hObj, const char *pszKey, char *pszVal, size_t cbVal)835 static int audioTestObjGetStr(PAUDIOTESTOBJINT pObj, const char *pszKey, char *pszVal, size_t cbVal) 835 836 { 836 837 /** @todo For now we only support .INI-style files. */ 837 AssertPtrReturn(p hObj->pSet, VERR_WRONG_ORDER);838 return RTIniFileQueryValue(p hObj->pSet->f.hIniFile, phObj->szSec, pszKey, pszVal, cbVal, NULL);838 AssertPtrReturn(pObj->pSet, VERR_WRONG_ORDER); 839 return RTIniFileQueryValue(pObj->pSet->f.hIniFile, pObj->szSec, pszKey, pszVal, cbVal, NULL); 839 840 } 840 841 … … 843 844 * 844 845 * @returns VBox status code. 845 * @param p hObj Object handle to get value for.846 * @param pObj Object handle to get value for. 846 847 * @param pszKey Key to get value from. 847 848 * @param pbVal Where to return the value on success. 848 849 */ 849 static int audioTestObjGetBool(PAUDIOTESTOBJINT p hObj, const char *pszKey, bool *pbVal)850 static int audioTestObjGetBool(PAUDIOTESTOBJINT pObj, const char *pszKey, bool *pbVal) 850 851 { 851 852 char szVal[_1K]; 852 int rc = audioTestObjGetStr(p hObj, pszKey, szVal, sizeof(szVal));853 int rc = audioTestObjGetStr(pObj, pszKey, szVal, sizeof(szVal)); 853 854 if (RT_SUCCESS(rc)) 854 855 *pbVal = (RTStrICmp(szVal, "true") == 0) … … 862 863 * 863 864 * @returns VBox status code. 864 * @param p hObj Object handle to get value for.865 * @param pObj Object handle to get value for. 865 866 * @param pszKey Key to get value from. 866 867 * @param puVal Where to return the value on success. 867 868 */ 868 static int audioTestObjGetUInt8(PAUDIOTESTOBJINT p hObj, const char *pszKey, uint8_t *puVal)869 static int audioTestObjGetUInt8(PAUDIOTESTOBJINT pObj, const char *pszKey, uint8_t *puVal) 869 870 { 870 871 char szVal[_1K]; 871 int rc = audioTestObjGetStr(p hObj, pszKey, szVal, sizeof(szVal));872 int rc = audioTestObjGetStr(pObj, pszKey, szVal, sizeof(szVal)); 872 873 if (RT_SUCCESS(rc)) 873 874 *puVal = RTStrToUInt8(szVal); … … 880 881 * 881 882 * @returns VBox status code. 882 * @param p hObj Object handle to get value for.883 * @param pObj Object handle to get value for. 883 884 * @param pszKey Key to get value from. 884 885 * @param puVal Where to return the value on success. 885 886 */ 886 static int audioTestObjGetUInt32(PAUDIOTESTOBJINT p hObj, const char *pszKey, uint32_t *puVal)887 static int audioTestObjGetUInt32(PAUDIOTESTOBJINT pObj, const char *pszKey, uint32_t *puVal) 887 888 { 888 889 char szVal[_1K]; 889 int rc = audioTestObjGetStr(p hObj, pszKey, szVal, sizeof(szVal));890 int rc = audioTestObjGetStr(pObj, pszKey, szVal, sizeof(szVal)); 890 891 if (RT_SUCCESS(rc)) 891 892 *puVal = RTStrToUInt32(szVal); … … 1027 1028 RTListForEachSafe(&pSet->lstObj, pObj, pObjNext, AUDIOTESTOBJINT, Node) 1028 1029 { 1029 rc = audioTestObjClose Internal(pObj);1030 rc = audioTestObjClose(pObj); 1030 1031 if (RT_SUCCESS(rc)) 1031 1032 { … … 1236 1237 RTListForEach(&pSet->lstObj, pObj, AUDIOTESTOBJINT, Node) 1237 1238 { 1238 int rc2 = audioTestObjClose Internal(pObj);1239 int rc2 = audioTestObjClose(pObj); 1239 1240 if (RT_SUCCESS(rc2)) 1240 1241 { … … 1280 1281 AssertPtrReturn(pThis, VERR_NO_MEMORY); 1281 1282 1282 RTListInit(&pThis->lstMeta);1283 audioTestObjInit(pThis); 1283 1284 1284 1285 if (RTStrPrintf2(pThis->szName, sizeof(pThis->szName), "%04RU32-%s", pSet->cObj, pszName) <= 0) … … 1401 1402 audioTestObjFinalize(pThis); 1402 1403 1403 return audioTestObjClose Internal(pThis);1404 return audioTestObjClose(pThis); 1404 1405 } 1405 1406 … … 1707 1708 1708 1709 /** 1710 * Initializes a test object. 1711 * 1712 * @param pObj Object to initialize. 1713 */ 1714 static void audioTestObjInit(PAUDIOTESTOBJINT pObj) 1715 { 1716 RT_BZERO(pObj, sizeof(AUDIOTESTOBJINT)); 1717 1718 pObj->cRefs = 1; 1719 1720 RTListInit(&pObj->lstMeta); 1721 } 1722 1723 /** 1709 1724 * Retrieves a child object of a specific parent object. 1710 1725 * 1711 1726 * @returns VBox status code. 1712 * @param p hParentParent object the child object contains.1727 * @param pParent Parent object the child object contains. 1713 1728 * @param idxObj Index of object to retrieve the object handle for. 1714 * @param p hObjWhere to store the object handle on success.1715 */ 1716 static int audioTestObjGetChild(PAUDIOTESTOBJINT p hParent, uint32_t idxObj, PAUDIOTESTOBJINT phObj)1729 * @param pObj Where to store the object handle on success. 1730 */ 1731 static int audioTestObjGetChild(PAUDIOTESTOBJINT pParent, uint32_t idxObj, PAUDIOTESTOBJINT pObj) 1717 1732 { 1718 1733 char szObj[AUDIOTEST_MAX_SEC_LEN]; … … 1721 1736 1722 1737 char szUuid[AUDIOTEST_MAX_SEC_LEN]; 1723 int rc = audioTestObjGetStr(p hParent, szObj, szUuid, sizeof(szUuid));1738 int rc = audioTestObjGetStr(pParent, szObj, szUuid, sizeof(szUuid)); 1724 1739 if (RT_SUCCESS(rc)) 1725 1740 { 1726 /** @todo r=bird: see comment in audioTestObjOpen about how reckless it is to 1727 * leave most of the phObj structure uninitialized. */ 1728 1729 if (RTStrPrintf2(phObj->szSec, sizeof(phObj->szSec), "obj_%s", szUuid) <= 0) 1730 AssertFailedReturn(VERR_BUFFER_OVERFLOW); /** @todo r=bird: AssertReturn(RTStrPrintf2() > 0); results in better code. */ 1741 audioTestObjInit(pObj); 1742 1743 AssertReturn(RTStrPrintf2(pObj->szSec, sizeof(pObj->szSec), "obj_%s", szUuid) > 0, VERR_BUFFER_OVERFLOW); 1731 1744 1732 1745 /** @todo Check test section existence. */ 1733 1746 1734 p hObj->pSet = phParent->pSet;1747 pObj->pSet = pParent->pSet; 1735 1748 } 1736 1749 … … 1744 1757 * @returns Error if the verification failed and test verification job has fKeepGoing not set. 1745 1758 * @param pVerJob Verification job to verify value for. 1746 * @param p hObjA Object handle A to verify value for.1747 * @param p hObjB Object handle B to verify value for.1759 * @param pObjA Object handle A to verify value for. 1760 * @param pObjB Object handle B to verify value for. 1748 1761 * @param pszKey Key to verify. 1749 1762 * @param pszVal Value to verify. … … 1752 1765 */ 1753 1766 static int audioTestVerifyValue(PAUDIOTESTVERIFYJOB pVerJob, 1754 PAUDIOTESTOBJINT p hObjA, PAUDIOTESTOBJINT phObjB, const char *pszKey, const char *pszVal, const char *pszErrFmt, ...)1767 PAUDIOTESTOBJINT pObjA, PAUDIOTESTOBJINT pObjB, const char *pszKey, const char *pszVal, const char *pszErrFmt, ...) 1755 1768 { 1756 1769 va_list va; … … 1758 1771 1759 1772 char szValA[_1K]; 1760 int rc = audioTestObjGetStr(p hObjA, pszKey, szValA, sizeof(szValA));1773 int rc = audioTestObjGetStr(pObjA, pszKey, szValA, sizeof(szValA)); 1761 1774 if (RT_SUCCESS(rc)) 1762 1775 { 1763 1776 char szValB[_1K]; 1764 rc = audioTestObjGetStr(p hObjB, pszKey, szValB, sizeof(szValB));1777 rc = audioTestObjGetStr(pObjB, pszKey, szValB, sizeof(szValB)); 1765 1778 if (RT_SUCCESS(rc)) 1766 1779 { … … 1791 1804 * 1792 1805 * @returns VBox status code. 1793 * @param phObj Object handle to open. 1794 * @param ppObj Where to return the pointer of the allocated and registered audio test object. 1795 */ 1796 static int audioTestObjOpen(PAUDIOTESTOBJINT phObj, PAUDIOTESTOBJINT *ppObj) 1797 { 1798 /** @todo r=bird: phObj and ppObj: why the 'h' in the first and not the 1799 * latter? They are of the same type, which is suffixed 'INT', so the 'h' 1800 * is probably out of place. 1801 * 1802 * An immediate question just looking at this function, would why this isn't a 1803 * 'duplicate' instead of a 'open' operation. However, looking at how little 1804 * audioTestObjGetChild actually does to the phObj we're getting from 1805 * audioTestVerifyTestToneData, it looks more like phObj is just a convenient 1806 * way of passing a PAUDIOTESTSET and a section name (szSec) around without 1807 * actually initializing anything else in the structure. 1808 * 1809 * This is reckless (7+ uninitialized members) and 'ing confusing code! */ 1810 PAUDIOTESTOBJINT pObj = (PAUDIOTESTOBJINT)RTMemAlloc(sizeof(AUDIOTESTOBJINT)); 1811 AssertPtrReturn(pObj, VERR_NO_MEMORY); 1806 * @param pObj Object to open. 1807 */ 1808 static int audioTestObjOpen(PAUDIOTESTOBJINT pObj) 1809 { 1810 AssertReturn(pObj->enmType == AUDIOTESTOBJTYPE_UNKNOWN, VERR_WRONG_ORDER); 1812 1811 1813 1812 char szFileName[AUDIOTEST_MAX_SEC_LEN]; 1814 int rc = audioTestObjGetStr(p hObj, "obj_name", szFileName, sizeof(szFileName));1813 int rc = audioTestObjGetStr(pObj, "obj_name", szFileName, sizeof(szFileName)); 1815 1814 if (RT_SUCCESS(rc)) 1816 1815 { 1817 1816 char szFilePath[RTPATH_MAX]; 1818 rc = RTPathJoin(szFilePath, sizeof(szFilePath), p hObj->pSet->szPathAbs, szFileName);1817 rc = RTPathJoin(szFilePath, sizeof(szFilePath), pObj->pSet->szPathAbs, szFileName); 1819 1818 if (RT_SUCCESS(rc)) 1820 1819 { … … 1828 1827 1829 1828 pObj->enmType = AUDIOTESTOBJTYPE_FILE; 1830 pObj->cRefs = 1; /* Currently only 1:1 mapping. */1831 1832 RTListAppend(&phObj->pSet->lstObj, &pObj->Node);1833 phObj->pSet->cObj++;1834 1835 *ppObj = pObj;1836 return VINF_SUCCESS;1837 1829 } 1838 1830 } 1839 1831 } 1840 1841 RTMemFree(pObj);1842 1832 return rc; 1843 1833 } … … 1849 1839 * @param pObj Object to close. 1850 1840 */ 1851 static int audioTestObjClose Internal(PAUDIOTESTOBJINT pObj)1841 static int audioTestObjClose(PAUDIOTESTOBJINT pObj) 1852 1842 { 1853 1843 int rc; … … 1886 1876 * 1887 1877 * @returns VBox status code. 1888 * @param p hObj Object to retrieve PCM properties for.1878 * @param pObj Object to retrieve PCM properties for. 1889 1879 * @param pProps Where to store the PCM properties on success. 1890 1880 */ 1891 static int audioTestObjGetTonePcmProps(PAUDIOTESTOBJINT p hObj, PPDMAUDIOPCMPROPS pProps)1881 static int audioTestObjGetTonePcmProps(PAUDIOTESTOBJINT pObj, PPDMAUDIOPCMPROPS pProps) 1892 1882 { 1893 1883 int rc; 1894 1884 uint32_t uHz; 1895 rc = audioTestObjGetUInt32(p hObj, "tone_pcm_hz", &uHz);1885 rc = audioTestObjGetUInt32(pObj, "tone_pcm_hz", &uHz); 1896 1886 AssertRCReturn(rc, rc); 1897 1887 uint8_t cBits; 1898 rc = audioTestObjGetUInt8(p hObj, "tone_pcm_bits", &cBits);1888 rc = audioTestObjGetUInt8(pObj, "tone_pcm_bits", &cBits); 1899 1889 AssertRCReturn(rc, rc); 1900 1890 uint8_t cChan; 1901 rc = audioTestObjGetUInt8(p hObj, "tone_pcm_channels", &cChan);1891 rc = audioTestObjGetUInt8(pObj, "tone_pcm_channels", &cChan); 1902 1892 AssertRCReturn(rc, rc); 1903 1893 bool fSigned; 1904 rc = audioTestObjGetBool(p hObj, "tone_pcm_is_signed", &fSigned);1894 rc = audioTestObjGetBool(pObj, "tone_pcm_is_signed", &fSigned); 1905 1895 AssertRCReturn(rc, rc); 1906 1896 … … 2029 2019 /** @todo For now ASSUME that we only have one object per test. */ 2030 2020 2031 AUDIOTESTOBJINT hObjA; 2032 2033 rc = audioTestObjGetChild(phTestA, 0 /* idxObj */, &hObjA); 2021 AUDIOTESTOBJINT ObjA; 2022 rc = audioTestObjGetChild(phTestA, 0 /* idxObj */, &ObjA); 2034 2023 CHECK_RC_MSG_MAYBE_RET(rc, pVerJob, "Unable to get object A"); 2035 2024 2036 PAUDIOTESTOBJINT pObjA; 2037 rc = audioTestObjOpen(&hObjA, &pObjA); 2025 rc = audioTestObjOpen(&ObjA); 2038 2026 CHECK_RC_MSG_MAYBE_RET(rc, pVerJob, "Unable to open object A"); 2039 2027 2040 AUDIOTESTOBJINT hObjB;2041 rc = audioTestObjGetChild(phTestB, 0 /* idxObj */, & hObjB);2028 AUDIOTESTOBJINT ObjB; 2029 rc = audioTestObjGetChild(phTestB, 0 /* idxObj */, &ObjB); 2042 2030 CHECK_RC_MSG_MAYBE_RET(rc, pVerJob, "Unable to get object B"); 2043 2031 2044 PAUDIOTESTOBJINT pObjB; 2045 rc = audioTestObjOpen(&hObjB, &pObjB); 2032 rc = audioTestObjOpen(&ObjB); 2046 2033 CHECK_RC_MSG_MAYBE_RET(rc, pVerJob, "Unable to open object B"); 2047 AssertReturn(pObjA->enmType == AUDIOTESTOBJTYPE_FILE, VERR_NOT_SUPPORTED);2048 AssertReturn(pObjB->enmType == AUDIOTESTOBJTYPE_FILE, VERR_NOT_SUPPORTED);2049 2034 2050 2035 /* … … 2052 2037 */ 2053 2038 uint64_t cbSizeA, cbSizeB; 2054 rc = RTFileQuerySize( pObjA->File.hFile, &cbSizeA);2055 AssertRCReturn(rc, rc); 2056 rc = RTFileQuerySize( pObjB->File.hFile, &cbSizeB);2039 rc = RTFileQuerySize(ObjA.File.hFile, &cbSizeA); 2040 AssertRCReturn(rc, rc); 2041 rc = RTFileQuerySize(ObjB.File.hFile, &cbSizeB); 2057 2042 AssertRCReturn(rc, rc); 2058 2043 2059 2044 if (!cbSizeA) 2060 2045 { 2061 int rc2 = audioTestErrorDescAddError(pVerJob->pErr, pVerJob->idxTest, "File '%s' is empty", pObjA->szName);2046 int rc2 = audioTestErrorDescAddError(pVerJob->pErr, pVerJob->idxTest, "File '%s' is empty", ObjA.szName); 2062 2047 AssertRC(rc2); 2063 2048 } … … 2065 2050 if (!cbSizeB) 2066 2051 { 2067 int rc2 = audioTestErrorDescAddError(pVerJob->pErr, pVerJob->idxTest, "File '%s' is empty", pObjB->szName);2052 int rc2 = audioTestErrorDescAddError(pVerJob->pErr, pVerJob->idxTest, "File '%s' is empty", ObjB.szName); 2068 2053 AssertRC(rc2); 2069 2054 } … … 2074 2059 2075 2060 int rc2 = audioTestErrorDescAddInfo(pVerJob->pErr, pVerJob->idxTest, "File '%s' is %zu bytes (%zums)", 2076 pObjA->szName, cbSizeA, PDMAudioPropsBytesToMilli(&pVerJob->PCMProps, cbSizeA));2061 ObjA.szName, cbSizeA, PDMAudioPropsBytesToMilli(&pVerJob->PCMProps, cbSizeA)); 2077 2062 AssertRC(rc2); 2078 2063 rc2 = audioTestErrorDescAddInfo(pVerJob->pErr, pVerJob->idxTest, "File '%s' is %zu bytes (%zums)", 2079 pObjB->szName, cbSizeB, PDMAudioPropsBytesToMilli(&pVerJob->PCMProps, cbSizeB));2064 ObjB.szName, cbSizeB, PDMAudioPropsBytesToMilli(&pVerJob->PCMProps, cbSizeB)); 2080 2065 AssertRC(rc2); 2081 2066 2082 2067 rc2 = audioTestErrorDescAddInfo(pVerJob->pErr, pVerJob->idxTest, "File '%s' is %u%% (%zu bytes, %zums) %s than '%s'", 2083 pObjA->szName,2068 ObjA.szName, 2084 2069 cbSizeA > cbSizeB ? 100 - ((cbSizeB * 100) / cbSizeA) : 100 - ((cbSizeA * 100) / cbSizeB), 2085 2070 cbDiffAbs, PDMAudioPropsBytesToMilli(&pVerJob->PCMProps, (uint32_t)cbDiffAbs), 2086 2071 cbSizeA > cbSizeB ? "bigger" : "smaller", 2087 pObjB->szName);2072 ObjB.szName); 2088 2073 AssertRC(rc2); 2089 2074 } … … 2097 2082 AUDIOTESTFILECMPPARMS FileA; 2098 2083 RT_ZERO(FileA); 2099 FileA.hFile = pObjA->File.hFile;2100 FileA.offStart = audioTestToneFileFind( pObjA->File.hFile, true /* fFindSilence */, 0 /* uOff */, &ToneParmsA);2101 FileA.cbSize = RT_MIN(audioTestToneFileFind( pObjA->File.hFile, false /* fFindSilence */, FileA.offStart, &ToneParmsA) + 1,2084 FileA.hFile = ObjA.File.hFile; 2085 FileA.offStart = audioTestToneFileFind(ObjA.File.hFile, true /* fFindSilence */, 0 /* uOff */, &ToneParmsA); 2086 FileA.cbSize = RT_MIN(audioTestToneFileFind(ObjA.File.hFile, false /* fFindSilence */, FileA.offStart, &ToneParmsA) + 1, 2102 2087 cbSizeA); 2103 2088 … … 2108 2093 AUDIOTESTFILECMPPARMS FileB; 2109 2094 RT_ZERO(FileB); 2110 FileB.hFile = pObjB->File.hFile;2111 FileB.offStart = audioTestToneFileFind( pObjB->File.hFile, true /* fFindSilence */, 0 /* uOff */, &ToneParmsB);2112 FileB.cbSize = RT_MIN(audioTestToneFileFind( pObjB->File.hFile, false /* fFindSilence */, FileB.offStart, &ToneParmsB),2095 FileB.hFile = ObjB.File.hFile; 2096 FileB.offStart = audioTestToneFileFind(ObjB.File.hFile, true /* fFindSilence */, 0 /* uOff */, &ToneParmsB); 2097 FileB.cbSize = RT_MIN(audioTestToneFileFind(ObjB.File.hFile, false /* fFindSilence */, FileB.offStart, &ToneParmsB), 2113 2098 cbSizeB); 2114 2099 2115 2100 Log2Func(("Test #%RU32\n", pVerJob->idxTest)); 2116 Log2Func(("File A ('%s'): cbOff=%RU64 cbSize=%RU64, cbFileSize=%RU64\n", pObjA->szName, FileA.offStart, FileA.cbSize - FileA.offStart, cbSizeA));2117 Log2Func(("File B ('%s'): cbOff=%RU64, cbSize=%RU64, cbFileSize=%RU64\n", pObjB->szName, FileB.offStart, FileB.cbSize - FileB.offStart, cbSizeB));2101 Log2Func(("File A ('%s'): cbOff=%RU64 cbSize=%RU64, cbFileSize=%RU64\n", ObjA.szName, FileA.offStart, FileA.cbSize - FileA.offStart, cbSizeA)); 2102 Log2Func(("File B ('%s'): cbOff=%RU64, cbSize=%RU64, cbFileSize=%RU64\n", ObjB.szName, FileB.offStart, FileB.cbSize - FileB.offStart, cbSizeB)); 2118 2103 2119 2104 uint32_t const cDiffs = audioTestFilesFindDiffsBinary(&FileA, &FileB, &ToneParmsA); 2120 2105 2121 2106 int rc2 = audioTestErrorDescAddInfo(pVerJob->pErr, pVerJob->idxTest, "Files '%s' and '%s' are %s (%RU32 different chunks, threshold is %RU32)", 2122 pObjA->szName, pObjB->szName, cDiffs == 0 ? "equal" : "different", cDiffs, pVerJob->cThresholdDiff);2107 ObjA.szName, ObjB.szName, cDiffs == 0 ? "equal" : "different", cDiffs, pVerJob->cThresholdDiff); 2123 2108 AssertRC(rc2); 2124 2109 … … 2126 2111 { 2127 2112 rc2 = audioTestErrorDescAddError(pVerJob->pErr, pVerJob->idxTest, "Files '%s' and '%s' do not match", 2128 pObjA->szName, pObjB->szName);2113 ObjA.szName, ObjB.szName); 2129 2114 AssertRC(rc2); 2130 2115 } 2131 2116 2132 rc = audioTestObjClose Internal(pObjA);2133 AssertRCReturn(rc, rc); 2134 rc = audioTestObjClose Internal(pObjB);2117 rc = audioTestObjClose(&ObjA); 2118 AssertRCReturn(rc, rc); 2119 rc = audioTestObjClose(&ObjB); 2135 2120 AssertRCReturn(rc, rc); 2136 2121
Note:
See TracChangeset
for help on using the changeset viewer.