コード例 #1
0
void 
ACAudioHWContext::InitCodecPort()
{
    UINT16 uiTmp;

    DEBUGMSG(ZONE_AC, (L"+ACAudioHWContext::InitCodecPort()\r\n"));

    // power down everything
    TSC2101Write(m_hSPI, TSC2101_AUDCTRL_POWER, CPC_MBIAS_HND | CPC_MBIAS_HED | CPC_ASTPWD |
                    CPC_SP1PWDN | CPC_SP2PWDN | CPC_DAPWDN | CPC_ADPWDN | CPC_VGPWDN |
                    CPC_COPWDN | CPC_LSPWDN);

    // headset input not muted, AGC for Headset In off
    TSC2101Write(m_hSPI, TSC2101_AUDCTRL_HEADSET, HGC_ADPGA_HED(0x7F));

    // handset input not muted, AGC for Handset In off
    TSC2101Write(m_hSPI, TSC2101_AUDCTRL_HANDSET, HNGC_ADPGA_HND(0x7F));

    // mute analog sidetone, select MIC_INHED input for headset
    // Cell Phone In not connected
    TSC2101Write(m_hSPI, TSC2101_AUDCTRL_MIXER, MPC_ASTMU | MPC_ASTG(0x600) | MPC_MICADC |
                    MPC_MICSEL(1));

    // ADC, DAC, Analog Sidetone, cellphone, buzzer
    // softstepping enabled, 1dB AGC hysteresis, MICes bias 2V 
    TSC2101Write(m_hSPI, TSC2101_AUDCTRL_4, AC4_MB_HED(0));

    // Set codec output volume
    TSC2101Write(m_hSPI, TSC2101_AUDCTRL_DAC, DGC_DALVL(0) | DGC_DARVL(0));

    // DAC left and right routed to SPK2, SPK1/2 unmuted
    TSC2101Write(m_hSPI, TSC2101_AUDCTRL_5, AC5_DAC2SPK1(3) | AC5_AST2SPK1 | AC5_KCL2SPK1 |
                    AC5_DAC2SPK2(3) | AC5_AST2SPK2 | AC5_KCL2SPK2 | AC5_HDSCPTC);

    // OUT8P/N muted, CPOUT muted
//  TSC2101Write(m_hSPI, TSC2101_AUDCTRL_6, AC6_MUTSPK2 |
    TSC2101Write(m_hSPI, TSC2101_AUDCTRL_6, AC6_MUTSPK2 | AC6_SPL2LSK | AC6_AST2LSK |
                    AC6_LDSCPTC | AC6_VGNDSCPTC);

    // Headset/Hook switch detect disabled
    TSC2101Write(m_hSPI, TSC2101_AUDCTRL_7, 0);

    // set I2S, word length, and reference sampling rate (RFS) divisor
    if (BITSPERSAMPLE == 20) uiTmp = 1;
    else if (BITSPERSAMPLE == 24) uiTmp = 2;
    else if (BITSPERSAMPLE == 32) uiTmp = 3;
    else uiTmp = 0;
    TSC2101Write(m_hSPI, TSC2101_AUDCTRL_1, AC1_WLEN(uiTmp) | AC1_DACFS(0) | AC1_ADCFS(0));

    // make the TSC2101 the master vs. the McBSP, set the RFS to 44100 or 48000
    uiTmp = AC3_SLVMS | ((SAMPLERATE == 44100) ? AC3_REFFS : 0);
    TSC2101Write(m_hSPI, TSC2101_AUDCTRL_3, uiTmp);

    // program the PLL's
    if (SAMPLERATE == 44100)
    {
        // 44.1 KHz, 12 MHz MCLK, 5264 D_VAL
        TSC2101Write(m_hSPI, TSC2101_AUDCTRL_PLL0, PLL1_PLLSEL | PLL1_PVAL(1) | PLL1_I_VAL(7));
        TSC2101Write(m_hSPI, TSC2101_AUDCTRL_PLL1, PLL2_D_VAL(5264));
    }
    else
    {
        // 48 KHz, 12 MHz MCLK, 1920 D_VAL
        TSC2101Write(m_hSPI, TSC2101_AUDCTRL_PLL0, PLL1_PLLSEL | PLL1_PVAL(1) | PLL1_I_VAL(8));
        TSC2101Write(m_hSPI, TSC2101_AUDCTRL_PLL1, PLL2_D_VAL(1920));
    }

    // go into idle mode and configure the clocks
    OUTREG16(&m_pMCBSPRegisters->usMCBSP_PCR, MCBSP_IDLEEN | MCBSP_CLKRM | MCBSP_SCLKME |
                MCBSP_FSXP | MCBSP_FSRP | MCBSP_CLKXP | MCBSP_CLKRP);

    if (BITSPERSAMPLE == 20) uiTmp = MCBSP_WORD_20;
    else if (BITSPERSAMPLE == 24) uiTmp = MCBSP_WORD_24;
    else if (BITSPERSAMPLE == 32) uiTmp = MCBSP_WORD_32;
    else uiTmp = MCBSP_WORD_16;

    // receive 1 word of BITSPERSAMPLE in a frame,
    // in 2 phases (1 word each) with a 1-bit delay
    OUTREG16(&m_pMCBSPRegisters->usMCBSP_RCR1, MCBSP_RFRLEN1(0) | MCBSP_RWDLEN1(uiTmp));
    OUTREG16(&m_pMCBSPRegisters->usMCBSP_RCR2, MCBSP_RPHASE | MCBSP_RFRLEN2(0) |
                MCBSP_RWDLEN2(uiTmp) | MCBSP_RDATDLY(1));

    // transmit 1 word of BITSPERSAMPLE in a frame,
    // in 2 phases (1 word each) with a 1-bit delay
    OUTREG16(&m_pMCBSPRegisters->usMCBSP_XCR1, MCBSP_XFRLEN1(0) | MCBSP_XWDLEN1(uiTmp));
    OUTREG16(&m_pMCBSPRegisters->usMCBSP_XCR2, MCBSP_XPHASE | MCBSP_XFRLEN2(0) |
                MCBSP_XWDLEN2(uiTmp) | MCBSP_XDATDLY(1) | MCBSP_XFIG);

    // set the clocks
    OUTREG16(&m_pMCBSPRegisters->usMCBSP_SRGR1, MCBSP_FWID(BITSPERSAMPLE - 1) |
                MCBSP_CLKGDV(0));
    OUTREG16(&m_pMCBSPRegisters->usMCBSP_SRGR2, MCBSP_GSYNC | MCBSP_CLKSP |
                MCBSP_FSGM | MCBSP_FPER(BITSPERSAMPLE * 2 - 1));

    //Left Justify, Clockstop with no delay, Receiver Disabled
    OUTREG16(&m_pMCBSPRegisters->usMCBSP_SPCR1, MCBSP_RINTM(3));

    // Set transmit interrupt on XSYNCERR.
    OUTREG16(&m_pMCBSPRegisters->usMCBSP_SPCR2, MCBSP_FREE | MCBSP_XINTM(3));

    // Delay while new divisors take effect.
    Sleep(100);
}
コード例 #2
0
/*
 * Sample rate changing
 */
void tsc2101_set_samplerate(long sample_rate)
{
	u8 count = 0;
	u16 data = 0;
	int clkgdv = 0;

	u16 srgr1, srgr2;
	/* wait for any frame to complete */
	udelay(125);
	ADEBUG();

	sample_rate	= sample_rate;
	/* Search for the right sample rate */
	while ((rate_reg_info[count].sample_rate != sample_rate) &&
	       (count < NUMBER_SAMPLE_RATES_SUPPORTED)) {
		count++;
	}
	if (count == NUMBER_SAMPLE_RATES_SUPPORTED) {
		printk(KERN_ERR "Invalid Sample Rate %d requested\n",
		       (int) sample_rate);
		return;		// -EPERM;
	}

	/* Set AC1 */
	data	= tsc2101_audio_read(TSC2101_AUDIO_CTRL_1);
	/* Clear prev settings */
	data	&= ~(AC1_DACFS(0x07) | AC1_ADCFS(0x07));
	data	|= AC1_DACFS(rate_reg_info[count].divisor) | 
			AC1_ADCFS(rate_reg_info[count].divisor);
	tsc2101_audio_write(TSC2101_AUDIO_CTRL_1, data);

	/* Set the AC3 */
	data	= tsc2101_audio_read(TSC2101_AUDIO_CTRL_3);
	/*Clear prev settings */
	data	&= ~(AC3_REFFS | AC3_SLVMS);
	data	|= (rate_reg_info[count].fs_44kHz) ? AC3_REFFS : 0;
#ifdef TSC_MASTER
	data	|= AC3_SLVMS;
#endif				/* #ifdef TSC_MASTER */
	tsc2101_audio_write(TSC2101_AUDIO_CTRL_3, data);

	/* Program the PLLs. This code assumes that the 12 Mhz MCLK is in use.
         * If MCLK rate is something else, these values must be changed.
	 * See the tsc2101 specification for the details.
	 */
	if (rate_reg_info[count].fs_44kHz) {
		/* samplerate = (44.1kHZ / x), where x is int. */
		tsc2101_audio_write(TSC2101_PLL_PROG_1, PLL1_PLLSEL |
				PLL1_PVAL(1) | PLL1_I_VAL(7));	/* PVAL 1; I_VAL 7 */
		tsc2101_audio_write(TSC2101_PLL_PROG_2, PLL2_D_VAL(0x1490));	/* D_VAL 5264 */
	} else {
		/* samplerate = (48.kHZ / x), where x is int. */
		tsc2101_audio_write(TSC2101_PLL_PROG_1, PLL1_PLLSEL |
			       PLL1_PVAL(1) | PLL1_I_VAL(8));	/* PVAL 1; I_VAL 8 */
		tsc2101_audio_write(TSC2101_PLL_PROG_2, PLL2_D_VAL(0x780));	/* D_VAL 1920 */
	}

	/* Set the sample rate */
#ifndef TSC_MASTER
	clkgdv	= CODEC_CLOCK / (sample_rate * (DEFAULT_BITPERSAMPLE * 2 - 1));
	if (clkgdv)
		srgr1 = (FWID(DEFAULT_BITPERSAMPLE - 1) | CLKGDV(clkgdv));
	else
		return (1);

	/* Stereo Mode */
	srgr2 = (CLKSM | FSGM | FPER(DEFAULT_BITPERSAMPLE * 2 - 1));
#else
	srgr1 = (FWID(DEFAULT_BITPERSAMPLE - 1) | CLKGDV(clkgdv));
	srgr2 = ((GSYNC | CLKSP | FSGM | FPER(DEFAULT_BITPERSAMPLE * 2 - 1)));

#endif				/* end of #ifdef TSC_MASTER */
	OMAP_MCBSP_WRITE(OMAP1610_MCBSP1_BASE, SRGR2, srgr2);
	OMAP_MCBSP_WRITE(OMAP1610_MCBSP1_BASE, SRGR1, srgr1);
}