예제 #1
0
파일: fsl_i2c_dma.c 프로젝트: 01org/zephyr
static void I2C_MasterTransferDMAConfig(I2C_Type *base, i2c_master_dma_handle_t *handle)
{
    dma_transfer_config_t transfer_config;
    dma_transfer_options_t transfer_options = kDMA_EnableInterrupt;

    if (handle->transfer.direction == kI2C_Read)
    {
        transfer_config.srcAddr = (uint32_t)I2C_GetDataRegAddr(base);
        transfer_config.destAddr = (uint32_t)(handle->transfer.data);
        transfer_config.transferSize = (handle->transfer.dataSize - 1);
        transfer_config.srcSize = kDMA_Transfersize8bits;
        transfer_config.enableSrcIncrement = false;
        transfer_config.destSize = kDMA_Transfersize8bits;
        transfer_config.enableDestIncrement = true;
    }
    else
    {
        transfer_config.srcAddr = (uint32_t)(handle->transfer.data + 1);
        transfer_config.destAddr = (uint32_t)I2C_GetDataRegAddr(base);
        transfer_config.transferSize = (handle->transfer.dataSize - 1);
        transfer_config.srcSize = kDMA_Transfersize8bits;
        transfer_config.enableSrcIncrement = true;
        transfer_config.destSize = kDMA_Transfersize8bits;
        transfer_config.enableDestIncrement = false;
    }

    DMA_SubmitTransfer(handle->dmaHandle, &transfer_config, transfer_options);
    DMA_StartTransfer(handle->dmaHandle);
}
예제 #2
0
status_t SPIFI_TransferReceiveDMA(SPIFI_Type *base, spifi_dma_handle_t *handle, spifi_transfer_t *xfer)
{
    assert(handle && (handle->dmaHandle));

    dma_transfer_config_t xferConfig;
    status_t status;

    /* If previous TX not finished. */
    if (kSPIFI_BusBusy == handle->state)
    {
        status = kStatus_SPIFI_Busy;
    }
    else
    {
        handle->state = kSPIFI_BusBusy;

        /* Prepare transfer. */
        DMA_PrepareTransfer(&xferConfig, (void *)SPIFI_GetDataRegisterAddress(base), xfer->data, sizeof(uint32_t),
                            xfer->dataSize, kDMA_PeripheralToMemory, NULL);

        /* Submit transfer. */
        DMA_SubmitTransfer(handle->dmaHandle, &xferConfig);
        DMA_StartTransfer(handle->dmaHandle);

        /* Enable SPIFI TX DMA. */
        SPIFI_EnableDMA(base, true);

        status = kStatus_Success;
    }

    return status;
}
예제 #3
0
파일: task1.c 프로젝트: LaneTee/xmega-intro
/*  AsyncMemCopy
 *
 *  Block size 0 = 64k. Enable the DMA channel to use first. 
 *  Then setup channel for copying data, increasing addresses, 
 *  no address pointer reload, with 8-byte bursts.
 *
 * \note This function is asynchronous and DOES NOT wait for 
 *       completion.This must be handled by the program 
 *       calling this function. 
 *       In this example, an interrupt.
 *
 */
