- /**
- * \file swif.c
- *
- * \brief swif APIs.
- *
- * This file contains the APIs for swif.
- */
- /*
- * Copyright (C) 2013 Texas Instruments Incorporated - http://www.ti.com/
- */
- /*
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the
- * distribution.
- *
- * Neither the name of Texas Instruments Incorporated nor the names of
- * its contributors may be used to endorse or promote products derived
- * from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- *
- */
- #include "..\Common\device.h"
- #include "..\Common\types.h" // Basic Type declarations
- #include "..\Common\hal_UCS.h"
- #include "..\Common\hal_pmm.h"
- #include "usb2any.h"
- #include "..\wavevision\_include\fpga.h"
- unsigned int DUTY_CYCLE_25,DUTY_CYCLE_50,DUTY_CYCLE_75,DUTY_CYCLE_35,DUTY_CYCLE_65;
- #define SWIF_INPUT 0x10
- #define SWIF_OUTPUT 0x08
- //definition for reading a register
- #define RD_TIME_UINT 125000
- #define RD_TIME_UINT_25 781
- #define RD_TIME_UINT_35 1093
- #define RD_TIME_UINT_50 1562
- #define RD_TIME_UINT_65 2031
- #define RD_TIME_UINT_75 2381
- static unsigned int cur_clk_s;
- //definition for sending a symbol to lmp91300
- #define SET_TX_HIGH 0xF7
- #define SET_TX_LOW 0x08
- #define ZERO_SYM 0
- #define ONE_SYM 1
- #define IDLE_SYM 2
- //------------------------------------------------------------------------------
- // reset_swif_for_spi
- //
- // DESCRIPTION:
- // initialize the pins for SPI interface
- //
- //------------------------------------------------------------------------------
- void reset_swif_for_spi(void)
- {
- P2SEL &= ~0x08; // p2.3 rx
- P2SEL &= ~0x10; // p2.4 tx
- P2DIR |= 0x18; // make it out, in spi mode, these two pin muts be low
- P2OUT &= ~0x18; // Make Low
- }
- //------------------------------------------------------------------------------
- // init_swif_set
- //
- // DESCRIPTION:
- // initialize the pins for SWIF interface
- // unsigned char swif_clk: SWIF transfer speed(k unit)
- //------------------------------------------------------------------------------
- void init_swif_set(unsigned char swif_clk)
- {
- unsigned int one_time_uint_cycles;
- P2SEL &= ~0x08; // p2.3 tx
- P2SEL &= ~0x10; // p2.4 rx
- P2DIR &= ~0x10; // make it input
- P2DIR |= 0x08; // make it output
- P2OUT &= ~0x08; // Make Low
- one_time_uint_cycles = MASTER_CLOCK_KHZ/swif_clk;
- DUTY_CYCLE_50 = one_time_uint_cycles >>1;
- DUTY_CYCLE_25 = DUTY_CYCLE_50>>1;
- DUTY_CYCLE_75 = DUTY_CYCLE_50 + DUTY_CYCLE_25 ;
- }
- //------------------------------------------------------------------------------
- // delay_cycles
- //
- // DESCRIPTION:
- // delay cpu cycles.
- //------------------------------------------------------------------------------
- void delay_cycles(unsigned int delay_cycles)
- {
- unsigned char count[4];
- unsigned int cur_clk;
- RTCCTL01 = 0;
- RTCCTL01 |= RTCHOLD; // Make sure RTC_A is stopped
- RTCNT1 = 10; // Load RTC_A (4 bytes to make a 32-bit)
- RTCNT2 = 0;
- //RTCNT3 = 0;
- //RTCNT4 = 0;
- RTCCTL01 = RTCSSEL_1 + RTCTEV_3; // CTR_A: Counter Mode, Enable Interrupt, MCLK Input, 32-bit overflow, Start counter
- do {
- cur_clk = 0;
- cur_clk = RTCNT2;
- cur_clk <<=8;
- cur_clk |= RTCNT1;
- }while (cur_clk < delay_cycles );
- }
- //------------------------------------------------------------------------------
- // void SWIFSendSymbol(uint8_t sym)
- //
- // DESCRIPTION:
- // Send symbol "sym" to lmp91300 on the SWIF TX pin.
- //------------------------------------------------------------------------------
- void SWIF_send_symbol(uint8_t sym)
- {
- P2OUT &= SET_TX_HIGH;
- switch (sym) {
- case ZERO_SYM:
- {
- delay_cycles(DUTY_CYCLE_25); // high period for symbol 0
- break;
- }
- case ONE_SYM:
- {
- delay_cycles(DUTY_CYCLE_75); // high period for symbol 1
- break;
- }
- case IDLE_SYM:
- {
- delay_cycles(DUTY_CYCLE_50); // high period for symbol idle
- break;
- }
- default:
- {
- delay_cycles(DUTY_CYCLE_50); // all low period
- break;
- }
- }
- // P2OUT &= SET_TX_LOW; // assert PRI_TX_EN_N
- P2OUT |= SET_TX_LOW;
- switch (sym) {
- case ZERO_SYM:
- {
- delay_cycles(DUTY_CYCLE_75); // low period for symbol 0
- break;
- }
- case ONE_SYM:
- {
- delay_cycles(DUTY_CYCLE_25); // low period for symbol 1
- break;
- }
- case IDLE_SYM:
- {
- delay_cycles(DUTY_CYCLE_50); // low period for idle symbol
- break;
- }
- default:
- {
- delay_cycles(DUTY_CYCLE_50); // all low period
- break;
- }
- }
- }
- //------------------------------------------------------------------------------
- // void SWIF_write_byte
- //
- // DESCRIPTION:
- // Send a byte to lmp91300 by swif interface
- // unsigned char data: the data written to lmp91300 via swif
- //------------------------------------------------------------------------------
- void SWIF_write_byte(unsigned char data)
- {
- int i;
- for ( i=7; i>=0; i--) {
- //output MSB first
- SWIF_send_symbol((data>>i) & 1 );
- }
- }
- //------------------------------------------------------------------------------
- // void SWIF_get_idle
- //
- // DESCRIPTION:
- // wait for a idle coming and measure a idle time unit
- // return: true, if the symbol is idle
- //------------------------------------------------------------------------------
- unsigned char SWIF_get_idle()
- {
- unsigned int cur_clk_d, cur_clk_e;
- unsigned int one_time_uint_cycles;
- do {
-
- {//wait for input become low
- cur_clk_d = RTCNT2;
- cur_clk_d <<=8;
- cur_clk_d |=RTCNT1;
- }
- if ((cur_clk_d - cur_clk_s) > RD_TIME_UINT) //8kbit, 1 time unit is 3125 (125* 25)
- return 0;
- if ((P2IN & SWIF_INPUT)==0x10)
- break;
- }while (1);
- do {
-
- {//wait for input become low
- cur_clk_e = RTCNT2;
- cur_clk_e <<=8;
- cur_clk_e |=RTCNT1;
- }
- if ((cur_clk_e - cur_clk_d) > RD_TIME_UINT) //8kbit, 1 time unit is 3125 (125* 25)
- return 0;
- //wait for high
- if ((P2IN & SWIF_INPUT)==0x0)
- break;
- }while (1);
- one_time_uint_cycles = cur_clk_e - cur_clk_s-5 ;
- DUTY_CYCLE_50 = one_time_uint_cycles >>1;
- DUTY_CYCLE_25 = DUTY_CYCLE_50>>1;
- DUTY_CYCLE_75 = DUTY_CYCLE_50 + DUTY_CYCLE_25 ;
- DUTY_CYCLE_35 = DUTY_CYCLE_25 + (DUTY_CYCLE_25>>1);//adjust 150 clk.
- DUTY_CYCLE_65 = DUTY_CYCLE_50 + (DUTY_CYCLE_25>>1);
- //keep the current change point
- if (((cur_clk_d- cur_clk_s) > DUTY_CYCLE_35 ) && ((cur_clk_d- cur_clk_s) < DUTY_CYCLE_65) ) {
- cur_clk_s = cur_clk_e;
- return 1;
- }
- return 0;
- }
- //------------------------------------------------------------------------------
- // void SWIF_get_sym
- //
- // DESCRIPTION:
- // read a sym
- // return : a sym
- //------------------------------------------------------------------------------
- unsigned char SWIF_get_sym()
- {
- unsigned char one_sym = 0xFF;
- unsigned int cur_clk_d, cur_clk_e;
- do {
-
- {//wait for input become low
- cur_clk_d = RTCNT2;
- cur_clk_d <<=8;
- cur_clk_d |=RTCNT1;
- }
- if ((cur_clk_d - cur_clk_s) > RD_TIME_UINT) //8kbit, 1 time unit is 3125 (125* 25)
- return 0xFF;
- //wait for low
- if ((P2IN & SWIF_INPUT)==0x10)
- break;
- }while (1);
- do {
-
- {//wait for input become high
- cur_clk_e = RTCNT2;
- cur_clk_e <<=8;
- cur_clk_e |=RTCNT1;
- }
- if ((cur_clk_e - cur_clk_d) > RD_TIME_UINT) { //8kbit, 1 time unit is 3125 (125* 25)
- return 0XFF;
- }
- //wait for high
- if ((P2IN & SWIF_INPUT)==0x0)
- break;
- }while (1);
- if (((cur_clk_d- cur_clk_s) < DUTY_CYCLE_35 ) && ((cur_clk_e- cur_clk_d) > DUTY_CYCLE_65) )
- one_sym = ZERO_SYM;
- else one_sym = ONE_SYM;
- //keep the current change point
- cur_clk_s = cur_clk_e;
- return one_sym;
- }
- //------------------------------------------------------------------------------
- // void SWIF_read_reg
- //
- // DESCRIPTION:
- // read a register from lmp91300 by swif interface
- // unsigned char cmd: the register address
- // unsigned char swif_capture_data[2]: the buffer to store the received data
- // return: none
- //------------------------------------------------------------------------------
- void SWIF_read_reg(unsigned char cmd,unsigned char swif_capture_data[2])
- {
- unsigned char data;
- unsigned int cur_clk;
- int i;
- //send read command
- SWIF_send_symbol(IDLE_SYM);
- SWIF_write_byte(cmd);
- SWIF_send_symbol(IDLE_SYM);
- //end transfer
- P2OUT &= SET_TX_HIGH;
- P2OUT &= SET_TX_HIGH;
- P2OUT &= SET_TX_HIGH;
- P2OUT |= SET_TX_LOW;
- //start time clk
- RTCCTL01 = 0;
- RTCCTL01 |= RTCHOLD; // Make sure RTC_A is stopped
- RTCNT1 = 0; // Load RTC_A (4 bytes to make a 32-bit)
- RTCNT2 = 0;
- RTCNT3 = 0;
- RTCNT4 = 0;
- RTCCTL01 = RTCSSEL_1 + RTCTEV_3; // CTR_A: Counter Mode, Enable Interrupt, MCLK Input, 32-bit overflow, Start counter
- //wait for getting the idle start point.
- do {
- if ((P2IN & SWIF_INPUT)==0x10) {//wait for input become high
- cur_clk = RTCNT2;
- cur_clk <<=8;
- cur_clk |=RTCNT1;
- } else {
- //reset the clk count
- RTCCTL01 = 0;
- RTCCTL01 |= RTCHOLD; // Make sure RTC_A is stopped
- RTCNT1 = 0; // Load RTC_A (4 bytes to make a 32-bit)
- RTCNT2 = 0;
- RTCNT3 = 0;
- RTCNT4 = 0;
- RTCCTL01 = RTCSSEL_1 + RTCTEV_3; // CTR_A: Counter Mode, Enable Interrupt, MCLK Input, 32-bit overflow, Start counter
- //initialize start point clk
- cur_clk_s = 0;
- break;
- }
- }while (1);
- if (SWIF_get_idle() ==0) { //for reading, the first symbol must be idle
- return ;
- }
- RTCCTL01 = 0;
- RTCCTL01 |= RTCHOLD; // Make sure RTC_A is stopped
- RTCNT1 = 0; // Load RTC_A (4 bytes to make a 32-bit)
- RTCNT2 = 0;
- RTCNT3 = 0;
- RTCNT4 = 0;
- RTCCTL01 = RTCSSEL_1 + RTCTEV_3; // CTR_A: Counter Mode, Enable Interrupt, MCLK Input, 32-bit overflow, Start counter
- //initialize start point clk
- cur_clk_s = 0;
- data = 0;
- for ( i=7; i>=0; i--) {
- //output MSB first
- //reset the clk count
- data |= (SWIF_get_sym()<< i);
- }
- swif_capture_data[0] = data;
- //don't read the second byte because some register only outputs a byte
- #if 0
- data =0;
- for ( i=7; i>=0; i--) {
- //output MSB first
- data |= (SWIF_get_sym()<< i);
- }
- swif_capture_data[1] = data;
- #endif
- //wait for the read done (8*8*125*25), one bit:125us
- __delay_cycles(4*125*25);
- }
- //------------------------------------------------------------------------------
- // void SWIF_read_data
- //
- // DESCRIPTION:
- // read data from lmp91300 by swif interface, this is for stream mode
- // unsigned char swif_capture_data[2]: the buffer to store the received data
- // return: none
- //------------------------------------------------------------------------------
- void SWIF_read_data(unsigned char swif_capture_data[2])
- {
- unsigned char data;
- unsigned char cmd;
- unsigned int cur_clk;
- int i;
- // init_swif_set(ctrl_data[FPGA_SPI_CFG]);
- init_swif_set(7);
- cmd =0xFA;//read address 0x7a|readflag
- //send read command
- SWIF_send_symbol(IDLE_SYM);
- SWIF_write_byte(cmd);
- SWIF_send_symbol(IDLE_SYM);
- //end transfer
- P2OUT &= SET_TX_HIGH;
- P2OUT &= SET_TX_HIGH;
- P2OUT &= SET_TX_HIGH;
- P2OUT |= SET_TX_LOW;
- //start time clk
- RTCCTL01 = 0;
- RTCCTL01 |= RTCHOLD; // Make sure RTC_A is stopped
- RTCNT1 = 0; // Load RTC_A (4 bytes to make a 32-bit)
- RTCNT2 = 0;
- RTCNT3 = 0;
- RTCNT4 = 0;
- RTCCTL01 = RTCSSEL_1 + RTCTEV_3; // CTR_A: Counter Mode, Enable Interrupt, MCLK Input, 32-bit overflow, Start counter
- //wait for getting the idle start point.
- do {
- if ((P2IN & SWIF_INPUT)==0x10) {//wait for input become high
- cur_clk = RTCNT2;
- cur_clk <<=8;
- cur_clk |=RTCNT1;
- } else {
- //reset the clk count
- RTCCTL01 = 0;
- RTCCTL01 |= RTCHOLD; // Make sure RTC_A is stopped
- RTCNT1 = 0; // Load RTC_A (4 bytes to make a 32-bit)
- RTCNT2 = 0;
- RTCNT3 = 0;
- RTCNT4 = 0;
- RTCCTL01 = RTCSSEL_1 + RTCTEV_3; // CTR_A: Counter Mode, Enable Interrupt, MCLK Input, 32-bit overflow, Start counter
- //initialize start point clk
- cur_clk_s = 0;
- break;
- }
- }while (1);
- if (SWIF_get_idle() ==0) { //for reading, the first symbol must be idle
- return ;
- }
- RTCCTL01 = 0;
- RTCCTL01 |= RTCHOLD; // Make sure RTC_A is stopped
- RTCNT1 = 0; // Load RTC_A (4 bytes to make a 32-bit)
- RTCNT2 = 0;
- RTCNT3 = 0;
- RTCNT4 = 0;
- RTCCTL01 = RTCSSEL_1 + RTCTEV_3; // CTR_A: Counter Mode, Enable Interrupt, MCLK Input, 32-bit overflow, Start counter
- //initialize start point clk
- cur_clk_s = 0;
- data = 0;
- for ( i=7; i>=0; i--) {
- data |= (SWIF_get_sym()<< i);
- }
- swif_capture_data[0] = data;
- data =0;
- for ( i=7; i>=0; i--) {
- //output MSB first
- data |= (SWIF_get_sym()<< i);
- }
- swif_capture_data[1] = data;
- }
- //------------------------------------------------------------------------------
- // void SWIF_write_reg
- //
- // DESCRIPTION:
- // write the value to a register by swif interface
- // unsigned char cmd: the register address
- // unsigned char data[2]: the value to write to register
- // unsigned char data_width: 0 8 bits, 1: 16 bits
- // return: none
- //------------------------------------------------------------------------------
- void SWIF_write_reg(unsigned char cmd, unsigned char data[2], unsigned char data_width)
- {
- //send idle
- SWIF_send_symbol(IDLE_SYM);
- //write write command
- SWIF_write_byte(cmd);
- //write data
- SWIF_write_byte(data[0]);
- if (data_width)//if it is 16 bit data
- SWIF_write_byte(data[1]);
- //send idle
- SWIF_send_symbol(IDLE_SYM);
- P2OUT &= SET_TX_HIGH;
- P2OUT &= SET_TX_HIGH;
- P2OUT &= SET_TX_HIGH;
- P2OUT |= SET_TX_LOW;
- }
- //------------------------------------------------------------------------------
- // unsigned char SWIF_Transfer
- //
- // DESCRIPTION:
- // perform SWIF transfer
- // unsigned char *ctrl_data: data package
- // return: none
- //------------------------------------------------------------------------------
- unsigned char SWIF_Transfer(unsigned char *ctrl_data)
- {
- unsigned char swif_capture_cmd;
- unsigned char swif_capture_data[2];
- unsigned char rw_flag;
- unsigned char data_width;
- init_swif_set(ctrl_data[FPGA_SPI_CFG]);
- // init_swif_set(7);
- //get address
- swif_capture_cmd = ctrl_data[FPGA_SPI_ADDR_H];
- //get read/write flag
- rw_flag = (ctrl_data[FPGA_SPI_CMD]>>1)&1;
- swif_capture_cmd |= ((( ctrl_data[FPGA_SPI_CMD]>>1)&1 ) <<7);
- data_width = (ctrl_data[FPGA_SPI_CMD]>>3) & 3;
- //get data
- swif_capture_data[0] = ctrl_data[FPGA_SPI_DATA_H];//if the data is 16 bits, it hold the MSB byte, if it is 8bit, it holds LSB
- swif_capture_data[1] = ctrl_data[FPGA_SPI_DATA_L];//if the data is 16 bits, it hold the LSB byte,
- if (rw_flag) {// rw_flag ==1: read)
- SWIF_read_reg(swif_capture_cmd,swif_capture_data);
- ctrl_data[FPGA_SPI_DATA_H] = swif_capture_data[0];//if the data is 16 bits, it hold the MSB byte, if it is 8bit, it holds LSB
- ctrl_data[FPGA_SPI_DATA_L] = swif_capture_data[1];//if the data is 16 bits, it hold the LSB byte,
- } else {
- SWIF_write_reg(swif_capture_cmd, swif_capture_data, data_width);
- }
- return 0;
- }
- //-------------------------------------------------------------------------------------------