示例#1
0
文件: spi_api.c 项目: sg-/mbed-os
void spi_format(spi_t *obj, int bits, int mode, int slave)
{
    TSB_SSP_TypeDef* spi;
    MBED_ASSERT(slave == SSP_MASTER);   // Master mode only

    spi = obj->spi;

    SSP_Disable(spi);

    obj->bits = bits;

    SSP_SetDataSize(spi, bits);
    SSP_SetClkPolarity(spi, (SSP_ClkPolarity)(mode & 0x1));
    SSP_SetClkPhase(spi, (SSP_ClkPhase)((mode >> 1) & 0x1));

    SSP_Enable(spi);
}
示例#2
0
void max11040_hw_init( void ) {
  int i;

  /* *** configure SPI ***  */
  /* setup pins for SSP (SCK, MISO, MOSI, SSEL) */
  PINSEL1 |= SSP_PINSEL1_SCK  | SSP_PINSEL1_MISO | SSP_PINSEL1_MOSI | SSP_PINSEL1_SSEL;

  /* setup SSP */
  SSPCR0 = SSPCR0_VAL;;
  SSPCR1 = SSPCR1_VAL;
  SSPCPSR = 0x02;

  /* initialize interrupt vector */
  VICIntSelect &= ~VIC_BIT( VIC_SPI1 );         /* SPI1 selected as IRQ */
  VICIntEnable = VIC_BIT( VIC_SPI1 );           /* enable it            */
  _VIC_CNTL(SPI1_VIC_SLOT) = VIC_ENABLE | VIC_SPI1;
  _VIC_ADDR(SPI1_VIC_SLOT) = (uint32_t)SSP_ISR;  /* address of the ISR   */


  /* *** configure DRDY pin***  */
  /* connected pin to EXINT */
  MAXM_DRDY_PINSEL |= MAXM_DRDY_PINSEL_VAL << MAXM_DRDY_PINSEL_BIT;
  SetBit(EXTMODE, MAXM_DRDY_EINT);     /* EINT is edge trigered */
  ClearBit(EXTPOLAR, MAXM_DRDY_EINT);  /* EINT is trigered on falling edge */
  SetBit(EXTINT, MAXM_DRDY_EINT);      /* clear pending EINT */

  /* initialize interrupt vector */
  VICIntSelect &= ~VIC_BIT( MAXM_DRDY_VIC_IT );                       /* select EINT as IRQ source */
  VICIntEnable = VIC_BIT( MAXM_DRDY_VIC_IT );                         /* enable it                 */
  _VIC_CNTL(MAX11040_DRDY_VIC_SLOT) = VIC_ENABLE | MAXM_DRDY_VIC_IT;
  _VIC_ADDR(MAX11040_DRDY_VIC_SLOT) = (uint32_t)EXTINT_ISR;           /* address of the ISR        */


  /* write configuration register */
  SSP_Send(0x60);       /* wr conf */
  for (i=0; i<MAXM_NB_ADCS; i++) {
    SSP_Send(0x40);     /* adcx: reset */
  }
  SSP_Enable();
  SSP_ClearRti();
  SSP_EnableRti();
}
示例#3
0
/* SSP_LoopBack function */
void SSP_LoopBack(void)
{
    SSP_InitTypeDef initSSP;
    SSP_FIFOState fifoState;
	
    uint16_t datTx = 0U;        /* must use 16bit type */
    uint32_t cntTx = 0U;
    uint32_t cntRx = 0U;

    uint16_t receive = 0U;
    uint16_t Rx_Buf[MAX_BUFSIZE] = { 0U };
    uint16_t Tx_Buf[MAX_BUFSIZE] = { 0U };

    SystemInit();

    /* enable the LED on board to display some info */
    UART_Configuration(UART);
    UART_Print(UART, "This is an example for SSP module!\n\r");

    /* configure the SSP module */
    initSSP.FrameFormat = SSP_FORMAT_SPI;

    /* default is to run at maximum bit rate */
    initSSP.PreScale = 2U;
    initSSP.ClkRate = 1U;
    /* define BITRATE_MIN to run at minimum bit rate */
    /*   BitRate = fSYS / (PreScale x (1 + ClkRate)) */
#ifdef BITRATE_MIN
    initSSP.PreScale = 254U;
    initSSP.ClkRate = 255U;
#endif
    initSSP.ClkPolarity = SSP_POLARITY_LOW;
    initSSP.ClkPhase = SSP_PHASE_FIRST_EDGE;
    initSSP.DataSize = 16U;
    initSSP.Mode = SSP_MASTER;
    SSP_Init(&initSSP);


    /* enable loop back mode for self test */
    SSP_SetLoopBackMode(ENABLE);

    /* enable and run SSP module */
    SSP_Enable();

    while (1) {
        
        datTx++;
        
        /* send data if Tx FIFO is available */
        fifoState = SSP_GetFIFOState(SSP_TX);
        if ((fifoState == SSP_FIFO_EMPTY) || (fifoState == SSP_FIFO_NORMAL)) {
            SSP_SetTxData(datTx);
            if (cntTx < MAX_BUFSIZE) {
                Tx_Buf[cntTx] = datTx;
                cntTx++;
            } else {
                /* do nothing */
            }
        } else {
            /* do nothing */
        }


        /* check if there is data arrived */
        fifoState = SSP_GetFIFOState(SSP_RX);
        if ((fifoState == SSP_FIFO_FULL) || (fifoState == SSP_FIFO_NORMAL)) {
            receive = SSP_GetRxData();
            if (cntRx < MAX_BUFSIZE) {
                Rx_Buf[cntRx] = receive;
                cntRx++;
            } else {
                /* Place a break point here to check if receive data is right.                */
                /* Success Criteria:                                                          */
                /*               Every data transmited from Tx_Buf is received in Rx_Buf.     */
                /* When the line "#define BITRATE_MIN" is commented, the SSP is run in maxium */
                /*  bit rate, so we can find there is enough time to transmit date from 1 to  */
                /*  MAX_BUFSIZE one by one. but if we uncomment that line, SSP is run in      */
                /*  minimum bit rate, we will find that receive data can't catch "datTx++",   */
                /*  in this so slow bit rate, when the Tx FIFO is available, the cntTx has    */
                /*  been increased so much.                                                   */
                __NOP();
            }

        } else {
            /* do nothing */
        }
        sprintf(message, "Received data is %d\n\r" + (uint8_t)(receive / 8000));
        UART_Print(UART, message);
    }
}
示例#4
0
文件: spi_api.c 项目: sg-/mbed-os
void spi_init(spi_t *obj, PinName mosi, PinName miso, PinName sclk, PinName ssel)
{
    SSP_InitTypeDef config;

    // Check pin parameters
    SPIName spi_mosi = (SPIName)pinmap_peripheral(mosi, PinMap_SPI_MOSI);
    SPIName spi_miso = (SPIName)pinmap_peripheral(miso, PinMap_SPI_MISO);
    SPIName spi_sclk = (SPIName)pinmap_peripheral(sclk, PinMap_SPI_SCLK);
    SPIName spi_ssel = (SPIName)pinmap_peripheral(ssel, PinMap_SPI_SSEL);
    SPIName spi_data = (SPIName)pinmap_merge(spi_mosi, spi_miso);
    SPIName spi_cntl = (SPIName)pinmap_merge(spi_sclk, spi_ssel);

    obj->module = (SPIName)pinmap_merge(spi_data, spi_sclk);
    obj->module = (SPIName)pinmap_merge(spi_data, spi_cntl);
    MBED_ASSERT((int)obj->module!= NC);

    // Identify SPI module to use
    switch ((int)obj->module) {
        case SPI_0:
            obj->spi = TSB_SSP0;
            break;
        case SPI_1:
            obj->spi = TSB_SSP1;
            break;
        case SPI_2:
            obj->spi = TSB_SSP2;
            break;
        default:
            obj->spi= NULL;
            obj->module = (SPIName)NC;
            error("Cannot found SPI module corresponding with input pins.");
            break;
    }

    // pin out the spi pins
    pinmap_pinout(mosi, PinMap_SPI_MOSI);
    pinmap_pinout(miso, PinMap_SPI_MISO);
    pinmap_pinout(sclk, PinMap_SPI_SCLK);

    if (ssel != NC) {
        pinmap_pinout(ssel, PinMap_SPI_SSEL);
    }

    // Declare Config
    config.FrameFormat = SSP_FORMAT_SPI;

    // bit_rate = Fsys / (clk_prescale * (clk_rate + 1))
    config.PreScale = 48;
    config.ClkRate = 0;

    config.ClkPolarity = SSP_POLARITY_LOW;
    config.ClkPhase = SSP_PHASE_FIRST_EDGE;
    config.DataSize = 0x08;

    obj->bits = config.DataSize;
    config.Mode = SSP_MASTER;
    SSP_Init(obj->spi, &config);

    // Disable all interrupt

    SSP_SetINTConfig(obj->spi, SSP_INTCFG_NONE);
    SSP_Enable(obj->spi);
}
示例#5
0
文件: spi_api.c 项目: sg-/mbed-os
void spi_frequency(spi_t *obj, int hz)
{
    TSB_SSP_TypeDef* spi;

    // Search Freq data
    int fr_gear = 1;
    int cur_hz = 1;
    int32_t best_diff = TMPM46B_SPI_FMAX;
    int best_cpsdvsr = 254;
    int best_scr = 255;
    int cur_cpsdvsr = 48;
    int cur_scr = 0;
    int32_t diff;

    /* Assert Min frequency
       Hz = Fsys / (CPSDVSR * (SCR + 1))
       Domain value of CPSDVSR is an even number between 2 to 254
       Domain value of SCR is a number between 0 to 255
       Hz Min if CPSDVSR and SCR max (CPSDVSR = 254, SCR = 255)
    */
    MBED_ASSERT((SystemCoreClock / 65024) <= (uint32_t)hz);

    if (obj->module == SPI_2) {
        MBED_ASSERT(hz <= TMPM46B_SPI_2_FMAX);
    } else {
        MBED_ASSERT(hz <= TMPM46B_SPI_FMAX); // Default value of SPI_0, SPI_1, SPI_2
    }

    spi = obj->spi;
    fr_gear = SystemCoreClock / hz;
    if (fr_gear < 48) {
        cur_cpsdvsr = fr_gear;
    }
    while (best_diff != 0 && cur_cpsdvsr <= 254) {
        cur_scr = fr_gear / cur_cpsdvsr - 1;

        if (cur_scr < 0) {
            break;
        }

        for (; cur_scr < 256; ++cur_scr) {
            cur_hz = SystemCoreClock / (cur_cpsdvsr * (1 + cur_scr));

            diff = cur_hz - hz;

            if (diff < 0) {
                diff = -diff;
            }

            if (diff < best_diff) {
                best_cpsdvsr = cur_cpsdvsr;
                best_scr = cur_scr;
                best_diff = diff;
            } else if (diff >= best_diff) {
                break;
            }
        }

        cur_cpsdvsr += 2;
    }

    SSP_Disable(spi);
    // Set bit rate of SPI
    SSP_SetClkPreScale(spi, (uint8_t)best_cpsdvsr, (uint8_t)best_scr);
    SSP_Enable(spi);
}
示例#6
0
mdev_t *ssp_drv_open(SSP_ID_Type ssp_id, SSP_FrameFormat_Type format,
		SSP_MS_Type mode, SSP_DMA dma, int cs, bool level)
{
	int ret;
	SSP_CFG_Type sspCfgStruct;
	SSP_FIFO_Type sspFifoCfg;
	SPI_Param_Type spiParaStruct;
	SSP_NWK_Type sspNetworkCfg;
	PSP_Param_Type pspParaStruct;
	sspdev_data_t *ssp_data_p;
	mdev_t *mdev_p = mdev_get_handle(mdev_ssp_name[ssp_id]);
	ssp_data_p = (sspdev_data_t *) mdev_p->private_data;

	if (mdev_p == NULL) {
		SSP_LOG("Unable to open device %s\r\n",
			mdev_ssp_name[ssp_id]);
		return NULL;
	}
	ssp_data_p->slave = mode;
	ret = os_mutex_get(&ssp_mutex[mdev_p->port_id], OS_WAIT_FOREVER);
	if (ret == -WM_FAIL) {
		SSP_LOG("failed to get mutex\r\n");
		return NULL;
	}
	/* If ringbuffer size is not set by user then set to default size */
	if (GET_RX_BUF_SIZE(ssp_data_p) == 0) {
		SET_RX_BUF_SIZE(ssp_data_p, SSP_RX_BUF_SIZE);
	}
	if (rx_buf_init(ssp_data_p)) {
		SSP_LOG("Unable to allocate ssp software ring buffer\r\n");
		return NULL;
	}
	/* If clk is not set by user then set it to default */
	if (ssp_data_p->freq == 0) {
		ret = ssp_drv_set_clk(mdev_p->port_id, DEFAULT_SSP_FREQ);
	}

	/* Configure the pinmux for ssp pins */
	if (cs >= 0 && mode == SSP_MASTER) {
		board_ssp_pin_config(mdev_p->port_id, 0);
		/* Use user specified chip select pin */
		ssp_data_p->cs = cs;
		ssp_data_p->cs_level = level;
		GPIO_PinMuxFun(cs, PINMUX_FUNCTION_0);
		GPIO_SetPinDir(cs, GPIO_OUTPUT);
		/* Initially keep slave de-selected */
		GPIO_WritePinOutput(cs, !level);
	} else {
		board_ssp_pin_config(mdev_p->port_id, 1);
	}

	/* Configure SSP interface */
	sspCfgStruct.mode = SSP_NORMAL;
	sspCfgStruct.masterOrSlave = mode;
	sspCfgStruct.trMode = SSP_TR_MODE;
	sspCfgStruct.dataSize = SSP_DATASIZE_8;
	sspCfgStruct.sfrmPola = SSP_SAMEFRM_PSP;
	sspCfgStruct.slaveClkRunning = SSP_SLAVECLK_TRANSFER;
	sspCfgStruct.txd3StateEnable = ENABLE;
	/* RXFIFO inactivity timeout, [timeout = 100 / 26MHz] (Bus clock) */
	sspCfgStruct.timeOutVal = 100;

	switch (format) {
	case SSP_FRAME_SPI:
		sspCfgStruct.frameFormat = SSP_FRAME_SPI;
		sspCfgStruct.txd3StateType = SSP_TXD3STATE_ELSB;
		break;
	case SSP_FRAME_PSP:
		sspCfgStruct.frameFormat = SSP_FRAME_PSP;
		sspCfgStruct.txd3StateType = SSP_TXD3STATE_12SLSB;
		break;
	case SSP_FRAME_SSP:
		SSP_LOG("Frame Format not implemented.\r\n");
		return NULL;
	}

	/* Configure SSP Fifo */
	sspFifoCfg.fifoPackMode =  DISABLE;

	/* See if dma needs to be enabled */
	if (dma == DMA_ENABLE) {
		/* Enable DMA controller clock */
		CLK_ModuleClkEnable(CLK_DMAC);
		sspFifoCfg.rxFifoFullLevel = SSP_DMA_FIFO_RX_THRESHOLD;
		sspFifoCfg.txFifoEmptyLevel = SSP_DMA_FIFO_TX_THRESHOLD;
		sspFifoCfg.rxDmaService = ENABLE;
		sspFifoCfg.txDmaService = ENABLE;
		ssp_data_p->dma = 1;
		sspCfgStruct.trailByte = SSP_TRAILBYTE_DMA;
	} else {
		sspFifoCfg.rxFifoFullLevel = SSP_FIFO_RX_THRESHOLD;
		sspFifoCfg.txFifoEmptyLevel = SSP_FIFO_TX_THRESHOLD;
		sspFifoCfg.rxDmaService = DISABLE;
		sspFifoCfg.txDmaService = DISABLE;
		sspCfgStruct.trailByte = SSP_TRAILBYTE_CORE;
	}

	/* Let the settings take effect */
	SSP_Disable(mdev_p->port_id);
	SSP_Init(mdev_p->port_id, &sspCfgStruct);
	SSP_FifoConfig(mdev_p->port_id, &sspFifoCfg);

	/* Do frame format config */
	switch (format) {
	case SSP_FRAME_SPI:
		spiParaStruct.spiClkPhase = SPI_SCPHA_1;
		spiParaStruct.spiClkPolarity = SPI_SCPOL_LOW;
		SPI_Config(mdev_p->port_id, &spiParaStruct);
		break;
	case SSP_FRAME_PSP:
		pspParaStruct.pspFsrtType = 0;
		pspParaStruct.pspClkMode = PSP_DRIVFALL_SAMPRISE_IDLELOW;
		pspParaStruct.pspFrmPola = PSP_SFRMP_LOW;
		pspParaStruct.pspEndTransState = PSP_ENDTRANS_LOW;
		pspParaStruct.startDelay = 0;
		pspParaStruct.dummyStart = 0;
		pspParaStruct.dummyStop = 0;
		pspParaStruct.frmDelay = 0;
		pspParaStruct.frmLength = 8;
		PSP_Config(mdev_p->port_id, &pspParaStruct);
		sspNetworkCfg.frameRateDiv = 1;
		sspNetworkCfg.txTimeSlotActive = 3;
		sspNetworkCfg.rxTimeSlotActive = 3;
		SSP_NwkConfig(mdev_p->port_id, &sspNetworkCfg);
		break;
	case SSP_FRAME_SSP:
		SSP_LOG("Frame Format not implemented.\r\n");
		return NULL;
	}

	/* Enable read interrupts only for slave when dma is disabled*/
	if (mode == SSP_SLAVE && dma == DMA_DISABLE) {
		install_int_callback(SSP_INT_BASE + mdev_p->port_id,
				     SSP_INT_RFFI,
				     ssp_read_irq_handler[mdev_p->port_id]);
		NVIC_EnableIRQ(SSP_IRQn_BASE + mdev_p->port_id);
		NVIC_SetPriority(SSP_IRQn_BASE + mdev_p->port_id, 0xF);
		SSP_IntMask(mdev_p->port_id, SSP_INT_RFFI, UNMASK);
	}

	SSP_Enable(mdev_p->port_id);
	return mdev_p;
}
示例#7
0
static int ssp_drv_dma_read(mdev_t *dev, uint8_t *data, int num)
{
	DMA_CFG_Type dma_tx, dma_rx;
	uint8_t dummy;
	uint16_t dma_trans = DMA_MAX_BLK_SIZE, len = num;
	uint32_t cnt;
	sspdev_data_t *ssp_data_p;

	ssp_data_p = (sspdev_data_t *) dev->private_data;
	dummy = SPI_DUMMY_BYTE;
	ssp_dma_get_tx_config(&dma_tx, (uint32_t) &dummy, dev->port_id, 1);
	ssp_dma_get_rx_config(&dma_rx, (uint32_t) data, dev->port_id, 0);

	while (num > 0) {
		if (num < DMA_MAX_BLK_SIZE)
			dma_trans = num;
		if (ssp_data_p->slave == SSP_SLAVE) {

			/* FIXME: To start a dma operation, ssp needs to
			 * be disabled and enable to flush HW fifo. Ideally
			 * this shouldn't be done as we can miss some
			 * data on line, but without disabling and enabling
			 * again we will read some garbage data from HW fifo.
			 */
			SSP_Disable(dev->port_id);
			DMA_Disable();
			SSP_Enable(dev->port_id);
			DMA_ChannelInit(SSP_RX_CHANNEL, &dma_rx);
			DMA_IntClr(SSP_RX_CHANNEL, INT_CH_ALL);
			DMA_IntMask(SSP_RX_CHANNEL, INT_CH_ALL, MASK);
			DMA_SetBlkTransfSize(SSP_RX_CHANNEL, dma_trans);

			DMA_Enable();
			DMA_ChannelCmd(SSP_RX_CHANNEL, ENABLE);

			/* Wait for dma transfer to complete on given channel */
			cnt = SSP_MAX_DMA_WAIT;
			while (--cnt &&
			(DMA->RAWBLOCK.BF.RAW & (1 << SSP_RX_CHANNEL)) == 0)
				;
			if (!cnt) {
				return 0;
			}
		} else {
			/* Configure channel 0 for tx and 1 for rx */
			DMA_Disable();
			DMA_ChannelInit(SSP_TX_CHANNEL, &dma_tx);
			DMA_IntClr(SSP_TX_CHANNEL, INT_CH_ALL);
			DMA_IntMask(SSP_TX_CHANNEL, INT_CH_ALL, MASK);
			DMA_SetBlkTransfSize(SSP_TX_CHANNEL, dma_trans);

			DMA_ChannelInit(SSP_RX_CHANNEL, &dma_rx);
			DMA_IntClr(SSP_RX_CHANNEL, INT_CH_ALL);
			DMA_IntMask(SSP_RX_CHANNEL, INT_CH_ALL, MASK);
			DMA_SetBlkTransfSize(SSP_RX_CHANNEL, dma_trans);

			DMA_Enable();
			DMA_ChannelCmd(SSP_TX_CHANNEL, ENABLE);
			DMA_ChannelCmd(SSP_RX_CHANNEL, ENABLE);

			/* Wait for dma transfer to complete on given channel */
			cnt = SSP_MAX_DMA_WAIT;
			while (--cnt &&
			(DMA->RAWBLOCK.BF.RAW & (1 << SSP_TX_CHANNEL)) == 0)
				;
			if (!cnt) {
				SSP_LOG("%s: dma tx operation timed out\r\n",
					__func__);
				return 0;
			}

			/* Wait for dma transfer to complete on given channel */
			cnt = SSP_MAX_DMA_WAIT;
			while (--cnt &&
		       (DMA->RAWBLOCK.BF.RAW & (1 << SSP_RX_CHANNEL)) == 0)
				;
			if (!cnt) {
				SSP_LOG("%s: dma rx operation timed out\r\n",
					__func__);
				return 0;
			}
		}
		/* Increment destination address for rx channel */
		dma_rx.destDmaAddr += dma_trans;
		num -= dma_trans;
	}
	return len;
}
示例#8
0
void SSP_LoopBack(void)
{
    SSP_InitTypeDef initSSP;
    SSP_FIFOState fifoState;

    uint16_t datTx = 0U;        /* must use 16bit type */
    uint32_t cntTx = 0U;
    uint32_t cntRx = 0U;

    uint16_t receive = 0U;
    uint16_t Rx_Buf[MAX_BUFSIZE] = { 0U };
    uint16_t Tx_Buf[MAX_BUFSIZE] = { 0U };

    /* configure the SSP module */
    initSSP.FrameFormat = SSP_FORMAT_SPI;

    /* default is to run at maximum bit rate */
    initSSP.PreScale = 2U;
    initSSP.ClkRate = 1U;
    /* define BITRATE_MIN to run at minimum bit rate */
    /*   BitRate = fSYS / (PreScale x (1 + ClkRate)) */
#ifdef BITRATE_MIN
    initSSP.PreScale = 254U;
    initSSP.ClkRate = 255U;
#endif
    initSSP.ClkPolarity = SSP_POLARITY_LOW;
    initSSP.ClkPhase = SSP_PHASE_FIRST_EDGE;
    initSSP.DataSize = 16U;
    initSSP.Mode = SSP_MASTER;
    SSP_Init(TSB_SSP0, &initSSP);

    /* enable loop back mode for self test */
    SSP_SetLoopBackMode(TSB_SSP0, ENABLE);

    /* enable and run SSP module */
    SSP_Enable(TSB_SSP0);

    /* initialize LEDs on M366-SK board before display something */
    GPIO_SetOutput(GPIO_PA,0xFFU);    
    GPIO_WriteData(GPIO_PA,0xFFU); 

    while (1) {

        datTx++;
        /* send data if Tx FIFO is available */
        fifoState = SSP_GetFIFOState(TSB_SSP0, SSP_TX);
        if ((fifoState == SSP_FIFO_EMPTY) || (fifoState == SSP_FIFO_NORMAL)) {
            SSP_SetTxData(TSB_SSP0, datTx);
            if (cntTx < MAX_BUFSIZE) {
                Tx_Buf[cntTx] = datTx;
                cntTx++;
            } else {
                /* do nothing */
            }
        } else {
            /* do nothing */
        }

        /* check if there is data arrived */
        fifoState = SSP_GetFIFOState(TSB_SSP0, SSP_RX);
        if ((fifoState == SSP_FIFO_FULL) || (fifoState == SSP_FIFO_NORMAL)) {
            receive = SSP_GetRxData(TSB_SSP0);
            if (cntRx < MAX_BUFSIZE) {
                Rx_Buf[cntRx] = receive;
                cntRx++;
            } else {
                /* Place a break point here to check if receive data is right.                */
                /* Success Criteria:                                                          */
                /*               Every data transmited from Tx_Buf is received in Rx_Buf.     */
                /* When the line "#define BITRATE_MIN" is commented, the SSP is run in maxium */
                /*  bit rate, so we can find there is enough time to transmit date from 1 to  */
                /*  MAX_BUFSIZE one by one. but if we uncomment that line, SSP is run in      */
                /*  minimum bit rate, we will find that receive data can't catch "datTx++",   */
                /*  in this so slow bit rate, when the Tx FIFO is available, the cntTx has    */
                /*  been increased so much.                                                   */
                __NOP();
                result = Buffercompare(Tx_Buf, Rx_Buf, MAX_BUFSIZE);
            }

        } else {
            /* do nothing */
        }

        DisplayLED(receive);
    }
}
PUBLIC t_ser_ab8500_core_error SER_AB8500_CORE_Read
(
IN t_uint8 block_add,
IN t_uint8 register_offset,
IN t_uint8 count,
IN t_uint8 *p_data_in,
OUT t_uint8 *p_data_out
)
{
    t_ser_ab8500_core_error error_ab8500 = SER_AB8500_CORE_OK;
#ifndef __PRCM_HWI2C
    t_ssp_error error_ssp = SSP_OK;
    t_ssp_device_id ssp_device_id = SSP_DEVICE_ID_0;
    t_uint32 rx_element,index = 0x00;
    t_uint32 data_packet=0x00;
    
    if(SSP_OK != SSP_Enable(ssp_device_id, SSP_DISABLE_RX_TX))
    {
        return(SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED);
    }
    
    /* flush receive fifo */
    ser_ab8500_core_FlushRecieveFifo();

    if(count <= SER_AB8500_CORE_SSPFIFO)
    {
        /* Perform Dummy read for first 0x00 data read with SSP */
        error_ab8500 = ser_ab8500_ReadSingleFifoTransaction(0x01, 0x00, 1, p_data_in, p_data_out);
        if(SER_AB8500_CORE_OK != error_ab8500)
        {
             return(error_ab8500);   
        } 

        /* Now perform proper read */
        error_ab8500 = ser_ab8500_ReadSingleFifoTransaction(block_add, register_offset, count, p_data_in, p_data_out);
        if(SER_AB8500_CORE_OK != error_ab8500)
        {
             return(error_ab8500);   
        }
    }
    else
    {
        /* Perform Dummy read for first 0x00 data read with SSP */
        error_ab8500 = ser_ab8500_ReadSingleFifoTransaction(0x01, 0x00, 1, p_data_in, p_data_out);
        if(SER_AB8500_CORE_OK != error_ab8500)
        {
             return(error_ab8500);   
        } 
     
        /* Now perform proper read */
        while ((index < SER_AB8500_CORE_SSPFIFO) && (SSP_OK == error_ssp))
        {        
            /* Data transmitted is write command and block address */
            block_add = (t_uint8)((MASK_BIT5) & block_add);
            data_packet = ((block_add << SHIFT_BYTE1) | register_offset);
            
            /* Tx FIFO is filled before enabling SSP */
            data_packet = ((data_packet << SHIFT_AB8500_DATA) | *p_data_in);
            error_ssp = SSP_SetData(ssp_device_id,data_packet);
            
            p_data_in++;
            register_offset++;
            index++;                
        }
        
        count = count - SER_AB8500_CORE_SSPFIFO;

        if(SSP_OK != error_ssp)
        {
            PRINT("SSP0 Error %d", error_ssp);
            return(SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED);
        }
        
        /* SSP is enabled */
        if(SSP_OK != SSP_Enable(ssp_device_id, SSP_ENABLE_RX_TX))
        {
            PRINT("SSP0 Error SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED");
            return(SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED);
        }

        /* Data recieved */
        index = 0;
        while (index < SER_AB8500_CORE_SSPFIFO)
        {
            if(SSP_OK != SSP_GetData(ssp_device_id,&rx_element))
            {
                 PRINT("SSP0 Error SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED");
                 return(SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED);
            }

            *p_data_out = (rx_element & MASK_ALL8);

            p_data_out++;
            index++; 
        }
        
        while(count)
        {
            /* Data transmitted is write command and block address */
            block_add = (t_uint8)((MASK_BIT5) & block_add);
            data_packet = ((block_add << SHIFT_BYTE1) | register_offset);
            
            /* Tx FIFO is filled before enabling SSP */
            data_packet = ((data_packet << SHIFT_AB8500_DATA) | *p_data_in);
            if(SSP_OK != SSP_SetData(ssp_device_id,data_packet))
            {
                 PRINT("SSP0 Error SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED");
                 return(SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED);
            }

            p_data_in++;
            count--;
            if(SSP_OK != SSP_GetData(ssp_device_id,&rx_element))
            {
                 PRINT("SSP0 Error SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED");
                 return(SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED);
            }

            *p_data_out = (rx_element & MASK_ALL8);
            p_data_out++;
            register_offset++;
        }
    } 
     
    if(SSP_OK != SSP_Enable(ssp_device_id, SSP_DISABLE_RX_TX))
    {
        return(SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED);
    }
    
#else
    error_ab8500 = SER_AB8500_CORE_ReadThruHWI2C(block_add, register_offset, count, p_data_in, p_data_out); 
#endif 
    return(error_ab8500); 
    
}
PRIVATE t_ser_ab8500_core_error ser_ab8500_ReadSingleFifoTransaction
(
IN t_uint8 block_add,
IN t_uint8 register_offset,
IN t_uint32 count,
IN t_uint8 *p_data_in,
OUT t_uint8 *p_data_out
)
{
    t_uint32 index=0x00, rx_element=0x0;
    t_uint32 data_packet=0x00, delay=0x00;
    t_ssp_error error_ssp = SSP_OK;

    while ((index < count) && (SSP_OK == error_ssp))
    {
        /* Data transmitted is write command and block address */
        block_add =(t_uint8) (MASK_BIT5 | block_add);
        data_packet = ((block_add << SHIFT_BYTE1) | register_offset);
         
        /* Tx FIFO is filled before enabling SSP */ 
        data_packet = ((data_packet << SHIFT_AB8500_DATA) | *p_data_in);

        /* Dummy Data */
        error_ssp = SSP_SetData(SSP_DEVICE_ID_0,data_packet);
         
        p_data_in++;
        register_offset++;
        index++;
        for(delay=0; delay<AB8500_CORE_MAX_SSPWRITE_DELAY; delay++);   
    }
    
    
    for(delay=0; delay<AB8500_CORE_MAX_SSPWRITE_DELAY; delay++);   
         
    /* SSP is enabled */
    if(SSP_OK != SSP_Enable(SSP_DEVICE_ID_0, SSP_ENABLE_RX_TX))
    {
        PRINT("SSP0 Error SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED");
        return(SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED);
    }
  
    for(delay=0; delay<AB8500_CORE_MAX_SSPWRITE_DELAY; delay++);   
        
    /* Data recieved */
    index = 0;
    while ((index < count) && (SSP_OK == error_ssp))
    {
        error_ssp = SSP_GetData(SSP_DEVICE_ID_0,&rx_element);
        *p_data_out = (rx_element & MASK_ALL8);
        p_data_out++;
        index++; 
         
        if(SSP_OK != error_ssp)
        {
             PRINT("SSP0 Error %d", error_ssp);
             return(SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED);
        }
        for(delay=0; delay<AB8500_CORE_MAX_SSPWRITE_DELAY; delay++);   
    }
    return(SER_AB8500_CORE_OK);
}
PUBLIC t_ser_ab8500_core_error SER_AB8500_CORE_Write
(
IN t_uint8 block_add,
IN t_uint8 register_offset,
IN t_uint8 count,
IN t_uint8 *p_data
)
{
    t_ser_ab8500_core_error error_ab8500 = SER_AB8500_CORE_OK;
#ifndef __PRCM_HWI2C
    t_uint32 delay = 0;
    t_uint32 data_packet = 0;
    t_ssp_error error_ssp = SSP_OK;
    t_uint32 index;
    t_ssp_device_id ssp_device_id = SSP_DEVICE_ID_0;
    error_ssp = SSP_Enable(ssp_device_id, SSP_DISABLE_RX_TX);
    
    if(SSP_OK != error_ssp)
    {
        error_ab8500 = SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED;
        return(error_ab8500);
    }
    
    /* flush receive fifo */
    ser_ab8500_core_FlushRecieveFifo();

    
    /* Fill the Tx FIFO */
    index = 0;       
    if(count <= SER_AB8500_CORE_SSPFIFO)
    {
        while ((index < count) && (SSP_OK == error_ssp))
        {        
            /* Data transmitted is write command and block address */
            block_add = (t_uint8)((~MASK_BIT5) & block_add);
            data_packet = ((block_add << SHIFT_BYTE1) | register_offset);
            
            /* Tx FIFO is filled before enabling SSP */
            data_packet = ((data_packet << SHIFT_AB8500_DATA) | *p_data);
        
            error_ssp = SSP_SetData(ssp_device_id,data_packet);
            if(SSP_OK != error_ssp)
            {
                PRINT("SSP0 Error %d", error_ssp);
                error_ab8500 = SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED;
                return(error_ab8500);
            }

            p_data++;
            register_offset++;
            index++;
            for(delay=0; delay<AB8500_CORE_MAX_SSPWRITE_DELAY; delay++);   
        }

        /* SSP is enabled */
        error_ssp = SSP_Enable(ssp_device_id, SSP_ENABLE_RX_TX);
        
        if(SSP_OK != error_ssp)
        {
            error_ab8500 = SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED;
            PRINT("SSP0 Error %d", error_ssp);
            return(error_ab8500);
        }
    }
    
    else
    {
        while ((index < SER_AB8500_CORE_SSPFIFO) && (SSP_OK == error_ssp))
        {        
            /* Data transmitted is write command and block address */
            block_add = (t_uint8)((~MASK_BIT5) & block_add);
            data_packet = ((block_add << SHIFT_BYTE1) | register_offset);
            
            /* Tx FIFO is filled before enabling SSP */
            data_packet = ((data_packet << SHIFT_AB8500_DATA) | *p_data);
            error_ssp = SSP_SetData(ssp_device_id,data_packet);
            
            p_data++;
            register_offset++;
            index++;                
        }

        count = count - SER_AB8500_CORE_SSPFIFO;

        if(SSP_OK != error_ssp)
        {
            PRINT("SSP0 Error %d", error_ssp);
            error_ab8500 = SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED;
            return(error_ab8500);
        }
        
        /* SSP is enabled */
        error_ssp = SSP_Enable(ssp_device_id, SSP_ENABLE_RX_TX);
        
        if(SSP_OK != error_ssp)
        {
            error_ab8500 = SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED;
            PRINT("SSP0 Error %d", error_ssp);
            return(error_ab8500);
        }
        
        while(count)
        {
            /* Data transmitted is write command and block address */
            block_add = (t_uint8)((~MASK_BIT5) & block_add);
            data_packet = ((block_add << SHIFT_BYTE1) | register_offset);
            
             /* Tx FIFO is filled before enabling SSP */
             data_packet = ((data_packet << SHIFT_AB8500_DATA) | *p_data);
             error_ssp = SSP_SetData(ssp_device_id,data_packet);
             
             p_data++;
             register_offset++;
             count--;
        }
      
        /* SSP is enabled */
        error_ssp = SSP_Enable(ssp_device_id, SSP_ENABLE_RX_TX);
        
        if(SSP_OK != error_ssp)
        {
            error_ab8500 = SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED;
            PRINT("SSP0 Error %d", error_ssp);
            return(error_ab8500);
        }
    } 

    /* flush receive fifo */
    ser_ab8500_core_FlushRecieveFifo();
       
    for(delay=0; delay<AB8500_CORE_MAX_SSPWRITE_DELAY; delay++);   
    
    if(SER_AB8500_CORE_OK == error_ab8500)
    {
        error_ssp = SSP_Enable(ssp_device_id, SSP_DISABLE_RX_TX);
        
        if(SSP_OK != error_ssp)
        {
            error_ab8500 = SER_AB8500_CORE_TRANSACTION_ON_SPI_FAILED;
            return(error_ab8500);
        }
    }

#else             
    error_ab8500 = SER_AB8500_CORE_WriteThruHWI2C(block_add, register_offset, count, p_data); 
#endif

    return(error_ab8500);
    
}