This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

TrxEB Show RSSI Value on C#

Other Parts Discussed in Thread: MSP430F5438A

Hi,

I want to read rssi value directly with usb or uart. Actually my primary objective is indicated rssi value on c# interface.

I don't have enough information about trxEb. It is not my thing.

I can make c# interface, no problem but I can not read rssi value directly and I can not transferred rssi value to my nterface program.

How can I read rssi value simly to transfer on c# program ? 

Thanks.

  • Hi,

    I assume you are working with one of our transceiver devices? Have you looked at the perl test interface as describes in the SMartRF Studio 7 user manual? Take a closer look. i think you should be able to use that and interface with your C# application.

    You'll find the perl examples in C:\Users\<your_user_name>\Documents\Texas Instruments\SmartRF Studio v7\scripts

  • You are right. I have your tranceiver devices. I want to make an application to show on c# interface rssi value. 

    I am looking for examples but ı can not read yet. Is it possible to read rssi value form TrxEB via serial port or another way ? 

    Thanks your help.

  • Hi,
    With TrxEB you can open UART over USB and read the RSSI register directly from the radio. The rssi value will be in 2's complement.
    You have to write UART function for MSP430 in order to achieve this.
  • Hi,
    Firstly I thank you.

    I do not enough experiments about MSP430 and TrxEB. I can read data using serial port with c# normally. But I do not know how I write UART function for msp430.

    Please help me about write it.

    Thanks
  • Hi,
    I have modified the Easylink example for TX to include the UART functionality. Please try this out.

    On the UART(setting 115200-1-8), you should be able to see the content of the transmitted packet, and the content of MARCSTATE register. Similarly you can read contents of any register by modifying the code.

    Feel free to build upon this basic driver. For more help refer to software examples provided for MSP430F5438A (used in TrxEB boards).

    cc112x_easy_link_tx.c
    //******************************************************************************
    //! @file       cc112x_easy_link_tx.c
    //! @brief      This program sets up an easy link between two trxEB's with
    //!             CC112x EM's connected.
    //!             The program can take any recomended register settings exported
    //!             from SmartRF Studio 7 without any modification with exeption
    //!             from the assumtions decribed below.
    //
    //              Notes: The following asumptions must be fulfilled for
    //              the program to work:
    //
    //                  1.  GPIO2 has to be set up with GPIO2_CFG = 0x06
    //                      PKT_SYNC_RXTX for correct interupt
    //                  2.  Packet engine has to be set up with status bytes enabled
    //                      PKT_CFG1.APPEND_STATUS = 1
    //
    //  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.
    //*****************************************************************************/
    
    
    /*******************************************************************************
    * INCLUDES
    */
    #include "msp430.h"
    #include "lcd_dogm128_6.h"
    #include "hal_spi_rf_trxeb.h"
    #include "cc112x_spi.h"
    #include "stdlib.h"
    #include "bsp.h"
    #include "bsp_key.h"
    #include "io_pin_int.h"
    #include "bsp_led.h"
    #include "cc112x_easy_link_reg_config.h"
    #include "UART_driver.h"
    
    
    /*******************************************************************************
    * DEFINES
    */
    #define ISR_ACTION_REQUIRED     1
    #define ISR_IDLE                0
    
    #define PKTLEN                  30  // 1 < PKTLEN < 126
    
    #define GPIO3                   0x04
    #define GPIO2                   0x08
    #define GPIO0                   0x80
    
    
    /*******************************************************************************
    * LOCAL VARIABLES
    */
    static uint8  packetSemaphore;
    static uint32 packetCounter = 0;
    
    
    /*******************************************************************************
    * STATIC FUNCTIONS
    */
    static void initMCU(void);
    static void registerConfig(void);
    static void manualCalibration(void);
    static void runTX(void);
    static void createPacket(uint8 randBuffer[]);
    static void radioTxISR(void);
    static void updateLcd(void);
    
    
    /*******************************************************************************
    *   @fn         main
    *
    *   @brief      Runs the main routine
    *
    *   @param      none
    *
    *   @return     none
    */
    void main(void) {
    
        // Initialize MCU and peripherals
        initMCU();
    UART_init();
    nextline();
    sendstring("UART Initialized");
    nextline();
        // Write radio registers
        registerConfig();
    
        // Enter runTX, never coming back
        runTX();
    }
    
    
    /*******************************************************************************
    *   @fn         runTX
    *
    *   @brief      Continuously sends packets on button push until button is pushed
    *               again. After the radio has gone into TX the function waits for
    *               interrupt that packet has been sent. Updates packet counter and
    *               display for each packet sent.
    *
    *   @param      none
    *
    *   @return    none
    */
    static void runTX(void) {
    
        // Initialize packet buffer of size PKTLEN + 1
        uint8 txBuffer[PKTLEN+1] = {0};
    uint8 marcState;
        // Connect ISR function to GPIO2
        ioPinIntRegister(IO_PIN_PORT_1, GPIO2, &radioTxISR);
    
        // Interrupt on falling edge
        ioPinIntTypeSet(IO_PIN_PORT_1, GPIO2, IO_PIN_FALLING_EDGE);
    
        // Clear ISR flag
        ioPinIntClear(IO_PIN_PORT_1, GPIO2);
    
        // Enable interrupt
        ioPinIntEnable(IO_PIN_PORT_1, GPIO2);
    
        // Update LCD
        updateLcd();
    
        // Calibrate radio according to errata
        manualCalibration();
    
        // Infinite loop
        while(TRUE) {
    
            // Wait for button push
            if(bspKeyPushed(BSP_KEY_ALL)) {
    
                // Continiously sent packets until button is pressed
                do {
    
                    // Update packet counter
                    packetCounter++;
    
                    // Create a random packet with PKTLEN + 2 byte packet
                    // counter + n x random bytes
                    createPacket(txBuffer);
                    for(int i = 0;i <= PKTLEN+1;i++){
                    TX_data(txBuffer[i]);nextline();
                    }
                 
                    // Write packet to TX FIFO
                    cc112xSpiWriteTxFifo(txBuffer, sizeof(txBuffer));
    
                    // Strobe TX to send packet
                    trxSpiCmdStrobe(CC112X_STX);
                    sendstring("CC112X_MARCSTATE");nextline();
                    TX_data(cc112xSpiReadReg(CC112X_MARCSTATE, &marcState, 1)); //read MARCSTATE register and send to UART
    
                    // Wait for interrupt that packet has been sent.
                    // (Assumes the GPIO connected to the radioRxTxISR function is
                    // set to GPIOx_CFG = 0x06)
                    while(packetSemaphore != ISR_ACTION_REQUIRED);
    
                    // Clear semaphore flag
                    packetSemaphore = ISR_IDLE;
    
                    // Update LCD
                    updateLcd();
                } while (!bspKeyPushed(BSP_KEY_ALL));
            }
        }
    }
    
    
    /*******************************************************************************
    *   @fn         radioTxISR
    *
    *   @brief      ISR for packet handling in TX. Sets packet semaphore
    *               and clears ISR flag
    *
    *   @param      none
    *
    *   @return     none
    */
    static void radioTxISR(void) {
    
        // Set packet semaphore
        packetSemaphore = ISR_ACTION_REQUIRED;
    
        // Clear ISR flag
        ioPinIntClear(IO_PIN_PORT_1, GPIO2);
    }
    
    
    /*******************************************************************************
    *   @fn         initMCU
    *
    *   @brief      Initialize MCU and board peripherals
    *
    *   @param      none
    *
    *   @return     none
    */
    static void initMCU(void) {
    
        // Init clocks and I/O
        bspInit(BSP_SYS_CLK_8MHZ);
    
        // Init LEDs
        bspLedInit();
    
        // Init buttons
        bspKeyInit(BSP_KEY_MODE_POLL);
    
        // Initialize SPI interface to LCD (shared with SPI flash)
        bspIoSpiInit(BSP_FLASH_LCD_SPI, BSP_FLASH_LCD_SPI_SPD);
    
        // Init LCD
        lcdInit();
    
        // Instantiate transceiver RF SPI interface to SCLK ~ 4 MHz
        // Input parameter is clockDivider
        // SCLK frequency = SMCLK/clockDivider
        trxRfSpiInterfaceInit(2);
    
        // Enable global interrupt
        _BIS_SR(GIE);
    }
    
    
    /*******************************************************************************
    *   @fn         registerConfig
    *
    *   @brief      Write register settings as given by SmartRF Studio found in
    *               cc112x_easy_link_reg_config.h
    *
    *   @param      none
    *
    *   @return     none
    */
    static void registerConfig(void) {
    
        uint8 writeByte;
    
        // Reset radio
        trxSpiCmdStrobe(CC112X_SRES);
    
        // Write registers to radio
        for(uint16 i = 0;
            i < (sizeof(preferredSettings)/sizeof(registerSetting_t)); i++) {
            writeByte = preferredSettings[i].data;
            cc112xSpiWriteReg(preferredSettings[i].addr, &writeByte, 1);
        }
    }
    
    
    /*******************************************************************************
    *   @fn         createPacket
    *
    *   @brief      This function is called before a packet is transmitted. It fills
    *               the txBuffer with a packet consisting of a length byte, two
    *               bytes packet counter and n random bytes.
    *
    *               The packet format is as follows:
    *               |--------------------------------------------------------------|
    *               |           |           |           |         |       |        |
    *               | pktLength | pktCount1 | pktCount0 | rndData |.......| rndData|
    *               |           |           |           |         |       |        |
    *               |--------------------------------------------------------------|
    *                txBuffer[0] txBuffer[1] txBuffer[2]            txBuffer[PKTLEN]
    *
    *   @param       Pointer to start of txBuffer
    *
    *   @return      none
    */
    static void createPacket(uint8 txBuffer[]) {
    
        txBuffer[0] = PKTLEN;                           // Length byte
        txBuffer[1] = (uint8) (packetCounter >> 8);     // MSB of packetCounter
        txBuffer[2] = (uint8)  packetCounter;           // LSB of packetCounter
    
        // Fill rest of buffer with random bytes
        for(uint8 i = 3; i < (PKTLEN + 1); i++) {
            txBuffer[i] = (uint8)rand();
        }
    }
    
    
    /*******************************************************************************
    *   @fn         updateLcd
    *
    *   @brief      Updates LCD buffer and sends buffer to LCD module
    *
    *   @param      none
    *
    *   @return     none
    */
    static void updateLcd(void) {
    
        // Update LDC buffer and send to screen.
        lcdBufferClear(0);
        lcdBufferPrintString(0, "EasyLink Test", 0, eLcdPage0);
        lcdBufferSetHLine(0, 0, LCD_COLS-1, 7);
        lcdBufferPrintString(0, "Sent packets:", 0, eLcdPage3);
        lcdBufferPrintInt(0, packetCounter, 70, eLcdPage4);
        lcdBufferPrintString(0, "Packet TX" , 0, eLcdPage7);
        lcdBufferSetHLine(0, 0, LCD_COLS-1, 55);
        lcdBufferInvertPage(0, 0, LCD_COLS, eLcdPage7);
        lcdSendBuffer(0);
    }
    
    
    /*******************************************************************************
    *   @fn         manualCalibration
    *
    *   @brief      Calibrates radio according to CC112x errata
    *
    *   @param      none
    *
    *   @return     none
    */
    #define VCDAC_START_OFFSET 2
    #define FS_VCO2_INDEX 0
    #define FS_VCO4_INDEX 1
    #define FS_CHP_INDEX 2
    static void manualCalibration(void) {
    
        uint8 original_fs_cal2;
        uint8 calResults_for_vcdac_start_high[3];
        uint8 calResults_for_vcdac_start_mid[3];
        uint8 marcstate;
        uint8 writeByte;
    
        // 1) Set VCO cap-array to 0 (FS_VCO2 = 0x00)
        writeByte = 0x00;
        cc112xSpiWriteReg(CC112X_FS_VCO2, &writeByte, 1);
    
        // 2) Start with high VCDAC (original VCDAC_START + 2):
        cc112xSpiReadReg(CC112X_FS_CAL2, &original_fs_cal2, 1);
        writeByte = original_fs_cal2 + VCDAC_START_OFFSET;
        cc112xSpiWriteReg(CC112X_FS_CAL2, &writeByte, 1);
    
        // 3) Calibrate and wait for calibration to be done
        //   (radio back in IDLE state)
        trxSpiCmdStrobe(CC112X_SCAL);
    
        do {
            cc112xSpiReadReg(CC112X_MARCSTATE, &marcstate, 1);
        } while (marcstate != 0x41);
    
        // 4) Read FS_VCO2, FS_VCO4 and FS_CHP register obtained with 
        //    high VCDAC_START value
        cc112xSpiReadReg(CC112X_FS_VCO2,
                         &calResults_for_vcdac_start_high[FS_VCO2_INDEX], 1);
        cc112xSpiReadReg(CC112X_FS_VCO4,
                         &calResults_for_vcdac_start_high[FS_VCO4_INDEX], 1);
        cc112xSpiReadReg(CC112X_FS_CHP,
                         &calResults_for_vcdac_start_high[FS_CHP_INDEX], 1);
    
        // 5) Set VCO cap-array to 0 (FS_VCO2 = 0x00)
        writeByte = 0x00;
        cc112xSpiWriteReg(CC112X_FS_VCO2, &writeByte, 1);
    
        // 6) Continue with mid VCDAC (original VCDAC_START):
        writeByte = original_fs_cal2;
        cc112xSpiWriteReg(CC112X_FS_CAL2, &writeByte, 1);
    
        // 7) Calibrate and wait for calibration to be done
        //   (radio back in IDLE state)
        trxSpiCmdStrobe(CC112X_SCAL);
    
        do {
            cc112xSpiReadReg(CC112X_MARCSTATE, &marcstate, 1);
        } while (marcstate != 0x41);
    
        // 8) Read FS_VCO2, FS_VCO4 and FS_CHP register obtained 
        //    with mid VCDAC_START value
        cc112xSpiReadReg(CC112X_FS_VCO2, 
                         &calResults_for_vcdac_start_mid[FS_VCO2_INDEX], 1);
        cc112xSpiReadReg(CC112X_FS_VCO4,
                         &calResults_for_vcdac_start_mid[FS_VCO4_INDEX], 1);
        cc112xSpiReadReg(CC112X_FS_CHP,
                         &calResults_for_vcdac_start_mid[FS_CHP_INDEX], 1);
    
        // 9) Write back highest FS_VCO2 and corresponding FS_VCO
        //    and FS_CHP result
        if (calResults_for_vcdac_start_high[FS_VCO2_INDEX] >
            calResults_for_vcdac_start_mid[FS_VCO2_INDEX]) {
            writeByte = calResults_for_vcdac_start_high[FS_VCO2_INDEX];
            cc112xSpiWriteReg(CC112X_FS_VCO2, &writeByte, 1);
            writeByte = calResults_for_vcdac_start_high[FS_VCO4_INDEX];
            cc112xSpiWriteReg(CC112X_FS_VCO4, &writeByte, 1);
            writeByte = calResults_for_vcdac_start_high[FS_CHP_INDEX];
            cc112xSpiWriteReg(CC112X_FS_CHP, &writeByte, 1);
        } else {
            writeByte = calResults_for_vcdac_start_mid[FS_VCO2_INDEX];
            cc112xSpiWriteReg(CC112X_FS_VCO2, &writeByte, 1);
            writeByte = calResults_for_vcdac_start_mid[FS_VCO4_INDEX];
            cc112xSpiWriteReg(CC112X_FS_VCO4, &writeByte, 1);
            writeByte = calResults_for_vcdac_start_mid[FS_CHP_INDEX];
            cc112xSpiWriteReg(CC112X_FS_CHP, &writeByte, 1);
        }
    }
    UART_driver.h
    UART_driver.c
    #include <stdio.h>
    #include <string.h>
    #include <stdlib.h>
    #include "msp430.h"
    #include "UART_driver.h"
    
    
    
    
    
    
    /******************************************************************************
     * @fn          Serial Port functions
     *
     * @brief       updates LCD buffer and sends bufer to LCD module.
     *
     * @param       none
     *
     * @return      none
     */
    void UART_init(void)
    {
    
      P5SEL = 0xC0;                             // P5.7,6 = USCI_A0 TXD/RXD
      UCA1CTL1 |= UCSWRST;                      // **Put state machine in reset**
      UCA1CTL1 |= UCSSEL_2;                     // SMCLK
      UCA1BR0 = 69;                              // 8MHz 115200 (see User's Guide)
      UCA1BR1 = 0;                              // 8MHz 115200
      UCA1MCTL |= UCBRS_1 + UCBRF_0;            // Modulation UCBRSx=1, UCBRFx=0
      UCA1CTL1 &= ~UCSWRST;                     // **Initialize USCI state machine**
    
    }
    
    
    void TX_data(unsigned char data)
    {
     
    
       UCA1TXBUF = ( data % 1000)/100+48;
       while((UCA1STAT & 0x01) == 1){};
       UCA1TXBUF = ( data % 100)/10+48;
       while((UCA1STAT & 0x01) == 1){};
       UCA1TXBUF = ( data % 10)/1+48;
       while((UCA1STAT & 0x01) == 1){};
        __delay_cycles(500);
        UCA1TXBUF = (char)9; // TAB, used to add space between output
        while((UCA1STAT & 0x01) == 1){};
     
    }
    
    
    void nextline(void)
    {
       //__delay_cycles(1000);
    
         UCA1TXBUF = (char)13; // line feed
       while((UCA1STAT & 0x01) == 1){};
       UCA1TXBUF = (char)10; // carriage return
    
    
    }
    void sendstring(char *str)
    {
    /*
      static int idx = 0;
      for(idx = 0; idx <= strlen(str); idx++)  {
        while (!(UCA1IFG & UCTXIFG)){}; // USCI_A0 TX buffer ready?
        UCA1TXBUF = str[idx];
      }
    
     */
      //while (!(UCA1IFG & UCTXIFG)){}; // USCI_A0 TX buffer ready?
      //UCA1TXBUF = 0x2E; //place a . after last element of uart_buffer...used for debug
      while(*str){
            while (!(UCA1IFG & UCTXIFG)){}; // USCI_A0 TX buffer ready?
        UCA1TXBUF = *str++;//[idx];
    
      }
    
    }