Esempio n. 1
0
void CCoreAudioDevice::Close()
{
  if (!m_DeviceId)
    return;

  // Stop the device if it was started
  Stop();

  // Unregister the IOProc if we have one
  if (m_IoProc)
    SetInputSource(NULL, 0, 0);

  SetHogStatus(false);
  CCoreAudioHardware::SetAutoHogMode(false);

  if (m_MixerRestore > -1) // We changed the mixer status
    SetMixingSupport((m_MixerRestore ? true : false));
  m_MixerRestore = -1;

  if (m_SampleRateRestore != 0.0f)
    SetNominalSampleRate(m_SampleRateRestore);

  if (m_BufferSizeRestore && m_BufferSizeRestore != GetBufferSize())
  {
    SetBufferSize(m_BufferSizeRestore);
    m_BufferSizeRestore = 0;
  }

  m_IoProc = NULL;
  m_pSource = NULL;
  m_DeviceId = 0;
  m_ObjectListenerProc = NULL;
}
Esempio n. 2
0
void CCoreAudioUnit::Close()
{
  if (!m_Initialized && !m_audioUnit)
    return;

  if (m_renderProc)
    SetInputSource(NULL);

  Stop();

  if (m_busNumber != INVALID_BUS)
  {
    OSStatus ret = AUGraphDisconnectNodeInput(m_audioGraph, m_audioNode, m_busNumber);
    if (ret)
    {
      CLog::Log(LOGERROR, "CCoreAudioUnit::Close: Unable to disconnect AudioUnit. Error = %s", GetError(ret).c_str());
    }

    ret = AUGraphRemoveNode(m_audioGraph, m_audioNode);
    if (ret)
    {
      CLog::Log(LOGERROR, "CCoreAudioUnit::Close: Unable to disconnect AudioUnit. Error = %s", GetError(ret).c_str());
    }
  }

  AUGraphUpdate(m_audioGraph, NULL);

  m_Initialized = false;
  m_audioUnit = NULL;
  m_audioNode = NULL;
  m_pSource = NULL;
}
Esempio n. 3
0
void CSTb710xHDMI::SetControl(stm_output_control_t ctrl, ULONG ulNewVal)
{
  DEBUGF2(2,("CSTb710xHDMI::SetControl: 0x%.8x/%lu\n", ctrl, ulNewVal));

  switch (ctrl)
  {
    case STM_CTRL_AV_SOURCE_SELECT:
      if(SetInputSource(ulNewVal))
        m_ulInputSource = ulNewVal;
      break;
    default:
      CSTmHDMI::SetControl(ctrl, ulNewVal);
      break;
  }
}
Esempio n. 4
0
bool CCoreAudioGraph::Close()
{
  if (!m_audioGraph)
    return false;

  OSStatus ret;

  Stop();

  SetInputSource(NULL);

  while (!m_auUnitList.empty())
  {
    CAUOutputDevice *d = m_auUnitList.front();
    m_auUnitList.pop_front();
    ReleaseBus(d->GetBus());
    d->Close();
    delete d;
  }

  if (m_inputUnit)
  {
    ReleaseBus(m_inputUnit->GetBus());
    m_inputUnit->Close();
    delete m_inputUnit;
    m_inputUnit = NULL;
  }

  if (m_mixerUnit)
  {
    m_mixerUnit->Close();
    delete m_mixerUnit;
    m_mixerUnit = NULL;
  }

  if (m_audioUnit)
  {
    m_audioUnit->Close();
    delete m_audioUnit;
    m_audioUnit = NULL;
  }

  ret = AUGraphUninitialize(m_audioGraph);
  if (ret)
  {
    CLog::Log(LOGERROR, "CCoreAudioGraph::Close: Error unitialize. Error = %s", GetError(ret).c_str());
  }

  ret = AUGraphClose(m_audioGraph);
  if (ret)
  {
    CLog::Log(LOGERROR, "CCoreAudioGraph::Close: Error close. Error = %s", GetError(ret).c_str());
  }

  ret = DisposeAUGraph(m_audioGraph);
  if (ret)
  {
    CLog::Log(LOGERROR, "CCoreAudioGraph::Close: Error dispose. Error = %s", GetError(ret).c_str());
  }

  return true;
}
Esempio n. 5
0
bool CCoreAudioGraph::Open(ICoreAudioSource *pSource, AEAudioFormat &format, bool allowMixing)
{
  OSStatus ret;

  AudioStreamBasicDescription inputFormat;
  AudioStreamBasicDescription outputFormat;

  m_allowMixing   = allowMixing;

  ret = NewAUGraph(&m_audioGraph);
  if (ret)
  {
    CLog::Log(LOGERROR, "CCoreAudioGraph::Open: Error create audio grpah. Error = %s", GetError(ret).c_str());
    return false;
  }
  ret = AUGraphOpen(m_audioGraph);
  if (ret)
  {
    CLog::Log(LOGERROR, "CCoreAudioGraph::Open: Error open audio grpah. Error = %s", GetError(ret).c_str());
    return false;
  }

  // get output unit
  if (m_audioUnit)
  {
    CLog::Log(LOGERROR, "CCoreAudioGraph::Open: Error audio unit already open. double call ?");
    return false;
  }

  m_audioUnit = new CAUOutputDevice();
  if (!m_audioUnit->Open(m_audioGraph, kAudioUnitType_Output, kAudioUnitSubType_RemoteIO, kAudioUnitManufacturer_Apple))
    return false;

  if (!m_audioUnit->EnableInputOuput())
    return false;

  m_audioUnit->GetFormatDesc(format, &inputFormat);

  //if(!allowMixing)
  //{
    if (!m_audioUnit->SetFormat(&inputFormat, kAudioUnitScope_Input, kOutputBus))
      return false;

    if (!m_audioUnit->SetFormat(&inputFormat, kAudioUnitScope_Output, kInputBus))
      return false;
  //}

  if (allowMixing)
  {
    // get mixer unit
    if (m_mixerUnit)
    {
      CLog::Log(LOGERROR, "CCoreAudioGraph::Open: Error mixer unit already open. double call ?");
      return false;
    }

    m_mixerUnit = new CAUMultiChannelMixer();

    if (!m_mixerUnit->Open(m_audioGraph, kAudioUnitType_Mixer, kAudioUnitSubType_MultiChannelMixer, kAudioUnitManufacturer_Apple))
      return false;

    // set number of input buses
    if (!m_mixerUnit->SetInputBusCount(MAX_CONNECTION_LIMIT))
      return false;

    //if(!m_mixerUnit->SetFormat(&fmt, kAudioUnitScope_Output, kOutputBus))
    //  return false;

    m_mixerUnit->SetBus(0);

    if (!m_audioUnit->GetFormat(&outputFormat, kAudioUnitScope_Input, kOutputBus))
      return false;

    /*
    if(!m_mixerUnit->SetInputBusFormat(MAX_CONNECTION_LIMIT, &outputFormat))
      return false;
    */

    ret =  AUGraphConnectNodeInput(m_audioGraph, m_mixerUnit->GetNode(), 0, m_audioUnit->GetNode(), 0);
    if (ret)
    {
      CLog::Log(LOGERROR, "CCoreAudioGraph::Open: Error connecting m_m_mixerNode. Error = %s", GetError(ret).c_str());
      return false;
    }

    // get output unit
    if (m_inputUnit)
    {
      CLog::Log(LOGERROR, "CCoreAudioGraph::Open: Error mixer unit already open. double call ?");
      return false;
    }

    m_inputUnit = new CAUOutputDevice();

    if (!m_inputUnit->Open(m_audioGraph, kAudioUnitType_FormatConverter, kAudioUnitSubType_AUConverter, kAudioUnitManufacturer_Apple))
      return false;

    if (!m_inputUnit->SetFormat(&inputFormat, kAudioUnitScope_Input, kOutputBus))
      return false;

    /*
    if(!m_inputUnit->SetFormat(&outputFormat, kAudioUnitScope_Output, kOutputBus))
      return false;
    */

    // configure output unit
    int busNumber = GetFreeBus();

    ret = AUGraphConnectNodeInput(m_audioGraph, m_inputUnit->GetNode(), 0, m_mixerUnit->GetNode(), busNumber);
    if (ret)
    {
      CLog::Log(LOGERROR, "CCoreAudioGraph::Open: Error connecting m_converterNode. Error = %s", GetError(ret).c_str());
      return false;
    }

    m_inputUnit->SetBus(busNumber);

    ret = AUGraphUpdate(m_audioGraph, NULL);
    if (ret)
    {
      CLog::Log(LOGERROR, "CCoreAudioGraph::Open: Error update graph. Error = %s", GetError(ret).c_str());
      return false;
    }
    ret = AUGraphInitialize(m_audioGraph);
    if (ret)
    {
      CLog::Log(LOGERROR, "CCoreAudioGraph::Open: Error initialize graph. Error = %s", GetError(ret).c_str());
      return false;
    }

    // Regenerate audio format and copy format for the Output AU
  }

  ret = AUGraphUpdate(m_audioGraph, NULL);
  if (ret)
  {
    CLog::Log(LOGERROR, "CCoreAudioGraph::Open: Error update graph. Error = %s", GetError(ret).c_str());
    return false;
  }

  std::string formatString;
  AudioStreamBasicDescription inputDesc_end, outputDesc_end;
  m_audioUnit->GetFormat(&inputDesc_end, kAudioUnitScope_Input, kOutputBus);
  m_audioUnit->GetFormat(&outputDesc_end, kAudioUnitScope_Output, kInputBus);
  CLog::Log(LOGINFO, "CCoreAudioGraph::Open: Input Stream Format  %s", StreamDescriptionToString(inputDesc_end, formatString));
  CLog::Log(LOGINFO, "CCoreAudioGraph::Open: Output Stream Format %s", StreamDescriptionToString(outputDesc_end, formatString));

  if (m_mixerUnit)
  {
    m_mixerUnit->GetFormat(&inputDesc_end, kAudioUnitScope_Input, kOutputBus);
    m_mixerUnit->GetFormat(&outputDesc_end, kAudioUnitScope_Output, kOutputBus);
    CLog::Log(LOGINFO, "CCoreAudioGraph::Open: Input Stream Format  %s", StreamDescriptionToString(inputDesc_end, formatString));
    CLog::Log(LOGINFO, "CCoreAudioGraph::Open: Output Stream Format %s", StreamDescriptionToString(outputDesc_end, formatString));
  }

  if (m_inputUnit)
  {
    m_inputUnit->GetFormat(&inputDesc_end, kAudioUnitScope_Input, kOutputBus);
    m_inputUnit->GetFormat(&outputDesc_end, kAudioUnitScope_Output, kOutputBus);
    CLog::Log(LOGINFO, "CCoreAudioGraph::Open: Input Stream Format  %s", StreamDescriptionToString(inputDesc_end, formatString));
    CLog::Log(LOGINFO, "CCoreAudioGraph::Open: Output Stream Format %s", StreamDescriptionToString(outputDesc_end, formatString));
  }

  ret = AUGraphInitialize(m_audioGraph);
  if (ret)
  {
    CLog::Log(LOGERROR, "CCoreAudioGraph::Open: Error initialize graph. Error = %s", GetError(ret).c_str());
    return false;
  }

  UInt32 bufferFrames = m_audioUnit->GetBufferFrameSize();

  m_audioUnit->SetMaxFramesPerSlice(bufferFrames);
  if (m_inputUnit)
    m_inputUnit->SetMaxFramesPerSlice(bufferFrames);

  SetInputSource(pSource);

  ShowGraph();

  return Start();
}
Esempio n. 6
0
bool CCoreAudioGraph::Open(ICoreAudioSource *pSource, AEAudioFormat &format,
  AudioDeviceID deviceId, bool allowMixing, AudioChannelLayoutTag layoutTag)
{
  AudioStreamBasicDescription fmt = {0};
  AudioStreamBasicDescription inputFormat = {0};
  AudioStreamBasicDescription outputFormat = {0};

  m_deviceId = deviceId;
  m_allowMixing = allowMixing;

  OSStatus ret = NewAUGraph(&m_audioGraph);
  if (ret)
  {
    CLog::Log(LOGERROR, "CCoreAudioGraph::Open: "
      "Error create audio grpah. Error = %s", GetError(ret).c_str());
    return false;
  }
  ret = AUGraphOpen(m_audioGraph);
  if (ret)
  {
    CLog::Log(LOGERROR, "CCoreAudioGraph::Open: "
      "Error open audio grpah. Error = %s", GetError(ret).c_str());
    return false;
  }

  // get output unit
  if (m_audioUnit)
  {
    CLog::Log(LOGERROR, "CCoreAudioGraph::Open: "
      "Error audio unit already open. double call ?");
    return false;
  }

  m_audioUnit = new CAUOutputDevice();
  if (!m_audioUnit->Open(m_audioGraph,
    kAudioUnitType_Output, kAudioUnitSubType_HALOutput, kAudioUnitManufacturer_Apple))
    return false;
  m_audioUnit->SetBus(GetFreeBus());

  m_audioUnit->GetFormatDesc(format, &inputFormat, &fmt);

  if (!m_audioUnit->EnableInputOuput())
    return false;

  if (!m_audioUnit->SetCurrentDevice(deviceId))
    return false;

  if (allowMixing)
  {
    delete m_mixMap;
    m_mixMap = CCoreAudioMixMap::CreateMixMap(m_audioUnit, format, layoutTag);

    if (m_mixMap || m_mixMap->IsValid())
    {
      // maximum input channel ber input bus
      //fmt.mChannelsPerFrame = MAXIMUM_MIXER_CHANNELS;

      // get output unit
      if (m_inputUnit)
      {
        CLog::Log(LOGERROR, "CCoreAudioGraph::Open: Error mixer unit already open. double call ?");
        return false;
      }

      m_inputUnit = new CAUOutputDevice();

      if (!m_inputUnit->Open(m_audioGraph,
        kAudioUnitType_FormatConverter, kAudioUnitSubType_AUConverter, kAudioUnitManufacturer_Apple))
        return false;

      if (!m_inputUnit->SetFormat(&inputFormat, kAudioUnitScope_Input, kOutputBus))
        return false;

      if (!m_inputUnit->SetFormat(&fmt, kAudioUnitScope_Output, kOutputBus))
        return false;

      // get mixer unit
      if (m_mixerUnit)
      {
        CLog::Log(LOGERROR, "CCoreAudioGraph::Open: Error mixer unit already open. double call ?");
        return false;
      }

      m_mixerUnit = new CAUMatrixMixer();

      if (!m_mixerUnit->Open(m_audioGraph,
        kAudioUnitType_Mixer, kAudioUnitSubType_MatrixMixer, kAudioUnitManufacturer_Apple))
        return false;

      // set number of input buses
      if (!m_mixerUnit->SetInputBusCount(MAX_CONNECTION_LIMIT))
        return false;

      // set number of output buses
      if (!m_mixerUnit->SetOutputBusCount(1))
        return false;

      if (!m_mixerUnit->SetInputBusFormat(MAX_CONNECTION_LIMIT, &fmt))
        return false;

      if (!m_mixerUnit->SetFormat(&fmt, kAudioUnitScope_Output, kOutputBus))
        return false;

      ret =  AUGraphConnectNodeInput(m_audioGraph, m_mixerUnit->GetNode(), 0, m_audioUnit->GetNode(), 0);
      if (ret)
      {
        CLog::Log(LOGERROR, "CCoreAudioGraph::Open: "
          "Error connecting m_m_mixerNode. Error = %s", GetError(ret).c_str());
        return false;
      }

      m_mixerUnit->SetBus(0);

      // configure output unit
      int busNumber = GetFreeBus();

      ret = AUGraphConnectNodeInput(m_audioGraph, m_inputUnit->GetNode(), 0, m_mixerUnit->GetNode(), busNumber);
      if (ret)
      {
        CLog::Log(LOGERROR, "CCoreAudioGraph::Open: "
          "Error connecting m_converterNode. Error = %s", GetError(ret).c_str());
        return false;
      }

      m_inputUnit->SetBus(busNumber);

      ret = AUGraphUpdate(m_audioGraph, NULL);
      if (ret)
      {
        CLog::Log(LOGERROR, "CCoreAudioGraph::Open: "
          "Error update graph. Error = %s", GetError(ret).c_str());
        return false;
      }
      ret = AUGraphInitialize(m_audioGraph);
      if (ret)
      {
        CLog::Log(LOGERROR, "CCoreAudioGraph::Open: "
          "Error initialize graph. Error = %s", GetError(ret).c_str());
        return false;
      }

      // Update format structure to reflect the desired format from the mixer
      // The output format of the mixer is identical to the input format, except for the channel count
      fmt.mChannelsPerFrame = m_mixMap->GetOutputChannels();

      UInt32 inputNumber = m_inputUnit->GetBus();
      int channelOffset = GetMixerChannelOffset(inputNumber);
      if (!CCoreAudioMixMap::SetMixingMatrix(m_mixerUnit, m_mixMap, &inputFormat, &fmt, channelOffset))
        return false;

      // Regenerate audio format and copy format for the Output AU
      outputFormat = fmt;
    }
    else
    {
      outputFormat = inputFormat;
    }

  }
  else
  {
    outputFormat = inputFormat;
  }

  if (!m_audioUnit->SetFormat(&outputFormat, kAudioUnitScope_Input, kOutputBus))
  {
    CLog::Log(LOGERROR, "CCoreAudioGraph::Open: "
      "Error setting input format on audio device. Channel count %d, set it to %d",
      (int)outputFormat.mChannelsPerFrame, format.m_channelLayout.Count());
    outputFormat.mChannelsPerFrame = format.m_channelLayout.Count();
    if (!m_audioUnit->SetFormat(&outputFormat, kAudioUnitScope_Input, kOutputBus))
      return false;
  }

  std::string formatString;
  // asume we are in dd-wave mode
  if (!m_inputUnit)
  {
    if (!m_audioUnit->SetFormat(&inputFormat, kAudioUnitScope_Output, kInputBus))
    {
      CLog::Log(LOGERROR, "CCoreAudioGraph::Open: "
        "Error setting Device Output Stream Format %s",
        StreamDescriptionToString(inputFormat, formatString));
    }
  }

  ret = AUGraphUpdate(m_audioGraph, NULL);
  if (ret)
  {
    CLog::Log(LOGERROR, "CCoreAudioGraph::Open: "
      "Error update graph. Error = %s", GetError(ret).c_str());
    return false;
  }

  AudioStreamBasicDescription inputDesc_end, outputDesc_end;
  m_audioUnit->GetFormat(&inputDesc_end, kAudioUnitScope_Input, kOutputBus);
  m_audioUnit->GetFormat(&outputDesc_end, kAudioUnitScope_Output, kInputBus);
  CLog::Log(LOGINFO, "CCoreAudioGraph::Open: Input Stream Format  %s",
    StreamDescriptionToString(inputDesc_end, formatString));
  CLog::Log(LOGINFO, "CCoreAudioGraph::Open: Output Stream Format %s",
    StreamDescriptionToString(outputDesc_end, formatString));

  if (m_mixerUnit)
  {
    m_mixerUnit->GetFormat(&inputDesc_end, kAudioUnitScope_Input, kOutputBus);
    m_mixerUnit->GetFormat(&outputDesc_end, kAudioUnitScope_Output, kOutputBus);
    CLog::Log(LOGINFO, "CCoreAudioGraph::Open: Input Stream Format  %s",
      StreamDescriptionToString(inputDesc_end, formatString));
    CLog::Log(LOGINFO, "CCoreAudioGraph::Open: Output Stream Format %s",
      StreamDescriptionToString(outputDesc_end, formatString));
  }

  if (m_inputUnit)
  {
    m_inputUnit->GetFormat(&inputDesc_end, kAudioUnitScope_Input, kOutputBus);
    m_inputUnit->GetFormat(&outputDesc_end, kAudioUnitScope_Output, kOutputBus);
    CLog::Log(LOGINFO, "CCoreAudioGraph::Open: Input Stream Format  %s",
      StreamDescriptionToString(inputDesc_end, formatString));
    CLog::Log(LOGINFO, "CCoreAudioGraph::Open: Output Stream Format %s",
      StreamDescriptionToString(outputDesc_end, formatString));
  }

  ret = AUGraphInitialize(m_audioGraph);
  if (ret)
  {
    CLog::Log(LOGERROR, "CCoreAudioGraph::Open: "
      "Error initialize graph. Error = %s", GetError(ret).c_str());
    return false;
  }

  UInt32 bufferFrames = m_audioUnit->GetBufferFrameSize();
  if (!m_audioUnit->SetMaxFramesPerSlice(bufferFrames))
    return false;

  SetInputSource(pSource);

  return Start();
}
Esempio n. 7
0
bool CSTmHDFormatterHDMI::Create(void)
{
  ULONG val;

  DENTRY();

  if(!CSTmHDMI::Create())
    return false;

  /*
   * Default digital configuration
   */
  val = (HDFMT_CFG_RCTRL_R << HDFMT_CFG_REORDER_RSHIFT) |
        (HDFMT_CFG_RCTRL_G << HDFMT_CFG_REORDER_GSHIFT) |
        (HDFMT_CFG_RCTRL_B << HDFMT_CFG_REORDER_BSHIFT) |
         HDFMT_CFG_CLIP_SAV_EAV;

  WriteHDFmtReg(HDFMT_DIG1_CFG, val);

  /*
   * Default HDFormatter/HDMI glue configuration
   */
  val = ReadHDMIReg(STM_HDMI_GPOUT);

  switch(m_Revision)
  {
    case STM_HDF_HDMI_REV1:
    {
      val &= ~(STM_HDMI_GPOUT_EXTERNAL_PCMPLAYER_EN   |
               STM_HDMI_GPOUT_DTS_FORMAT_EN           |
               STM_HDMI_GPOUT_CTS_CLK_DIV_BYPASS      |
               STM_HDMI_GPOUT_DTS_SPDIF_MODE_EN);

      val |= (STM_HDMI_GPOUT_I2S_EN           |
              STM_HDMI_GPOUT_SPDIF_EN         |
              STM_HDMI_GPOUT_I2S_N_SPDIF_DATA |
              STM_HDMI_GPOUT_HDCP_VSYNC_DISABLE);
      break;
    }
    case STM_HDF_HDMI_REV2:
    {
      val &= ~(STM_HDMI_GPOUT_EXTERNAL_PCMPLAYER_EN   |
               STM_HDMI_GPOUT_DTS_SPDIF_MODE_EN       |
               STM_HDMI_GPOUT_DROP_CB_N_CR            |
               STM_HDMI_GPOUT_DROP_EVEN_N_ODD_SAMPLES |
               STM_HDMI_GPOUT_IN_MASK);

      val |= (STM_HDMI_GPOUT_I2S_EN            |
              STM_HDMI_GPOUT_SPDIF_EN          |
              STM_HDMI_GPOUT_I2S_N_SPDIF_DATA  |
              STM_HDMI_GPOUT_I2S_N_SPDIF_CLOCK |
              STM_HDMI_GPOUT_IN_HDFORMATTER    |
              STM_HDMI_GPOUT_HDCP_VSYNC_DISABLE);
      break;
    }
    case STM_HDF_HDMI_REV3:
    {
      val &= ~STM_HDMI_GPOUT_EXTERNAL_PCMPLAYER_EN;

      val |= (STM_HDMI_GPOUT_I2S_EN            |
              STM_HDMI_GPOUT_SPDIF_EN          |
              STM_HDMI_GPOUT_I2S_N_SPDIF_DATA  |
              STM_HDMI_GPOUT_I2S_N_SPDIF_CLOCK |
              STM_HDMI_GPOUT_HDCP_VSYNC_DISABLE);
      break;
    }
  }

  WriteHDMIReg(STM_HDMI_GPOUT, val);

  SetInputSource((STM_AV_SOURCE_MAIN_INPUT | STM_AV_SOURCE_2CH_I2S_INPUT));

  DEXIT();
  return true;
}
Esempio n. 8
0
void CSTmHDFormatterHDMI::SetControl(stm_output_control_t ctrl, ULONG ulNewVal)
{
  DEBUGF2(3,("CSTmHDFormatterHDMI::SetControl\n"));

  switch (ctrl)
  {
    case STM_CTRL_AV_SOURCE_SELECT:
    {
      SetInputSource(ulNewVal);
      break;
    }
    case STM_CTRL_SIGNAL_RANGE:
    {
      if(ulNewVal> STM_SIGNAL_VIDEO_RANGE)
        break;

      m_signalRange = (stm_display_signal_range_t)ulNewVal;

      ULONG val = ReadHDFmtReg(HDFMT_DIG1_CFG) & ~(HDFMT_CFG_CLIP_SAV_EAV |
                                                   HDFMT_CFG_CLIP_EN);

      switch(m_signalRange)
      {
        case STM_SIGNAL_FILTER_SAV_EAV:
          DEBUGF2(2,("CSTmHDFormatterHDMI::SetControl - Filter SAV/EAV\n"));
          val |= HDFMT_CFG_CLIP_SAV_EAV;
          break;
        case STM_SIGNAL_VIDEO_RANGE:
          DEBUGF2(2,("CSTmHDFormatterHDMI::SetControl - Clip input to video range\n"));
          val |= HDFMT_CFG_CLIP_EN;
          break;
        default:
          DEBUGF2(2,("CSTmHDFormatterHDMI::SetControl - Full signal range\n"));
          break;
      }

      WriteHDFmtReg(HDFMT_DIG1_CFG, val);
      m_pIFrameManager->ForceAVIUpdate();

      break;
    }
    case STM_CTRL_HDMI_AUDIO_OUT_SELECT:
    {
      /*
       * We are not supporting anything other than basic audio on Rev1, i.e.
       * 7200cut1.
       */
      if(m_Revision == STM_HDF_HDMI_REV1)
        return;

      /*
       * Don't do anything if the value isn't changing
       */
      if(m_ulAudioOutputType == (stm_hdmi_audio_output_type_t)ulNewVal)
        return;

      /*
       * Check the validity of the setup
       */
      switch(ulNewVal)
      {
        case STM_HDMI_AUDIO_TYPE_NORMAL:
        case STM_HDMI_AUDIO_TYPE_ONEBIT:
          break;
        case STM_HDMI_AUDIO_TYPE_DST:
        case STM_HDMI_AUDIO_TYPE_DST_DOUBLE:
          if(m_ulInputSource & STM_AV_SOURCE_8CH_I2S_INPUT)
            return;
          break;
        case STM_HDMI_AUDIO_TYPE_HBR:
          if((m_ulInputSource & STM_AV_SOURCE_2CH_I2S_INPUT) ||
             ((m_Revision == STM_HDF_HDMI_REV3) && (m_ulInputSource & STM_AV_SOURCE_SPDIF_INPUT)))
          {
            return;
          }
          break;
        default:
          return;
      }

      DEBUGF2(2,("%s: change audio output type to %lu\n",__PRETTY_FUNCTION__,ulNewVal));

      /*
       * We are being told there is a change to the audio stream, so stop the
       * current audio processing and get the audio update interrupt handling
       * to sort it out.
       */
      g_pIOS->LockResource(m_statusLock);

      InvalidateAudioPackets();

      m_ulAudioOutputType = (stm_hdmi_audio_output_type_t)ulNewVal;
      m_audioState.status = STM_HDMI_AUDIO_STOPPED;

      SetSPDIFPlayerMode();

      g_pIOS->UnlockResource(m_statusLock);
      break;
    }
    default:
    {
      CSTmHDMI::SetControl(ctrl, ulNewVal);
      break;
    }
  }
}