VirtualBox

source: vbox/trunk/src/VBox/Devices/Audio/AudioTest.h@ 92463

Last change on this file since 92463 was 92396, checked in by vboxsync, 3 years ago

Audio/Validation Kit: Implemented test ID encoding into the pre / post beacons plus cleaning up the tes ID setting / handling while at it. That way it should be easier to (visually) distinguish beacons from different tests. See comments for more details. bugref:10008

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 17.8 KB
Line 
1/* $Id: AudioTest.h 92396 2021-11-12 11:46:06Z vboxsync $ */
2/** @file
3 * Audio testing routines.
4 * Common code which is being used by the ValidationKit audio test (VKAT)
5 * and the debug / ValdikationKit audio driver(s).
6 */
7
8/*
9 * Copyright (C) 2021 Oracle Corporation
10 *
11 * This file is part of VirtualBox Open Source Edition (OSE), as
12 * available from http://www.virtualbox.org. This file is free software;
13 * you can redistribute it and/or modify it under the terms of the GNU
14 * General Public License (GPL) as published by the Free Software
15 * Foundation, in version 2 as it comes in the "COPYING" file of the
16 * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
17 * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
18 */
19
20#ifndef VBOX_INCLUDED_SRC_Audio_AudioTest_h
21#define VBOX_INCLUDED_SRC_Audio_AudioTest_h
22#ifndef RT_WITHOUT_PRAGMA_ONCE
23# pragma once
24#endif
25
26/** @todo Some stuff here can be private-only to the implementation. */
27
28/** Maximum length in characters an audio test tag can have. */
29#define AUDIOTEST_TAG_MAX 64
30/** Maximum length in characters a single audio test error description can have. */
31#define AUDIOTEST_ERROR_DESC_MAX 256
32/** Prefix for audio test (set) directories. */
33#define AUDIOTEST_PATH_PREFIX_STR "vkat"
34/** Maximum tests a beacon can have.
35 * Maximum number of tests is 240 (so it can fit into 8-bit mono channels). */
36#define AUDIOTEST_BEACON_TESTS_MAX 240
37/** Returns a pre-beacon for a given test number.
38 * Maximum number of tests is 240 (so it can fit into 8-bit mono channels).
39 *
40 * That way it's easy to visually inspect beacon data in a hex editor --
41 * e.g. for test #5 a pre-beacon would be 0x5A + post-beacon 0x5B. */
42#define AUDIOTEST_BEACON_MAKE_PRE(a_TstNum) \
43 ( (uint8_t)((a_TstNum) & 0xf) << 4 \
44 | (uint8_t)(0xA))
45/** Returns a post-beacon for a given test number.
46 * Maximum number of tests is 250 (so it can fit into 8-bit mono channels).
47 *
48 * That way it's easy to visually inspect beacon data in a hex editor --
49 * e.g. for test #2 a pre-beacon would be 0x2A + post-beacon 0x2B. */
50#define AUDIOTEST_BEACON_MAKE_POST(a_TstNum) \
51 ( (uint8_t)((a_TstNum) & 0xf) << 4 \
52 | (uint8_t)(0xB))
53/** Pre / post audio beacon size (in audio frames). */
54#define AUDIOTEST_BEACON_SIZE_FRAMES 1024
55
56/**
57 * Enumeration for an audio test tone (wave) type.
58 */
59typedef enum AUDIOTESTTONETYPE
60{
61 /** Invalid type. */
62 AUDIOTESTTONETYPE_INVALID = 0,
63 /** Sine wave. */
64 AUDIOTESTTONETYPE_SINE,
65 /** Square wave. Not implemented yet. */
66 AUDIOTESTTONETYPE_SQUARE,
67 /** Triangluar wave. Not implemented yet. */
68 AUDIOTESTTONETYPE_TRIANGLE,
69 /** Sawtooth wave. Not implemented yet. */
70 AUDIOTESTTONETYPE_SAWTOOTH,
71 /** The usual 32-bit hack. */
72 AUDIOTESTTONETYPE_32BIT_HACK = 0x7fffffff
73} AUDIOTESTTONETYPE;
74
75/**
76 * Structure for handling an audio (sine wave) test tone.
77 */
78typedef struct AUDIOTESTTONE
79{
80 /** The tone's wave type. */
81 AUDIOTESTTONETYPE enmType;
82 /** The PCM properties. */
83 PDMAUDIOPCMPROPS Props;
84 /** Current sample index for generate the sine wave. */
85 uint64_t uSample;
86 /** The fixed portion of the sin() input. */
87 double rdFixed;
88 /** Frequency (in Hz) of the sine wave to generate. */
89 double rdFreqHz;
90} AUDIOTESTTONE;
91/** Pointer to an audio test tone. */
92typedef AUDIOTESTTONE *PAUDIOTESTTONE;
93
94/**
95 * Structure for a common test parameters header.
96 */
97typedef struct AUDIOTESTPARMSHDR
98{
99 /** Test index these test parameters belong to.
100 * Set to UINT32_MAX if not being used. */
101 uint32_t idxTest;
102 /** Time of the caller when this test was being created. */
103 RTTIME tsCreated;
104} AUDIOTESTPARMSHDR;
105/** Pointer to an audio test tone. */
106typedef AUDIOTESTPARMSHDR *PAUDIOTESTPARMSHDR;
107
108/**
109 * Structure for handling audio test tone parameters.
110 */
111typedef struct AUDIOTESTTONEPARMS
112{
113 /** Common test header. */
114 AUDIOTESTPARMSHDR Hdr;
115 /** The PCM properties. */
116 PDMAUDIOPCMPROPS Props;
117 /** Tone frequency (in Hz) to use.
118 * Will be later converted to a double value. */
119 double dbFreqHz;
120 /** Prequel (in ms) to play silence. Optional and can be set to 0. */
121 RTMSINTERVAL msPrequel;
122 /** Duration (in ms) to play the test tone. */
123 RTMSINTERVAL msDuration;
124 /** Sequel (in ms) to play silence. Optional and can be set to 0. */
125 RTMSINTERVAL msSequel;
126 /** Volume (in percent, 0-100) to use.
127 * If set to 0, the tone is muted (i.e. silent). */
128 uint8_t uVolumePercent;
129} AUDIOTESTTONEPARMS;
130/** Pointer to audio test tone parameters. */
131typedef AUDIOTESTTONEPARMS *PAUDIOTESTTONEPARMS;
132
133/**
134 * Enumeration defining an audio test beacon type.
135 */
136typedef enum AUDIOTESTTONEBEACONTYPE
137{
138 /** Invalid type. */
139 AUDIOTESTTONEBEACONTYPE_INVALID = 0,
140 /** Playback beacon (pre). */
141 AUDIOTESTTONEBEACONTYPE_PLAY_PRE = 1,
142 /** Playback beacon (post). */
143 AUDIOTESTTONEBEACONTYPE_PLAY_POST = 2,
144 /** Recording beacon (pre). */
145 AUDIOTESTTONEBEACONTYPE_REC_PRE = 3,
146 /** Recording beacon (post). */
147 AUDIOTESTTONEBEACONTYPE_REC_POST = 4,
148 /** The usual 32-bit hack. */
149 OTESTTONEBEACONTYPE_32BIT_HACK = 0x7fffffff
150} AUDIOTESTTONEBEACONTYPE;
151
152/**
153 * Structure defining an audio test tone beacon.
154 *
155 * This is being used for (optionally) marking beginning/ending of audio test data.
156 */
157typedef struct AUDIOTESTTONEBEACON
158{
159 /** Test number this beacon is for. */
160 uint8_t uTest;
161 /** The beacon type. */
162 AUDIOTESTTONEBEACONTYPE enmType;
163 /** PCM properties to use for this beacon. */
164 PDMAUDIOPCMPROPS Props;
165 /** Beacon bytes to process.
166 * When doing test tone playback: Beacon bytes to write.
167 * When doing test tone recording: Beacon bytes to read. */
168 uint32_t cbSize;
169 /** Beacon bytes already processed.
170 * When doing test tone playback: Beacon bytes written.
171 * When doing test tone recording: Beacon bytes read. */
172 uint32_t cbUsed;
173} AUDIOTESTTONEBEACON;
174/** Pointer to audio test tone beacon. */
175typedef AUDIOTESTTONEBEACON *PAUDIOTESTTONEBEACON;
176/** Pointer (const) to audio test tone beacon. */
177typedef AUDIOTESTTONEBEACON const *PCAUDIOTESTTONEBEACON;
178
179/**
180 * Enumeration for the test set mode.
181 */
182typedef enum AUDIOTESTSETMODE
183{
184 /** Invalid test set mode. */
185 AUDIOTESTSETMODE_INVALID = 0,
186 /** Test set is being created (testing in progress). */
187 AUDIOTESTSETMODE_TEST,
188 /** Existing test set is being verified. */
189 AUDIOTESTSETMODE_VERIFY,
190 /** The usual 32-bit hack. */
191 AUDIOTESTSETMODE_32BIT_HACK = 0x7fffffff
192} AUDIOTESTSETMODE;
193
194/**
195 * Enumeration to specify an audio test type.
196 */
197typedef enum AUDIOTESTTYPE
198{
199 /** Invalid test type, do not use. */
200 AUDIOTESTTYPE_INVALID = 0,
201 /** Play a test tone. */
202 AUDIOTESTTYPE_TESTTONE_PLAY,
203 /** Record a test tone. */
204 AUDIOTESTTYPE_TESTTONE_RECORD,
205 /** The usual 32-bit hack. */
206 AUDIOTESTTYPE_32BIT_HACK = 0x7fffffff
207} AUDIOTESTTYPE;
208
209/**
210 * Audio test request data.
211 */
212typedef struct AUDIOTESTPARMS
213{
214 /** Audio device to use. */
215 PDMAUDIOHOSTDEV Dev;
216 /** How much to delay (wait, in ms) the test being executed. */
217 RTMSINTERVAL msDelay;
218 /** The test direction. */
219 PDMAUDIODIR enmDir;
220 /** The test type. */
221 AUDIOTESTTYPE enmType;
222 /** Union for test type-specific data. */
223 union
224 {
225 AUDIOTESTTONEPARMS TestTone;
226 };
227} AUDIOTESTPARMS;
228/** Pointer to a test parameter structure. */
229typedef AUDIOTESTPARMS *PAUDIOTESTPARMS;
230
231/** Test object handle. */
232typedef R3R0PTRTYPE(struct AUDIOTESTOBJINT RT_FAR *) AUDIOTESTOBJ;
233/** Pointer to test object handle. */
234typedef AUDIOTESTOBJ RT_FAR *PAUDIOTESTOBJ;
235/** Nil test object handle. */
236#define NIL_AUDIOTESTOBJ ((AUDIOTESTOBJ)~(RTHCINTPTR)0)
237
238struct AUDIOTESTSET;
239
240/**
241 * Structure specifying a single audio test entry of a test set.
242 *
243 * A test set can contain zero or more test entry (tests).
244 */
245typedef struct AUDIOTESTENTRY
246{
247 /** List node. */
248 RTLISTNODE Node;
249 /** Pointer to test set parent. */
250 AUDIOTESTSET *pParent;
251 /** Friendly description of the test. */
252 char szDesc[64];
253 /** Audio test parameters this test needs to perform the actual test. */
254 AUDIOTESTPARMS Parms;
255 /** Number of test objects bound to this test. */
256 uint32_t cObj;
257 /** Absolute offset (in bytes) where to write the "obj_count" value later. */
258 uint64_t offObjCount;
259 /** Overall test result. */
260 int rc;
261} AUDIOTESTENTRY;
262/** Pointer to an audio test entry. */
263typedef AUDIOTESTENTRY *PAUDIOTESTENTRY;
264
265/**
266 * Structure specifying an audio test set.
267 */
268typedef struct AUDIOTESTSET
269{
270 /** The set's tag. */
271 char szTag[AUDIOTEST_TAG_MAX];
272 /** Absolute path where to store the test audio data. */
273 char szPathAbs[RTPATH_MAX];
274 /** Current mode the test set is in. */
275 AUDIOTESTSETMODE enmMode;
276 union
277 {
278 /** @todo r=bird: RTSTREAM not RTFILE. That means you don't have to check
279 * every write status code and it's buffered and thus faster. Also,
280 * you don't have to re-invent fprintf-style RTFileWrite wrappers. */
281 RTFILE hFile;
282 RTINIFILE hIniFile;
283 } f;
284 /** Number of test objects in lstObj. */
285 uint32_t cObj;
286 /** Absolute offset (in bytes) where to write the "obj_count" value later. */
287 uint64_t offObjCount;
288 /** List containing PAUDIOTESTOBJ test object entries. */
289 RTLISTANCHOR lstObj;
290 /** Number of performed tests.
291 * Not necessarily bound to the test object entries above. */
292 uint32_t cTests;
293 /** Absolute offset (in bytes) where to write the "test_count" value later. */
294 uint64_t offTestCount;
295 /** List containing PAUDIOTESTENTRY test entries. */
296 RTLISTANCHOR lstTest;
297 /** Current test running. Can be NULL if no test is running. */
298 PAUDIOTESTENTRY pTestCur;
299 /** Number of tests currently running.
300 * Currently we only allow one concurrent test running at a given time. */
301 uint32_t cTestsRunning;
302 /** Number of total (test) failures. */
303 uint32_t cTotalFailures;
304} AUDIOTESTSET;
305/** Pointer to an audio test set. */
306typedef AUDIOTESTSET *PAUDIOTESTSET;
307
308/**
309 * Audio test verification options.
310 */
311typedef struct AUDIOTESTVERIFYOPTS
312{
313 /** Flag indicating whether to keep going after an error has occurred. */
314 bool fKeepGoing;
315 /** Whether to perform audio normalization or not. */
316 bool fNormalize;
317 /** Threshold of file differences (number of chunks) at when we consider audio files
318 * as not matching. 0 means an exact match. */
319 uint32_t cMaxDiff;
320 /** Threshold of file differences (difference in percent) at when we consider audio files
321 * as not matching. 0 means an exact match. */
322 uint8_t uMaxDiffPercent;
323 /** Threshold of file size (+/-, in percent) at when we consider audio files
324 * as not matching. 0 means an exact match.*/
325 uint8_t uMaxSizePercent;
326 /** Search window (in ms) to use for treating / classifying audio data. */
327 uint32_t msSearchWindow;
328} AUDIOTESTVERIFYOPTS;
329/** Pointer to audio test verification options. */
330typedef AUDIOTESTVERIFYOPTS *PAUDIOTESTVERIFYOPTS;
331
332/**
333 * Structure for holding a single audio test error entry.
334 */
335typedef struct AUDIOTESTERRORENTRY
336{
337 /** The entrie's list node. */
338 RTLISTNODE Node;
339 /** Additional rc. */
340 int rc;
341 /** Actual error description. */
342 char szDesc[AUDIOTEST_ERROR_DESC_MAX];
343} AUDIOTESTERRORENTRY;
344/** Pointer to an audio test error description. */
345typedef AUDIOTESTERRORENTRY *PAUDIOTESTERRORENTRY;
346
347/**
348 * Structure for holding an audio test error description.
349 * This can contain multiple errors (FIFO list).
350 */
351typedef struct AUDIOTESTERRORDESC
352{
353 /** List entries containing the (FIFO-style) errors of type AUDIOTESTERRORENTRY. */
354 RTLISTANCHOR List;
355 /** Number of errors in the list. */
356 uint32_t cErrors;
357} AUDIOTESTERRORDESC;
358/** Pointer to an audio test error description. */
359typedef AUDIOTESTERRORDESC *PAUDIOTESTERRORDESC;
360/** Const pointer to an audio test error description. */
361typedef AUDIOTESTERRORDESC const *PCAUDIOTESTERRORDESC;
362
363/**
364 * Enumeration specifying an internal test state.
365 */
366typedef enum AUDIOTESTSTATE
367{
368 /** Test is initializing. */
369 AUDIOTESTSTATE_INIT = 0,
370 /** Test is in pre-run phase. */
371 AUDIOTESTSTATE_PRE,
372 /** Test is running */
373 AUDIOTESTSTATE_RUN,
374 /** Test is in post-run phase. */
375 AUDIOTESTSTATE_POST,
376 /** Test has been run. */
377 AUDIOTESTSTATE_DONE,
378 /** The usual 32-bit hack. */
379 AUDIOTESTSTATE_32BIT_HACK = 0x7fffffff
380} AUDIOTESTSTATE;
381
382double AudioTestToneInit(PAUDIOTESTTONE pTone, PPDMAUDIOPCMPROPS pProps, double dbFreq);
383double AudioTestToneInitRandom(PAUDIOTESTTONE pTone, PPDMAUDIOPCMPROPS pProps);
384double AudioTestToneGetRandomFreq(void);
385int AudioTestToneGenerate(PAUDIOTESTTONE pTone, void *pvBuf, uint32_t cbBuf, uint32_t *pcbWritten);
386
387void AudioTestBeaconInit(PAUDIOTESTTONEBEACON pBeacon, uint8_t uTest, AUDIOTESTTONEBEACONTYPE enmType, PPDMAUDIOPCMPROPS pProps);
388int AudioTestBeaconAddConsecutive(PAUDIOTESTTONEBEACON pBeacon, const uint8_t *auBuf, size_t cbBuf, size_t *pOff);
389int AudioTestBeaconWrite(PAUDIOTESTTONEBEACON pBeacon, void *pvBuf, uint32_t cbBuf);
390uint32_t AudioTestBeaconGetSize(PCAUDIOTESTTONEBEACON pBeacon);
391const char *AudioTestBeaconTypeGetName(AUDIOTESTTONEBEACONTYPE enmType);
392AUDIOTESTTONEBEACONTYPE AudioTestBeaconGetType(PCAUDIOTESTTONEBEACON pBeacon);
393uint32_t AudioTestBeaconGetRemaining(PCAUDIOTESTTONEBEACON pBeacon);
394uint32_t AudioTestBeaconGetUsed(PCAUDIOTESTTONEBEACON pBeacon);
395bool AudioTestBeaconIsComplete(PCAUDIOTESTTONEBEACON pBeacon);
396
397int AudioTestGenTag(char *pszTag, size_t cbTag);
398
399int AudioTestPathGetTemp(char *pszPath, size_t cbPath);
400int AudioTestPathCreateTemp(char *pszPath, size_t cbPath, const char *pszUUID);
401int AudioTestPathCreate(char *pszPath, size_t cbPath, const char *pszUUID);
402
403int AudioTestSetObjCreateAndRegister(PAUDIOTESTSET pSet, const char *pszName, PAUDIOTESTOBJ pObj);
404
405int AudioTestObjWrite(AUDIOTESTOBJ Obj, const void *pvBuf, size_t cbBuf);
406int AudioTestObjAddMetadataStr(AUDIOTESTOBJ Obj, const char *pszFormat, ...);
407int AudioTestObjClose(AUDIOTESTOBJ Obj);
408
409int AudioTestSetTestBegin(PAUDIOTESTSET pSet, const char *pszDesc, PAUDIOTESTPARMS pParms, PAUDIOTESTENTRY *ppEntry);
410int AudioTestSetTestFailed(PAUDIOTESTENTRY pEntry, int rc, const char *pszErr);
411int AudioTestSetTestDone(PAUDIOTESTENTRY pEntry);
412bool AudioTestSetTestIsRunning(PAUDIOTESTENTRY pEntry);
413
414int AudioTestSetCreate(PAUDIOTESTSET pSet, const char *pszPath, const char *pszTag);
415int AudioTestSetDestroy(PAUDIOTESTSET pSet);
416int AudioTestSetOpen(PAUDIOTESTSET pSet, const char *pszPath);
417int AudioTestSetClose(PAUDIOTESTSET pSet);
418int AudioTestSetWipe(PAUDIOTESTSET pSet);
419const char *AudioTestSetGetTag(PAUDIOTESTSET pSet);
420uint32_t AudioTestSetGetTestsTotal(PAUDIOTESTSET pSet);
421uint32_t AudioTestSetGetTestsRunning(PAUDIOTESTSET pSet);
422uint32_t AudioTestSetGetTotalFailures(PAUDIOTESTSET pSet);
423bool AudioTestSetIsPacked(const char *pszPath);
424bool AudioTestSetIsRunning(PAUDIOTESTSET pSet);
425int AudioTestSetPack(PAUDIOTESTSET pSet, const char *pszOutDir, char *pszFileName, size_t cbFileName);
426int AudioTestSetUnpack(const char *pszFile, const char *pszOutDir);
427
428void AudioTestSetVerifyOptsInitStrict(PAUDIOTESTVERIFYOPTS pOpts);
429void AudioTestSetVerifyOptsInit(PAUDIOTESTVERIFYOPTS pOpts);
430bool AudioTestSetVerifyOptsAreEqual(PAUDIOTESTVERIFYOPTS pOptsA, PAUDIOTESTVERIFYOPTS pOptsB);
431
432int AudioTestSetVerify(PAUDIOTESTSET pSetA, PAUDIOTESTSET pSetB, PAUDIOTESTERRORDESC pErrDesc);
433int AudioTestSetVerifyEx(PAUDIOTESTSET pSetA, PAUDIOTESTSET pSetB, PAUDIOTESTVERIFYOPTS pOpts, PAUDIOTESTERRORDESC pErrDesc);
434
435uint32_t AudioTestErrorDescCount(PCAUDIOTESTERRORDESC pErr);
436bool AudioTestErrorDescFailed(PCAUDIOTESTERRORDESC pErr);
437
438void AudioTestErrorDescDestroy(PAUDIOTESTERRORDESC pErr);
439
440const char *AudioTestStateToStr(AUDIOTESTSTATE enmState);
441
442/** @name Wave File Accessors
443 * @{ */
444/**
445 * An open wave (.WAV) file.
446 */
447typedef struct AUDIOTESTWAVEFILE
448{
449 /** Magic value (AUDIOTESTWAVEFILE_MAGIC). */
450 uint32_t u32Magic;
451 /** Set if we're in read-mode, clear if in write mode. */
452 bool fReadMode;
453 /** The file handle. */
454 RTFILE hFile;
455 /** The absolute file offset of the first sample */
456 uint32_t offSamples;
457 /** Number of bytes of samples. */
458 uint32_t cbSamples;
459 /** The current read position relative to @a offSamples. */
460 uint32_t offCur;
461 /** The PCM properties for the file format. */
462 PDMAUDIOPCMPROPS Props;
463} AUDIOTESTWAVEFILE;
464/** Pointer to an open wave file. */
465typedef AUDIOTESTWAVEFILE *PAUDIOTESTWAVEFILE;
466
467/** Magic value for AUDIOTESTWAVEFILE::u32Magic (Miles Dewey Davis III). */
468#define AUDIOTESTWAVEFILE_MAGIC UINT32_C(0x19260526)
469/** Magic value for AUDIOTESTWAVEFILE::u32Magic after closing. */
470#define AUDIOTESTWAVEFILE_MAGIC_DEAD UINT32_C(0x19910928)
471
472int AudioTestWaveFileOpen(const char *pszFile, PAUDIOTESTWAVEFILE pWaveFile, PRTERRINFO pErrInfo);
473int AudioTestWaveFileCreate(const char *pszFile, PCPDMAUDIOPCMPROPS pProps, PAUDIOTESTWAVEFILE pWaveFile, PRTERRINFO pErrInfo);
474int AudioTestWaveFileRead(PAUDIOTESTWAVEFILE pWaveFile, void *pvBuf, size_t cbBuf, size_t *pcbRead);
475int AudioTestWaveFileWrite(PAUDIOTESTWAVEFILE pWaveFile, const void *pvBuf, size_t cbBuf);
476int AudioTestWaveFileClose(PAUDIOTESTWAVEFILE pWaveFile);
477
478/** @} */
479
480#endif /* !VBOX_INCLUDED_SRC_Audio_AudioTest_h */
481
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette