1 | /************************* START OF SPECIinCATIONS ***
|
---|
2 | *
|
---|
3 | * SOURCE FILE NAME: VSDINI.C
|
---|
4 | *
|
---|
5 | * DESCRIPTIVE NAME: Ini file and resource file manipulator
|
---|
6 | *
|
---|
7 | * COPYRIGHT: IBM Confidential
|
---|
8 | * Copyright (c) IBM Corporation 1991
|
---|
9 | * All Rights Reserved
|
---|
10 | *
|
---|
11 | * STATUS: OS/2 Release 2.x
|
---|
12 | *
|
---|
13 | * FUNCTION: This source module contains routines to retrieve information
|
---|
14 | * from the VSD resource file and MMPM2.INI file.
|
---|
15 | *
|
---|
16 | * ISV can manipulate their own ini files here.
|
---|
17 | *
|
---|
18 | * Notes: the following concepts are illustrated.
|
---|
19 | *
|
---|
20 | * 1. How to read in a resource dll and retrieve VSD specific info.
|
---|
21 | * (SetupResourceTable)
|
---|
22 | * 2. How to determine the amount of resource a particular device
|
---|
23 | * consumes (GetClassInformation)
|
---|
24 | *
|
---|
25 | *
|
---|
26 | * Change History:
|
---|
27 | * DATE DEVELOPER CHANGE DESCRIPTION
|
---|
28 | * 12/07/92 Linden deCarmo File created
|
---|
29 | * 05/24/94 Linden deCarmo Moved CAPIOCTL to VSDIOCTL
|
---|
30 | * 06/29/95 Linden deCarmo Cleanup Hardware mixer support (15552).
|
---|
31 | *
|
---|
32 | ************************** END OF SPECIFICATIONS **************************/
|
---|
33 |
|
---|
34 | #define INCL_NOPMAPI
|
---|
35 | #define INCL_DOS
|
---|
36 | #define INCL_ERRORS
|
---|
37 | #define INCL_AUDIO_VSD
|
---|
38 | #include <os2.h>
|
---|
39 | #include <os2me.h>
|
---|
40 | #include <mcd.h>
|
---|
41 | #include <audio.h>
|
---|
42 | #include <stdio.h>
|
---|
43 | #include <string.h>
|
---|
44 | #include <hhpheap.h>
|
---|
45 | #include <stdlib.h>
|
---|
46 |
|
---|
47 | #include <vsdcmds.h>
|
---|
48 | #include <vsdaud.h>
|
---|
49 | #include <mmdsload.h>
|
---|
50 |
|
---|
51 | // 15552
|
---|
52 | #ifndef INCL_MM_WPOS
|
---|
53 | RIFFTABLE RiffTable[NUMMODES] =
|
---|
54 | {
|
---|
55 | {DATATYPE_WAVEFORM, PCM},
|
---|
56 | {DATATYPE_ADPCM_AVC, ADPCM},
|
---|
57 | {DATATYPE_MULAW, MU_LAW},
|
---|
58 | {DATATYPE_ALAW, A_LAW},
|
---|
59 | {DATATYPE_MIDI, MIDI},
|
---|
60 | {DATATYPE_SPV2, SPV2},
|
---|
61 | {DATATYPE_CDXA_AUDIO, ADPCMXA},
|
---|
62 | {DATATYPE_CT_ADPCM, CT_ADPCM}
|
---|
63 | };
|
---|
64 |
|
---|
65 |
|
---|
66 |
|
---|
67 | /************************** START OF SPECIFICATIONS ************************
|
---|
68 | * *
|
---|
69 | * SUBROUTINE NAME: SetupResourceTable *
|
---|
70 | * *
|
---|
71 | * DESCRIPTIVE NAME: Retrives VSD Resource information obtained from ini *
|
---|
72 | * *
|
---|
73 | * FUNCTION: This function loads a resource dll (specified in the device *
|
---|
74 | * specific parameters of the amp-mix device). It then parses *
|
---|
75 | * the resource dll and sets up appropriate instance values. *
|
---|
76 | * *
|
---|
77 | * If you are writing your own VSD, you DO NOT have to utilize *
|
---|
78 | * these ini functions, however, you are welcome to utilize the *
|
---|
79 | * same functionality. *
|
---|
80 | * INPUT: *
|
---|
81 | * *
|
---|
82 | * OUTPUT: VSDERR_SUCESS if there was a match *
|
---|
83 | * An MCI error otherwise *
|
---|
84 | * *
|
---|
85 | * SIDE EFFECTS: *
|
---|
86 | * *
|
---|
87 | *************************** END OF SPECIFICATIONS **************************/
|
---|
88 |
|
---|
89 |
|
---|
90 |
|
---|
91 | ULONG SetupResourceTable( PVSD_INSTANCE pInstance )
|
---|
92 |
|
---|
93 | {
|
---|
94 | ULONG rc;
|
---|
95 | PULONG pulResourceWalker; // used to walk through the resource file
|
---|
96 |
|
---|
97 |
|
---|
98 | HMODULE hModule; // module handle of dll where the resource
|
---|
99 | // stored.
|
---|
100 |
|
---|
101 | //ULONG ulOffset =1;
|
---|
102 |
|
---|
103 | if (!strcmp(pInstance->pResourceDLL, "AUDIOIF") || //@LP01
|
---|
104 | !pInstance->pResourceDLL[0])
|
---|
105 | rc = MM_DosLoadModule( NULL, 0, "MMPM", &hModule ); //@LP01
|
---|
106 | else if (!pInstance->pResourceDLL[0])
|
---|
107 | rc = MM_DosLoadModule( NULL, 0, "AUDIOIF", &hModule ); //@LP01
|
---|
108 | else
|
---|
109 | rc = 1;
|
---|
110 |
|
---|
111 | if ( rc ) //@LP01
|
---|
112 | rc = MM_DosLoadModule( NULL, 0, pInstance->pResourceDLL, &hModule );
|
---|
113 |
|
---|
114 | // rc = DosLoadModule( NULL, 0, pInstance->pResourceDLL, &hModule );
|
---|
115 |
|
---|
116 | if ( rc )
|
---|
117 | return ( rc );
|
---|
118 |
|
---|
119 | /*-----------------------------------
|
---|
120 | * It the device specific parameters of
|
---|
121 | * the amp, the user specified which
|
---|
122 | * card to use by the resource id. The
|
---|
123 | * amp placed this info in the instance.
|
---|
124 | --------------------------------------*/
|
---|
125 |
|
---|
126 | rc = DosGetResource( hModule,
|
---|
127 | RT_RCDATA,
|
---|
128 | pInstance->ulResourceID,
|
---|
129 | &pInstance->pAudioModeData );
|
---|
130 |
|
---|
131 | if ( rc )
|
---|
132 | return ( rc );
|
---|
133 |
|
---|
134 | /*******************************************************
|
---|
135 | * Set up product information pointer--this must be the
|
---|
136 | * first item in the resource table.
|
---|
137 | ********************************************************/
|
---|
138 |
|
---|
139 | pInstance->pProdInfo = (PSZ ) pInstance->pAudioModeData;
|
---|
140 |
|
---|
141 | pulResourceWalker = (PULONG ) (pInstance->pProdInfo +
|
---|
142 | strlen(pInstance->pProdInfo) + 1);
|
---|
143 |
|
---|
144 | /*******************************************************
|
---|
145 | * Set up device idnformation pointer--this follows right
|
---|
146 | * after the product information string.
|
---|
147 | ********************************************************/
|
---|
148 |
|
---|
149 |
|
---|
150 | pInstance->ulDeviceID = *(pulResourceWalker)++;
|
---|
151 |
|
---|
152 |
|
---|
153 | /*******************************************************
|
---|
154 | * Determine if the manufacturer has any RIFF->AUDIODD maps
|
---|
155 | * in the resource table (this mapping is necessary since
|
---|
156 | * RIFF format tags do not match with AUDIODD modes.
|
---|
157 | ********************************************************/
|
---|
158 |
|
---|
159 | pInstance->ulNumMappingRows = *(pulResourceWalker)++;
|
---|
160 |
|
---|
161 | if ( pInstance->ulNumMappingRows )
|
---|
162 | {
|
---|
163 | pInstance->pMapTable = ( RIFFTABLE * ) pulResourceWalker;
|
---|
164 | pulResourceWalker += ( 2 * pInstance->ulNumMappingRows) ;
|
---|
165 | }
|
---|
166 |
|
---|
167 | /*******************************************************
|
---|
168 | * Access the data type table. This contains a description
|
---|
169 | * of the data types this device supports.
|
---|
170 | ********************************************************/
|
---|
171 |
|
---|
172 |
|
---|
173 | pInstance->ulNumDataTypes = *( pulResourceWalker)++;
|
---|
174 | pInstance->pDataTypeTable = ( PVOID ) pulResourceWalker;
|
---|
175 |
|
---|
176 | return ( VSDERR_SUCCESS );
|
---|
177 |
|
---|
178 | } /* SetUpResourceTable */
|
---|
179 |
|
---|
180 | #endif
|
---|
181 |
|
---|
182 | // 15552
|
---|
183 |
|
---|
184 |
|
---|
185 |
|
---|
186 |
|
---|
187 |
|
---|
188 | /************************** START OF SPECIFICATIONS ************************
|
---|
189 | * *
|
---|
190 | * SUBROUTINE NAME: GetClassInformation *
|
---|
191 | * *
|
---|
192 | * DESCRIPTIVE NAME: Retrives VSD Resource information obtained from ini *
|
---|
193 | * *
|
---|
194 | * FUNCTION: This function examines an instance to see if a match can be *
|
---|
195 | * found between what the device currently supports and what *
|
---|
196 | * the user has requested. If a match cannot be found, then the *
|
---|
197 | * best guess (best fit) will be returned. *
|
---|
198 | * *
|
---|
199 | * If you are writing your own VSD, you DO NOT have to utilize *
|
---|
200 | * these ini functions, however, you are welcome to utilize the *
|
---|
201 | * same functionality. *
|
---|
202 | * *
|
---|
203 | * INPUT: ulPort *
|
---|
204 | * *
|
---|
205 | * OUTPUT: VSDERR_SUCESS if there was a match *
|
---|
206 | * An MCI error otherwise *
|
---|
207 | * *
|
---|
208 | * SIDE EFFECTS: *
|
---|
209 | * *
|
---|
210 | *************************** END OF SPECIFICATIONS **************************/
|
---|
211 |
|
---|
212 |
|
---|
213 |
|
---|
214 |
|
---|
215 | ULONG GetClassInformation( PVSD_INSTANCE pInstance )
|
---|
216 |
|
---|
217 | {
|
---|
218 | ULONG ulLoop;
|
---|
219 |
|
---|
220 | ULONG rc = VSDERR_SUCCESS;
|
---|
221 |
|
---|
222 | SHORT sModeBackup = pInstance->sMode;
|
---|
223 | BOOL fContinousRate = FALSE;
|
---|
224 |
|
---|
225 | // these variables will be used to return an intelligent error
|
---|
226 |
|
---|
227 | BOOL fFoundBits = FALSE; // found bitspersample
|
---|
228 | //BOOL fFoundOperation = FALSE; // found operation (either play or record)
|
---|
229 | BOOL fFoundSamples = FALSE; // Found sampling rate
|
---|
230 | BOOL fFoundChannels = FALSE; // Found channels
|
---|
231 | BOOL fFoundTag = FALSE; // Found format tag
|
---|
232 |
|
---|
233 | VSD_BEST_FIT vsdBestFit; /* VSD best fit structure */
|
---|
234 |
|
---|
235 | CLASS_DATA *pDataTypeTable = ( CLASS_DATA * ) pInstance->pDataTypeTable;
|
---|
236 |
|
---|
237 | if ( pInstance->fDriverCaps )
|
---|
238 | {
|
---|
239 |
|
---|
240 | rc = CapIOCTL( pInstance);
|
---|
241 | if (!rc)
|
---|
242 | {
|
---|
243 | pInstance->ulHardwareMode = pInstance->ulDataType;
|
---|
244 | }
|
---|
245 | return ( rc );
|
---|
246 | }
|
---|
247 | else
|
---|
248 | {
|
---|
249 |
|
---|
250 | // 15552
|
---|
251 | #ifndef INCL_MM_WPOS
|
---|
252 | /*---------------------------------------------------------
|
---|
253 | * Work around problems created by Microsoft (boy isn't this
|
---|
254 | * a common theme). They redefined mulaw and alaw. Map
|
---|
255 | * these to the defines we know about already.
|
---|
256 | *----------------------------------------------------------*/
|
---|
257 | if ( pInstance->sMode == DATATYPE_RIFF_MULAW )
|
---|
258 | {
|
---|
259 | pInstance->sMode = DATATYPE_MULAW;
|
---|
260 | }
|
---|
261 |
|
---|
262 | if ( pInstance->sMode == DATATYPE_RIFF_ALAW )
|
---|
263 | {
|
---|
264 | pInstance->sMode = DATATYPE_ALAW;
|
---|
265 | }
|
---|
266 |
|
---|
267 | memset( &vsdBestFit, '\0', sizeof( VSD_BEST_FIT ) );
|
---|
268 |
|
---|
269 | pInstance->ulMatch = FALSE;
|
---|
270 |
|
---|
271 | /************************************************************
|
---|
272 | * The caller has requested a specific data type, sampling rate,
|
---|
273 | * bps etc. We will search through the data type table until we
|
---|
274 | * either find a match or run out of table elements to compare.
|
---|
275 | **************************************************************/
|
---|
276 |
|
---|
277 | for ( ulLoop = 0; ulLoop < pInstance->ulNumDataTypes; ulLoop++ )
|
---|
278 | {
|
---|
279 | /*---------------------------------------------------------
|
---|
280 | * Prepare for best fit just in case a match is not found
|
---|
281 | * This routine will give us the closest supported rate
|
---|
282 | * that the device supports given the sampling rate,
|
---|
283 | * bps and channels.
|
---|
284 | *---------------------------------------------------------*/
|
---|
285 |
|
---|
286 | BestGuess( pInstance->lBitsPerSRate,
|
---|
287 | ( LONG ) pDataTypeTable->sBitsPerSRate,
|
---|
288 | ( LONG ) pInstance->sChannels,
|
---|
289 | ( LONG ) pDataTypeTable->usChannels,
|
---|
290 | pInstance->lSRate,
|
---|
291 | ( LONG ) pDataTypeTable->sSRate,
|
---|
292 | ( LONG ) pDataTypeTable->ulSamplingDescription,
|
---|
293 | &vsdBestFit );
|
---|
294 |
|
---|
295 | if ( pInstance->sMode == pDataTypeTable->ulDataType )
|
---|
296 | {
|
---|
297 | fFoundTag = TRUE;
|
---|
298 |
|
---|
299 | if ( pInstance->lBitsPerSRate == (LONG ) pDataTypeTable->sBitsPerSRate )
|
---|
300 | {
|
---|
301 | fFoundBits = TRUE;
|
---|
302 | if ( pInstance->sChannels == ( SHORT ) pDataTypeTable->usChannels )
|
---|
303 | {
|
---|
304 | fFoundChannels = TRUE;
|
---|
305 | if ( pInstance->lSRate == pDataTypeTable->sSRate ||
|
---|
306 | ( fContinousRate &&
|
---|
307 | pInstance->lSRate < pDataTypeTable->sSRate ) )
|
---|
308 | {
|
---|
309 |
|
---|
310 | fFoundSamples = TRUE;
|
---|
311 |
|
---|
312 | pInstance->ulDataType = pDataTypeTable->ulDataType;
|
---|
313 | pInstance->ulSubType = pDataTypeTable->ulSubType;
|
---|
314 |
|
---|
315 | /* Translate RIFF mode to AUDIODD mode */
|
---|
316 |
|
---|
317 | MapModes ( pInstance );
|
---|
318 |
|
---|
319 | /***************************************************
|
---|
320 | * The resource file contains resource management
|
---|
321 | * information which is used by MDM. The playback
|
---|
322 | * mode may contain different resource management
|
---|
323 | * data than record mode so retrieve from the
|
---|
324 | * right spot.
|
---|
325 | ***************************************************/
|
---|
326 |
|
---|
327 | if ( pInstance->ulOperation == OPERATION_RECORD )
|
---|
328 | {
|
---|
329 | if ( pDataTypeTable->usRecordClass == 0 )
|
---|
330 | {
|
---|
331 | return ( VSDERR_UNSUPP_FORMAT_MODE );
|
---|
332 | }
|
---|
333 |
|
---|
334 | pInstance->ulClass = pDataTypeTable->usRecordClass;
|
---|
335 | pInstance->ulResourcesUsed = pDataTypeTable->usRecordUnits;
|
---|
336 | } /* Get playback resource information */
|
---|
337 | else
|
---|
338 | {
|
---|
339 |
|
---|
340 | if ( pDataTypeTable->usPlayClass == 0 )
|
---|
341 | {
|
---|
342 | pInstance->ulClass = pDataTypeTable->usRecordClass;
|
---|
343 | pInstance->ulResourcesUsed = pDataTypeTable->usRecordUnits;
|
---|
344 | pInstance->ulOperation = OPERATION_RECORD;
|
---|
345 |
|
---|
346 | }
|
---|
347 | else
|
---|
348 | {
|
---|
349 | pInstance->ulClass = pDataTypeTable->usPlayClass;
|
---|
350 | pInstance->ulResourcesUsed = pDataTypeTable->usPlayUnits;
|
---|
351 | }
|
---|
352 |
|
---|
353 |
|
---|
354 |
|
---|
355 | } /* Get record resource information */
|
---|
356 |
|
---|
357 | pInstance->ulCanRecord = ( pDataTypeTable->usRecordClass > 0 ) ? 1 : 0;
|
---|
358 | /* Set flag indicating that this mode is valid */
|
---|
359 |
|
---|
360 | pInstance->ulMatch = TRUE;
|
---|
361 |
|
---|
362 | /*-----------------------------------------------
|
---|
363 | * In our attempt to work around a Microsoft
|
---|
364 | * kludge, we may have overwritten the callers
|
---|
365 | * datatype. Restore before leaving.
|
---|
366 | *----------------------------------------------*/
|
---|
367 |
|
---|
368 | pInstance->sMode = sModeBackup;
|
---|
369 |
|
---|
370 |
|
---|
371 | return ( VSDERR_SUCCESS );
|
---|
372 |
|
---|
373 | } /* Sampling rate is the same */
|
---|
374 | else
|
---|
375 | {
|
---|
376 | if ( pInstance->lSRate > pDataTypeTable->sSRate &&
|
---|
377 | pDataTypeTable->ulSamplingDescription == BEGIN_CONTINUOUS )
|
---|
378 | {
|
---|
379 | fContinousRate = TRUE;
|
---|
380 | }
|
---|
381 | else
|
---|
382 | {
|
---|
383 | fContinousRate = FALSE;
|
---|
384 | }
|
---|
385 | } /* Sampling rate differs */
|
---|
386 |
|
---|
387 | } /* if the channels are the same */
|
---|
388 | } /* if the bits/sample are the same */
|
---|
389 |
|
---|
390 | } /* if the format tags are the same */
|
---|
391 |
|
---|
392 | pDataTypeTable++;
|
---|
393 | } /* loop through each data type till we find a match */
|
---|
394 |
|
---|
395 |
|
---|
396 | /*-----------------------------------------------
|
---|
397 | * In our attempt to work around a Microsoft
|
---|
398 | * kludge, we may have overwritten the callers
|
---|
399 | * datatype. Restore before leaving.
|
---|
400 | *----------------------------------------------*/
|
---|
401 |
|
---|
402 | pInstance->sMode = sModeBackup;
|
---|
403 |
|
---|
404 | /* Setup best-fit info to the caller */
|
---|
405 |
|
---|
406 | pInstance->sBestFitMode = DATATYPE_WAVEFORM;
|
---|
407 | pInstance->ulBestFitBPS = vsdBestFit.lBPSGuess;
|
---|
408 | pInstance->ulBestFitChan = vsdBestFit.lChanGuess;
|
---|
409 | pInstance->ulBestFitRate = vsdBestFit.lSampGuess;
|
---|
410 |
|
---|
411 |
|
---|
412 | /* Return non-zero value to indicate failure */
|
---|
413 |
|
---|
414 |
|
---|
415 | if ( !fFoundTag )
|
---|
416 | {
|
---|
417 | return ( VSDERR_UNSUPP_FORMAT_TAG );
|
---|
418 | }
|
---|
419 | else if ( !fFoundBits )
|
---|
420 | {
|
---|
421 | return ( VSDERR_UNSUPP_BITSPERSAMPLE );
|
---|
422 | }
|
---|
423 | else if ( !fFoundChannels )
|
---|
424 | {
|
---|
425 | return ( VSDERR_UNSUPP_CHANNELS );
|
---|
426 | }
|
---|
427 | else if ( !fFoundSamples )
|
---|
428 | {
|
---|
429 | return ( VSDERR_UNSUPP_SAMPLESPERSEC );
|
---|
430 | }
|
---|
431 |
|
---|
432 | else
|
---|
433 | {
|
---|
434 | return ( VSDERR_UNSUPP_FORMAT_MODE );
|
---|
435 | }
|
---|
436 | #endif
|
---|
437 | // 15552
|
---|
438 | } /* Device driver does not support capabilities IOCTL */
|
---|
439 |
|
---|
440 | } /* GetClassInformation */
|
---|
441 |
|
---|
442 |
|
---|
443 | // 15552
|
---|
444 | #ifndef INCL_MM_WPOS
|
---|
445 | /************************** START OF SPECIFICATIONS ************************
|
---|
446 | * *
|
---|
447 | * SUBROUTINE NAME: BestGuess *
|
---|
448 | * *
|
---|
449 | * DESCRIPTIVE NAME: Retrives VSD Resource information obtained from ini *
|
---|
450 | * *
|
---|
451 | * FUNCTION: This function tries to determine the closest mode a device *
|
---|
452 | * supports compared to what the user requested. *
|
---|
453 | * *
|
---|
454 | * INPUT: pInstance *
|
---|
455 | * *
|
---|
456 | * OUTPUT: None. *
|
---|
457 | * *
|
---|
458 | * SIDE EFFECTS: *
|
---|
459 | * *
|
---|
460 | *************************** END OF SPECIFICATIONS **************************/
|
---|
461 |
|
---|
462 | void BestGuess ( LONG lBPSRequest,
|
---|
463 | LONG lBPSValue,
|
---|
464 | LONG lChanRequest,
|
---|
465 | LONG lChanValue,
|
---|
466 | LONG lSampRequest,
|
---|
467 | LONG lSampValue,
|
---|
468 | LONG lContinuous,
|
---|
469 | VSD_BEST_FIT *pvsdBestFit )
|
---|
470 |
|
---|
471 | {
|
---|
472 | LONG lDifference;
|
---|
473 | LONG lNewDifference;
|
---|
474 | BOOL fContinuous = FALSE;
|
---|
475 |
|
---|
476 |
|
---|
477 |
|
---|
478 | /*------------------------------------------------------
|
---|
479 | * If we have not guessed at the nearest supported
|
---|
480 | * bps value already, then the guess and the max and
|
---|
481 | * min supported rates must be the currently supported
|
---|
482 | * rate.
|
---|
483 | *-----------------------------------------------------*/
|
---|
484 |
|
---|
485 | if ( !pvsdBestFit->lBPSGuess )
|
---|
486 | {
|
---|
487 | pvsdBestFit->lBPSGuess = lBPSValue;
|
---|
488 | }
|
---|
489 | else
|
---|
490 | {
|
---|
491 |
|
---|
492 | /* Determine which is closer, our guess or the new # */
|
---|
493 |
|
---|
494 | lDifference = abs( lBPSRequest - pvsdBestFit->lBPSGuess );
|
---|
495 | lNewDifference = abs( lBPSRequest - lBPSValue );
|
---|
496 |
|
---|
497 | /* If our new number is closer, then use that as the guess */
|
---|
498 |
|
---|
499 | if ( lNewDifference < lDifference )
|
---|
500 | {
|
---|
501 | pvsdBestFit->lBPSGuess = lBPSValue;
|
---|
502 | } /* New number is closer */
|
---|
503 |
|
---|
504 | /* 4-bit actually means some type of ADPCM */
|
---|
505 |
|
---|
506 | if ( lBPSRequest == 4 && lBPSValue == 16 )
|
---|
507 | {
|
---|
508 | pvsdBestFit->lBPSGuess = lBPSValue;
|
---|
509 | }
|
---|
510 | } /* else there was a best fit guess */
|
---|
511 |
|
---|
512 | /*------------------------------------------------------
|
---|
513 | * If we have not guessed at the nearest supported
|
---|
514 | * bps value already, then the guess and the max and
|
---|
515 | * min supported rates must be the currently supported
|
---|
516 | * rate.
|
---|
517 | *-----------------------------------------------------*/
|
---|
518 |
|
---|
519 | if ( !pvsdBestFit->lChanGuess )
|
---|
520 | {
|
---|
521 | pvsdBestFit->lChanGuess = lChanValue;
|
---|
522 | }
|
---|
523 | else
|
---|
524 | {
|
---|
525 | /* Determine which is closer, our guess or the new # */
|
---|
526 |
|
---|
527 | lDifference = abs( lChanRequest - pvsdBestFit->lChanGuess );
|
---|
528 | lNewDifference = abs( lChanRequest - lChanValue );
|
---|
529 |
|
---|
530 | /* If our new number is closer, then use that as the guess */
|
---|
531 |
|
---|
532 | if ( lNewDifference < lDifference )
|
---|
533 | {
|
---|
534 | pvsdBestFit->lChanGuess = lChanValue;
|
---|
535 | } /* New number is closer */
|
---|
536 |
|
---|
537 | } /* else there was a best fit guess */
|
---|
538 |
|
---|
539 |
|
---|
540 | if ( lContinuous == BEGIN_CONTINUOUS ||
|
---|
541 | lContinuous == END_CONTINUOUS )
|
---|
542 | {
|
---|
543 | fContinuous = TRUE;
|
---|
544 | }
|
---|
545 | /*------------------------------------------------------
|
---|
546 | * If we have not guessed at the nearest supported
|
---|
547 | * samp/rate value already, then the guess and the max and
|
---|
548 | * min supported rates must be the currently supported
|
---|
549 | * rate.
|
---|
550 | *-----------------------------------------------------*/
|
---|
551 |
|
---|
552 | if ( fContinuous )
|
---|
553 | {
|
---|
554 | pvsdBestFit->lSampGuess = lSampRequest;
|
---|
555 | }
|
---|
556 |
|
---|
557 | else
|
---|
558 | {
|
---|
559 | if ( !pvsdBestFit->lSampGuess )
|
---|
560 | {
|
---|
561 | pvsdBestFit->lSampGuess = lSampValue;
|
---|
562 | }
|
---|
563 | else
|
---|
564 | {
|
---|
565 | /* Determine which is closer, our guess or the new # */
|
---|
566 |
|
---|
567 | lDifference = abs( lSampRequest - pvsdBestFit->lSampGuess );
|
---|
568 | lNewDifference = abs( lSampRequest - lSampValue );
|
---|
569 |
|
---|
570 | /* If our new number is closer, then use that as the guess */
|
---|
571 |
|
---|
572 | if ( lNewDifference < lDifference )
|
---|
573 | {
|
---|
574 | pvsdBestFit->lSampGuess = lSampValue;
|
---|
575 | } /* New number is closer */
|
---|
576 |
|
---|
577 | } /* else there was a best fit guess */
|
---|
578 | } /* Not a device with integral sampling rates */
|
---|
579 |
|
---|
580 | } /* BestGuess */
|
---|
581 |
|
---|
582 |
|
---|
583 |
|
---|
584 | /************************** START OF SPECIFICATIONS ************************
|
---|
585 | * *
|
---|
586 | * SUBROUTINE NAME: MapModes *
|
---|
587 | * *
|
---|
588 | * DESCRIPTIVE NAME: Converts a Riff Mode to an AUDIODD mode. *
|
---|
589 | * *
|
---|
590 | * FUNCTION: Due to a very unfortunate choice (i.e. one out of our control) *
|
---|
591 | * the AUDIODD architecture defines conflict with RIFF modes. *
|
---|
592 | * This function maps from RIFF->AUDIODD mode *
|
---|
593 | * Newer drivers can indicate that they support RIFF datatypes *
|
---|
594 | * via the AUDIO capability ioctl. *
|
---|
595 | * *
|
---|
596 | * *
|
---|
597 | * INPUT: pInstance *
|
---|
598 | * *
|
---|
599 | * OUTPUT: None. *
|
---|
600 | * *
|
---|
601 | * SIDE EFFECTS: *
|
---|
602 | * *
|
---|
603 | *************************** END OF SPECIFICATIONS **************************/
|
---|
604 |
|
---|
605 |
|
---|
606 |
|
---|
607 | void MapModes( PVSD_INSTANCE pInstance )
|
---|
608 |
|
---|
609 | {
|
---|
610 | ULONG ulLoop = 0;
|
---|
611 |
|
---|
612 | RIFFTABLE *pMapTable = pInstance->pMapTable;
|
---|
613 |
|
---|
614 |
|
---|
615 |
|
---|
616 |
|
---|
617 | if ( !(pInstance->fDriverCaps & SUPPORT_RIFF_MODES) )
|
---|
618 | {
|
---|
619 | while ( ulLoop < KNOWN_AUDIODD_MAPS )
|
---|
620 | {
|
---|
621 |
|
---|
622 | if ( pInstance->sMode == RiffTable[ ulLoop ].ulDataType )
|
---|
623 | {
|
---|
624 | pInstance->ulHardwareMode = RiffTable[ ulLoop ].ulAUDIODDMode;
|
---|
625 | return;
|
---|
626 | }
|
---|
627 | ulLoop++;
|
---|
628 | }
|
---|
629 |
|
---|
630 | ulLoop = 0;
|
---|
631 |
|
---|
632 | while ( ulLoop < pInstance->ulNumMappingRows )
|
---|
633 | {
|
---|
634 | if ( pInstance->sMode == (pMapTable + ulLoop)->ulDataType )
|
---|
635 | {
|
---|
636 | pInstance->ulHardwareMode = (pMapTable + ulLoop)->ulAUDIODDMode;
|
---|
637 | // ensure that we can stream this data.
|
---|
638 | pInstance->ulDataType = DATATYPE_WAVEFORM;
|
---|
639 |
|
---|
640 | return;
|
---|
641 | }
|
---|
642 | ulLoop++;
|
---|
643 | }
|
---|
644 | } /* If the driver does not support RIFF datatypes */
|
---|
645 |
|
---|
646 | /* Worst case, assume that they are the same */
|
---|
647 |
|
---|
648 | pInstance->ulHardwareMode = pInstance->ulDataType;
|
---|
649 | return;
|
---|
650 |
|
---|
651 | } /* MapModes */
|
---|
652 |
|
---|
653 |
|
---|
654 | /************************ START OF SPECIFICATIONS **************************
|
---|
655 | *
|
---|
656 | * SUBROUTINE NAME: ACPABestFit()
|
---|
657 | *
|
---|
658 | * FUNCTION: Since ACPA 1.02 has no best fit, best fit for it
|
---|
659 | *
|
---|
660 | * INPUT: pInstance - pointer to AMP/Mixer instance structure
|
---|
661 | *
|
---|
662 | * OUTPUT: returns VSDERR_SUCCESS if successful, otherwise it returns an
|
---|
663 | * MCI error code.
|
---|
664 | *
|
---|
665 | * *
|
---|
666 | *************************** END OF SPECIFICATIONS *************************/
|
---|
667 | void ACPABestFit( PVSD_INSTANCE pInstance )
|
---|
668 |
|
---|
669 | {
|
---|
670 | if ( ( !pInstance->ulMatch &&
|
---|
671 | pInstance->sMode == DATATYPE_WAVEFORM ) )
|
---|
672 |
|
---|
673 | {
|
---|
674 | if ( pInstance->lSRate < 9000 )
|
---|
675 | {
|
---|
676 | pInstance->lSRate = 8000;
|
---|
677 | }
|
---|
678 | else if ( pInstance->lSRate < 15000 )
|
---|
679 | {
|
---|
680 | pInstance->lSRate = 11025;
|
---|
681 | }
|
---|
682 | else if ( pInstance->lSRate < 33400 )
|
---|
683 | {
|
---|
684 | pInstance->lSRate = 22050;
|
---|
685 | }
|
---|
686 | else
|
---|
687 | {
|
---|
688 | pInstance->lSRate = 44100;
|
---|
689 | }
|
---|
690 |
|
---|
691 | pInstance->ulHardwareMode = PCM;
|
---|
692 |
|
---|
693 | GetClassInformation( pInstance );
|
---|
694 |
|
---|
695 | } /* If sampling rate is not directly supported */
|
---|
696 |
|
---|
697 |
|
---|
698 | } /* ACPABestFit */
|
---|
699 |
|
---|
700 | #endif
|
---|
701 | // 15552
|
---|