/*----------------------------------------------------------------------------- IMiniportStreamAudioEngineNode::SetStreamChannelVolume Decscription: When handling SET volume KS property for the device, Portcls calls this method, inside its property handlers, to set the current setting on the specific channel. Parameters: _In_ Channel: the target channel for this GET volume operation _In_ TargetVolume: volume value to set _In_ CurveType: type of curve to apply to the ramp _In_ CurveDuration: amount of time in hns over which to ramp the volume Return Value: Appropriate NTSTATUS code Called at PASSIVE_LEVEL Remarks -------------------------------------------------------------------------------------------------------------------------*/ STDMETHODIMP_(NTSTATUS) CMiniportWaveRTStream::SetStreamChannelVolume ( _In_ UINT32 Channel, _In_ LONG TargetVolume, _In_ AUDIO_CURVE_TYPE CurveType, _In_ ULONGLONG CurveDuration ) { UNREFERENCED_PARAMETER(CurveType); UNREFERENCED_PARAMETER(CurveDuration); NTSTATUS ntStatus = STATUS_INVALID_DEVICE_REQUEST; PAGED_CODE (); DPF_ENTER(("[CMiniportWaveRTStream::SetStreamChannelVolume]")); // Snap the volume level to our range of steppings. LONG lVolume = VOLUME_NORMALIZE_IN_RANGE(TargetVolume); // If Channel is ALL_CHANNELS_ID, then set the level on all channels if ( ALL_CHANNELS_ID == Channel ) { for (UINT32 i = 0; i < m_pWfExt->Format.nChannels; i++) { ntStatus = SetChannelVolume(i, lVolume); } } else { ntStatus = SetChannelVolume(Channel, lVolume); } return ntStatus; }
/*----------------------------------------------------------------------------- IMiniportAudioEngineNode::SetDeviceChannelVolume Decscription: When handling SET volume KS property for the device, Portcls calls this method, inside its property handlers, to set the current setting on the specific channel. Parameters: _In_ _ulNodeId: node id for the target audio engine node _In_ _uiChannel: the target channel for this GET volume operation _In_ _Volume: volume value to set Return Value: Appropriate NTSTATUS code Called at PASSIVE_LEVEL Remarks -------------------------------------------------------------------------------------------------------------------------*/ STDMETHODIMP_(NTSTATUS) CMiniportWaveRT::SetDeviceChannelVolume(_In_ ULONG _ulNodeId, _In_ UINT32 _uiChannel, _In_ LONG _Volume) { NTSTATUS ntStatus = STATUS_INVALID_DEVICE_REQUEST; PAGED_CODE (); DPF_ENTER(("[CMiniportWaveRT::SetEndpointChannelVolume]")); IF_TRUE_ACTION_JUMP(_ulNodeId != KSNODE_WAVE_AUDIO_ENGINE, ntStatus = STATUS_INVALID_DEVICE_REQUEST, Exit); // Snap the volume level to our range of steppings. LONG lVolume = VOLUME_NORMALIZE_IN_RANGE(_Volume); ntStatus = SetChannelVolume(_uiChannel, lVolume); Exit: return ntStatus; }
NTSTATUS PropertyHandler_Volume ( _In_ PADAPTERCOMMON AdapterCommon, _In_ PPCPROPERTY_REQUEST PropertyRequest, _In_ ULONG MaxChannels ) /*++ Routine Description: Property handler for KSPROPERTY_AUDIO_VOLUMELEVEL Arguments: AdapterCommon - interface to the common adapter object. PropertyRequest - property request structure. MaxChannels - # of supported channels. Return Value: NT status code. --*/ { PAGED_CODE(); DPF_ENTER(("[%s]",__FUNCTION__)); NTSTATUS ntStatus = STATUS_INVALID_DEVICE_REQUEST; ULONG ulChannel; PLONG plVolume; if (PropertyRequest->Verb & KSPROPERTY_TYPE_BASICSUPPORT) { ntStatus = PropertyHandler_BasicSupportVolume( PropertyRequest, MaxChannels); } else { ntStatus = ValidatePropertyParams ( PropertyRequest, sizeof(LONG), // volume value is a LONG sizeof(ULONG) // instance is the channel number ); if (NT_SUCCESS(ntStatus)) { ulChannel = * (PULONG (PropertyRequest->Instance)); plVolume = PLONG (PropertyRequest->Value); if (ulChannel >= MaxChannels && ulChannel != ALL_CHANNELS_ID) { ntStatus = STATUS_INVALID_PARAMETER; } else if (PropertyRequest->Verb & KSPROPERTY_TYPE_GET) { *plVolume = AdapterCommon->MixerVolumeRead ( PropertyRequest->Node, ulChannel == ALL_CHANNELS_ID ? 0 : ulChannel ); PropertyRequest->ValueSize = sizeof(ULONG); } else if (PropertyRequest->Verb & KSPROPERTY_TYPE_SET) { if (ALL_CHANNELS_ID == ulChannel) { for (ULONG i=0; i<ulChannel; ++i) { AdapterCommon->MixerVolumeWrite ( PropertyRequest->Node, i, VOLUME_NORMALIZE_IN_RANGE(*plVolume) ); } } else { AdapterCommon->MixerVolumeWrite ( PropertyRequest->Node, ulChannel, VOLUME_NORMALIZE_IN_RANGE(*plVolume) ); } } } if (!NT_SUCCESS(ntStatus)) { DPF(D_TERSE, ("[%s - ntStatus=0x%08x]",__FUNCTION__,ntStatus)); } } return ntStatus; } // PropertyHandlerVolume