source: cmedia/trunk/Vsd/AudioIF/vsdquery.c@ 354

Last change on this file since 354 was 354, checked in by stevenhl, 17 years ago

Import untested baseline cmedia sources, work products and binaries
Binaries and work products should be deleted from repository.
once new builds are verified to work.

File size: 21.5 KB
Line 
1/************************* START OF SPECIinCATIONS ***
2*
3* SOURCE FILE NAME: VSDQUERY.C
4*
5* DESCRIPTIVE NAME: Device dependent porition of amp-mixer.
6*
7* COPYRIGHT: IBM 1993
8*
9* STATUS: OS/2 Release 2.x
10*
11* FUNCTION:
12*
13* NOTES: This source module is responsbile for dealing with VSD_QUERY request
14* including: VSD_QUERYDATTYPE
15* VSD_QUERYAUDIOATTRIBUTES
16* VSD_QUERYCONNECTOR
17* VSD_QUERYMIXCONNECTIONS
18* VSD_QUERYMIXLINES
19* VSD_QUERYMIXCONTROL
20*
21* other sub-functions return unsupported function.
22*
23*
24* Change History:
25* DATE DEVELOPER CHANGE DESCRIPTION
26* 07/28/93 Linden deCarmo File created
27* 05/24/94 Linden deCarmo Updated query case--use VSD_CONNECTOR
28* 06/15/94 Linden deCarmo Updated query datatype to determine if
29* device supports requested mode.
30* 06/16/94 Linden deCarmo Removed excess case statements.
31* 06/16/94 Linden deCarmo Fixed error conditions on set connector.
32* 06/16/94 Linden deCarmo Greatly improved the comments in the VSD.
33* 04/11/95 Linden deCarmo Ensure only audio attributes which device
34* supports are processed
35* 06/29/95 Linden deCarmo Cleanup Hardware mixer support (15552).
36************************** END OF SPECIFICATIONS **************************/
37
38#define INCL_NOPMAPI
39#define INCL_DOS
40#define INCL_ERRORS
41#define INCL_AUDIO_VSD
42
43
44#include <os2.h>
45#include <os2me.h>
46#include <mcd.h>
47#include <audio.h>
48#include <stdio.h>
49#include <string.h>
50#include <hhpheap.h>
51
52#include <vsdcmds.h>
53#include <vsdaud.h>
54#include <os2mixer.h>
55#include <vsdmix.h>
56
57// 15552
58#ifdef MMDEBUG
59#include <stdio.h>
60#endif
61// 15552
62
63
64/************************ START OF SPECIFICATIONS **************************
65*
66* SUBROUTINE NAME: Status_Driver()
67*
68* FUNCTION: Sends audio status IOCTL request to PDD
69*
70* INPUT: pInstance - pointer to AMP/Mixer instance structure
71* ulFlags - flag indicating what info to return
72* pQueryParms - structure to return information in
73*
74* SUCESS: VSDERR_SUCCESS
75*
76* FAILURE : VSD error code.
77*
78* OS/2 CALLS: DosDevIOCtl()
79*
80* C CALLS: None
81*
82* INTERNAL CALLS: MCI_Error()
83*
84*************************** END OF SPECIFICATIONS *************************/
85
86LONG VsdQuery( PVSD_INSTANCE pInstance,
87 ULONG ulFlags,
88 PVOID pQueryParms )
89
90 {
91 LONG lError = VSDERR_SUCCESS;
92
93// ULONG ulLeftVolume;
94// ULONG ulRightVolume;
95
96 // 5622 hack for mute state;
97
98// BOOL fLeftActive = TRUE;
99// BOOL fRightActive = TRUE;
100
101
102
103 /***************************************************************((*
104 * NO error checking--if the caller passes a bogus param--they trap.
105 * If this sounds harsh, the purpose of the VSD is to be a simple
106 * interface to the audio device for responsible MCI drivers.
107 ******************************************************************/
108
109// if ( !pQueryParms )
110// {
111// return ( VSDERR_MISSING_PARAMETER );
112// }
113
114
115 switch( ulFlags )
116 {
117 case VSD_QUERYDATATYPE :
118 {
119 MCI_AMP_INSTANCE TempAmp;
120 PVSD_AUDIODATATYPE_PARMS pAudioSettings;
121
122 pAudioSettings = ( PVSD_AUDIODATATYPE_PARMS ) pQueryParms;
123
124 memmove ( &TempAmp, pInstance, sizeof( MCI_AMP_INSTANCE ) );
125
126 TempAmp.lSRate = ( LONG ) pAudioSettings->ulSamplingRate;
127 TempAmp.sMode = ( SHORT ) pAudioSettings->ulDataType;
128 TempAmp.lBitsPerSRate = ( LONG ) pAudioSettings->ulBitsPerSample;
129 TempAmp.sChannels = ( LONG ) pAudioSettings->ulChannels;
130 TempAmp.ulOperation = pAudioSettings->ulOperation;
131
132 /*-----------------------------------------------------------------*
133 * Return the resource class and number of resource units for the
134 * mode that the caller has specified.
135 *-----------------------------------------------------------------*/
136
137 lError = GetClassInformation( &TempAmp );
138
139 if ( lError )
140 {
141 pAudioSettings->ulDataType = TempAmp.sBestFitMode;
142 pAudioSettings->ulBitsPerSample = TempAmp.ulBestFitBPS;
143 pAudioSettings->ulChannels = TempAmp.ulBestFitChan;
144 pAudioSettings->ulSamplingRate = TempAmp.ulBestFitRate;
145
146 return (lError);
147 }
148
149 }
150 break;
151
152 case VSD_QUERYVOLUME:
153 {
154 PVSD_VOLUME_PARMS pVol;
155 MIXERCONTROL MixControl;
156
157 pVol = ( PVSD_VOLUME_PARMS ) pQueryParms;
158
159 pVol->ulVolume = pInstance->lLeftVolume;
160 pVol->fMute = !(pInstance->fMute);
161
162 if ( pInstance->fHardwareMix )
163 {
164 if ( !(pInstance->ulVSDFlags & VSD_VOLUME_KNOWN ) )
165 {
166 #ifdef PERFORMANCE_TRACE
167// console_printf("querying current volume setting\n");
168 #endif
169 MixControl.ulLength = sizeof( MIXERCONTROL); // length of the struct
170 MixControl.ulLine = pInstance->ulLine;
171 MixControl.ulControl = MIX_VOLUME;
172 mixGetControl ( pInstance->hMix,
173 &MixControl );
174 pVol->ulVolume = ( MixControl.ulSetting / MIXER_MULTIPLIER) ;
175 }
176 #ifdef PERFORMANCE_TRACE
177// else
178// {
179// console_printf("cached volume request\n");
180// }
181 #endif
182
183 }
184
185 }
186 break;
187
188 case VSD_QUERYAUDIOATTRIBUTES :
189 {
190 PVSD_AUDIOATTRIBUTES_PARMS pAudioAttributes;
191 MIXERCONTROL MixControl;
192
193 pAudioAttributes = ( PVSD_AUDIOATTRIBUTES_PARMS ) pQueryParms;
194 ulFlags = pAudioAttributes->ulFlags;
195
196#ifdef PERFORMANCE_TRACE
197// console_printf("querying audio attributes\n");
198#endif
199 if ( ulFlags == VSD_BALANCE )
200 {
201 pAudioAttributes->ulValue = pInstance->lBalance;
202 MixControl.ulControl = MIX_BALANCE;
203 }
204
205 else if ( ulFlags == VSD_GAIN )
206 {
207 pAudioAttributes->ulValue = pInstance->ulGainLevel;
208 // 10253 -- broken
209
210 MixControl.ulControl = MIX_GAIN;
211 }
212
213 else if ( ulFlags == VSD_BASS )
214 {
215 pAudioAttributes->ulValue = pInstance->lBass;
216 MixControl.ulControl = MIX_BASS;
217 }
218
219 else if ( ulFlags == VSD_TREBLE )
220 {
221 pAudioAttributes->ulValue = pInstance->lTreble;
222 MixControl.ulControl = MIX_TREBLE;
223 }
224
225 else if ( ulFlags == VSD_PITCH )
226 {
227 pAudioAttributes->ulValue = pInstance->lPitch;
228 // 10253 --- this doesn't work
229 MixControl.ulControl = MIX_PITCH;
230 }
231
232 if ( pInstance->fHardwareMix )
233 {
234 MixControl.ulLength = sizeof( MIXERCONTROL); // length of the struct
235 MixControl.ulLine = pInstance->ulLine;
236
237 // see if the device supports this setting
238 // if not, no purpose in even asking
239 // what the current value is
240 // lad--capability addition
241 if ( LineSupport( pInstance, &MixControl ) )
242 {
243 lError = mixGetControl ( pInstance->hMix,
244 &MixControl );
245 }
246 else
247 {
248 // device doesn't support this capability
249
250 lError = MCIERR_UNSUPPORTED_FLAG;
251 }
252
253 // lad--capability addition
254 pAudioAttributes->ulValue = MixControl.ulSetting / MIXER_MULTIPLIER ;
255 }
256
257
258 } /* switch audio attributes */
259 break;
260 case VSD_QUERYMONITOR:
261 {
262 PULONG pMon = ( PULONG ) pQueryParms;
263
264 *pMon = pInstance->lMonitor;
265 break;
266 }
267 /*--------------------------------------------------------------------------------
268 * The IBM Amp-mixer device has the notion of logical connections. See below:
269 *
270 * Input Output
271 * -------------------------------------
272 * | |
273 * Microphone - | |-Speakers (Internal and External)
274 * Line In - | Mixer Device |-Headphones
275 * Internal Audio - | |-
276 * | |
277 * Amp Stream - | |
278 * | |
279 * ------------------------------------
280 *
281 * However, the logical mixer device performs no checking on the type of connectors
282 * so, vendors can easily add support for additional connectors. The logical mixer
283 * device takes the request to enable, disable or query the connector and forwards
284 * it directly to the VSD. The VSD should either perform the action or return
285 * one of the following errors:
286 *
287 * VSDERR_UNSUPPORTED_CONN_TYPE
288 * VSDERR_CANNOT_MODIFY_CONNECTOR
289 * VSDERR_INVALID_CONNECTOR_TYPE
290 *-------------------------------------------------------------------------------*/
291
292 case VSD_QUERYCONNECTOR :
293 {
294 PVSD_CONNECTOR_PARMS pVsdCon;
295
296 pVsdCon = ( PVSD_CONNECTOR_PARMS ) pQueryParms;
297
298 if ( pVsdCon->ulConn_Type == MCI_HEADPHONES_CONNECTOR ||
299 pVsdCon->ulConn_Type == MCI_VIDEO_IN_CONNECTOR ||
300 pVsdCon->ulConn_Type == MCI_VIDEO_OUT_CONNECTOR ||
301 pVsdCon->ulConn_Type == MCI_PHONE_SET_CONNECTOR ||
302 pVsdCon->ulConn_Type == MCI_PHONE_LINE_CONNECTOR ||
303 pVsdCon->ulConn_Type == MCI_UNIVERSAL_CONNECTOR ||
304 pVsdCon->ulConn_Type == MCI_MIDI_STREAM_CONNECTOR ||
305 pVsdCon->ulConn_Type == MCI_CD_STREAM_CONNECTOR ||
306 pVsdCon->ulConn_Type == MCI_WAVE_STREAM_CONNECTOR )
307 {
308 return (VSDERR_UNSUPPORTED_CONN_TYPE);
309 }
310
311 if ( lError= ValidateIndex( pVsdCon->ulConn_Type, pVsdCon->ulIndex ))
312 {
313 return (lError );
314 }
315
316 /*-----------------------------------------------------
317 * For now, the amp-stream connector is always enabled.
318 * since any MCI driver can always connect to us.
319 *----------------------------------------------------*/
320
321 if ( pVsdCon->ulConn_Type == MCI_AMP_STREAM_CONNECTOR )
322 {
323
324 pVsdCon->fEnabled = MCI_TRUE;
325 return (lError );
326 }
327
328 /*--------------------------------------------------
329 * Does the device support the new mixer IOCTL set?
330 * If it does, then enabling the connectors will
331 * utilze the new IOCTL set.
332 *-------------------------------------------------*/
333
334 if ( pInstance->fHardwareMix )
335 {
336 LINECONNECTIONS mixinfo;
337
338 /* The MCI connectors DON'T map directly to mixer connectors */
339
340 MapConnectorsVSD( &mixinfo.ulLine, pVsdCon->ulConn_Type);
341
342 /*----------------------------------------
343 * Actually, all map except for the spaker
344 * connector. MCI used indexes and mixer
345 * interface always uses defines.
346 *----------------------------------------*/
347
348 if ( pVsdCon->ulConn_Type == MCI_SPEAKERS_CONNECTOR &&
349 pVsdCon->ulIndex == 2)
350 {
351 mixinfo.ulLine = SINK_SPEAKER ;
352 }
353
354
355 /*----------------------------------------
356 * Ask the mixer device if it the connector
357 * is enabled.
358 *----------------------------------------*/
359
360 lError = mixGetConnections ( pInstance->hMix,
361 &mixinfo );
362
363 /*--------------------------------------------
364 * Tell the caller if the connector is enabled.
365 *--------------------------------------------*/
366
367 if ( !lError )
368 {
369 pVsdCon->fEnabled = ( mixinfo.ulConnection) ? MCI_TRUE : MCI_FALSE;
370 }
371
372 }
373 else
374 {
375// 15552
376#ifndef INCL_MM_WPOS
377 /*-------------------------------------------------------------*
378 * Enable connector
379 *-------------------------------------------------------------*/
380
381 switch( pVsdCon->ulConn_Type )
382 {
383 ULONG ulMicType;
384
385 case MCI_LINE_IN_CONNECTOR:
386 case MCI_AUDIO_IN_CONNECTOR :
387
388 pVsdCon->fEnabled = StatusIOPort( STEREO_LINE_INPUT,
389 pInstance,
390 INPUT_PORT );
391
392 break;
393
394 case MCI_MICROPHONE_CONNECTOR:
395
396 if ( pInstance->ulGainLevel >= 70 )
397 {
398 ulMicType = BOOSTED_MIC_INPUT;
399 }
400 else
401 {
402 ulMicType = MIC_INPUT;
403 }
404 pVsdCon->fEnabled = StatusIOPort( ulMicType,
405 pInstance,
406 INPUT_PORT );
407 break;
408
409 case MCI_LINE_OUT_CONNECTOR:
410 case MCI_AUDIO_OUT_CONNECTOR :
411
412 pVsdCon->fEnabled = StatusIOPort( STEREO_LINE_OUTPUT,
413 pInstance,
414 OUTPUT_PORT );
415
416 break;
417
418 case MCI_SPEAKERS_CONNECTOR:
419
420 if ( pVsdCon->ulIndex == 2 )
421 {
422 pVsdCon->fEnabled = StatusIOPort( SPEAKER_OUTPUT,
423 pInstance,
424 OUTPUT_PORT );
425 }
426 else
427 {
428 pVsdCon->fEnabled = StatusIOPort( HEADSET_OUTPUT,
429 pInstance,
430 OUTPUT_PORT );
431 }
432
433 break;
434 case MCI_INTERNAL_AUDIO_CONNECTOR :
435 lError = VSDERR_UNSUPPORTED_CONN_TYPE;
436 break;
437 default:
438 lError = VSDERR_INVALID_CONNECTOR_TYPE;
439 break;
440 }
441// 15552
442#endif
443 } /* If no hardware mixing caps */
444
445 } /* Query a connector */
446
447 break;
448 case VSD_QUERYMIXCONNECTIONS:
449 if ( pInstance->fHardwareMix )
450 {
451 lError = mixGetConnections ( pInstance->hMix,
452 ( PLINECONNECTIONS ) pQueryParms );
453 }
454 else
455 {
456 lError = VSDERR_UNSUPPORTED_COMMAND;
457 }
458
459 break;
460 case VSD_QUERYMIXCONTROL:
461 if ( pInstance->fHardwareMix )
462 {
463// 16061
464 if ( LineSupport( pInstance, ( PMIXERCONTROL ) pQueryParms ) )
465 {
466 lError = mixGetControl ( pInstance->hMix,
467 ( PMIXERCONTROL ) pQueryParms );
468 }
469 else
470 {
471 lError = MCIERR_UNSUPPORTED_ATTRIBUTE;
472 }
473// 16061
474 }
475 else
476 {
477 lError = VSDERR_UNSUPPORTED_COMMAND;
478 }
479
480 break;
481 case VSD_QUERYMIXLINE:
482 if ( pInstance->fHardwareMix )
483 {
484 lError = mixGetLineInfo ( pInstance->hMix,
485 ( PMIXERLINEINFO ) pQueryParms );
486 }
487 else
488 {
489 lError = VSDERR_UNSUPPORTED_COMMAND;
490 }
491
492 break;
493 case VSD_QUERYDISPLAY :
494 case VSD_QUERYVIDEOATTRIBUTES :
495 case VSD_QUERYIMAGEATTRIBUTES :
496 case VSD_QUERYTTSATTRIBUTES :
497 case VSD_QUERYCDCAPS :
498 case VSD_QUERYINPUTLEVELS :
499 case VSD_QUERYSTATUSLEVEL :
500 case VSD_QUERYPROCESSINTERNAL :
501 case VSD_QUERYDOOR :
502 case VSD_QUERYTOC :
503 case VSD_QUERYUPC :
504 case VSD_QUERYCOMMSETTINGS :
505 case VSD_QUERYMEDIATYPE :
506 case VSD_QUERYKEYLOCK :
507 case VSD_QUERYRATELEVELS :
508 case VSD_QUERYCUE :
509 case VSD_QUERYCOUNTER :
510 case VSD_QUERYLENGTH :
511 case VSD_QUERYCOMPATIBLECONNECTORS :
512 case VSD_QUERYSUPPORTEDEVENTS :
513 case VSD_QUERYEVENTLIST :
514 case VSD_QUERYVIEWPORTPOSITION :
515 case VSD_QUERYVIEWPORT :
516 case VSD_QUERYFREEZE :
517 case VSD_QUERYTRACKS :
518 case VSD_QUERYIMAGEFORMAT :
519 case VSD_QUERYDIRECTION :
520 case VSD_QUERYPOSITION :
521 return ( VSDERR_UNSUPPORTED_COMMAND );
522 } /* switch ulFlags */
523 return ( lError );
524
525 } /* VSDQuery */
526
527
528
529/************************ START OF SPECIFICATIONS **************************
530*
531* SUBROUTINE NAME: MapConnectorsVSD
532*
533* DESCRIPTIVE NAME: Map MCI connector request to VSD mixer API
534*
535* FUNCTION: maps connectors
536*
537* NOTES:
538*
539* OUTPUT: returns MCIERR_SUCCESS if successful, otherwise it returns an
540* MCI error code.
541*
542*************************** END OF SPECIFICATIONS *************************/
543
544LONG MapConnectorsVSD( PULONG pLine,
545 ULONG ulConnector )
546
547
548{
549 switch ( ulConnector )
550 {
551 case MCI_MIDI_STREAM_CONNECTOR :
552 case MCI_MIDI_OUT_CONNECTOR :
553 *pLine = SOURCE_SYNTHESIZER;
554
555 break;
556 case MCI_AUDIO_IN_CONNECTOR :
557 case MCI_LINE_IN_CONNECTOR :
558 *pLine = SOURCE_LINE;
559
560 break;
561 case MCI_INTERNAL_AUDIO_CONNECTOR :
562 *pLine = SOURCE_INTERNAL_AUDIO;
563
564 break;
565 case MCI_MICROPHONE_CONNECTOR :
566 *pLine = SOURCE_MICROPHONE;
567
568 break;
569 case MCI_WAVE_STREAM_CONNECTOR :
570 *pLine = SOURCE_WAVE;
571
572 break;
573 case MCI_LINE_OUT_CONNECTOR:
574 case MCI_AUDIO_OUT_CONNECTOR :
575 *pLine = SINK_LINE_OUT;
576
577 break;
578 case MCI_MIDI_IN_CONNECTOR :
579 *pLine = SOURCE_MIDI;
580
581 break;
582 case MCI_SPEAKERS_CONNECTOR : // note --there are actually two
583 *pLine = SINK_HEADPHONES;
584
585 break;
586
587 case MCI_HEADPHONES_CONNECTOR :
588 *pLine = SINK_HEADPHONES;
589 break;
590
591 case MCI_AMP_STREAM_CONNECTOR :
592 *pLine = SINK_ALL;
593 break;
594
595 default :
596 return (MCIERR_INVALID_CONNECTOR_TYPE );
597 } /* modify the connectors */
598
599
600 return ( MCIERR_SUCCESS );
601} /* MapConnectorsVSD */
Note: See TracBrowser for help on using the repository browser.