void AsyncMemCopy( const void * src,
                   void * dest,
                   uint16_t blockSize,
                   DMA_CH_t * dmaChannel )
{
	DMA_EnableChannel( dmaChannel );

	DMA_SetupBlock( dmaChannel,
	                src,
	                DMA_CH_SRCRELOAD_NONE_gc,
	                DMA_CH_SRCDIR_INC_gc,
	                dest,
	                DMA_CH_DESTRELOAD_NONE_gc,
	                DMA_CH_DESTDIR_INC_gc,
	                blockSize,
	                DMA_CH_BURSTLEN_8BYTE_gc,
	                0,
	                false );

	DMA_StartTransfer( dmaChannel );
}
예제 #4
0
파일: task1.c 프로젝트: LaneTee/xmega-intro
bool MemCopy( const void * src, void * dest, uint16_t blockSize,
                          DMA_CH_t * dmaChannel )
{
    uint8_t flags = 0;

	DMA_EnableChannel( dmaChannel );
	DMA_SetupBlock( dmaChannel,
	                src,
	                DMA_CH_SRCRELOAD_NONE_gc,
	                DMA_CH_SRCDIR_INC_gc,
	                dest,
	                DMA_CH_DESTRELOAD_NONE_gc,
	                DMA_CH_DESTDIR_INC_gc,
	                blockSize,
	                DMA_CH_BURSTLEN_8BYTE_gc,
	                0, 
	                false ); // no repeat

	DMA_StartTransfer( dmaChannel );

    // Wait until the completion or error flag is set. The flags
	// must be cleared manually.
    do {
        flags = DMA_ReturnStatus_non_blocking( dmaChannel );
    } while ( flags == 0 );

	// Clear flags
    DMA.CH0.CTRLB |= ( flags );

    // Check if error flag is set
    if ( ( flags & DMA_CH_ERRIF_bm ) != 0x00 ) 
    {
        return true;
    } else 
    {
        return false;
    }
}
예제 #5
0
status_t USART_TransferReceiveDMA(USART_Type *base, usart_dma_handle_t *handle, usart_transfer_t *xfer)
{
    assert(handle);
    assert(handle->rxDmaHandle);
    assert(xfer);
    assert(xfer->data);
    assert(xfer->dataSize);

    dma_transfer_config_t xferConfig;
    status_t status;

    /* If previous RX not finished. */
    if (kUSART_RxBusy == handle->rxState)
    {
        status = kStatus_USART_RxBusy;
    }
    else
    {
        handle->rxState = kUSART_RxBusy;
        handle->rxDataSizeAll = xfer->dataSize;

        /* Enable DMA request from rxFIFO */
        USART_EnableRxDMA(base, true);

        /* Prepare transfer. */
        DMA_PrepareTransfer(&xferConfig, (void *)&base->FIFORD, xfer->data, sizeof(uint8_t), xfer->dataSize,
                            kDMA_PeripheralToMemory, NULL);

        /* Submit transfer. */
        DMA_SubmitTransfer(handle->rxDmaHandle, &xferConfig);
        DMA_StartTransfer(handle->rxDmaHandle);

        status = kStatus_Success;
    }

    return status;
}
예제 #6
0
status_t UART_TransferReceiveDMA(UART_Type *base, uart_dma_handle_t *handle, uart_transfer_t *xfer)
{
    assert(handle);
    assert(handle->rxDmaHandle);
    assert(xfer);
    assert(xfer->data);
    assert(xfer->dataSize);

    dma_transfer_config_t xferConfig;
    status_t status;

    /* If previous RX not finished. */
    if (kUART_RxBusy == handle->rxState)
    {
        status = kStatus_UART_RxBusy;
    }
    else
    {
        handle->rxState = kUART_RxBusy;
        handle->rxDataSizeAll = xfer->dataSize;

        /* Prepare transfer. */
        DMA_PrepareTransfer(&xferConfig, (void *)UART_GetDataRegisterAddress(base), sizeof(uint8_t), xfer->data,
                            sizeof(uint8_t), xfer->dataSize, kDMA_PeripheralToMemory);

        /* Submit transfer. */
        DMA_SubmitTransfer(handle->rxDmaHandle, &xferConfig, kDMA_EnableInterrupt);
        DMA_StartTransfer(handle->rxDmaHandle);

        /* Enable UART RX DMA. */
        UART_EnableRxDMA(base, true);

        status = kStatus_Success;
    }

    return status;
}
예제 #7
0
/*! \brief Example of a repeated block memory copy operation.
 *
 *  Block size 0 = 64k. Enable the DMA channel to use first and the channel
 *  will be disabled automatically. A parameter check to avoid illegal values.
 *  Setup channel for copying data, increasing addresses, no address pointer
 *  reload, with 8-byte bursts.
 *
 * \note This function wait until the transfer is complete and use a blocking
 *       function which also makes this function blocking, hence the function
 *       will dead-lock if the completion or error flag never get set.
 *
 * \retval true   if success.
 * \retval false  if failure.
 */
bool MultiBlockMemCopy( const void * src, void * dest, uint16_t blockSize,
                          uint8_t repeatCount, volatile DMA_CH_t * dmaChannel )
{
	uint8_t flags;

	DMA_EnableChannel( dmaChannel );
	DMA_SetupBlock( dmaChannel,
	                src,
	                DMA_CH_SRCRELOAD_NONE_gc,
	                DMA_CH_SRCDIR_INC_gc,
	                dest,
	                DMA_CH_DESTRELOAD_NONE_gc,
	                DMA_CH_DESTDIR_INC_gc,
	                blockSize,
	                DMA_CH_BURSTLEN_8BYTE_gc,
	                repeatCount,
	                true );

	DMA_StartTransfer( dmaChannel );

	/* Wait until the completion or error flag is set. The flags
	 * must be cleared manually.
	 */
	do {
		flags = DMA_ReturnStatus_non_blocking( dmaChannel );
	} while ( flags == 0);

	dmaChannel->CTRLB |= ( flags );

	/* Check if error flag is set. */
	if ( ( flags & DMA_CH_ERRIF_bm ) != 0x00 ) {
		return false;
	} else {
		return true;
	}
}
예제 #8
0
파일: ddc_i2s.c 프로젝트: zenGit/barcelona
/**
 *   \brief Call back function for DMA transmit complete
 *
 *  This function will be called when DMA transmit completes.
 *  This function changes the source address of the DMA channel and
 *  restarts the DMA transfer.
 *
 *   \param dmaStatus    [IN]    Status of the DMA transfer
 *   \param dataCallback [IN]    I2S handle
 *
 *   \return   void
 *
 */
