📄 pcm.c
字号:
rPCM_CLKCTL = (1<<19) | (0<<18) | (3<<9) | (31<<0);
#else //org>>
rPCM_CLKCTL = (1<<19) | (0<<18) | (3<<9) | (31<<0);
#endif
//<-
rPCM_CTL = (8 <<13) |(1<<6) | (0<<4) | (0<<3)| (1<<2) | (1<<0);
while(1)
{
//printf("STAT3: 0x%x CURR_TC: 0x%x DCDST3: 0x%x\n", rDSTAT3&0x300000, rDSTAT3&0xfffff, rDCDST3);
Exit_Key=getchar();
if( (Exit_Key == 'x') | (Exit_Key == 'X'))
break;
}
ClearPending(BIT_DMA_SBUS);
rSUBSRCPND=(BIT_SUB_DMA1);
rDMASKTRIG1 = (1<<2); //DMA1 stop
rINTMSK |= (BIT_DMA_SBUS);
rINTSUBMSK |=(BIT_SUB_DMA1);
//PCM PCM Out Channel Finish
rPCM_CTL = 0;//PCM Out Transfer Mode Off
printf("\nEnd of Play!\n");
}
void __irq DMA1_Play_Done(void)
{
rINTMSK |=(BIT_DMA_SBUS);
rINTSUBMSK|=(BIT_SUB_DMA1);
printf("\n~~~");
ClearPending(BIT_DMA_SBUS);
rSUBSRCPND=(BIT_SUB_DMA1);
rINTMSK = ~(BIT_DMA_SBUS);
rINTSUBMSK = ~(BIT_SUB_DMA1);
}
void PCM_PCMout_INT(unsigned int PCM_Size)
{
//PCM_BUF initialize
Rec_PCM_BUF = (unsigned short *)(DOWN_BUF);
Play_PCM_BUF = Rec_PCM_BUF;
End_PCM_BUF = (Rec_PCM_BUF + PCM_Size/2);
//PCM IRQ Entry
pISR_PCM_AC97= (unsigned)Irq_PCM_PCMout;
printf("\nConnect head-phone plug into speaker-out socket on SMDK2460 and Press any key.\n");
getchar();
printf("\nNow Play...\n");
ClearPending(BIT_PCM_AC97);
rSUBSRCPND=(BIT_SUB_PCM);
rINTMSK=~(BIT_PCM_AC97);
rINTSUBMSK=~(BIT_SUB_PCM);
rPCM_IRQ_CTL = (1<<14) |(1<<10); //TXFIFO Almost Empty IRQ enable
//PCM Clock Setting
//Transfer data enable
//->
//khs.050516
// modified for mode selection
#if 1 //new>>
if(pcm_mode==0)
rPCM_CLKCTL = (1<<19) | (1<<18) | (124<<9) |(31<<0);
else
rPCM_CLKCTL = (1<<19) | (0<<18) | (3<<9) | (31<<0);
#else //org>>
rPCM_CLKCTL = (1<<19) | (0<<18) | (3<<9) | (31<<0);
#endif
//<-
//Transfer data enable
rPCM_CTL = (8 <<13) |(0<<4) |(0<<3)|(1<<2)|(1<<0);
while(1)
{
if(PCM_Out_INT_Exit == 1)
break;
}
//PCM PCM Out Channel Finish
rPCM_CTL = 0;//PCM Out Transfer Mode Off
rINTSUBMSK|=(BIT_SUB_PCM);
rINTMSK|=(BIT_PCM_AC97);
printf("\nEnd of Play!\n");
}
void __irq Irq_PCM_PCMout(void)
{
unsigned int i, PCM_Stat;
//printf("\nIRQ for PCM Out!\n");
rINTMSK |=(BIT_PCM_AC97);
rINTSUBMSK|=(BIT_SUB_PCM);
for(i=0; i<PCM_OUT_Threshold; i++)
{
rPCM_TXFIFO = *(Play_PCM_BUF++);
if(Play_PCM_BUF == End_PCM_BUF)
break;
}
if(Play_PCM_BUF == End_PCM_BUF)
{
rPCM_IRQ_CTL &= ~(1<<10); //TXFIFO Almost Empty IRQ disable
PCM_Out_INT_Exit =1;
}
rSUBSRCPND=(BIT_SUB_PCM);
ClearPending(BIT_PCM_AC97);
rINTSUBMSK &= ~(BIT_SUB_PCM);
rINTMSK &= ~(BIT_PCM_AC97);
}
//////////////////////////////////////////////////////////////////////////////////////
void PCM_PCMin_DMA2(unsigned int PCM_Size)
{
Rec_PCM_BUF = (unsigned short *)(DOWN_BUF);
//IRQ Initialize
pISR_DMA_SBUS = (unsigned)DMA2_Rec_Done;
ClearPending(BIT_DMA_SBUS);
rSUBSRCPND=(BIT_SUB_DMA2);
rINTMSK = ~(BIT_DMA_SBUS);
rINTSUBMSK=~(BIT_SUB_DMA2);
//DMA2 Initialize
rDISRC2 = (0x4620000C); //PCM Input Data FIFO
rDISRCC2 = (1<<1) + (1<<0); //APB, Fix
rDIDST2 = (unsigned)Rec_PCM_BUF; //Record PCM_BUF initializ
rDIDSTC2 = (0<<1) + (0<<0); //AHB, Increment
//rDCON2 = (1<<31)+(0<<30)+(1<<29)+(0<<28)+(0<<27)+(1<<22)+(1<<20)+(PCM_Size/2);
rDCON2 = (0<<31)+(0<<30)+(1<<29)+(0<<28)+(0<<27)+(1<<22)+(1<<20)+(PCM_Size/2);
rDMAREQSEL2 = (5<<1) + (1<<0);
printf("Connect Sound Line-out plug into Line-in Socket on SMDK2460\n");
printf("Press any key to start record.\n");
getchar();
printf("Recording...\n");
rDMASKTRIG2 = (0<<2) + (1<<1) + 0; //No-stop, DMA2 channel on, No-sw trigger
//Transfer data enable
//Transfer data enable
//->
//khs.050516
// modified for mode selection
#if 1 //new>>
if(pcm_mode==0)
rPCM_CLKCTL = (1<<19) | (1<<18) | (124<<9) |(31<<0);
else
rPCM_CLKCTL = (1<<19) | (0<<18) | (3<<9) | (31<<0);
#else //org>>
rPCM_CLKCTL = (1<<19) | (0<<18) | (3<<9) | (31<<0);
#endif
//<-
rPCM_CTL = (8 <<7) |(1<<5) | (0<<4) | (0<<3)| (1<<1) | (1<<0);
while(PCM_Rec_Done ==0)
{
printf(".");
Delay(3000);
//printf("STAT2: 0x%x CURR_TC: 0x%x DCDST2: 0x%x\n", rDSTAT2&0x300000, rDSTAT2&0xfffff, rDCDST2);
}
PCM_Rec_Done = 0;
ClearPending(BIT_DMA_SBUS);
rSUBSRCPND=(BIT_SUB_DMA2);
rDMASKTRIG2 = (1<<2); //DMA2 stop
rINTMSK |= (BIT_DMA_SBUS);
rINTSUBMSK |=(BIT_SUB_DMA2);
//PCM PCM In Channel Finish
rPCM_CTL = 0; //PCM Out Transfer Mode Off
Delay(1000);
printf("\nEnd of Record!\n");
}
void __irq DMA2_Rec_Done(void)
{
ClearPending(BIT_DMA_SBUS);
rSUBSRCPND=(BIT_SUB_DMA2);
PCM_Rec_Done = 1;
}
void PCM_PCMin_INT(unsigned int PCM_Size)
{
//PCM_BUF initialize
Rec_PCM_BUF = (unsigned short *)(DOWN_BUF);
Play_PCM_BUF = Rec_PCM_BUF;
End_PCM_BUF = (Rec_PCM_BUF +PCM_Size/2);
//IRQ Initialization
pISR_PCM_AC97= (unsigned)Irq_PCM_PCMin;
printf("Are you ready to record sound via Line-in socket on SMDK2460?\n");
printf("Press any key to start record.\n");
getchar();
printf("Recording...\n");
ClearPending(BIT_PCM_AC97);
rSUBSRCPND=(BIT_SUB_PCM);
rINTMSK=~(BIT_PCM_AC97);
rINTSUBMSK=~(BIT_SUB_PCM);
rPCM_IRQ_CTL = (1<<14) |(1<<2); //Rx FIFO Almost Full IRQ enable
//PCM Clock Setting
//rPCM_CLKCTL = (1<<19) | (0<<18) | (31<<9) | (31<<0);
//Transfer data enable
//->
//khs.050516
// modified for mode selection
#if 1 //new>>
if(pcm_mode==0)
rPCM_CLKCTL = (1<<19) | (1<<18) | (124<<9) |(31<<0);
else
rPCM_CLKCTL = (1<<19) | (0<<18) | (3<<9) | (31<<0);
#else //org>>
rPCM_CLKCTL = (1<<19) | (0<<18) | (3<<9) | (31<<0);
#endif
//<-
//Transfer data enable
rPCM_CTL = (8 <<7) | (0<<4) | (0<<3)| (1<<1) | (1<<0);
while(1)
{
if(PCM_In_INT_Exit == 1)
break;
}
//PCM PCM Out Channel Finish
rPCM_CTL = 0;//PCM Out Transfer Mode Off
rINTSUBMSK|=(BIT_SUB_PCM);
rINTMSK|=(BIT_PCM_AC97);
printf("\nEnd of Record!\n");
}
void __irq Irq_PCM_PCMin(void)
{
unsigned int i;
static unsigned long cnt=0;
rINTMSK |=(BIT_PCM_AC97);
rINTSUBMSK|=(BIT_SUB_PCM);
cnt++;
if((cnt%100)==0)
WrUTXH0('.');
for(i=0; i<PCM_IN_Threshold; i++)
{
*(Play_PCM_BUF++) = (unsigned short)rPCM_RXFIFO;
if(Play_PCM_BUF == End_PCM_BUF)
break;
}
if(Play_PCM_BUF == End_PCM_BUF)
{
rPCM_IRQ_CTL &= ~(1<<2); //Rx FIFO Almost Full IRQ disable
PCM_In_INT_Exit =1;
cnt = 0;
}
rSUBSRCPND=(BIT_SUB_PCM);
ClearPending(BIT_PCM_AC97);
rINTSUBMSK &= ~(BIT_SUB_PCM);
rINTMSK &= ~(BIT_PCM_AC97);
}
//////////////////////////////////////////////////////////////////////////////////////
void AK2430_IIC_Write(unsigned int slvAddr, unsigned int addr, unsigned char data)
{
unsigned int iicSt, i;
unsigned char _iicData[2];
int _iicDataCount, _iicStatus, _iicPt;
_iicData[0] = (unsigned char)addr;
_iicData[1] = data;
_iicDataCount = 2;
_iicPt = 0;
rIICCON = (1<<7) | (0<<6) | (1<<5) | (0xf); //Enable ACK, Prescaler IICCLK=PCLK/16, Enable interrupt, Transmit clock value Tx clock=IICCLK/16
rIICSTAT = 0x10; //IIC bus data output enable(Rx/Tx)
rIICLC = (1<<2)|(1); //Filter enable, 15 clocks SDA output delay
//Data Write Phase
rIICDS = slvAddr; //0xa0
rIICSTAT = 0xf0;
while(_iicDataCount!=-1)
{
if(rIICCON & 0x10)
{
if((_iicDataCount--)==0)
{
break;
}
rIICDS = _iicData[_iicPt++];
for(i=0;i<10;i++); //for setup time until rising edge of IICSCL
rIICCON = 0xaf; //resumes IIC operation.
}
}
rIICSTAT = 0xd0; //Master Tx condition, Stop(Write), Output Enable
rIICCON = 0xaf; //Resumes IIC operation.
Delay(1); //Wait until stop condtion is in effect.
//Write is completed.
}
unsigned char AK2430_IIC_Read(unsigned int slvAddr, unsigned char addr)
{
unsigned char _iicData;
int _iicDataCount, i;
_iicData = addr;
_iicDataCount = 1;
//Register Address Write Phase
rIICCON = (1<<7) | (0<<6) | (1<<5) | (0<<4) | (0xf); //Enable ACK, Prescaler IICCLK=PCLK/16, Enable interrupt, Transmit clock value Tx clock=IICCLK/16
rIICSTAT = 0x10; //IIC bus data output enable(Rx/Tx)
rIICLC = (1<<2)|(1); //Filter enable, 15 clocks SDA output delay
rIICDS = slvAddr;
rIICSTAT = 0xf0; //MasTx,Start
while(_iicDataCount!=-1)
{
if(rIICCON & 0x10)
{ //Tx/Rx Interrupt Enable
if((_iicDataCount--)==0)
{
break;
}
rIICDS = _iicData;
for(i=0;i<10;i++); //for setup time until rising edge of IICSCL
rIICCON = 0xaf; //resumes IIC operation.
}
}
_iicDataCount = 1;
rIICCON = (1<<7) | (0<<6) | (1<<5) | (0<<4) | (0xf);
//Register Data Read Phase
rIICDS = slvAddr;
rIICSTAT = 0xb0; //Master Rx,Start
while(_iicDataCount!=-1)
{
if(rIICCON & 0x10) //Tx/Rx Interrupt Enable
{
if((_iicDataCount--)==0)
{
_iicData = (uint8)rIICDS;
rIICSTAT = 0x90; //Stop MasRx condition
rIICCON = 0xaf; //Resumes IIC operation.
Delay(1); //Wait until stop condtion is in effect.
//Too long time...
//The pending bit will not be set after issuing stop condition.
break;
}
rIICCON = 0x2f; //Resumes IIC operation with NOACK.
}
}
return _iicData;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -