zoukankan      html  css  js  c++  java
  • MT6737 Android N 平台 Audio系统学习----录音到播放录音流程分析

    http://blog.csdn.net/u014310046/article/details/54133688

    本文将从主mic录音到播放流程来进行学习mtk audio系统架构。 
    这里写图片描述

    在AudioFlinger::RecordThread::threadLoop中会调用mInput->stream->read读取数据,stream就是audio_stream_in_t类型的指针,在执行open_input_stream时被初始化,先在它其实是一个legacy_stream_in类型的指针。当调用read时,in_read将会被调用。然后真正执行的是AudioStreamIn类中的read函数。

    这里写图片描述
    从上图可知要想实现mic录音,需要打通ADC0_L、ADC0_R/PreampL、PreampR/AIN0_P、AIN0_N(main mic)/AIN1_P、AIN1_N(headset mic)/AIN2_P、AIN2_N(ref mic)。 
    下面开始分析从main mic录音。

    1、snd_pcm_ops mtk_afe_capture_ops

    static struct snd_pcm_ops mtk_afe_capture_ops = { 
    .open = mtk_capture_pcm_open, 
    .close = mtk_capture_pcm_close, 
    .ioctl = snd_pcm_lib_ioctl, 
    .hw_params = mtk_capture_pcm_hw_params, 
    .hw_free = mtk_capture_pcm_hw_free, 
    .prepare = mtk_capture_pcm_prepare, 
    .trigger = mtk_capture_pcm_trigger, 
    .pointer = mtk_capture_pcm_pointer, 
    .copy = mtk_capture_pcm_copy, 
    .silence = mtk_capture_pcm_silence, 
    .page = mtk_capture_pcm_page, 
    };

    会先调用.open = mtk_capture_pcm_open打开capture。

    
    static int mtk_capture_pcm_open(struct snd_pcm_substream *substream)
    {
        struct snd_pcm_runtime *runtime = substream->runtime;
        int ret = 0;
    
        AudDrv_Clk_On();
        AudDrv_ADC_Clk_On();
        VUL_Control_context = Get_Mem_ControlT(Soc_Aud_Digital_Block_MEM_VUL);
    
        /* can allocate sram_dbg */
        AfeControlSramLock();
    
    #ifndef CAPTURE_FORCE_USE_DRAM
        if (GetSramState() ==  SRAM_STATE_FREE) {
            pr_warn("mtk_capture_pcm_open use sram
    ");
            mtk_capture_hardware.buffer_bytes_max = GetCaptureSramSize();
            SetSramState(SRAM_STATE_CAPTURE);
            mCaptureUseSram = true;
        } else {
            pr_warn("mtk_capture_pcm_open use dram
    ");
            mtk_capture_hardware.buffer_bytes_max = UL1_MAX_BUFFER_SIZE;
            mCaptureUseSram = false;
        }
    #else
        pr_warn("mtk_capture_pcm_open use dram
    ");
        mtk_capture_hardware.buffer_bytes_max = UL1_MAX_BUFFER_SIZE;
    #endif
    
        AfeControlSramUnLock();
    
        runtime->hw = mtk_capture_hardware;
        memcpy((void *)(&(runtime->hw)), (void *)&mtk_capture_hardware , sizeof(struct snd_pcm_hardware));
    
        ret = snd_pcm_hw_constraint_list(runtime, 0, SNDRV_PCM_HW_PARAM_RATE,
                         &constraints_sample_rates);
        ret = snd_pcm_hw_constraint_integer(runtime, SNDRV_PCM_HW_PARAM_PERIODS);
    
        if (ret < 0)
            pr_warn("snd_pcm_hw_constraint_integer failed
    ");
    
    
    
        if (ret < 0) {
            pr_err("mtk_capture_pcm_close
    ");
            mtk_capture_pcm_close(substream);
            return ret;
        }
    
        if (mCaptureUseSram == false)
            AudDrv_Emi_Clk_On();
    
        pr_warn("mtk_capture_pcm_open return
    ");
        return 0;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56

    接着调用mtk_capture_pcm_hw_params

    
    static int mtk_capture_pcm_hw_params(struct snd_pcm_substream *substream,
                         struct snd_pcm_hw_params *hw_params)
    {
        struct snd_pcm_runtime *runtime = substream->runtime;
        struct snd_dma_buffer *dma_buf = &substream->dma_buffer;
        int ret = 0;
    
        pr_warn("mtk_capture_pcm_hw_params
    ");
    
        dma_buf->dev.type = SNDRV_DMA_TYPE_DEV;
        dma_buf->dev.dev = substream->pcm->card->dev;
        dma_buf->private_data = NULL;
    
        if (mCaptureUseSram == true) {
            runtime->dma_bytes = params_buffer_bytes(hw_params);
            pr_warn("mtk_capture_pcm_hw_params mCaptureUseSram dma_bytes = %zu
    ", runtime->dma_bytes);
            substream->runtime->dma_area = (unsigned char *)Get_Afe_SramBase_Pointer();
            substream->runtime->dma_addr = Get_Afe_Sram_Phys_Addr();
        } else if (Capture_dma_buf->area) {
            pr_warn("Capture_dma_buf = %p Capture_dma_buf->area = %p apture_dma_buf->addr = 0x%lx
    ",
                   Capture_dma_buf, Capture_dma_buf->area, (long) Capture_dma_buf->addr);
            runtime->dma_bytes = params_buffer_bytes(hw_params);
            runtime->dma_area = Capture_dma_buf->area;
            runtime->dma_addr = Capture_dma_buf->addr;
        } else {
            pr_warn("mtk_capture_pcm_hw_params snd_pcm_lib_malloc_pages
    ");
            ret =  snd_pcm_lib_malloc_pages(substream, params_buffer_bytes(hw_params));
        }
    
        SetVULBuffer(substream, hw_params);
    
        pr_warn("mtk_capture_pcm_hw_params dma_bytes = %zu dma_area = %p dma_addr = 0x%lx
    ",
               substream->runtime->dma_bytes, substream->runtime->dma_area, (long)substream->runtime->dma_addr);
        return ret;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37

    调用mtk_capture_pcm_trigger

    static int mtk_capture_pcm_trigger(struct snd_pcm_substream *substream, int cmd)
    {
        pr_warn("mtk_capture_pcm_trigger cmd = %d
    ", cmd);
        //mtk_capture_pcm_trigger cmd = 1
        switch (cmd) {
        case SNDRV_PCM_TRIGGER_START:
        case SNDRV_PCM_TRIGGER_RESUME:
            return mtk_capture_alsa_start(substream);//调用mtk_capture_alsa_start
        case SNDRV_PCM_TRIGGER_STOP:
        case SNDRV_PCM_TRIGGER_SUSPEND:
            return mtk_capture_alsa_stop(substream);
        }
        return -EINVAL;
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14

    调用mtk_capture_alsa_start

    
    static int mtk_capture_alsa_start(struct snd_pcm_substream *substream)
    {
        pr_warn("mtk_capture_alsa_start
    ");
        SetMemifSubStream(Soc_Aud_Digital_Block_MEM_VUL, substream);
        StartAudioCaptureHardware(substream);
    #ifdef DENALI_FPGA_EARLYPORTING /* ccc early porting, copy from TurnOnDacPower() and ADC_LOOP_DAC_Func() */
        /* Afe_Set_Reg(AFE_SGEN_CON0, 0x24862862, 0xffffffff); */
    
        /* Ana_Set_Reg(PMIC_AFE_TOP_CON0, 0x0002, 0x0002);   //UL from sinetable */
        /* Ana_Set_Reg(PMIC_AFE_TOP_CON0, 0x0001, 0x0001);   //DL from sinetable */
    
        /* Ana_Set_Reg(AFE_SGEN_CFG0 , 0x0080 , 0xffff); */
        /* Ana_Set_Reg(AFE_SGEN_CFG1 , 0x0101 , 0xffff); */
    
        Ana_Get_Reg(AFE_AUDIO_TOP_CON0);   /* power on clock */
    
        Ana_Get_Reg(AFUNC_AUD_CON2);
        Ana_Get_Reg(AFUNC_AUD_CON0); /* sdm audio fifo clock power on */
        Ana_Get_Reg(AFUNC_AUD_CON2); /* sdm power on */
        Ana_Get_Reg(AFUNC_AUD_CON2); /* sdm fifo enable */
        Ana_Get_Reg(AFE_DL_SDM_CON1); /* set attenuation gain */
        Ana_Get_Reg(AFE_UL_DL_CON0); /* [0] afe enable */
    
        Ana_Get_Reg(AFE_PMIC_NEWIF_CFG0); /* 8k sample rate */
        Ana_Get_Reg(AFE_DL_SRC2_CON0_H);/* 8k sample rate */
        Ana_Get_Reg(AFE_DL_SRC2_CON0_L); /* turn off mute function and turn on dl */
        Ana_Get_Reg(PMIC_AFE_TOP_CON0); /* set DL in normal path, not from sine gen table */
        Ana_Get_Reg(AFE_SGEN_CFG0); /* set DL in normal path, not from sine gen table */
        Ana_Get_Reg(AFE_SGEN_CFG1); /* set DL in normal path, not from sine gen table */
    
        Ana_Get_Reg(TOP_CLKSQ); /* Enable CLKSQ 26MHz */
        Ana_Get_Reg(TOP_CLKSQ_SET); /* Turn on 26MHz source clock */
        Ana_Get_Reg(AFE_AUDIO_TOP_CON0);   /* power on clock */
    
        Ana_Get_Reg(FPGA_CFG1); /* must set in FPGA platform for PMIC digital loopback */
    #endif
        return 0;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40

    接着调用StartAudioCaptureHardware

    
    static void StartAudioCaptureHardware(struct snd_pcm_substream *substream)
    {
        pr_warn("StartAudioCaptureHardware
    ");
    
        ConfigAdcI2S(substream);
        SetI2SAdcIn(mAudioDigitalI2S);
    
        SetMemIfFetchFormatPerSample(Soc_Aud_Digital_Block_MEM_VUL, AFE_WLEN_16_BIT);
        SetMemIfFetchFormatPerSample(Soc_Aud_Digital_Block_MEM_VUL, AFE_WLEN_16_BIT);
        SetoutputConnectionFormat(OUTPUT_DATA_FORMAT_16BIT, Soc_Aud_InterConnectionOutput_O09);
        SetoutputConnectionFormat(OUTPUT_DATA_FORMAT_16BIT, Soc_Aud_InterConnectionOutput_O10);
    
        if (GetMemoryPathEnable(Soc_Aud_Digital_Block_I2S_IN_ADC) == false) {
            SetMemoryPathEnable(Soc_Aud_Digital_Block_I2S_IN_ADC, true);
            SetI2SAdcEnable(true);
        } else {
            SetMemoryPathEnable(Soc_Aud_Digital_Block_I2S_IN_ADC, true);
        }
    
        SetConnection(Soc_Aud_InterCon_Connection, Soc_Aud_InterConnectionInput_I03, Soc_Aud_InterConnectionOutput_O09);
        SetConnection(Soc_Aud_InterCon_Connection, Soc_Aud_InterConnectionInput_I04, Soc_Aud_InterConnectionOutput_O10);
    
    
        if (substream->runtime->format == SNDRV_PCM_FORMAT_S32_LE ||
            substream->runtime->format == SNDRV_PCM_FORMAT_U32_LE) {
            SetMemIfFetchFormatPerSample(Soc_Aud_Digital_Block_MEM_VUL, AFE_WLEN_32_BIT_ALIGN_8BIT_0_24BIT_DATA);
            SetoutputConnectionFormat(OUTPUT_DATA_FORMAT_24BIT, Soc_Aud_InterConnectionOutput_O09);
            SetoutputConnectionFormat(OUTPUT_DATA_FORMAT_24BIT, Soc_Aud_InterConnectionOutput_O10);
        }
    
        /* here to set interrupt */
        irq_add_user(substream,
                 Soc_Aud_IRQ_MCU_MODE_IRQ2_MCU_MODE,
                 substream->runtime->rate,
                 substream->runtime->period_size);
    
        SetSampleRate(Soc_Aud_Digital_Block_MEM_VUL, substream->runtime->rate);
        SetMemoryPathEnable(Soc_Aud_Digital_Block_MEM_VUL, true);
    
        EnableAfe(true);
    
    #ifdef DENALI_FPGA_EARLYPORTING /* ccc early porting test, copy from TurnOnADcPowerACC() */
        /* here to set digital part */
        /* Topck_Enable(true); */
        /* AdcClockEnable(true); */
        /* Ana_Set_Reg(AFE_ADDA2_UL_SRC_CON1_L, 0x0000, 0xffff);   //power on ADC clk //early porting 6752 remove */
    
        Ana_Set_Reg(AFE_AUDIO_TOP_CON0, 0x0000, 0xffff);   /* power on clock */
        /* Ana_Set_Reg(AFE_ADDA2_UL_SRC_CON1_L, 0x0000, 0xffff);   //power on ADC clk //early porting 6752 remove */
        Ana_Set_Reg(PMIC_AFE_TOP_CON0, 0x0000, 0xffff);       /* configure ADC setting */
    
        Ana_Set_Reg(AFE_UL_DL_CON0, 0x0001, 0xffff);   /* turn on afe */
    
        Ana_Set_Reg(AFE_PMIC_NEWIF_CFG2, 0x302F, 0xffff); /* config UL up8x_rxif adc voice mode, 8k sample rate */
        Ana_Set_Reg(AFE_UL_SRC0_CON0_H, (0 << 3 | 0 << 1) , 0x001f);/* ULsampling rate, 8k sample rate */
        /* Ana_Set_Reg(AFE_ADDA2_UL_SRC_CON0_H,
        (ULSampleRateTransform(SampleRate_VUL2) << 3 |
        ULSampleRateTransform(SampleRate_VUL2) << 1) , 0x001f); // ULsampling rate */
        /* Ana_Set_Reg(AFE_ADDA2_UL_SRC_CON0_L, 0x0041, 0xffff); */
    
        Ana_Set_Reg(AFE_UL_SRC0_CON0_L, 0x0005, 0xffff);   /* power on uplink, and loopback to DL */
    
        Afe_Set_Reg(FPGA_CFG1, 0x1, 0xffff); /* must set in FPGA platform for PMIC digital loopback */
    
    #endif
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68

    下面对上面函数进行分析 
    (1)SetI2SAdcIn

    ////////////////////////////////////////////////////*
    static void ConfigAdcI2S(struct snd_pcm_substream *substream)
    {
        mAudioDigitalI2S->mLR_SWAP = Soc_Aud_LR_SWAP_NO_SWAP;
        mAudioDigitalI2S->mBuffer_Update_word = 8;
        mAudioDigitalI2S->mFpga_bit_test = 0;
        mAudioDigitalI2S->mFpga_bit = 0;
        mAudioDigitalI2S->mloopback = 0;
        mAudioDigitalI2S->mINV_LRCK = Soc_Aud_INV_LRCK_NO_INVERSE;
        mAudioDigitalI2S->mI2S_FMT = Soc_Aud_I2S_FORMAT_I2S;
        mAudioDigitalI2S->mI2S_WLEN = Soc_Aud_I2S_WLEN_WLEN_16BITS;
        mAudioDigitalI2S->mI2S_SAMPLERATE = (substream->runtime->rate);
    }
    */////////////////////////////////////////////////////
    
    bool SetI2SAdcIn(AudioDigtalI2S *DigtalI2S)
    {
        uint32 Audio_I2S_Adc = 0;
    
        memcpy((void *)AudioAdcI2S, (void *)DigtalI2S, sizeof(AudioDigtalI2S));
    
        if (false == AudioAdcI2SStatus) {
            uint32 eSamplingRate = SampleRateTransform(AudioAdcI2S->mI2S_SAMPLERATE);
            uint32 dVoiceModeSelect = 0;
    
            Afe_Set_Reg(AFE_ADDA_TOP_CON0, 0, 0x1); /* Using Internal ADC */
            if (eSamplingRate == Soc_Aud_I2S_SAMPLERATE_I2S_8K)
                dVoiceModeSelect = 0;
            else if (eSamplingRate == Soc_Aud_I2S_SAMPLERATE_I2S_16K)
                dVoiceModeSelect = 1;
            else if (eSamplingRate == Soc_Aud_I2S_SAMPLERATE_I2S_32K)
                dVoiceModeSelect = 2;
            else if (eSamplingRate == Soc_Aud_I2S_SAMPLERATE_I2S_48K)
                dVoiceModeSelect = 3;
    
            Afe_Set_Reg(AFE_ADDA_UL_SRC_CON0,
                    (dVoiceModeSelect << 19) | (dVoiceModeSelect << 17), 0x001E0000);
            Afe_Set_Reg(AFE_ADDA_NEWIF_CFG0, 0x03F87201, 0xFFFFFFFF);   /* up8x txif sat on */
            Afe_Set_Reg(AFE_ADDA_NEWIF_CFG1, ((dVoiceModeSelect < 3) ? 1 : 3) << 10,
                    0x00000C00);
        } else {
            Afe_Set_Reg(AFE_ADDA_TOP_CON0, 1, 0x1); /* Using External ADC */
            Audio_I2S_Adc |= (AudioAdcI2S->mLR_SWAP << 31);
            Audio_I2S_Adc |= (AudioAdcI2S->mBuffer_Update_word << 24);
            Audio_I2S_Adc |= (AudioAdcI2S->mINV_LRCK << 23);
            Audio_I2S_Adc |= (AudioAdcI2S->mFpga_bit_test << 22);
            Audio_I2S_Adc |= (AudioAdcI2S->mFpga_bit << 21);
            Audio_I2S_Adc |= (AudioAdcI2S->mloopback << 20);
            Audio_I2S_Adc |= (SampleRateTransform(AudioAdcI2S->mI2S_SAMPLERATE) << 8);
            Audio_I2S_Adc |= (AudioAdcI2S->mI2S_FMT << 3);
            Audio_I2S_Adc |= (AudioAdcI2S->mI2S_WLEN << 1);
            pr_debug("%s Audio_I2S_Adc = 0x%x", __func__, Audio_I2S_Adc);
            Afe_Set_Reg(AFE_I2S_CON2, Audio_I2S_Adc, MASK_ALL);
        }
    
        return true;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58

    (2) 
    SetConnection(Soc_Aud_InterCon_Connection, Soc_Aud_InterConnectionInput_I03, Soc_Aud_InterConnectionOutput_O09); 
    SetConnection(Soc_Aud_InterCon_Connection, Soc_Aud_InterConnectionInput_I04, Soc_Aud_InterConnectionOutput_O10); 
    (3)设置中断

    /* here to set interrupt */
        irq_add_user(substream,
                 Soc_Aud_IRQ_MCU_MODE_IRQ2_MCU_MODE,
                 substream->runtime->rate,
                 substream->runtime->period_size);
    • 1
    • 2
    • 3
    • 4
    • 5
    • 1
    • 2
    • 3
    • 4
    • 5
    int irq_add_user(const void *_user,
             enum Soc_Aud_IRQ_MCU_MODE _irq,
             unsigned int _rate,
             unsigned int _count)
    {
        unsigned long flags;
        struct irq_user *new_user;
        struct irq_user *ptr;
    
        spin_lock_irqsave(&afe_control_lock, flags);
        //irq_add_user(), user dc5fa000, irq 1, rate 48000, count 960
        pr_debug("%s(), user %p, irq %d, rate %d, count %d
    ",
             __func__, _user, _irq, _rate, _count);
    
        /* check if user already exist */
        list_for_each_entry(ptr, &irq_managers[_irq].users, list) {
            if (ptr->user == _user) {
                pr_err("error, _user %p already exist
    ", _user);
                dump_irq_manager();
                pr_err("error, _user already exist
    ");
            }
        }
    
        /* create instance */
        new_user = kzalloc(sizeof(*new_user), GFP_ATOMIC);
        if (!new_user) {
            spin_unlock_irqrestore(&afe_control_lock, flags);
            return -ENOMEM;
        }
    
        new_user->user = _user;
        new_user->request_rate = _rate;
        new_user->request_count = _count;
        INIT_LIST_HEAD(&new_user->list);
    
        /* add user to list */
        list_add(&new_user->list, &irq_managers[_irq].users);
    
        /* */
        if (irq_managers[_irq].is_on) {
            if (is_period_smaller(_irq, new_user))
                check_and_update_irq(new_user, _irq);
        } else {
            enable_aud_irq(new_user,
                       _irq,
                       _rate,
                       _count);
        }
    
        spin_unlock_irqrestore(&afe_control_lock, flags);
        return 0;
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    /* IRQ Manager */
    static int enable_aud_irq(const struct irq_user *_irq_user,
                  enum Soc_Aud_IRQ_MCU_MODE _irq,
                  unsigned int _rate,
                  unsigned int _count)
    {
    /*
    SetIrqMcuSampleRate(), Irqmode 1, SampleRate 48000
    SetIrqMcuCounter(), Irqmode 1, Counter 960
    SetIrqEnable(), Irqmode 1, bEnable 1
    */
        SetIrqMcuSampleRate(_irq, _rate);
        SetIrqMcuCounter(_irq, _count);
        SetIrqEnable(_irq, true);
    
        irq_managers[_irq].is_on = true;
        irq_managers[_irq].rate = _rate;
        irq_managers[_irq].count = _count;
        irq_managers[_irq].selected_user = _irq_user;
    
        return 0;
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22

    (4) 
    SetSampleRate(Soc_Aud_Digital_Block_MEM_VUL, substream->runtime->rate);

    
    bool SetSampleRate(uint32 Aud_block, uint32 SampleRate)
    {
        /* pr_debug("%s Aud_block = %d SampleRate = %d
    ", __func__, Aud_block, SampleRate); */
        //
        SampleRate = SampleRateTransform(SampleRate);
    
        switch (Aud_block) {
        case Soc_Aud_Digital_Block_MEM_DL1:{
                Afe_Set_Reg(AFE_DAC_CON1, SampleRate, 0x0000000f);
                break;
            }
        case Soc_Aud_Digital_Block_MEM_DL2:{
                Afe_Set_Reg(AFE_DAC_CON1, SampleRate << 4, 0x000000f0);
                break;
            }
        case Soc_Aud_Digital_Block_MEM_I2S:{
                Afe_Set_Reg(AFE_DAC_CON1, SampleRate << 8, 0x00000f00);
                break;
            }
        case Soc_Aud_Digital_Block_MEM_AWB:{
                Afe_Set_Reg(AFE_DAC_CON1, SampleRate << 12, 0x0000f000);
                break;
            }
        case Soc_Aud_Digital_Block_MEM_VUL:{
                Afe_Set_Reg(AFE_DAC_CON1, SampleRate << 16, 0x000f0000);
                break;
            }
        case Soc_Aud_Digital_Block_MEM_DAI:{
                if (SampleRate == Soc_Aud_I2S_SAMPLERATE_I2S_8K)
                    Afe_Set_Reg(AFE_DAC_CON0, 0 << 24, 3 << 24);
                else if (SampleRate == Soc_Aud_I2S_SAMPLERATE_I2S_16K)
                    Afe_Set_Reg(AFE_DAC_CON0, 1 << 24, 3 << 24);
                else if (SampleRate == Soc_Aud_I2S_SAMPLERATE_I2S_32K)
                    Afe_Set_Reg(AFE_DAC_CON0, 2 << 24, 3 << 24);
                else
                    return false;
                break;
            }
        case Soc_Aud_Digital_Block_MEM_MOD_DAI:{
                if (SampleRate == Soc_Aud_I2S_SAMPLERATE_I2S_8K)
                    Afe_Set_Reg(AFE_DAC_CON1, 0 << 30, 3 << 30);
                else if (SampleRate == Soc_Aud_I2S_SAMPLERATE_I2S_16K)
                    Afe_Set_Reg(AFE_DAC_CON1, 1 << 30, 3 << 30);
                else
                    return false;
                break;
            }
        case Soc_Aud_Digital_Block_MEM_VUL_DATA2:{
                Afe_Set_Reg(AFE_DAC_CON0, SampleRate << 20, 0x00f00000);
                break;
            }
            return true;
        }
        return false;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57

    (5)

    bool SetMemoryPathEnable(uint32 Aud_block, bool bEnable)
    {
        /*pr_debug("%s Aud_block = %d bEnable = %d
    ", __func__, Aud_block, bEnable);*/
        if (Aud_block >= Soc_Aud_Digital_Block_NUM_OF_DIGITAL_BLOCK)
            return false;
    
        /* set for counter */
        if (bEnable == true) {
            if (mAudioMEMIF[Aud_block]->mUserCount == 0)
                mAudioMEMIF[Aud_block]->mState = true;
            mAudioMEMIF[Aud_block]->mUserCount++;
        } else {
            mAudioMEMIF[Aud_block]->mUserCount--;
            if (mAudioMEMIF[Aud_block]->mUserCount == 0)
                mAudioMEMIF[Aud_block]->mState = false;
            if (mAudioMEMIF[Aud_block]->mUserCount < 0) {
                mAudioMEMIF[Aud_block]->mUserCount = 0;
                pr_err("warning , user count <0
    ");
            }
        }
        /*pr_debug("%s Aud_block = %d mAudioMEMIF[Aud_block]->mUserCount = %d
    ", __func__, Aud_block,
             mAudioMEMIF[Aud_block]->mUserCount);*/
    
        if (Aud_block > Soc_Aud_Digital_Block_NUM_OF_MEM_INTERFACE)
            return true;
    
        if ((bEnable == true) && (mAudioMEMIF[Aud_block]->mUserCount == 1))
            Afe_Set_Reg(AFE_DAC_CON0, bEnable << (Aud_block + 1), 1 << (Aud_block + 1));
        else if ((bEnable == false) && (mAudioMEMIF[Aud_block]->mUserCount == 0))
            Afe_Set_Reg(AFE_DAC_CON0, bEnable << (Aud_block + 1), 1 << (Aud_block + 1));
    
        return true;
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33

    (6)

                     */
    void EnableAfe(bool bEnable)
    {
        unsigned long flags;
        bool MemEnable = false;
    #ifdef CONFIG_OF
    #ifdef CONFIG_MTK_LEGACY
    
        int ret;
    
        ret = GetGPIO_Info(1, &pin_audclk, &pin_mode_audclk);
        if (ret < 0) {
            pr_err("EnableAfe GetGPIO_Info FAIL1!!!
    ");
            return;
        }
    
        ret = GetGPIO_Info(2, &pin_audmiso, &pin_mode_audmiso);
        if (ret < 0) {
            pr_err("EnableAfe GetGPIO_Info FAIL2!!!
    ");
            return;
        }
    
        ret = GetGPIO_Info(3, &pin_audmosi, &pin_mode_audmosi);
        if (ret < 0) {
            pr_err("EnableAfe GetGPIO_Info FAIL3!!!
    ");
            return;
        }
    #endif
    #endif
        spin_lock_irqsave(&afe_control_lock, flags);
        MemEnable = CheckMemIfEnable();
    
        if (false == bEnable && false == MemEnable) {
            Afe_Set_Reg(AFE_DAC_CON0, 0x0, 0x1);
    #ifndef CONFIG_FPGA_EARLY_PORTING
    #ifdef CONFIG_OF
    #if defined(CONFIG_MTK_LEGACY)
    
            mt_set_gpio_mode(pin_audclk, GPIO_MODE_00); /* GPIO24, AUD_CLK_MOSI. */
    
            /* this GPIO only use in record and VOW */
            mt_set_gpio_mode(pin_audmiso, GPIO_MODE_00);    /* GPIO25, AUD_DAT_MISO */
    
            mt_set_gpio_mode(pin_audmosi, GPIO_MODE_00);    /* GPIO26, AUD_DAT_MOSI */
    #else
            AudDrv_GPIO_PMIC_Select(bEnable);
    #endif
    #else
            mt_set_gpio_mode(GPIO_AUD_CLK_MOSI_PIN, GPIO_MODE_00);  /* GPIO24, AUD_CLK_MOSI. */
    
            /* this GPIO only use in record and VOW */
            mt_set_gpio_mode(GPIO_AUD_DAT_MISO_PIN, GPIO_MODE_00);  /* GPIO25, AUD_DAT_MISO */
    
            mt_set_gpio_mode(GPIO_AUD_DAT_MOSI_PIN, GPIO_MODE_00);  /* GPIO26, AUD_DAT_MOSI */
    
    #endif
    #endif
        } else if (true == bEnable && true == MemEnable) {
    #ifndef CONFIG_FPGA_EARLY_PORTING
    #ifdef CONFIG_OF
    #if defined(CONFIG_MTK_LEGACY)
    
            mt_set_gpio_mode(pin_audclk, GPIO_MODE_01); /* GPIO24, AUD_CLK_MOSI */
    
            /* this GPIO only use in record and VOW */
            mt_set_gpio_mode(pin_audmiso, GPIO_MODE_01);    /* GPIO25, AUD_DAT_MISO */
    
            mt_set_gpio_mode(pin_audmosi, GPIO_MODE_01);    /* GPIO26, AUD_DAT_MOSI */
    #else
            AudDrv_GPIO_PMIC_Select(bEnable);
    #endif
    #else
            mt_set_gpio_mode(GPIO_AUD_CLK_MOSI_PIN, GPIO_MODE_01);  /* GPIO24, AUD_CLK_MOSI */
    
            /* this GPIO only use in record and VOW */
            mt_set_gpio_mode(GPIO_AUD_DAT_MISO_PIN, GPIO_MODE_01);  /* GPIO25, AUD_DAT_MISO */
    
            mt_set_gpio_mode(GPIO_AUD_DAT_MOSI_PIN, GPIO_MODE_01);  /* GPIO26, AUD_DAT_MOSI */
    
    #endif
    #endif
            Afe_Set_Reg(AFE_DAC_CON0, 0x1, 0x1);
        }
        spin_unlock_irqrestore(&afe_control_lock, flags);
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 69
    • 70
    • 71
    • 72
    • 73
    • 74
    • 75
    • 76
    • 77
    • 78
    • 79
    • 80
    • 81
    • 82
    • 83
    • 84
    • 85
    • 86
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 69
    • 70
    • 71
    • 72
    • 73
    • 74
    • 75
    • 76
    • 77
    • 78
    • 79
    • 80
    • 81
    • 82
    • 83
    • 84
    • 85
    • 86

    上面打开capture,配置了硬件 ,配置afe,设置中断。下面进入codec。

    对mic模式选择设置

    SOC_ENUM_EXT("Audio_MIC1_Mode_Select", Audio_UL_Enum[17], Audio_Mic1_Mode_Select_Get,
                 Audio_Mic1_Mode_Select_Set),
    SOC_ENUM_EXT("Audio_MIC2_Mode_Select", Audio_UL_Enum[18], Audio_Mic2_Mode_Select_Get,
                 Audio_Mic2_Mode_Select_Set),
    • 1
    • 2
    • 3
    • 4
    • 1
    • 2
    • 3
    • 4
    
    //Audio_Mic1_Mode_Select_Set() mAudio_Analog_Mic1_mode = 0
    static int Audio_Mic1_Mode_Select_Set(struct snd_kcontrol *kcontrol,
                          struct snd_ctl_elem_value *ucontrol)
    {
        pr_warn("%s()
    ", __func__);
        if (ucontrol->value.enumerated.item[0] > ARRAY_SIZE(Audio_AnalogMic_Mode)) {
            pr_err("return -EINVAL
    ");
            return -EINVAL;
        }
        mAudio_Analog_Mic1_mode = ucontrol->value.integer.value[0];
        pr_warn("%s() mAudio_Analog_Mic1_mode = %d
    ", __func__, mAudio_Analog_Mic1_mode);
        return 0;
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    //Audio_Mic2_Mode_Select_Set() mAudio_Analog_Mic2_mode = 0
    static int Audio_Mic2_Mode_Select_Set(struct snd_kcontrol *kcontrol,
                          struct snd_ctl_elem_value *ucontrol)
    {
        pr_warn("%s()
    ", __func__);
        if (ucontrol->value.enumerated.item[0] > ARRAY_SIZE(Audio_AnalogMic_Mode)) {
            pr_err("return -EINVAL
    ");
            return -EINVAL;
        }
        mAudio_Analog_Mic2_mode = ucontrol->value.integer.value[0];
        pr_warn("%s() mAudio_Analog_Mic2_mode = %d
    ", __func__, mAudio_Analog_Mic2_mode);
        return 0;
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    
    static int mAudio_Analog_Mic1_mode = AUDIO_ANALOGUL_MODE_ACC;
    static int mAudio_Analog_Mic2_mode = AUDIO_ANALOGUL_MODE_ACC;
    typedef enum {
        AUDIO_ANALOGUL_MODE_ACC = 0,
        AUDIO_ANALOGUL_MODE_DCC,
        AUDIO_ANALOGUL_MODE_DMIC,
        AUDIO_ANALOGUL_MODE_DCCECMDIFF,
        AUDIO_ANALOGUL_MODE_DCCECMSINGLE,
    } AUDIO_ANALOGUL_MODE;
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11

    mAudio_Analog_Mic1_mode = ucontrol->value.integer.value[0]; 
    mAudio_Analog_Mic2_mode = ucontrol->value.integer.value[0]; 
    从mAudio_Analog_Mic1_mode和mAudio_Analog_Mic2_mode值可判断mic使用的模式,0:ACC 1:DCC 2:DMIC 3:DCCECMDIFF 4:DCCECMSINGLE

    下面设置Audio_MicSource1_Set 
    SOC_ENUM_EXT(“Audio_MicSource1_Setting”, Audio_UL_Enum[13], Audio_MicSource1_Get, 
    Audio_MicSource1_Set),

    //Audio_MicSource1_Set() index = 0 done
    static int Audio_MicSource1_Set(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
    {
        /* 6752 used for ADC1 Mic source selection, "ADC1" is main_mic, "ADC2" is headset_mic */
        int index = 0;
    
        pr_warn("%s()
    ", __func__);
        if (ucontrol->value.enumerated.item[0] > ARRAY_SIZE(Pmic_Digital_Mux)) {
            pr_err("return -EINVAL
    ");
            return -EINVAL;
        }
        index = ucontrol->value.integer.value[0];
        pr_warn("%s() index = %d done
    ", __func__, index);
        mCodec_data->mAudio_Ana_Mux[AUDIO_MICSOURCE_MUX_IN_1] = ucontrol->value.integer.value[0];
    
        return 0;
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17

    接下来设置 
    SOC_ENUM_EXT(“Audio_ADC_1_Switch”, Audio_UL_Enum[0], Audio_ADC1_Get, Audio_ADC1_Set), 
    SOC_ENUM_EXT(“Audio_ADC_2_Switch”, Audio_UL_Enum[1], Audio_ADC2_Get, Audio_ADC2_Set),

    
    static int Audio_ADC1_Set(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
    {
        pr_warn("%s()
    ", __func__);
        mutex_lock(&Ana_Power_Mutex);
        if (ucontrol->value.integer.value[0]) {
            if (mAudio_Analog_Mic1_mode == AUDIO_ANALOGUL_MODE_ACC)
                TurnOnADcPowerACC(AUDIO_ANALOG_DEVICE_IN_ADC1, true);
            else if (mAudio_Analog_Mic1_mode == AUDIO_ANALOGUL_MODE_DCC)
                TurnOnADcPowerDCC(AUDIO_ANALOG_DEVICE_IN_ADC1, true, 0);
            else if (mAudio_Analog_Mic1_mode == AUDIO_ANALOGUL_MODE_DMIC)
                TurnOnADcPowerDmic(AUDIO_ANALOG_DEVICE_IN_ADC1, true);
            else if (mAudio_Analog_Mic1_mode == AUDIO_ANALOGUL_MODE_DCCECMDIFF)
                TurnOnADcPowerDCC(AUDIO_ANALOG_DEVICE_IN_ADC1, true, 1);
            else if (mAudio_Analog_Mic1_mode == AUDIO_ANALOGUL_MODE_DCCECMSINGLE)
                TurnOnADcPowerDCC(AUDIO_ANALOG_DEVICE_IN_ADC1, true, 2);
    
            mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_IN_ADC1] =
                ucontrol->value.integer.value[0];
        } else {
            mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_IN_ADC1] =
                ucontrol->value.integer.value[0];
            if (mAudio_Analog_Mic1_mode == AUDIO_ANALOGUL_MODE_ACC)
                TurnOnADcPowerACC(AUDIO_ANALOG_DEVICE_IN_ADC1, false);
            else if (mAudio_Analog_Mic1_mode == AUDIO_ANALOGUL_MODE_DCC)
                TurnOnADcPowerDCC(AUDIO_ANALOG_DEVICE_IN_ADC1, false, 0);
            else if (mAudio_Analog_Mic1_mode == AUDIO_ANALOGUL_MODE_DMIC)
                TurnOnADcPowerDmic(AUDIO_ANALOG_DEVICE_IN_ADC1, false);
            else if (mAudio_Analog_Mic1_mode == AUDIO_ANALOGUL_MODE_DCCECMDIFF)
                TurnOnADcPowerDCC(AUDIO_ANALOG_DEVICE_IN_ADC1, false, 1);
            else if (mAudio_Analog_Mic1_mode == AUDIO_ANALOGUL_MODE_DCCECMSINGLE)
                TurnOnADcPowerDCC(AUDIO_ANALOG_DEVICE_IN_ADC1, false, 2);
    
        }
        mutex_unlock(&Ana_Power_Mutex);
        return 0;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    static int Audio_ADC2_Set(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
    {
        pr_warn("%s()
    ", __func__);
        mutex_lock(&Ana_Power_Mutex);
        if (ucontrol->value.integer.value[0]) {
            if (mAudio_Analog_Mic2_mode == AUDIO_ANALOGUL_MODE_ACC)
                TurnOnADcPowerACC(AUDIO_ANALOG_DEVICE_IN_ADC2, true);
            else if (mAudio_Analog_Mic2_mode == AUDIO_ANALOGUL_MODE_DCC)
                TurnOnADcPowerDCC(AUDIO_ANALOG_DEVICE_IN_ADC2, true, 0);
            else if (mAudio_Analog_Mic2_mode == AUDIO_ANALOGUL_MODE_DMIC)
                TurnOnADcPowerDmic(AUDIO_ANALOG_DEVICE_IN_ADC2, true);
            else if (mAudio_Analog_Mic2_mode == AUDIO_ANALOGUL_MODE_DCCECMDIFF)
                TurnOnADcPowerDCC(AUDIO_ANALOG_DEVICE_IN_ADC2, true, 1);
            else if (mAudio_Analog_Mic2_mode == AUDIO_ANALOGUL_MODE_DCCECMSINGLE)
                TurnOnADcPowerDCC(AUDIO_ANALOG_DEVICE_IN_ADC2, true, 2);
    
            mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_IN_ADC2] =
                ucontrol->value.integer.value[0];
        } else {
            mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_IN_ADC2] =
                ucontrol->value.integer.value[0];
            if (mAudio_Analog_Mic2_mode == AUDIO_ANALOGUL_MODE_ACC)
                TurnOnADcPowerACC(AUDIO_ANALOG_DEVICE_IN_ADC2, false);
            else if (mAudio_Analog_Mic2_mode == AUDIO_ANALOGUL_MODE_DCC)
                TurnOnADcPowerDCC(AUDIO_ANALOG_DEVICE_IN_ADC2, false, 0);
            else if (mAudio_Analog_Mic2_mode == AUDIO_ANALOGUL_MODE_DMIC)
                TurnOnADcPowerDmic(AUDIO_ANALOG_DEVICE_IN_ADC2, false);
            else if (mAudio_Analog_Mic2_mode == AUDIO_ANALOGUL_MODE_DCCECMDIFF)
                TurnOnADcPowerDCC(AUDIO_ANALOG_DEVICE_IN_ADC2, false, 1);
            else if (mAudio_Analog_Mic2_mode == AUDIO_ANALOGUL_MODE_DCCECMSINGLE)
                TurnOnADcPowerDCC(AUDIO_ANALOG_DEVICE_IN_ADC2, false, 2);
    
        }
        mutex_unlock(&Ana_Power_Mutex);
        return 0;
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36

    TurnOnADcPowerACC ADCType = 13 enable = 1, refmic_using_ADC_L=0 
    TurnOnADcPowerACC ADCType = 14 enable = 1, refmic_using_ADC_L=0

    
    
    static bool TurnOnADcPowerACC(int ADCType, bool enable)
    {
        bool refmic_using_ADC_L;
    
        refmic_using_ADC_L = false;
    
        pr_warn("%s ADCType = %d enable = %d, refmic_using_ADC_L=%d
    ", __func__, ADCType,
               enable, refmic_using_ADC_L);
    
        if (enable) {
            /* uint32 ULIndex = GetULFrequency(mBlockSampleRate[AUDIO_ANALOG_DEVICE_IN_ADC]); */
            uint32 SampleRate_VUL1 = mBlockSampleRate[AUDIO_ANALOG_DEVICE_IN_ADC];
            /* uint32 SampleRate_VUL2 = mBlockSampleRate[AUDIO_ANALOG_DEVICE_IN_ADC_2]; */
            if (GetMicbias == 0) {
                MicbiasRef = Ana_Get_Reg(AUDENC_ANA_CON9) & 0x0700;
                /* save current micbias ref set by accdet */
                pr_warn("MicbiasRef=0x%x
    ", MicbiasRef);
                GetMicbias = 1;
            }
            if (GetAdcStatus() == false) {
                audckbufEnable(true);
                /* Ana_Set_Reg(LDO_VCON1, 0x0301, 0xffff);
                //VA28 remote sense //removed in MT6328 */
    
                Ana_Set_Reg(LDO_CON2, 0x8102, 0xffff);
                /* LDO enable control by RG_VAUD28_EN, Enable AVDD28_LDO (Default on) */
    
                NvregEnable(true);
                /* ClsqAuxEnable(true); */
                ClsqEnable(true);
    
                Ana_Set_Reg(AUDDEC_ANA_CON6, 0x0004, 0x0004);
                /* Enable audio ADC CLKGEN */
    
                Ana_Set_Reg(AUDENC_ANA_CON3, 0x0000, 0xffff);
                /* ADC CLK from CLKGEN (13MHz) */
                Ana_Set_Reg(AUDDEC_ANA_CON6, 0x0104, 0x0104);
                /* Enable  LCLDO_ENC 1P8V */
    
                Ana_Set_Reg(AUDDEC_ANA_CON7, 0x0006, 0x0006);
                /* LCLDO_ENC remote sense */
                /* Ana_Set_Reg(AUDENC_ANA_CON6, 0x1515, 0xffff); //default value */
                Ana_Set_Reg(AUDENC_ANA_CON6, 0x0555, 0xffff);
                /* default value MT6328 */
    
                Ana_Set_Reg(AUDENC_ANA_CON4, 0x0800, 0xffff);
                /* default value */
            }
    
            if (ADCType == AUDIO_ANALOG_DEVICE_IN_ADC1) {   /* main and headset mic */
                pr_warn("%s  AUDIO_ANALOG_DEVICE_IN_ADC1 mux =%d
    ", __func__,
                       mCodec_data->mAudio_Ana_Mux[AUDIO_MICSOURCE_MUX_IN_1]);
                if (mCodec_data->mAudio_Ana_Mux[AUDIO_MICSOURCE_MUX_IN_1] == 0) {//主mic
                    /* "ADC1", main_mic */
                    SetDCcoupleNP(AUDIO_MIC_BIAS0, mAudio_Analog_Mic1_mode);
                    /* micbias0 DCCopuleNP */
                    /* Ana_Set_Reg(AUDENC_ANA_CON9, 0x0201, 0xff09);
                    //Enable MICBIAS0, MISBIAS0 = 1P9V */
                    Ana_Set_Reg(AUDENC_ANA_CON9, 0x0711, 0xff19);
                    /* Enable MICBIAS0, MISBIAS0 = 1P9V,
                    also enable MICBIAS1 at the same time to avoid noise */
                } else if (mCodec_data->mAudio_Ana_Mux[AUDIO_MICSOURCE_MUX_IN_1] == 1) {//耳机mic
                    /* "ADC2", headset mic */
                    SetDCcoupleNP(AUDIO_MIC_BIAS1, mAudio_Analog_Mic1_mode);
                    /* micbias1 DCCopuleNP */
                    Ana_Set_Reg(AUDENC_ANA_CON9, 0x0710, 0xff90);
                    /* Enable MICBIAS1, MISBIAS1 = 2P5V ?// or 2P7V George? */
                }
                /* Ana_Set_Reg(AUDENC_ANA_CON15, 0x0003, 0x000f); //Audio L PGA 18 dB gain(SMT) */
                Ana_Set_Reg(AUDENC_ANA_CON10, 0x0003, 0x000f);  /* Audio L PGA 18 dB gain(SMT) MT6328 */
    
            } else if (ADCType == AUDIO_ANALOG_DEVICE_IN_ADC2) {    /* ref mic */
                pr_warn("%s  AUDIO_ANALOG_DEVICE_IN_ADC2 refmic_using_ADC_L =%d
    ", __func__,
                       refmic_using_ADC_L);
                SetDCcoupleNP(AUDIO_MIC_BIAS0, mAudio_Analog_Mic2_mode);
                /* micbias0 DCCopuleNP */
    
                if (mCodec_data->mAudio_Ana_Mux[AUDIO_MICSOURCE_MUX_IN_1] == 1) {
                    /*Enable MICBIAS0, MISBIAS0 = 2P7V */
                    Ana_Set_Reg(AUDENC_ANA_CON9, 0x0710, 0xff90);
    
                } else {
                    /* "ADC2", headset mic */
                    SetDCcoupleNP(AUDIO_MIC_BIAS1, mAudio_Analog_Mic1_mode);
                    /* micbias1 DCCopuleNP */
                    Ana_Set_Reg(AUDENC_ANA_CON9, 0x0711, 0xff19);
                    /* Enable MICBIAS1, MISBIAS1 = 1P9V// or 2P7V George? */
                    /* Enable MICBIAS0, MISBIAS0 = 1P9V, also enable MICBIAS1 to avoid noise */
                }
    
    
                if (refmic_using_ADC_L == false) {
                    /* Ana_Set_Reg(AUDENC_ANA_CON15, 0x0030, 0x00f0); //Audio R PGA 18 dB gain(SMT) */
                    Ana_Set_Reg(AUDENC_ANA_CON10, 0x0033, 0x00ff);
                    /* Audio R PGA 18 dB gain(SMT) MT6328 */
                } else {
                    /* Ana_Set_Reg(AUDENC_ANA_CON15, 0x0003, 0x000f);
                    //Audio L PGA 18 dB gain(SMT) */
                    Ana_Set_Reg(AUDENC_ANA_CON10, 0x0003, 0x000f);
                    /* Audio L PGA 18 dB gain(SMT) MT6328 */
                }
            }
    
            if (ADCType == AUDIO_ANALOG_DEVICE_IN_ADC1) {   /* main and headset mic */
                Ana_Set_Reg(AUDENC_ANA_CON3, 0x0800, 0xf900);   /* PGA stb enhance */
    
                if (mCodec_data->mAudio_Ana_Mux[AUDIO_MICSOURCE_MUX_IN_1] == 0) {
                    /* "ADC1", main_mic */
                    Ana_Set_Reg(AUDENC_ANA_CON0, 0x0041, 0x00C1);
                    /* Audio L preamplifier input sel : AIN0. Enable audio L PGA */
                    Ana_Set_Reg(AUDENC_ANA_CON0, 0x0541, 0xffff);
                    /* Audio L ADC input sel : L PGA. Enable audio L ADC */
                } else if (mCodec_data->mAudio_Ana_Mux[AUDIO_MICSOURCE_MUX_IN_1] == 1) {
                    /* "ADC2", headset mic */
                    Ana_Set_Reg(AUDENC_ANA_CON0, 0x0500, 0xffff);
                    /* Audio L ADC input sel : L PGA. Enable audio L ADC */
                    Ana_Set_Reg(AUDENC_ANA_CON0, 0x0581, 0xffff);
                    /* Audio L preamplifier input sel : AIN1. Enable audio L PGA */
    
                }
            } else if (ADCType == AUDIO_ANALOG_DEVICE_IN_ADC2) {
                /* ref mic */
                Ana_Set_Reg(AUDENC_ANA_CON3, 0x0800, 0xf900);
                /* PGA stb enhance */
                if (refmic_using_ADC_L == false) {
                    Ana_Set_Reg(AUDENC_ANA_CON1, 0x00C1, 0x00C1);
                    /* Audio R preamplifier input sel : AIN2. Enable audio R PGA */
                    Ana_Set_Reg(AUDENC_ANA_CON1, 0x05C1, 0xffff);
                    /* Audio R ADC input sel : R PGA. Enable audio R ADC */
                } else {
                    Ana_Set_Reg(AUDENC_ANA_CON0, 0x00c1, 0x00C1);
                    /* Audio L preamplifier input sel : AIN2. Enable audio L PGA */
                    Ana_Set_Reg(AUDENC_ANA_CON0, 0x05c1, 0xffff);
                    /* Audio L ADC input sel : L PGA. Enable audio L ADC */
                }
            }
    
            SetMicPGAGain();
    
            if (GetAdcStatus() == false) {
                /* here to set digital part */
                Topck_Enable(true);
                /* AdcClockEnable(true); */
                if (GetDacStatus() == false) {
                    Ana_Set_Reg(AFE_AUDIO_TOP_CON0, 0x005a, 0xffff);
                    /* power on clock */
                } else {
                    Ana_Set_Reg(AFE_AUDIO_TOP_CON0, 0x0000, 0xffff);
                    /* power on clock */
                }
                Ana_Set_Reg(PMIC_AFE_TOP_CON0, 0x0000, 0xffff);
                /* configure ADC setting */
                /* Ana_Set_Reg(AFUNC_AUD_CON2, 0x0006, 0xffff);
                //sdm audio fifo clock power on */
                /* Ana_Set_Reg(AFUNC_AUD_CON0, 0xc3a1, 0xffff);
                //scrambler clock on enable */
                /* Ana_Set_Reg(AFUNC_AUD_CON2, 0x0003, 0xffff);
                //sdm power on */
                /* Ana_Set_Reg(AFUNC_AUD_CON2, 0x000b, 0xffff);
                //sdm fifo enable */
                /* Ana_Set_Reg(AFE_DL_SDM_CON1, 0x001e, 0xffff);
                //set attenuation gain */
                Ana_Set_Reg(AFE_UL_DL_CON0, 0x0001, 0xffff);
                /* [0] afe enable */
    
                Ana_Set_Reg(AFE_UL_SRC0_CON0_H,
                (ULSampleRateTransform(SampleRate_VUL1) << 3 | ULSampleRateTransform(SampleRate_VUL1) << 1),
                0x001f);
                /* UL sample rate and mode configure */
                Ana_Set_Reg(AFE_UL_SRC0_CON0_L, 0x0001, 0xffff);
                /* UL turn on */
            }
        } else {
            if (GetMicbias == 0) {
                MicbiasRef = Ana_Get_Reg(AUDENC_ANA_CON9) & 0x0700;
                /* save current micbias ref set by accdet */
                pr_warn("MicbiasRef=0x%x
    ", MicbiasRef);
                GetMicbias = 1;
            }
            if (GetAdcStatus() == false) {
                Ana_Set_Reg(AFE_UL_SRC0_CON0_L, 0x0000, 0xffff);
                /* UL turn off */
                Ana_Set_Reg(AFE_AUDIO_TOP_CON0, 0x0020, 0x0020);
                /* up-link power down */
            }
            if (ADCType == AUDIO_ANALOG_DEVICE_IN_ADC1) {
                /* main and headset mic */
                if (mCodec_data->mAudio_Ana_Mux[AUDIO_MICSOURCE_MUX_IN_1] == 0) {
                    /* "ADC1", main_mic */
                    Ana_Set_Reg(AUDENC_ANA_CON0, 0x0041, 0xffff);
                    /* Audio L ADC input sel : off, disable audio L ADC */
                    Ana_Set_Reg(AUDENC_ANA_CON3, 0x0000, 0xffff);
                    /* PGA stb enhance off */
                    /* Ana_Set_Reg(AUDENC_ANA_CON15, 0x0000, 0x000f); //Audio L PGA 0 dB gain */
                    Ana_Set_Reg(AUDENC_ANA_CON10, 0x0000, 0x000f);
                    /* MT6328 Audio L PGA 0 dB gain */
    
                    Ana_Set_Reg(AUDENC_ANA_CON0, 0x0000, 0xffff);
                    /* Audio L preamplifier input sel : off, disable audio L PGA */
                } else if (mCodec_data->mAudio_Ana_Mux[AUDIO_MICSOURCE_MUX_IN_1] == 1) {
                    /* "ADC2", headset mic */
                    Ana_Set_Reg(AUDENC_ANA_CON0, 0x0500, 0xffff);
                    /* Audio L preamplifier input sel : off, disable audio L PGA */
                    Ana_Set_Reg(AUDENC_ANA_CON0, 0x0000, 0xffff);
                    /* Audio L ADC input sel : off, disable audio L ADC */
                    Ana_Set_Reg(AUDENC_ANA_CON3, 0x0000, 0xffff);
                    /* PGA stb enhance off */
                    /* Ana_Set_Reg(AUDENC_ANA_CON15, 0x0000, 0x000f);
                    //Audio L PGA 0 dB gain */
                    Ana_Set_Reg(AUDENC_ANA_CON10, 0x0000, 0x000f);
                    /* MT6328 Audio L PGA 0 dB gain */
                }
    
                Ana_Set_Reg(AUDENC_ANA_CON4, 0x0000, 0xffff);   /*  */
                Ana_Set_Reg(AUDENC_ANA_CON6, 0x2020, 0xffff);   /*  */
    
                if (mCodec_data->mAudio_Ana_Mux[AUDIO_MICSOURCE_MUX_IN_1] == 0) {
                    /* "ADC1", main_mic */
                    /* Ana_Set_Reg(AUDENC_ANA_CON9, (MicbiasRef|0x0000), 0xff09);
                    //disable MICBIAS0, restore to micbias set by accdet */
                    Ana_Set_Reg(AUDENC_ANA_CON9, (MicbiasRef | 0x0000), 0xff19);
                    /* disable MICBIAS0 and MICBIAS1, restore to micbias set by accdet */
                } else if (mCodec_data->mAudio_Ana_Mux[AUDIO_MICSOURCE_MUX_IN_1] == 1) {
                    /* "ADC2", headset mic */
                    Ana_Set_Reg(AUDENC_ANA_CON9, (MicbiasRef | 0x0000), 0xff90);
                    /* disable MICBIAS1, restore to micbias set by accdet */
                }
            } else if (ADCType == AUDIO_ANALOG_DEVICE_IN_ADC2) {    /* ref mic */
                if (refmic_using_ADC_L == false) {
                    Ana_Set_Reg(AUDENC_ANA_CON1, 0x00C1, 0xffff);
                    /* Audio R ADC input sel : off, disable audio R ADC */
                    Ana_Set_Reg(AUDENC_ANA_CON3, 0x0000, 0xffff);
                    /* PGA stb enhance off */
                    Ana_Set_Reg(AUDENC_ANA_CON10, 0x0000, 0x00ff);
                    /* Audio R PGA 0 dB gain //MT6328 */
                    Ana_Set_Reg(AUDENC_ANA_CON1, 0x0000, 0xffff);
                    /* Audio R preamplifier input sel : off, disable audio R PGA */
                } else {
                    Ana_Set_Reg(AUDENC_ANA_CON0, 0x00c1, 0xffff);
                    /* Audio L ADC input sel : off, disable audio L ADC */
                    Ana_Set_Reg(AUDENC_ANA_CON3, 0x0000, 0xffff);
                    /* PGA stb enhance off */
                    Ana_Set_Reg(AUDENC_ANA_CON10, 0x0000, 0x000f);
                    /* Audio L PGA 0 dB gain */
                    Ana_Set_Reg(AUDENC_ANA_CON0, 0x0000, 0xffff);
                    /* Audio L preamplifier input sel : off, disable audio L PGA */
                }
                Ana_Set_Reg(AUDENC_ANA_CON4, 0x0000, 0xffff);   /*  */
                Ana_Set_Reg(AUDENC_ANA_CON6, 0x2020, 0xffff);   /*  */
    
                /* Ana_Set_Reg(AUDENC_ANA_CON9, (MicbiasRef|0x0000), 0xff09);
                //disable MICBIAS0, restore to micbias set by accdet */
                Ana_Set_Reg(AUDENC_ANA_CON9, (MicbiasRef | 0x0000), 0xff19);
                /* disable MICBIAS0 and MICBIAS1, restore to micbias set by accdet */
            }
            if (GetAdcStatus() == false) {
                Ana_Set_Reg(AUDDEC_ANA_CON7, 0x0000, 0x0006);
                /* LCLDO_ENC remote sense off */
                Ana_Set_Reg(AUDDEC_ANA_CON6, 0x0004, 0x0104);
                /* disable LCLDO_ENC 1P8V */
    
                Ana_Set_Reg(AUDENC_ANA_CON3, 0x0000, 0xffff);
                /* disable ADC CLK from CLKGEN (13MHz) */
                Ana_Set_Reg(AUDDEC_ANA_CON6, 0x0000, 0x0104);
                /* disable audio ADC CLKGEN */
    
                if (GetDLStatus() == false) {
                    Ana_Set_Reg(AFE_UL_DL_CON0, 0x0000, 0xffff);
                    /* afe disable */
                    Ana_Set_Reg(AFE_AUDIO_TOP_CON0, 0x0084, 0x0084);
                    /* afe power down and total audio clk disable */
                }
    
                /* AdcClockEnable(false); */
                Topck_Enable(false);
                /* ClsqAuxEnable(false); */
                ClsqEnable(false);
                NvregEnable(false);
                audckbufEnable(false);
            }
            GetMicbias = 0;
        }
        return true;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 69
    • 70
    • 71
    • 72
    • 73
    • 74
    • 75
    • 76
    • 77
    • 78
    • 79
    • 80
    • 81
    • 82
    • 83
    • 84
    • 85
    • 86
    • 87
    • 88
    • 89
    • 90
    • 91
    • 92
    • 93
    • 94
    • 95
    • 96
    • 97
    • 98
    • 99
    • 100
    • 101
    • 102
    • 103
    • 104
    • 105
    • 106
    • 107
    • 108
    • 109
    • 110
    • 111
    • 112
    • 113
    • 114
    • 115
    • 116
    • 117
    • 118
    • 119
    • 120
    • 121
    • 122
    • 123
    • 124
    • 125
    • 126
    • 127
    • 128
    • 129
    • 130
    • 131
    • 132
    • 133
    • 134
    • 135
    • 136
    • 137
    • 138
    • 139
    • 140
    • 141
    • 142
    • 143
    • 144
    • 145
    • 146
    • 147
    • 148
    • 149
    • 150
    • 151
    • 152
    • 153
    • 154
    • 155
    • 156
    • 157
    • 158
    • 159
    • 160
    • 161
    • 162
    • 163
    • 164
    • 165
    • 166
    • 167
    • 168
    • 169
    • 170
    • 171
    • 172
    • 173
    • 174
    • 175
    • 176
    • 177
    • 178
    • 179
    • 180
    • 181
    • 182
    • 183
    • 184
    • 185
    • 186
    • 187
    • 188
    • 189
    • 190
    • 191
    • 192
    • 193
    • 194
    • 195
    • 196
    • 197
    • 198
    • 199
    • 200
    • 201
    • 202
    • 203
    • 204
    • 205
    • 206
    • 207
    • 208
    • 209
    • 210
    • 211
    • 212
    • 213
    • 214
    • 215
    • 216
    • 217
    • 218
    • 219
    • 220
    • 221
    • 222
    • 223
    • 224
    • 225
    • 226
    • 227
    • 228
    • 229
    • 230
    • 231
    • 232
    • 233
    • 234
    • 235
    • 236
    • 237
    • 238
    • 239
    • 240
    • 241
    • 242
    • 243
    • 244
    • 245
    • 246
    • 247
    • 248
    • 249
    • 250
    • 251
    • 252
    • 253
    • 254
    • 255
    • 256
    • 257
    • 258
    • 259
    • 260
    • 261
    • 262
    • 263
    • 264
    • 265
    • 266
    • 267
    • 268
    • 269
    • 270
    • 271
    • 272
    • 273
    • 274
    • 275
    • 276
    • 277
    • 278
    • 279
    • 280
    • 281
    • 282
    • 283
    • 284
    • 285
    • 286
    • 287
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 69
    • 70
    • 71
    • 72
    • 73
    • 74
    • 75
    • 76
    • 77
    • 78
    • 79
    • 80
    • 81
    • 82
    • 83
    • 84
    • 85
    • 86
    • 87
    • 88
    • 89
    • 90
    • 91
    • 92
    • 93
    • 94
    • 95
    • 96
    • 97
    • 98
    • 99
    • 100
    • 101
    • 102
    • 103
    • 104
    • 105
    • 106
    • 107
    • 108
    • 109
    • 110
    • 111
    • 112
    • 113
    • 114
    • 115
    • 116
    • 117
    • 118
    • 119
    • 120
    • 121
    • 122
    • 123
    • 124
    • 125
    • 126
    • 127
    • 128
    • 129
    • 130
    • 131
    • 132
    • 133
    • 134
    • 135
    • 136
    • 137
    • 138
    • 139
    • 140
    • 141
    • 142
    • 143
    • 144
    • 145
    • 146
    • 147
    • 148
    • 149
    • 150
    • 151
    • 152
    • 153
    • 154
    • 155
    • 156
    • 157
    • 158
    • 159
    • 160
    • 161
    • 162
    • 163
    • 164
    • 165
    • 166
    • 167
    • 168
    • 169
    • 170
    • 171
    • 172
    • 173
    • 174
    • 175
    • 176
    • 177
    • 178
    • 179
    • 180
    • 181
    • 182
    • 183
    • 184
    • 185
    • 186
    • 187
    • 188
    • 189
    • 190
    • 191
    • 192
    • 193
    • 194
    • 195
    • 196
    • 197
    • 198
    • 199
    • 200
    • 201
    • 202
    • 203
    • 204
    • 205
    • 206
    • 207
    • 208
    • 209
    • 210
    • 211
    • 212
    • 213
    • 214
    • 215
    • 216
    • 217
    • 218
    • 219
    • 220
    • 221
    • 222
    • 223
    • 224
    • 225
    • 226
    • 227
    • 228
    • 229
    • 230
    • 231
    • 232
    • 233
    • 234
    • 235
    • 236
    • 237
    • 238
    • 239
    • 240
    • 241
    • 242
    • 243
    • 244
    • 245
    • 246
    • 247
    • 248
    • 249
    • 250
    • 251
    • 252
    • 253
    • 254
    • 255
    • 256
    • 257
    • 258
    • 259
    • 260
    • 261
    • 262
    • 263
    • 264
    • 265
    • 266
    • 267
    • 268
    • 269
    • 270
    • 271
    • 272
    • 273
    • 274
    • 275
    • 276
    • 277
    • 278
    • 279
    • 280
    • 281
    • 282
    • 283
    • 284
    • 285
    • 286
    • 287

    下面设置 
    SOC_ENUM_EXT(“Audio_Preamp1_Switch”, Audio_UL_Enum[4], Audio_PreAmp1_Get, 
    Audio_PreAmp1_Set), 
    SOC_ENUM_EXT(“Audio_Preamp2_Switch”, Audio_UL_Enum[23], Audio_PreAmp2_Get, 
    Audio_PreAmp2_Set),

    //AudioPreAmp1_Sel Mul_Sel = 1
    static int Audio_PreAmp1_Set(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
    {
        pr_warn("%s()
    ", __func__);
    
        if (ucontrol->value.enumerated.item[0] > ARRAY_SIZE(PreAmp_Mux_function)) {
            pr_err("return -EINVAL
    ");
            return -EINVAL;
        }
        mCodec_data->mAudio_Ana_Mux[AUDIO_ANALOG_MUX_IN_PREAMP_1] =
            ucontrol->value.integer.value[0];
        AudioPreAmp1_Sel(mCodec_data->mAudio_Ana_Mux[AUDIO_ANALOG_MUX_IN_PREAMP_1]);
        pr_warn("%s() done
    ", __func__);
        return 0;
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    static bool AudioPreAmp1_Sel(int Mul_Sel)
    {
        pr_warn("%s Mul_Sel = %d ", __func__, Mul_Sel);
        if (Mul_Sel == 0)
            Ana_Set_Reg(AUDENC_ANA_CON0, 0x0000, 0x00C0);   /* pinumx open */
        else if (Mul_Sel == 1)
            Ana_Set_Reg(AUDENC_ANA_CON0, 0x0040, 0x00C0);   /* AIN0 */
        else if (Mul_Sel == 2)
            Ana_Set_Reg(AUDENC_ANA_CON0, 0x0080, 0x00C0);   /* AIN1 */
        else if (Mul_Sel == 3)
            Ana_Set_Reg(AUDENC_ANA_CON0, 0x00C0, 0x00C0);   /* AIN2 */
        else
            pr_warn("AudioPreAmp1_Sel warning");
    
        return true;
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    //AudioPreAmp2_Sel Mul_Sel = 1
    static int Audio_PreAmp2_Set(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
    {
        pr_warn("%s()
    ", __func__);
    
        if (ucontrol->value.enumerated.item[0] > ARRAY_SIZE(PreAmp_Mux_function)) {
            pr_err("return -EINVAL
    ");
            return -EINVAL;
        }
        mCodec_data->mAudio_Ana_Mux[AUDIO_ANALOG_MUX_IN_PREAMP_2] =
            ucontrol->value.integer.value[0];
        AudioPreAmp2_Sel(mCodec_data->mAudio_Ana_Mux[AUDIO_ANALOG_MUX_IN_PREAMP_2]);
        pr_warn("%s() done
    ", __func__);
        return 0;
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    static bool AudioPreAmp2_Sel(int Mul_Sel)
    {
        pr_warn("%s Mul_Sel = %d ", __func__, Mul_Sel);
    
        if (Mul_Sel == 0)
            Ana_Set_Reg(AUDENC_ANA_CON1, 0x0000, 0x00C0);   /* pinumx open */
        else if (Mul_Sel == 1)
            Ana_Set_Reg(AUDENC_ANA_CON1, 0x0040, 0x00C0);   /* AIN0 */
        else if (Mul_Sel == 2)
            Ana_Set_Reg(AUDENC_ANA_CON1, 0x0080, 0x00C0);   /* AIN1 */
        else if (Mul_Sel == 3)
            Ana_Set_Reg(AUDENC_ANA_CON1, 0x00C0, 0x00C0);   /* AIN2 */
        else
            pr_warn("AudioPreAmp1_Sel warning");
    
        return true;
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17

    到此MIC录音准备工作已经完成,后面就是录音。

    下面看下播放录音

    设置Audio_AmpR_Set()

    SOC_ENUM_EXT(“Audio_Amp_R_Switch”, Audio_DL_Enum[0], Audio_AmpR_Get, Audio_AmpR_Set),

    static int Audio_AmpR_Set(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
    {
        mutex_lock(&Ana_Ctrl_Mutex);
    
        pr_warn("%s()
    ", __func__);
        if ((ucontrol->value.integer.value[0] == true)
            && (mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_OUT_HEADSETR] == false)) {
            Audio_Amp_Change(AUDIO_ANALOG_CHANNELS_RIGHT1, true);
            mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_OUT_HEADSETR] =
                ucontrol->value.integer.value[0];
        } else if ((ucontrol->value.integer.value[0] == false)
               && (mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_OUT_HEADSETR] ==
                   true)) {
            mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_OUT_HEADSETR] =
                ucontrol->value.integer.value[0];
            Audio_Amp_Change(AUDIO_ANALOG_CHANNELS_RIGHT1, false);
        }
        mutex_unlock(&Ana_Ctrl_Mutex);
        return 0;
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    
    static void Audio_Amp_Change(int channels, bool enable)
    {
        if (enable) {
            if (GetDLStatus() == false)
                TurnOnDacPower();
    
            /* here pmic analog control */
            if (mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_OUT_HEADSETL] == false
                && mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_OUT_HEADSETR] ==
                false) {
                pr_warn("%s
    ", __func__);
    
                /* upmu_set_rg_vio18_cal(1);// for MT6328 E1 VIO18 patch only */
                /* set analog part (HP playback) */
                Ana_Set_Reg(AUDNCP_CLKDIV_CON1, 0x0001, 0xffff);
                /* Turn on DA_600K_NCP_VA18 */
                Ana_Set_Reg(AUDNCP_CLKDIV_CON2, 0x002B, 0xffff);
                /* Set NCP clock as 604kHz // 26MHz/43 = 604KHz */
                Ana_Set_Reg(AUDNCP_CLKDIV_CON0, 0x0001, 0xffff);
                /* Toggle RG_DIVCKS_CHG */
                Ana_Set_Reg(AUDNCP_CLKDIV_CON4, 0x0000, 0xffff);
                /* Set NCP soft start mode as default mode */
                Ana_Set_Reg(AUDNCP_CLKDIV_CON3, 0x0000, 0xffff);
                /* Enable NCP */
                Ana_Set_Reg(AUDDEC_ANA_CON6, 0x0A41, 0xfeeb);
                /* Enable cap-less HC LDO (1.5V) & LDO VA33REFGEN */
                Ana_Set_Reg(AUDDEC_ANA_CON6, 0x2AC1, 0xfeeb);
                /* Enable cap-less LC LDO (1.5V) */
                Ana_Set_Reg(AUDDEC_ANA_CON7, 0x8000, 0x8000);
                /* Enable NV regulator (-1.5V) */
                Ana_Set_Reg(ZCD_CON0, 0x0000, 0xffff);
                /* Disable AUD_ZCD */
                Ana_Set_Reg(AUDDEC_ANA_CON0, 0xE080, 0xffff);
                /* Disable headphone, voice and short-ckt protection. HP MUX is opened, voice MUX is set mute */
                Ana_Set_Reg(AUDDEC_ANA_CON6, 0x2AC0, 0xfeeb);
                /* Enable IBIST */
                Ana_Set_Reg(AUDDEC_ANA_CON4, 0x0700, 0xffff);
                /* Enable HP & HS drivers bias circuit */
                Ana_Set_Reg(AUDDEC_ANA_CON5, 0x5490, 0xffff);
                /* HP/HS ibias & DR bias current optimization */
                udelay(50);
                Ana_Set_Reg(ZCD_CON2, 0x0F9F, 0xffff);
                /* Set HPR/HPL gain as minimum (~ -40dB) */
                Ana_Set_Reg(ZCD_CON3, 0x001F, 0xffff);
                /* Set voice gain as minimum (~ -40dB) */
                Ana_Set_Reg(AUDDEC_ANA_CON1, 0x0480, 0xffff);
                /* De_OSC of HP and enable output STBENH */
                Ana_Set_Reg(AUDDEC_ANA_CON1, 0x1480, 0xffff);
                /* De_OSC of voice, enable output STBENH */
                Ana_Set_Reg(AUDDEC_ANA_CON0, 0xE090, 0xffff);
                /* Enable voice driver */
                Ana_Set_Reg(AUDDEC_ANA_CON1, 0x14A0, 0xffff);
                /* Enable pre-charge buffer */
                udelay(50);
                Ana_Set_Reg(AUDDEC_ANA_CON6, 0x2AC2, 0xfeeb);
                /* Enable AUD_CLK */
                Ana_Set_Reg(AUDDEC_ANA_CON0, 0xE09F, 0xffff);
                /* Enable Audio DAC */
    
                /* Apply digital DC compensation value to DAC */
                Ana_Set_Reg(ZCD_CON2, 0x0489, 0xffff);
                /* Set HPR/HPL gain to -1dB, step by step */
                SetDcCompenSation();
                udelay(100);
                Ana_Set_Reg(AUDDEC_ANA_CON0, 0xF49F, 0xffff);
                /* Switch HP MUX to audio DAC */
                /* here may cause pop */
                /* msleep(1); //6752 removed */
                Ana_Set_Reg(AUDDEC_ANA_CON0, 0xF4FF, 0xffff);
                /* Enable HPR/HPL */
                udelay(50);
                Ana_Set_Reg(AUDDEC_ANA_CON1, 0x1480, 0xffff);
                /* Disable pre-charge buffer */
                Ana_Set_Reg(AUDDEC_ANA_CON1, 0x0480, 0xffff);
                /* Disable De_OSC of voice */
                /* Ana_Set_Reg(AUDDEC_ANA_CON0, 0xF46F, 0xffff); //Disable voice buffer & Open HS input MUX */
                Ana_Set_Reg(AUDDEC_ANA_CON0, 0xF46F, 0xffff);
                /* Disable voice buffer & Open HS input MUX  //MT6328 George table error */
    
                Ana_Set_Reg(AUDDEC_ANA_CON4, 0x0300, 0xffff);
                /* Disable HS drivers bias circuit */
    
                /* apply volume setting */
                HeadsetVoloumeSet();
            }
    
        } else {
            if (mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_OUT_HEADSETL] == false
                && mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_OUT_HEADSETR] ==
                false) {
                pr_warn("Audio_Amp_Change off amp
    ");
                HeadsetVoloumeRestore();    /* Set HPR/HPL gain as -1dB, step by step */
                Ana_Set_Reg(ZCD_CON2, 0x0F9F, 0xffff); /* Set HPR/HPL gain as minimum (~ -40dB) */
                Ana_Set_Reg(AUDDEC_ANA_CON0, 0xF40F, 0xffff);   /* Disable HPR/HPL */
            }
    
            if (GetDLStatus() == false) {
                Ana_Set_Reg(AUDDEC_ANA_CON4, 0x0000, 0xffff);
                /* Disable drivers bias circuit */
                Ana_Set_Reg(AUDDEC_ANA_CON0, 0x0000, 0xffff);
                /* Disable Audio DAC */
                Ana_Set_Reg(AUDDEC_ANA_CON6, 0x2AC0, 0xfeeb);
                /* Disable AUD_CLK, bit2/4/8 is for ADC, do not set */
                Ana_Set_Reg(AUDDEC_ANA_CON7, 0x0000, 0x8000);
                /* Disable NV regulator (-1.5V) */
                /*Ana_Set_Reg(AUDDEC_ANA_CON6, 0x0001, 0xfeeb);*/
                Ana_Set_Reg(AUDDEC_ANA_CON6, 0x02c1, 0xfeeb); /* for AUX detection */               
                /* Disable cap-less LDOs (1.5V) & Disable IBIST */
                TurnOffDacPower();
            }
            EnableDcCompensation(false);
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 69
    • 70
    • 71
    • 72
    • 73
    • 74
    • 75
    • 76
    • 77
    • 78
    • 79
    • 80
    • 81
    • 82
    • 83
    • 84
    • 85
    • 86
    • 87
    • 88
    • 89
    • 90
    • 91
    • 92
    • 93
    • 94
    • 95
    • 96
    • 97
    • 98
    • 99
    • 100
    • 101
    • 102
    • 103
    • 104
    • 105
    • 106
    • 107
    • 108
    • 109
    • 110
    • 111
    • 112
    • 113
    • 114
    • 115
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 69
    • 70
    • 71
    • 72
    • 73
    • 74
    • 75
    • 76
    • 77
    • 78
    • 79
    • 80
    • 81
    • 82
    • 83
    • 84
    • 85
    • 86
    • 87
    • 88
    • 89
    • 90
    • 91
    • 92
    • 93
    • 94
    • 95
    • 96
    • 97
    • 98
    • 99
    • 100
    • 101
    • 102
    • 103
    • 104
    • 105
    • 106
    • 107
    • 108
    • 109
    • 110
    • 111
    • 112
    • 113
    • 114
    • 115
    static void HeadsetVoloumeSet(void)
    {
        int index = 0, oldindex = 0, offset = 0, count = 1;
    
        index = mCodec_data->mAudio_Ana_Volume[AUDIO_ANALOG_VOLUME_HPOUTR];
        oldindex = 8;
        if (index > oldindex) {
            pr_warn("%s index = %d oldindex = %d
    ", __func__ , index, oldindex);
            offset = index - oldindex;
            while (offset > 0) {
                Ana_Set_Reg(ZCD_CON2, ((oldindex + count) << 7) | (oldindex + count),
                        0xf9f);
                offset--;
                count++;
                udelay(200);
            }
        } else {
            pr_warn("%s index = %d oldindex = %d
    ", __func__ , index, oldindex);
            offset = oldindex - index;
            while (offset > 0) {
                Ana_Set_Reg(ZCD_CON2, ((oldindex - count) << 7) | (oldindex - count),
                        0xf9f);
                offset--;
                count++;
                udelay(200);
            }
        }
        Ana_Set_Reg(ZCD_CON2, (index << 7) | (index), 0xf9f);
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29

    下面设置Audio_AmpL_Set 
    SOC_ENUM_EXT(“Audio_Amp_L_Switch”, Audio_DL_Enum[1], Audio_AmpL_Get, Audio_AmpL_Set),

    static int Audio_AmpL_Set(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
    {
        mutex_lock(&Ana_Ctrl_Mutex);
    
        pr_warn("%s() gain = %ld
     ", __func__, ucontrol->value.integer.value[0]);
        if ((ucontrol->value.integer.value[0] == true)
            && (mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_OUT_HEADSETL] == false)) {
            Audio_Amp_Change(AUDIO_ANALOG_CHANNELS_LEFT1, true);
            mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_OUT_HEADSETL] =
                ucontrol->value.integer.value[0];
        } else if ((ucontrol->value.integer.value[0] == false)
               && (mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_OUT_HEADSETL] ==
                   true)) {
            mCodec_data->mAudio_Ana_DevicePower[AUDIO_ANALOG_DEVICE_OUT_HEADSETL] =
                ucontrol->value.integer.value[0];
            Audio_Amp_Change(AUDIO_ANALOG_CHANNELS_LEFT1, false);
        }
        mutex_unlock(&Ana_Ctrl_Mutex);
        return 0;
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20

    mtklog:

    01-02 06:11:00.406964  5247  5247 W [15525.148408]: (1)[5247:AudioIn_1E][name:mt_soc_codec_63xx&]Audio_Mic1_Mode_Select_Set()
    01-02 06:11:00.406989  5247  5247 W [15525.148433]: (1)[5247:AudioIn_1E][name:mt_soc_codec_63xx&]Audio_Mic1_Mode_Select_Set() mAudio_Analog_Mic1_mode = 0
    01-02 06:11:00.407547  5247  5247 W [15525.148991]: (1)[5247:AudioIn_1E][name:mt_soc_codec_63xx&]Audio_Mic2_Mode_Select_Set()
    01-02 06:11:00.407572  5247  5247 W [15525.149016]: (1)[5247:AudioIn_1E][name:mt_soc_codec_63xx&]Audio_Mic2_Mode_Select_Set() mAudio_Analog_Mic2_mode = 0
    • 1
    • 2
    • 3
    • 4
    • 1
    • 2
    • 3
    • 4

    从mAudio_Analog_Mic1_mode和mAudio_Analog_Mic2_mode值可判断mic使用的模式,0:ACC 1:DCC 2:DMIC 3:DCCECMDIFF 4:DCCECMSINGLE

    Audio_ADC1_Set()
    //ADCType代表打开电源类型  enable :1:打开电源 0:关闭电源
    TurnOnADcPowerACC ADCType = 13 enable = 1, refmic_using_ADC_L=0
    MicbiasRef=0x700
    TurnOnADcPowerACC  AUDIO_ANALOG_DEVICE_IN_ADC1 mux =0
    SetDCcoupleNP MicBias= 0 mode = 0
    SetMicPGAGain  AUDIO_ANALOG_VOLUME_MICAMP1 index =3
    Audio_ADC2_Set()
    TurnOnADcPowerACC ADCType = 14 enable = 1, refmic_using_ADC_L=0
    TurnOnADcPowerACC  AUDIO_ANALOG_DEVICE_IN_ADC2 refmic_using_ADC_L =0
    SetDCcoupleNP MicBias= 0 mode = 0
    SetDCcoupleNP MicBias= 1 mode = 0
    SetMicPGAGain  AUDIO_ANALOG_VOLUME_MICAMP1 index =3
    //mux值: 0:main mic  1:headset mic
    //AUDIO_ANALOG_DEVICE_IN_ADC1 main mic和 headset mic
    //AUDIO_ANALOG_DEVICE_IN_ADC2 ref mic
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    Audio_PreAmp1_Set()
    AudioPreAmp1_Sel Mul_Sel = 1 
    Audio_PreAmp1_Set() done
    Audio_PreAmp2_Set()
    AudioPreAmp2_Sel Mul_Sel = 1
    Audio_PreAmp2_Set() done
    Mul_Sel值:  0:pinumx open  1:AIN0  2:AIN2  3:AIN3
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    Audio_AmpR_Set() 
    TurnOnDacPower 
    Audio_Amp_Change 
    SetHprOffsetTrim mHprTrimOffset = 2043 TrimOffset = 2048 
    SetHpLOffsetTrim mHprTrimOffset = 2045 TrimOffset = 2048 
    HeadsetVoloumeSet index = 7 oldindex = 8 
    Audio_AmpL_Set() gain = 1 //gain为1代表播放 gain为0代表关闭 
    Ext_Speaker_Amp_Change ON+ 
    Sgm3718_Switch_Off enter 
    Sgm3718_Switch_Off out 
    Ext_Speaker_Amp_Change AW87318_AW87319_Switch_Audio_OFF- 
    Sgm3718_Switch_On enter 
    Ext_Speaker_Amp_Change AW87318_AW87319_Switch_Audio_Speaker 
    Ext_Speaker_Amp_Change ON-

  • 相关阅读:
    鸡啄米vc++2010系列46(Ribbon界面开发:使用更多控件并为控件添加消息处理函数)
    鸡啄米vc++2010系列45(Ribbon界面开发:为Ribbon Bar添加控件)
    鸡啄米vc++2010系列44(Ribbon界面开发:创建Ribbon样式的应用程序框架)
    鸡啄米vc++2010系列43(MFC常用类:定时器Timer)
    鸡啄米vc++2010系列42(MFC常用类:CTime类和CTimeSpan类)
    鸡啄米vc++2010系列41(MFC常用类:CString类)
    pcl库的配置
    鸡啄米vc++2010系列40(文档、视图和框架:分割窗口)
    鸡啄米vc++2010系列39(文档、视图和框架:各对象之间的关系)
    c 函数传入数组。
  • 原文地址:https://www.cnblogs.com/Ph-one/p/6879750.html
Copyright © 2011-2022 走看看