void I2S_DmaTxCallBack(PSP_DMATransferStatus    dmaStatus,
                       void    *dataCallback)
{
#if 0 // currently unused
    Uint16 i;
    Int16 status;
    Uint16 * ptr_tx_left;
    Uint16 * ptr_tx_right;
    Uint16 * ptr_tx_codec_buf;
    Uint16 next_position;
    Uint16 wrap;

    prevDmaTxferComplete = TRUE;

    if((dataCallback != NULL) && (dmaStatus == PSP_DMA_TRANSFER_COMPLETE))
    {
        if(usb_play_mode == FALSE)
        {
            //playback not active- use zero buffer
            DMA_ChangeI2SSrcAddr(hDmaTxLeft,gZeroBuf);
            DMA_ChangeI2SSrcAddr(hDmaTxRight,gZeroBuf);

            /* Start dma transfer */
            DMA_StartTransfer(hDmaTxLeft);
            DMA_StartTransfer(hDmaTxRight);
            return;
        }

        // playback is active - get the next output buffer
        if(nextBuffer == TRUE)
        {
            nextBuffer = FALSE;

            //if(gEp2Buff2Full == TRUE)
            if(1)
            {
                // output pong buffer
                gEp2Buff2Full = FALSE;
                DMA_ChangeI2SSrcAddr(hDmaTxLeft,gi2sNextTxLeftBuf);
                DMA_ChangeI2SSrcAddr(hDmaTxRight,gi2sNextTxRightBuf);
            }
            else
            {
                // buffer is not ready
            //    dma_error++;
            //    DMA_ChangeI2SSrcAddr(hDmaTxLeft,gZeroBuf);
            //    DMA_ChangeI2SSrcAddr(hDmaTxRight,gZeroBuf);
            }

            /* Start dma transfer */
            DMA_StartTransfer(hDmaTxLeft);
            DMA_StartTransfer(hDmaTxRight);

            // fill the next buffer
            if(enable_asrc == TRUE)
            {
                // fill output buffer with ASRC output
                for(i = 0; i < I2S_TXBUFF_SIZE; i++)
                {
                    /* Generate output samples L and R */
                    status = ASRC_genOutAdaptCoefs16b(hAsrc, (Int16 *)&ping_i2sTxLeftBuf[i]);
                    if (status != ASRC_SOK)
                    {
                        dma_error++;
                    }
                    else
                    {
                        // save the right sample to the right output buffer
                        ping_i2sTxRightBuf[i] = ping_i2sTxLeftBuf[i + 1];
                    }

                    status = ASRC_accPhaseAdapt(hAsrc);
                    if (status != ASRC_SOK)
                    {
                        dma_error++;
                    }
                }
            }
            else // - fill output buffer with data from circular buffer
            {
                // this buffer needs to be filled with data to output
                ptr_tx_left = &ping_i2sTxLeftBuf[0];
                ptr_tx_right = &ping_i2sTxRightBuf[0];

                ptr_tx_codec_buf = &codec_output_buffer[codec_output_buffer_output_index];

                next_position = codec_output_buffer_output_index + (2*I2S_TXBUFF_SIZE);

                //prepare the next buffer
                if(next_position < CODEC_OUTPUT_BUFFER_SIZE)
                {
                    // copy without wrap
                    for(i = 0; i < I2S_TXBUFF_SIZE; i++)
                    {
                        *ptr_tx_left++ = *ptr_tx_codec_buf++;
                        *ptr_tx_right++ = *ptr_tx_codec_buf++;
                    }
                    // update index into circular buffer - 'x2' due to 2 writes
                    codec_output_buffer_output_index += (2*I2S_TXBUFF_SIZE);
                }
                else
                {
                    // copy with wrap
                    outwrap++;
                    wrap = (CODEC_OUTPUT_BUFFER_SIZE - codec_output_buffer_output_index)>>1;
                    // copy prior to wrap
                    for(i = 0; i < wrap; i++)
                    {
                        *ptr_tx_left++ = *ptr_tx_codec_buf++;
                        *ptr_tx_right++ = *ptr_tx_codec_buf++;
                    }
                    // now wrap
                    ptr_tx_codec_buf = &codec_output_buffer[0];
                    wrap = I2S_TXBUFF_SIZE - wrap;
                    // copy after wrap
                    for(i = 0; i < wrap; i++)
                    {
                        *ptr_tx_left++ = *ptr_tx_codec_buf++;
                        *ptr_tx_right++ = *ptr_tx_codec_buf++;
                    }
                    // update index into circular buffer - 'x2' due to 2 writes
                    codec_output_buffer_output_index = 2*wrap;
                }
            }
        }
        else
        {
예제 #9
0
파일: ddc_i2s.c 프로젝트: zenGit/barcelona
/**
 *  \brief DMA data read.
 *
 *  Function to receive the data from I2S using DMA.
 *  This API is called by the driver code from DDA to receive
 *  I2S data using DMA.
 *
 *  \param i2sHandle      [IN]  Handle to the I2S instance
 *  \param nextRxLeftBuf  [IN]  Pointer to next left receive buffer
 *  \param nextRxRightBuf [IN]  Pointer to next right receive buffer
 *  \param hDmaRxLeft     [IN]  Dma handle for left receive channel
 *  \param hDmaRxRight    [IN]  Dma handle for right receive channel
 *
 *  \return PSP_SOK -  if successful, else suitable error code
 */
Int16 DDC_I2SDMARead(PSP_Handle        i2sHandle,
                       Uint32            *nextRxLeftBuf,
                     Uint32            *nextRxRightBuf,
                     DMA_ChanHandle    hDmaRxLeft,
                     DMA_ChanHandle    hDmaRxRight)
{
    DDC_I2SHandle    hI2S;
    Uint16           leftDmaChanNum;
    Uint16           dmaChanCount;
    Uint16           dmaNum;
    Int16            status;
    PSP_Result       status0;
    PSP_Result       status1;

    status   =  PSP_E_INVAL_PARAM;
    status0  =  PSP_E_INVAL_PARAM;
    status1  =  PSP_E_INVAL_PARAM;

    if(i2sHandle != NULL)
    {
        hI2S  =  (DDC_I2SHandle)i2sHandle;
        leftDmaChanNum  =  hDmaRxLeft->chanNum;
        dmaChanCount  =  4;
        dmaNum  =  0;
        //gNextRxLeftBuf   =  (Uint32)nextRxLeftBuf;
        //gNextRxRightBuf  =  (Uint32)nextRxRightBuf;
        if(hDmaRxLeft != NULL)
        {
            /* Find out the DMA engine number and channel number for
             * left Rx DMA channel */
            while(leftDmaChanNum >= dmaChanCount)
            {
                leftDmaChanNum  -=  dmaChanCount;
                   dmaNum   +=  1;
            }
            /* Disable the DMA interrupts on left receive channel */
            CSL_DMAEVTINT_REGS->DMAINTEN  &=  ~(0x0001 <<
                                       (dmaNum*dmaChanCount + leftDmaChanNum));
        }

        /* Enable I2S reception */
        LLC_I2SEnable(hI2S->regs);

        switch(hI2S->chanType)
        {
            case PSP_I2S_CHAN_STEREO:  /* Stereo data */
                if((hDmaRxLeft != NULL) && (hDmaRxRight != NULL) &&
                   (nextRxLeftBuf != NULL) && (nextRxRightBuf != NULL))
                {
                    /* Enable transfer on two dma channels */
                    status0  =  DMA_StartTransfer(hDmaRxLeft);
                    status1  =  DMA_StartTransfer(hDmaRxRight);
                }
                break;

            case PSP_I2S_CHAN_MONO:  /* Mono data */
                if((hDmaRxLeft != NULL) && (nextRxLeftBuf != NULL))
                {
                    /* Enable transfer on one dma channel */
                    status0  =  DMA_StartTransfer(hDmaRxLeft);
                    status1  =  PSP_SOK;
                }
                break;

            default:
                break;
        }

        if((status0 == PSP_SOK) && (status1 == PSP_SOK))
        {
            status  =  PSP_SOK;
        }
    }

    return status;
}
/**
 *  \brief  Audio Class intialization function
 *
 *  \param  None
 *
 *  \return None
 */
void CSL_acTest(void)
{
    I2sInitPrms i2sInitPrms;
    CSL_UsbConfig usbConfig;
    PSP_Result result;
    Int16 status;
    HWI_Attrs attrs;


    LOG_printf(&trace, "USB ISO FULL SPEED MODE\n");

    /* Initialize audio module */
    result = AIC3254_init();
    if(result != 0)
    {
        LOG_printf(&trace, "ERROR: Unable to configure audio codec");
    }
    else
    {
#if !defined(SAMPLE_BY_SAMPLE_PB) || !defined(SAMPLE_BY_SAMPLE_REC)
        DMA_HwInit();
        DMA_DrvInit();
#endif

        /* Initialize I2S and associated DMA channels for Playback and Record */
        i2sInitPrms.enablePlayback = TRUE;
        i2sInitPrms.enableStereoPb = TRUE;
#ifdef SAMPLE_BY_SAMPLE_PB
        i2sInitPrms.sampleBySamplePb = TRUE;
#else /* Configuration untested since ASRC only works with I2S in sample-by-sample mode */
        i2sInitPrms.sampleBySamplePb = FALSE;
        i2sInitPrms.enableDmaPingPongPb = FALSE;
        i2sInitPrms.pingI2sTxLeftBuf = ping_i2sTxLeftBuf;
        i2sInitPrms.pongI2sTxLeftBuf = pong_i2sTxLeftBuf;
        i2sInitPrms.pingI2sTxRightBuf = ping_i2sTxRightBuf;
        i2sInitPrms.pongI2sTxRightBuf = pong_i2sTxRightBuf;
        i2sInitPrms.zeroBuf = ZeroBuf;
#endif
        i2sInitPrms.i2sPb = PSP_I2S_TX_INST_ID;
        i2sInitPrms.enableRecord = TRUE;
        i2sInitPrms.enableStereoRec = FALSE;
#ifdef SAMPLE_BY_SAMPLE_REC
        i2sInitPrms.sampleBySampleRec = TRUE;
#else
        i2sInitPrms.sampleBySampleRec = FALSE;
        i2sInitPrms.enableDmaPingPongRec = TRUE;
        i2sInitPrms.pingI2sRxLeftBuf = (Int16 *)ping_pong_i2sRxLeftBuf;
        i2sInitPrms.pongI2sRxLeftBuf = NULL;
        i2sInitPrms.pingI2sRxRightBuf = (Int16 *)ping_pong_i2sRxRightBuf;
        i2sInitPrms.pongI2sRxRightBuf = NULL;
#endif
        i2sInitPrms.i2sRec = PSP_I2S_RX_INST_ID;
        status = i2sInit(&i2sInitPrms);
        if (status != I2SSAMPLE_SOK)
        {
            LOG_printf(&trace, "ERROR: Unable to initialize I2S");
        }

#ifdef C5535_EZDSP_DEMO
		// initialize the OLED display        
        oled_init();
#endif
        
        /* Initialising the Pointer to the Audio Class Handle to the Buffer Allocated */
        AC_AppHandle.pAcObj = &ACAppBuffer[0];

        usbConfig.devNum                = CSL_USB0;
        usbConfig.opMode                = CSL_USB_OPMODE_POLLED;
#ifdef APP_USB_SELF_POWERED
        usbConfig.selfPowered           = TRUE;
#else
        usbConfig.selfPowered           = FALSE;
#endif
        usbConfig.maxCurrent            = APP_USB_MAX_CURRENT;
        usbConfig.appSuspendCallBack    = (CSL_USB_APP_CALLBACK)CSL_suspendCallBack;
        usbConfig.appWakeupCallBack     = (CSL_USB_APP_CALLBACK)CSL_selfWakeupCallBack;
        usbConfig.startTransferCallback  = StartTransfer;
        usbConfig.completeTransferCallback = CompleteTransfer;

        USB_init(&usbConfig);

        USB_setFullSpeedMode(0x40); /* parameter is EP0 data size in bytes */

        USB_resetDev(CSL_USB0);

        /* Calling init routine */
        /* Giving all the table hanldes and the buffers to the Audio Class module */
        AC_AppHandle.strDescrApp = (char **)&string_descriptor[0];
        AC_AppHandle.lbaBufferPbApp = &lbaBufferPbApp[0];
        AC_AppHandle.lbaBufferRecApp = &lbaBufferRecApp[0];
        AC_AppHandle.lbaBufferHidReportApp = &lbaBufferHidReportApp[0];
        AC_AppHandle.acReqTableApp = USB_ReqTable;
        AC_AppHandle.pId = pId;
        AC_AppHandle.vId = vId;

#ifndef ENABLE_PLAYBACK_TWO_SAMPLE_RATES
        #ifdef SAMPLE_RATE_TX_48kHz
        LOG_printf(&trace, "PLAYBACK: 48KHZ ");
        #ifdef ENABLE_STEREO_PLAYBACK
        LOG_printf(&trace, "STEREO\n");
        AC_AppHandle.rxPktSize = EP_PB_MAXP; // max packet size for 48K stereo
        #else // ENABLE_STEREO_PLAYBACK
        LOG_printf(&trace, "MONO\n");
        AC_AppHandle.rxPktSize = 0x60; // max packet size for 48K mono
        #endif // ENABLE_STEREO_PLAYBACK
        #endif // SAMPLE_RATE_TX_48kHz

        #ifdef SAMPLE_RATE_TX_44_1kHz
        LOG_printf(&trace, "PLAYBACK: 44.1KHZ ");
        #ifdef ENABLE_STEREO_PLAYBACK
        LOG_printf(&trace, "STEREO\n");
        AC_AppHandle.rxPktSize = 0xB0; // max packet size for 44.1 stereo
        #else // ENABLE_STEREO_PLAYBACK
        LOG_printf(&trace, "MONO\n");
        AC_AppHandle.rxPktSize = 0x58; // max packet size for 44.1 mono
        #endif // ENABLE_STEREO_PLAYBACK
        #endif // SAMPLE_RATE_TX_44_1kHz

        #ifdef SAMPLE_RATE_TX_32kHz
        LOG_printf(&trace, "PLAYBACK: 32KHZ ");
        #ifdef ENABLE_STEREO_PLAYBACK
        LOG_printf(&trace, "STEREO\n");
        AC_AppHandle.rxPktSize = 0x80; // max packet size for 32K stereo
        #else // ENABLE_STEREO_PLAYBACK
        LOG_printf(&trace, "MONO\n");
        AC_AppHandle.rxPktSize = 0x40; // max packet size for 32K mono
        #endif // ENABLE_STEREO_PLAYBACK
        #endif // SAMPLE_RATE_TX_32kHz

        #ifdef SAMPLE_RATE_TX_16kHz
        LOG_printf(&trace, "PLAYBACK: 16KHZ ");
        #ifdef ENABLE_STEREO_PLAYBACK
        LOG_printf(&trace, "STEREO\n");
        AC_AppHandle.rxPktSize = RX_PKT_SIZE_16K_PLAYBACK_STEREO; // max packet size for 16K stereo
        rx_pkt_size_16K_playback = RX_PKT_SIZE_16K_PLAYBACK_STEREO; // max packet size for 16K stereo
        #else // ENABLE_STEREO_PLAYBACK
        LOG_printf(&trace, "MONO\n");
        AC_AppHandle.rxPktSize = RX_PKT_SIZE_16K_PLAYBACK_MONO; // max packet size for 16K mono
        rx_pkt_size_16K_playback = RX_PKT_SIZE_16K_PLAYBACK_MONO;  // max packet size for 16K mono
        #endif // ENABLE_STEREO_PLAYBACK
        #endif // SAMPLE_RATE_TX_16kHz

#else /* ENABLE_PLAYBACK_TWO_SAMPLE_RATES */
        LOG_printf(&trace, "PLAYBACK: 48KHZ ");
        #ifdef ENABLE_STEREO_PLAYBACK
        LOG_printf(&trace, "STEREO\n");
        AC_AppHandle.rxPktSize = EP_PB_MAXP; // max packet size for 48K stereo
        #else // ENABLE_STEREO_PLAYBACK
        LOG_printf(&trace, "MONO\n");
        AC_AppHandle.rxPktSize = 0x60; // max packet size for 48K mono
        #endif // ENABLE_STEREO_PLAYBACK

        LOG_printf(&trace, "PLAYBACK: 16KHZ ");
        #ifdef ENABLE_STEREO_PLAYBACK
        rx_pkt_size_16K_playback = RX_PKT_SIZE_16K_PLAYBACK_STEREO; // max packet size for 16K stereo
        LOG_printf(&trace, "STEREO\n");
        #else // ENABLE_STEREO_PLAYBACK
        rx_pkt_size_16K_playback = RX_PKT_SIZE_16K_PLAYBACK_MONO;  // max packet size for 16K mono
        LOG_printf(&trace, "MONO\n");
        #endif // ENABLE_STEREO_PLAYBACK
#endif /* ENABLE_PLAYBACK_TWO_SAMPLE_RATES */

        AC_AppHandle.txPktSize = EP_REC_MAXP; // max packet size for 16K mono
        AC_AppHandle.hidTxPktSize = EP_HID_MAXP; // max packet size for HID output report

        /* All Function Handlers need to be Initialised */
        AC_AppHandle.playAudioApp = appPlayAudio;
        AC_AppHandle.recordAudioApp = appRecordAudio;
        AC_AppHandle.initPlayAudioApp = appInitPlayAudio;
        AC_AppHandle.initRecordAudioApp = appInitRecordAudio;
        AC_AppHandle.stopPlayAudioApp = appStopPlayAudio;
        AC_AppHandle.stopRecordAudioApp = appStopRecordAudio;
        AC_AppHandle.mediaGetPresentStateApp = AppGetMediaStatus;
        AC_AppHandle.mediaInitApp = AppMediaInit;
        AC_AppHandle.mediaEjectApp = AppMediaEject;
        AC_AppHandle.mediaLockUnitApp = AppLockMedia;
        AC_AppHandle.getMediaSizeApp = AppGetMediaSize;
        AC_AppHandle.getHidReportApp = appGetHidReport;
        AC_AppHandle.ctrlHandler  = appCtrlFxn;
        AC_AppHandle.isoHandler   = appIsoFxn;
        AC_AppHandle.hidHandler = appHidFxn;

        AC_AppHandle.numLun = 2;

        /* Initialize End point descriptors */
        AC_initDescriptors(AC_AppHandle.pAcObj, (Uint16 *)deviceDescriptorB,
                            CSL_AC_DEVICE_DESCR, sizeof(deviceDescriptorB));

        AC_initDescriptors(AC_AppHandle.pAcObj, (Uint16 *)deviceQualifierDescr,
                            CSL_AC_DEVICE_QUAL_DESCR, 10);

        AC_initDescriptors(AC_AppHandle.pAcObj, (Uint16 *)configDescriptor,
                            CSL_AC_CONFIG_DESCR, sizeof(configDescriptor));

        AC_initDescriptors(AC_AppHandle.pAcObj, (Uint16 *)stringLanId,
                            CSL_AC_STRING_LANGID_DESC, 6);

        AC_initDescriptors(AC_AppHandle.pAcObj, (Uint16 *)acHidReportDescriptor,
                            CSL_AC_HID_REPORT_DESC, sizeof(acHidReportDescriptor));

        /* Initialize HID */
        AC_AppHandle.acHidIfNum = IF_NUM_HID; // HID interface number
        AC_AppHandle.acHidReportId = HID_REPORT_ID; // HID report ID
        AC_AppHandle.acHidReportLen = HID_REPORT_SIZE_BYTES; // HID report length (bytes)
        genHidReport(UI_PUSH_BUTTON_NONE, gHidReport); // init. HID report for Get Report 

        /* Call Init API */
        AC_Open(&AC_AppHandle);

        /* Enable CPU USB interrupts */
        CSL_FINST(CSL_CPU_REGS->IER1, CPU_IER1_USB, ENABLE);

        /* Initialize active sample rate */
        initSampleRate(RATE_48_KHZ, &active_sample_rate, 
            &i2sTxBuffSz);

        /* Initialize ASRC */ 
        Init_Sample_Rate_Converter(active_sample_rate);

        /* Reset codec output buffer */
        reset_codec_output_buffer();

        #ifdef ENABLE_RECORD
        #ifdef SAMPLE_RATE_RX_48kHz
        LOG_printf(&trace, "RECORD: 48KHZ ");
        #else
        LOG_printf(&trace, "RECORD: 16KHZ ");
        #endif // SAMPLE_RATE_RX_48kHz
        // start the rx DMAs
        DMA_StartTransfer(hDmaRxLeft);

        #ifdef ENABLE_STEREO_RECORD
        LOG_printf(&trace, "STEREO  NOT SUPPORTED - RECORD WILL BE MONO\n");
        DMA_StartTransfer(hDmaRxRight);
         #else
        LOG_printf(&trace, "MONO\n");
        #endif

        #endif // ENABLE_RECORD

#ifdef STORE_PARAMETERS_TO_SDRAM
        initSdram(FALSE, 0x0000);
#endif // STORE_PARAMETERS_TO_SDRAM
#ifdef SAMPLE_BY_SAMPLE_PB
        /* SampleBySample, init interrupt */       
        /* Use with compiler "interrupt" keyword */
        //IRQ_plug(I2S_TX_EVENT, i2s_txIsr);
        
        /* Use with dispatcher, no "interrupt" keyword */
        attrs.ier0mask = 0xFFFF;
        attrs.ier1mask = 0xFFFF;
        HWI_dispatchPlug(I2S_TX_EVENT, (Fxn)i2s_txIsr, &attrs);

        IRQ_enable(I2S_TX_EVENT);   /* SampleBySample, enable IRQ for I2S Tx */
#endif
#if defined(SAMPLE_BY_SAMPLE_REC) && !defined(COMBINE_I2S_TX_RX_ISR)
        /* SampleBySample, init interrupt */
        /* Use with compiler "interrupt" keyword */
        IRQ_plug(I2S_RX_EVENT, i2s_rxIsr);
        
        /* Use with dispatcher, no "interrupt" keyword */
        //attrs.ier0mask = 0xFFFF;
        //attrs.ier1mask = 0xFFFF;
        //HWI_dispatchPlug(I2S_RX_EVENT, (Fxn)i2s_rxIsr, &attrs);

        IRQ_enable(I2S_RX_EVENT);    /* SampleBySample, enable IRQ for I2S Rx */
#endif
#if defined(SAMPLE_BY_SAMPLE_PB) || defined(SAMPLE_BY_SAMLE_REC)
        DDC_I2S_transEnable((DDC_I2SHandle)i2sHandleTx, TRUE);    /* SampleBySample, enable I2S transmit and receive */
#endif
#ifndef SAMPLE_BY_SAMPLE_PB
        i2sTxStart(); // - moved from appPlayAudio()
#endif

#ifdef C5535_EZDSP_DEMO
        // clock gating usused peripherals
		ClockGating();
#endif
    }
}
예제 #11
0
status_t SPI_MasterTransferDMA(SPI_Type *base, spi_dma_handle_t *handle, spi_transfer_t *xfer)
{
    assert(handle && xfer);

    dma_transfer_config_t config = {0};

    /* Check if the device is busy */
    if (handle->state == kSPI_Busy)
    {
        return kStatus_SPI_Busy;
    }

    /* Check if input parameter invalid */
    if (((xfer->txData == NULL) && (xfer->rxData == NULL)) || (xfer->dataSize == 0U))
    {
        return kStatus_InvalidArgument;
    }
    
    /* Disable SPI and then enable it, this is used to clear S register*/
    SPI_Enable(base, false);
    SPI_Enable(base, true);
    
    /* Configure tx transfer DMA */
    config.destAddr = SPI_GetDataRegisterAddress(base);
    config.enableDestIncrement = false;
    if (handle->bytesPerFrame == 1U)
    {
        config.srcSize = kDMA_Transfersize8bits;
        config.destSize = kDMA_Transfersize8bits;
    }
    else
    {
        config.srcSize = kDMA_Transfersize16bits;
        config.destSize = kDMA_Transfersize16bits;
    }
    config.transferSize = xfer->dataSize;
    /* Configure DMA channel */
    if (xfer->txData)
    {
        config.enableSrcIncrement = true;
        config.srcAddr = (uint32_t)(xfer->txData);
    }
    else
    {
        /* Disable the source increasement and source set to dummyData */
        config.enableSrcIncrement = false;
        config.srcAddr = (uint32_t)(&s_dummyData);
    }
    DMA_SubmitTransfer(handle->txHandle, &config, true);

    /* Handle rx transfer */
    if (xfer->rxData)
    {
        /* Set the source address */
        DMA_SetDestinationAddress(handle->rxHandle->base, handle->rxHandle->channel, (uint32_t)(xfer->rxData));

        /* Set the transfer size */
        DMA_SetTransferSize(handle->rxHandle->base, handle->rxHandle->channel, xfer->dataSize);
    }

    /* Change the state of handle */
    handle->transferSize = xfer->dataSize;
    handle->state = kSPI_Busy;

    /* Start Rx transfer if needed */
    if (xfer->rxData)
    {
        handle->rxInProgress = true;
        SPI_EnableDMA(base, kSPI_RxDmaEnable, true);
        DMA_StartTransfer(handle->rxHandle);
    }

    /* Always start Tx transfer */
    handle->txInProgress = true;
    SPI_EnableDMA(base, kSPI_TxDmaEnable, true);
    DMA_StartTransfer(handle->txHandle);

    return kStatus_Success;
}