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.

not able to read and write into the rtc registers continuously

Other Parts Discussed in Thread: BQ32000, TM4C129ENCPDT, BQ2000, TM4C129XNCZAD

Hi everyone

I am santosh prasad new to  tiva c series controllers. I am using TM4C129encpdt controller and interfaced with BQ2000. I2C is the protocol that is used to communicate with RTC BQ32000. I am able to read and write to the RTC register only once ,when i make the second write the read it back there is no change in the data and if i try to read the data from rtc continously after a single write i get default values i.e date register shows 00 month 00 year 2000 hrs 00 min 00 sec 00. Please help me on this how to read and write to the rtc repeatedly.

 i am placing the code below

Thanks in advance

santosh prasad s

#include <stdbool.h>
#include <stdint.h>
#include "inc/hw_i2c.h"
#include "inc/hw_ints.h"
#include "inc/hw_memmap.h"
#include "inc/hw_types.h"
#include "driverlib/gpio.h"
#include "driverlib/i2c.h"
#include "driverlib/rom.h"
#include "driverlib/interrupt.h"
#include "driverlib/pin_map.h"
#include "driverlib/sysctl.h"
#include "driverlib/uart.h"
#include "utils/uartstdio.h"
#include <stdint.h>
//#include "inc/tm4c129xnczad.h"



#define RTC_SLAVE_ADDR ( 0xD0 >> 1)

#define SEC_REG 0x00
#define MIN_REG 0x01
#define HOUR_REG 0x02
#define DAY_REG 0x03 //MON, TUE, WED,..
#define DATE_REG 0x04
#define MONTH_REG 0x05
#define YEAR_REG 0x06


uint8_t GetRTC( uint8_t nReg);
bool SetRTCRegister( uint8_t nReg, uint8_t nVal);
void RTCTest(void);

void RTCTest()
{

uint8_t hr,min,date,month,year,sec;
sec = GetRTC(0x00);
min = GetRTC(0x01);
hr = GetRTC(0x02);
date = GetRTC(0x04);
month = GetRTC(0x05);
year = GetRTC(0x06);
UARTprintf("**Date= %02x-%02x-20%02x*** Hour:Min:Sec = %x:%x:%x**",date,month,year,hr,min,sec);

}

bool SetRTCRegister(uint8_t nReg,uint8_t nVal)
{

I2CMasterDataPut(I2C0_BASE,nReg);
I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_START);//I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_SEND);
while(I2CMasterBusy(I2C0_BASE)){}
I2CMasterDataPut(I2C0_BASE,nVal);
I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_FINISH);//I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_SEND);
return true;
}
uint8_t GetRTC(uint8_t nReg)
{
uint8_t nVal;
nVal = I2CMasterDataGet(I2C0_BASE);
I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_RECEIVE);
while(I2CMasterBusy(I2C0_BASE)){}
switch(nReg)
{
case MIN_REG:
nVal &= 0x7F;
break;
case HOUR_REG:
nVal &= 0x3F;
break;
case DATE_REG:
nVal &= 0x3F;
break;
case MONTH_REG:
nVal &= 0x1F;
break;
case YEAR_REG:
case SEC_REG:
nVal &= 0xFF;
break;
default:
UARTprintf("Wrong RTC register selected\n");
}
return nVal;
}

void InitConsole(void)
{
SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOA); // UART0 POARTA
GPIOPinConfigure(GPIO_PA0_U0RX);
GPIOPinConfigure(GPIO_PA1_U0TX)
SysCtlPeripheralEnable(SYSCTL_PERIPH_UART0); //Enabling the UART
UARTClockSourceSet(UART0_BASE, UART_CLOCK_PIOSC); //Using !6mhz internal clock sourc
GPIOPinTypeUART(GPIO_PORTA_BASE, GPIO_PIN_0 | GPIO_PIN_1);
UARTStdioConfig(0, 115200, 16000000); //Initialising the UART
}

int main(void)
{

SysCtlClockSet(SYSCTL_SYSDIV_1 | SYSCTL_USE_OSC | SYSCTL_OSC_MAIN |
SYSCTL_XTAL_16MHZ);
SysCtlPeripheralEnable(SYSCTL_PERIPH_I2C0);

SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOB);

GPIOPinConfigure(GPIO_PB2_I2C0SCL);
GPIOPinConfigure(GPIO_PB3_I2C0SDA);

GPIOPinTypeI2CSCL(GPIO_PORTB_BASE, GPIO_PIN_2);
GPIOPinTypeI2C(GPIO_PORTB_BASE, GPIO_PIN_3);

I2CMasterEnable(I2C0_BASE);
I2CMasterInitExpClk(I2C0_BASE,160000000,true);
InitConsole();

SysCtlDelay(50000);
SysCtlDelay(50000);
SysCtlDelay(50000);

I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,false);

SetRTCRegister(0x00,0x00);
SetRTCRegister(0x01,0x02);
SetRTCRegister(0x02,0x10);
SetRTCRegister(0x04,0x11);
SetRTCRegister(0x05,0x06);
SetRTCRegister(0x06,0x12);
I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,true);
RTCTest();
while(1)
{

}
}

 

  • Hello Santosh,

    1. The TM4C129 does not use SysCtlClockSet API but SysCtlFreqSet API for configuring the system clock. The return value of this function is the System Clock Frequency

    2. The I2CMasterInitExpClk API's 2 parameter is configured as 160MHz. The maximum system frequency for TM4C129 is 120MHz and since you plan to use the MOSC clock then it would be 16MHz. Please be aware that DK/EK for TM4C129 boards have a 25MHz crystal and not a 16MHz crystal

    3, I2C Transactions for devices in general use a Repeated Start and not Stop for read. In this case it does not seem that in the GetRTC function. You need to use I2C_MASTER_CMD_BURST_SEND_START to first send the nReg in write mode, then use I2C_MASTER_CMD_SINGLE_RECEIVE to get the data in read mode. Also the data should be read after the I2CMasterBusy Flag gets cleared

    Regards

    Amit

  • Hello Amit,

                   Thanks for information you gave. After making the changes you mentioned i was able to achieve it to some extent. I was able to read the rtc data continuously (ie it did not show the default values).

    1) But once i do a power cycle i am not able to write to the rtc again (battery is not connected right now it is running only on mains)

    2) after this not even the continuously read is not working.

    3) am i reading or writing wrongly?

    Thanks & Regards

    Santosh Prasad S

  • Hello Amit,

                           I feel i am not writing as  well not reading properly from BQ32000.

    1) Battery not being connected will bq32000 not function properly even though the code may be write ?

  • Hello Santosh,

    It very well could be. But then how did it work the first time around when there was no battery? Do check the I2C transaction on a scope or a LA to see there is no NACK happeining on I2C. Also try to power cycle the BQ32000 device as well.

    Regards

    Amit

  • Hello Amit,

                    ok i will try talking to my hardware team about this and find out..But when it is continuously running on mains rtc timer should keep running right.

    I have made some changes in the code i will post for you to have a look. now what is happening is i am able to write and read continuously but only some registers are getting update. especially date month does change.

    And 1 more clarification i require when we write to the register it gets updated and the rtc timer starts running . so wen i read bcak the register the seconds and minutes registers should have changed by itself if timer is running.

    This response i am not able to see in the code i have written now.

    #include <stdbool.h>
    #include <stdint.h>
    #include "inc/hw_i2c.h"
    #include "inc/hw_ints.h"
    #include "inc/hw_memmap.h"
    #include "inc/hw_types.h"
    #include "driverlib/gpio.h"
    #include "driverlib/i2c.h"
    #include "driverlib/rom.h"
    #include "driverlib/interrupt.h"
    #include "driverlib/pin_map.h"
    #include "driverlib/sysctl.h"
    #include "driverlib/uart.h"
    #include "utils/uartstdio.h"
    #include <stdint.h>


    #define SEC_REG 0x00
    #define MIN_REG 0x01
    #define HOUR_REG 0x02
    #define DAY_REG 0x03 //MON, TUE, WED,..
    #define DATE_REG 0x04
    #define MONTH_REG 0x05
    #define YEAR_REG 0x06

    void I2C_Init();
    bool SetRTCRegister(uint8_t nReg,uint8_t nVal);
    uint8_t GetRTCRegister(uint8_t nReg);
    void DisplayCurrentRTC();
    void RTCInit();
    void RTC_2_WRITE();


    uint32_t RTC_FLAG = 0;
    uint32_t i = 0;

    #define RTC_SLAVE_ADDR ( 0xD0 >> 1) //Slave address specific to Bq 32000 (Fixed)

    void RTCPeripheralTest(void *ptr)
    {
    uint8_t hr,min,sec;
    uint8_t date,month,year;

    hr = GetRTCRegister(HOUR_REG);

    min = GetRTCRegister(MIN_REG);

    sec = GetRTCRegister(SEC_REG);

    date = GetRTCRegister(DATE_REG);

    month = GetRTCRegister(MONTH_REG);

    year = GetRTCRegister(YEAR_REG);

    UARTprintf("******Date = %02x-%02x-20%02x******Hour:Min:Sec = %x:%x:%x********\n",date,month,year,hr,min,sec);
    }

    void DisplayCurrentRTC()
    {
    uint8_t hr,min,sec;
    uint8_t date,month,year;

    hr=GetRTCRegister(HOUR_REG);

    min=GetRTCRegister(MIN_REG);

    sec=GetRTCRegister(SEC_REG);

    date=GetRTCRegister(DATE_REG);

    month=GetRTCRegister(MONTH_REG);

    year=GetRTCRegister(YEAR_REG);

    UARTprintf("**Date = %02x-%02x-20%0x***Hour:Min:Sec=%x:%x:%x**\n",date,month,year,hr,min,sec);
    }

    void I2C_Init()
    {
    SysCtlPeripheralEnable(SYSCTL_PERIPH_I2C0);

    SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOB);

    GPIOPinConfigure(GPIO_PB2_I2C0SCL);
    GPIOPinConfigure(GPIO_PB3_I2C0SDA);

    GPIOPinTypeI2CSCL(GPIO_PORTB_BASE, GPIO_PIN_2);
    GPIOPinTypeI2C(GPIO_PORTB_BASE, GPIO_PIN_3);


    I2CMasterEnable(I2C0_BASE);
    I2CMasterInitExpClk(I2C0_BASE,16000000,true);
    }
    bool SetRTCRegister(uint8_t nReg,uint8_t nVal)
    {
    //first set the RTC device address
    I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,false);
    //Write the RTC sub address.
    I2CMasterDataPut(I2C0_BASE,nReg);
    //Continue transfer..
    I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_START);
    //Wait until current byte has been transferred.
    while(I2CMasterBusy(I2C0_BASE)){}
    //Write the next byte to the controller
    I2CMasterDataPut(I2C0_BASE,nVal);
    //End the transfer
    I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_FINISH);
    //Give some delay--
    SysCtlDelay(50000);

    return true;
    }
    uint8_t GetRTCRegister(uint8_t nReg)
    {
    uint8_t nVal;
    //write the RTC device address first
    I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,false);
    //write the sub address/register to be read from
    I2CMasterDataPut(I2C0_BASE,nReg);
    //perform a single send, write the register address only
    I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_SEND);
    //wait until the current byte has been transferred
    while(I2CMasterBusy(I2C0_BASE)){}
    //Put the master in receive mode now
    I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,true);
    //start the receive
    I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_RECEIVE);
    //wait until the current byte has been read
    while(I2CMasterBusy(I2C0_BASE)){}
    //read the received character
    nVal = I2CMasterDataGet(I2C0_BASE);

    switch(nReg)
    {
    case MIN_REG:
    nVal &= 0x7F;
    break;

    case HOUR_REG:
    nVal &= 0x3F;
    break;

    case DATE_REG:
    nVal &= 0x3F;
    break;

    case MONTH_REG:
    nVal &= 0x1F;
    break;

    case YEAR_REG:
    case SEC_REG:
    nVal &= 0xFF;
    break;

    default:
    UARTprintf("Wrong RTC register selected");
    }

    return nVal;
    }
    void RTCInit()
    {
    I2C_Init();

    SetRTCRegister(SEC_REG,0x00);
    SetRTCRegister(MIN_REG,0x02);
    SetRTCRegister(HOUR_REG,0x10); //18

    SetRTCRegister(DATE_REG,0x11);
    SetRTCRegister(MONTH_REG,0x06);
    SetRTCRegister(YEAR_REG,0x12);

    }
    void InitConsole(void)
    {

    SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOA); // UART0 POARTA

    GPIOPinConfigure(GPIO_PA0_U0RX);
    GPIOPinConfigure(GPIO_PA1_U0TX);

    SysCtlPeripheralEnable(SYSCTL_PERIPH_UART0);


    UARTClockSourceSet(UART0_BASE, UART_CLOCK_PIOSC); //Using!6mhz internal clock source


    GPIOPinTypeUART(GPIO_PORTA_BASE, GPIO_PIN_0 | GPIO_PIN_1);

    UARTStdioConfig(0,115200,16000000);


    }
    void RTC_2_WRITE()
    {
    I2C_Init();

    SetRTCRegister(SEC_REG,0x00);
    SetRTCRegister(MIN_REG,0x18);
    SetRTCRegister(HOUR_REG,0x22); //18

    SetRTCRegister(DATE_REG,0x30);
    SetRTCRegister(MONTH_REG,0x14);
    SetRTCRegister(YEAR_REG,0x15);
    }
    int main(void)
    {
    SysCtlClockSet(SYSCTL_SYSDIV_1 | SYSCTL_USE_OSC | SYSCTL_OSC_MAIN |
    SYSCTL_XTAL_16MHZ);
    RTCInit();
    ROM_IntMasterEnable();
    InitConsole();
    // DisplayCurrentRTC();
    while(1)
    {
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    if(RTC_FLAG == 0)
    {
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    RTC_2_WRITE();
    RTC_FLAG = 1;
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    }
    if(RTC_FLAG == 1)
    {
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    DisplayCurrentRTC();
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    RTC_FLAG = 2;
    }
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    SysCtlDelay(50000);
    }
    }

  • Vendor rep has clearly gone, "above/beyond" the tech support reasonably expected! 

    You are asking for "hard core/specific" application assistance for another vendor's product.   To my (and my group's) mind - you here are bordering upon, "vendor abuse."

    If many here requested in this manner the "true purpose" of this forum would be severely degraded.

    Like you - I'm a user/specifier - but I try my best to confine my issues to "real, vendor-based" issues - not the detailed/ongoing debug of foreign (non-vendor MCU) devices...

    Many here do care and value this (best in its class) forum - limiting requests to real, vendor MCU issues should be a requirement!

  • Hello cb1_mobile,

                                         Even we do care and value this forum... I would like to apologize if u feel the question posted by us is not related to MCU or any ic manufactured by TI. As per the ques posted it is purely related to tm4c129encpdt and bq32000 which both are products of TI. We posted the question as we are facing problem and stuck in the process of using TI's product in our product. We are seeking for complete solution we are just here to verify whether are we using your product properly to get benefited.  We once again apologize if u feel it was not relevant.

  • Hello Santosh

    In the Get function you have, the issue is that you are still doing a single transmit operation after sending the address for the register to be read. Please read in my initial reply-post.

    I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_SEND);

    has to be

    I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_START);

    Regards

    Amit

  • Hi Amit,

                  I did change that and it is 90% working and one last problem i am facing i.e when i am reading data continuously some register values gets changed when read for exam if i have read 20 times out of 20 around 4 to 5 reads either the date he or year gets changed. problem with rtc or with my read ?

    Here is the code for you,

    #include <stdbool.h>
    #include <stdint.h>
    #include "inc/hw_i2c.h"
    #include "inc/hw_ints.h"
    #include "inc/hw_memmap.h"
    #include "inc/hw_types.h"
    #include "driverlib/gpio.h"
    #include "driverlib/i2c.h"
    #include "driverlib/rom.h"
    #include "driverlib/interrupt.h"
    #include "driverlib/pin_map.h"
    #include "driverlib/sysctl.h"
    #include "driverlib/uart.h"
    #include "utils/uartstdio.h"
    #include <stdint.h>
    //#include "inc/tm4c129xnczad.h"

    #define SEC_REG 0x00
    #define MIN_REG 0x01
    #define HOUR_REG 0x02
    #define DAY_REG 0x03 //MON, TUE, WED,..
    #define DATE_REG 0x04
    #define MONTH_REG 0x05
    #define YEAR_REG 0x06

    void I2C_Init();
    bool SetRTCRegister(uint8_t nReg,uint8_t nVal);
    uint8_t GetRTCRegister(uint8_t nReg);
    void DisplayCurrentRTC();
    void RTCInit();
    void RTC_2_WRITE();
    void delay(int num);


    uint32_t RTC_FLAG = 0,loop,loop1;
    uint32_t i = 0;
    uint8_t hr1 = 0,min1 = 0,sec1 = 0,date1 = 0,month1 = 0,year1 = 0;

    #define RTC_SLAVE_ADDR ( 0xD0 >> 1) //Slave address specific to Bq 32000 (Fixed)

    void delay(int num)
    {
    for(loop = 0;loop < num;loop++)
    {
    for(loop1 = 0;loop1 < 200000;loop1++);
    }
    }
    void RTCPeripheralTest(void *ptr)
    {
    uint8_t hr,min,sec;
    uint8_t date,month,year;

    hr = GetRTCRegister(HOUR_REG);

    min = GetRTCRegister(MIN_REG);

    sec = GetRTCRegister(SEC_REG);

    date = GetRTCRegister(DATE_REG);

    month = GetRTCRegister(MONTH_REG);

    year = GetRTCRegister(YEAR_REG);

    UARTprintf("******Date = %02x-%02x-20%02x******Hour:Min:Sec = %x:%x:%x********\n",date,month,year,hr,min,sec);
    }

    void DisplayCurrentRTC()
    {
    uint8_t hr,min,sec;
    uint8_t date,month,year;
    delay(500);
    sec = GetRTCRegister(SEC_REG);
    delay(500);
    min = GetRTCRegister(MIN_REG);
    delay(500);
    hr = GetRTCRegister(HOUR_REG);
    delay(500);
    date = GetRTCRegister(DATE_REG);
    delay(500);
    month = GetRTCRegister(MONTH_REG);
    delay(500);
    year = GetRTCRegister(YEAR_REG);
    delay(500);
    // UARTprintf("******Date = %02x-%02x-20%02x******Hour:Min:Sec = %x:%x:%x********\n",date,month,year,hr,min,sec);
    UARTprintf("******Date = %02x-%02x-20%02x******Hour:Min:Sec = %02x:%02x:%02x********\n",date,month,year,hr,min,sec);
    delay(500);
    }

    void I2C_Init()
    {
    SysCtlPeripheralEnable(SYSCTL_PERIPH_I2C0);

    SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOB);

    GPIOPinConfigure(GPIO_PB2_I2C0SCL);
    GPIOPinConfigure(GPIO_PB3_I2C0SDA);

    GPIOPinTypeI2CSCL(GPIO_PORTB_BASE, GPIO_PIN_2);
    GPIOPinTypeI2C(GPIO_PORTB_BASE, GPIO_PIN_3);


    I2CMasterEnable(I2C0_BASE);
    I2CMasterInitExpClk(I2C0_BASE,16000000,true);
    }
    bool SetRTCRegister(uint8_t nReg,uint8_t nVal)
    {
    //first set the RTC device address
    I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,false);
    //Write the RTC sub address.
    I2CMasterDataPut(I2C0_BASE,nReg);
    //Continue transfer..
    I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_START);
    //Wait until current byte has been transferred.
    while(I2CMasterBusy(I2C0_BASE)){}
    //Write the next byte to the controller
    I2CMasterDataPut(I2C0_BASE,nVal);
    //End the transfer
    I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_FINISH);
    //Give some delay--
    SysCtlDelay(50000);

    return true;
    }
    uint8_t GetRTCRegister(uint8_t nReg)
    {
    uint8_t nVal;
    //write the RTC device address first
    I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,false);
    //write the sub address/register to be read from
    I2CMasterDataPut(I2C0_BASE,nReg);
    //perform a single send, write the register address only
    I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_START);//I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_SEND);
    //wait until the current byte has been transferred
    while(I2CMasterBusy(I2C0_BASE)){}
    //Put the master in receive mode now
    I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,true);
    //start the receive
    I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_RECEIVE);
    //wait until the current byte has been read
    while(I2CMasterBusy(I2C0_BASE)){}
    //read the received character
    nVal = I2CMasterDataGet(I2C0_BASE);

    // I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_RECEIVE_FINISH);
    switch(nReg)
    {
    case MIN_REG:
    nVal &= 0x7F;
    break;

    case HOUR_REG:
    nVal &= 0x3F;
    break;

    case DATE_REG:
    nVal &= 0x3F;
    break;

    case MONTH_REG:
    nVal &= 0x1F;
    break;

    case YEAR_REG:
    case SEC_REG:
    nVal &= 0x7F; //nVal &= 0x7F; as per pic example
    break;

    default:
    UARTprintf("Wrong RTC register selected");
    }
    return nVal;
    }
    void RTCInit()
    {
    SetRTCRegister(SEC_REG,0x00); // 0x02
    SetRTCRegister(MIN_REG,0x02); // 0x10
    SetRTCRegister(HOUR_REG,0x18); //18
    // 0x11
    SetRTCRegister(DATE_REG,0x11); // 0x06
    SetRTCRegister(MONTH_REG,0x06); // 0x12
    SetRTCRegister(YEAR_REG,0x12);
    }
    void InitConsole(void)
    {

    SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOA); // UART0 POARTA

    GPIOPinConfigure(GPIO_PA0_U0RX);
    GPIOPinConfigure(GPIO_PA1_U0TX);

    SysCtlPeripheralEnable(SYSCTL_PERIPH_UART0);

    //Enabling the UART


    UARTClockSourceSet(UART0_BASE, UART_CLOCK_PIOSC); //Using!6mhz internal clock source


    GPIOPinTypeUART(GPIO_PORTA_BASE, GPIO_PIN_0 | GPIO_PIN_1);

    UARTStdioConfig(0,115200,16000000);


    }
    void RTC_2_WRITE()
    {
    I2C_Init();
    SetRTCRegister(SEC_REG,0x00);
    SetRTCRegister(MIN_REG,0x18);
    SetRTCRegister(HOUR_REG,0x22); //18

    SetRTCRegister(DATE_REG,0x28);
    SetRTCRegister(MONTH_REG,0x05);
    SetRTCRegister(YEAR_REG,0x14); //0x15 worked
    }
    int main(void)
    {
    SysCtlClockSet(SYSCTL_SYSDIV_1 | SYSCTL_USE_OSC | SYSCTL_OSC_MAIN |
    SYSCTL_XTAL_16MHZ);
    I2C_Init();
    RTCInit();
    ROM_IntMasterEnable();
    InitConsole();
    // DisplayCurrentRTC();
    while(1)
    {
    delay(500);
    delay(500);
    delay(500);
    RTC_FLAG++;
    if(RTC_FLAG > 1000000)
    {
    delay(500);
    delay(100);
    for(i = 0;i < 1000000;i++);
    delay(500);
    delay(500);
    sec1 = GetRTCRegister(0x00);
    delay(500);
    delay(500);
    min1 = GetRTCRegister(0x01);
    delay(500);
    delay(500);
    hr1 = GetRTCRegister(0x02);
    delay(500);
    delay(500);
    date1 = GetRTCRegister(0x04);
    delay(500);
    delay(500);
    month1 = GetRTCRegister(0x05);
    delay(500);
    delay(500);
    year1 = GetRTCRegister(0x06);
    delay(500);
    delay(500);
    UARTprintf("******Date = %02x-%02x-20%02x******Hour:Min:Sec = %02x:%02x:%02x********\n",date1,month1,year1,hr1,min1,sec1);
    for(i = 0;i < 1000000;i++);
    RTC_FLAG = 0;
    }
    delay(500);
    delay(500);
    delay(500);
    delay(500);
    }

    }

    Regards'

    Santosh Prasad S

  • Hello Santosh,

    90% of the time would mean that it is that the communication is working fine. There could be issue with the Pull Up strength on the board or a noise that causes data to be corrupted. I would advise to hook up a scope and check for I2C bus behavior.

    Regards

    Amit

  • Hi Amit,

                  That is the last option left for me. i am posting snapshot where you can see how is the response .

            Data is read every 1 min and i see changes only in the hr register it is showing some times as 11 i dont know for what reason were rest of the registers stay intact

  • Hello Santosh,

    It would be good to capture the scope data when such a reading happens. I haven't got any information on the Pull Strength.

    Also do try running the I2C at 100KHz instead of 400KHz.

    Regards

    Amit

  • Hello Amit,

    The Pull up strength is 10k to vcc and i will try running i2c at 100khz and check once...

  • Hello Amit,

    The Pull up strength is 10k to vcc and i will try running i2c at 100khz and check once...

  • Hello Santosh

    The application diagram in the BQ32000 suggests using 4.7K as Pull Up. This is generally based on the Board Cap as minimal and highest operating baud rate supported by the device.

    Regards

    Amit

  • Hi Santosh,

    Sorry to say, but your GetRTCRegister() function is wrong - you completely ignore the data sheet which states that the data in (many) registers is in BCD format. Let me explain, on register 1, supposing the read from i2c is correct and saved in nVal variable, then for display minutes you need two characters (like for instance "34" printed on screen which means 0x33, 0x34) - which can be obtained from two expressions like this:
    ((nVal & 0x70)>>4)+0x30; // this gives you tens-of-minutes ('3')
    (nVal & 0x0F) + 0x30;  // this gives you units-of-minutes ('4')
    Apply this concept to the rest of data - takes into account how are described in the data sheet.
    Petrei
  • The application says the external pull up has to be greater than the internal pull up which is 4.7k internal and we have pulled it up by 10k  externally.

    Amit oi tried running at 100khz also but no improvement.

  • Hello Petrei,

    I will try applying what ever you suggested and see.

    Regards

    Santosh Prasad S

  • Hello Petrei,

                             i tried doing as you suggested and i ran the test for half and hour reading every min.... yet i was able to see the hr register showing 11 in few reads other registers remain intact.

  • Hi,

    The hour register must be masked with 0x03 - only two bits available - read carefully the data sheet - you should modify your function for all items. Do not use "printf" to display since: a)you get faster the characters and b)data is not anymore straight binary - use a string to insert these characters into and then send that string to UART.

    static uint8_t timeinfo[9]; // to have a string in format "hh:mm:ss" 

    Petrei

  • Hi,

            !0_HOUR and 1_HOUR part is available to us know. which D5 to Do bit of Hour register(0x02 address) then the masking value becomes 0x3F. and i will try changing the uart and get back to you

    Regards

    Santosh Prasad s 

  • Hi,

    Take care with BCD format - you must process each nibble separately - the mask should be 0x30 for upper nibble (tens hours) and 0x0F for lower nibble - 

    Petrei

  • Hi Petrei,

                         That is how i did it yet 11 appeared and i did not understand in the example yu showed why were you adding 0x30?

    Regards

    Santosh 

  • Hi,

    Remember my example: ((nVal & 0x70)>>4)+0x30;

    for hours instead 0x70 should be 0x30 to select only bits 4 and 5. BCD format accept only 0..9 digits! So a maximum value in a byte is 99, not usual 0xFF.

    Petrei

  • Hi ,

          I have done the same way as you have mentioned but i was not able to achieve it. that +0x30 should be added to every comparison?

    santosh

  • Hi,

    Yes, to get the ASCII equivalent without using printf - it easier and faster. Once the character is obtained, just insert it into a string and get the date/time. Otherwise you need to call printf twice, for each nibble separately, cannot be done in  a single pass (nor try to convert to binary and then back to two ASCII characters).

    Petrei

  • Hello Petrei and Amit,

                                           I found out what is causing that problem.It is the reading of the registers adjacent to hour register. when read the value present in the adjacent register is appearing in the hour register.I am not sure whether what ever delay i have given is not sufficient or more than sufficient which is creating problem for this..can you please help me in solving this.

    Regards

    Santosh

  • Hi, 

    Can you define which is the "adjacent" register to hours register? (name as designated in data sheet).

    Petrei

  • Hi,

    say i am reading DATE register address 0x04 after reading hour register The value that date register some times shows up when read hour register. What ever register you read say year month(0x05) minutes(0x01) etc reading after hour register is showing those register values in hour register when read

    Santosh

  • Hi, 

    Can you post the actual code? (but in a separate file). Also, did you tried to use another chip to see if it is hardware problem ( RTC chip) or software?

    Petrei

  • Hi,

          Are you sure what problem i am facing is due to hardware ? ok i am posting you the code

    santosh

    
    #include <stdbool.h>
    #include <stdint.h>
    #include "inc/hw_i2c.h"
    #include "inc/hw_ints.h"
    #include "inc/hw_memmap.h"
    #include "inc/hw_types.h"
    #include "driverlib/gpio.h"
    #include "driverlib/i2c.h"
    #include "driverlib/rom.h"
    #include "driverlib/interrupt.h"
    #include "driverlib/pin_map.h"
    #include "driverlib/sysctl.h"
    #include "driverlib/uart.h"
    #include "utils/uartstdio.h"
    #include <stdint.h>
    //#include "inc/tm4c129xnczad.h"
    
    #define SEC_REG    0x00
    #define MIN_REG    0x01
    #define HOUR_REG   0x02
    #define DAY_REG    0x03 //MON, TUE, WED,..
    #define DATE_REG   0x04
    #define MONTH_REG  0x05
    #define YEAR_REG   0x06
    
    void I2C_Init();
    bool SetRTCRegister(uint8_t nReg,uint8_t nVal);
    uint8_t GetRTCRegister(uint8_t nReg);
    void DisplayCurrentRTC();
    void RTCInit();
    void RTC_2_WRITE();
    void delay(int num);
    void DelayMs();
    
    
    uint32_t RTC_FLAG = 0,RTC_FLAG1 = 0,loop,loop1;
    uint32_t i = 0;
    uint8_t hr1 = 0,min1 = 0,sec1 = 0,date1 = 0,month1 = 0,year1 = 0;
    
    #define RTC_SLAVE_ADDR		( 0xD0 >> 1)	//Slave address specific to Bq 32000 (Fixed)
    
    void delay(int num)
    {
    	for(loop = 0;loop < num;loop++)
    	{
    		for(loop1 = 0;loop1 < 200000;loop1++);
    	}
    }
    
    
    void DisplayCurrentRTC()
    {
    	uint8_t hr,min,sec;
    	uint8_t date,month,year;
    
    	sec = GetRTCRegister(SEC_REG);
    
    	min = GetRTCRegister(MIN_REG);
    
    	hr = GetRTCRegister(HOUR_REG);
    
    	date = GetRTCRegister(DATE_REG);
    
    	month = GetRTCRegister(MONTH_REG);
    
    	year = GetRTCRegister(YEAR_REG);
    
    //	UARTprintf("******Date = %02x-%02x-20%02x******Hour:Min:Sec = %x:%x:%x********\n",date,month,year,hr,min,sec);
    	UARTprintf("******Date = %02x-%02x-20%02x******Hour:Min:Sec = %02x:%02x:%02x********\n",date,month,year,hr,min,sec);
    }
    
    void I2C_Init()
    {
    	SysCtlPeripheralEnable(SYSCTL_PERIPH_I2C0);
    
    	SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOB);
    
    	GPIOPinConfigure(GPIO_PB2_I2C0SCL);
    	GPIOPinConfigure(GPIO_PB3_I2C0SDA);
    
    	GPIOPinTypeI2CSCL(GPIO_PORTB_BASE, GPIO_PIN_2);
    	GPIOPinTypeI2C(GPIO_PORTB_BASE, GPIO_PIN_3);
    
    
    	I2CMasterEnable(I2C0_BASE);
    	I2CMasterInitExpClk(I2C0_BASE,16000000,true);
    }
    bool SetRTCRegister(uint8_t nReg,uint8_t nVal)
    {
    	//first set the RTC device address
    	I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,false);
    	//Write the RTC sub address.
    	I2CMasterDataPut(I2C0_BASE,nReg);
    	//Continue transfer..
    	I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_START);
    	//Wait until current byte has been transferred.
    	while(I2CMasterBusy(I2C0_BASE)){}
    	//Write the next byte to the controller
    	I2CMasterDataPut(I2C0_BASE,nVal);
    	//End the transfer
    	I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_FINISH);
    	//Give some delay--
    	SysCtlDelay(50000);
    
    	return true;
    }
    uint8_t GetRTCRegister(uint8_t nReg)
    {
    	uint8_t nVal = 0;
    	uint8_t nVal1 = 0;
    	uint8_t nVal2 = 0;
    	//write the RTC device address first
    	I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,false);
    	//write the sub address/register to be read from
    	I2CMasterDataPut(I2C0_BASE,nReg);
    	//perform a single send, write the register address only
    	I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_START);//I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_SEND);
    	//wait until the current byte has been transferred
    	while(I2CMasterBusy(I2C0_BASE)){}
    	//Put the master in receive mode now
    	I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,true);
    	//start the receive
    	I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_RECEIVE);
    	//wait until the current byte has been read
    	while(I2CMasterBusy(I2C0_BASE)){}
    	//read the received character
    	nVal = I2CMasterDataGet(I2C0_BASE);
    
    	I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_RECEIVE_FINISH);
    
    	switch(nReg)
    	{
    	case MIN_REG:
    		nVal = ((nVal & 0x70)>>4)| 0x30 ;
    		nVal = (nVal & 0x0F)|0x30; // this gives you tens-of-minutes ('3')
    		nVal2 = nVal | nVal1;//		nVal  = nVal|nVal1;
    		//nVal &= 0x7F;
    		break;
    
    	case HOUR_REG:
    		nVal = ((nVal & 0x30)>>4)| 0x30 ;
    		nVal1 = (nVal & 0x0F)|0x30;                    //nVal &= 0x3F;
    		nVal2 = nVal | nVal1;//		nVal  = nVal|nVal1;
    		break;
    
    	case DATE_REG:
    		nVal = ((nVal & 0x30)>>4)| 0x30 ;
    		nVal1 = (nVal & 0x0F)|0x30;//nVal &= 0x3F;
            nVal2 = nVal | nVal1;  //		nVal  = nVal|nVal1;
    		break;
    
    	case MONTH_REG:
    		nVal = ((nVal & 0x10)>>4)| 0x30 ;
    	    nVal1 = (nVal & 0x0F)|0x30;//nVal &= 0x1F;
    	    nVal2 = nVal | nVal1;//	    nVal  = nVal|nVal1;
    		break;
    
    	case YEAR_REG:
    		break;
    	case SEC_REG:
    		nVal = ((nVal & 0x70)>>4)| 0x30 ;
    	    nVal1 = (nVal & 0x0F)|0x30;//nVal &= 0x7F;   //nVal &= 0x7F; as per pic example
    	    nVal2 = nVal | nVal1;//	    nVal  = nVal|nVal1;
    		break;
    
    	default:
    		UARTprintf("Wrong RTC register selected");
    	}
    	return nVal2;
    }
    
    
    }
    
    
    void RTCInit()
    {
    	SetRTCRegister(SEC_REG,0x20);		//  0x02
        SetRTCRegister(MIN_REG,0x24);		//  0x10
    	SetRTCRegister(HOUR_REG,0x13);	    //18
    			                            //  0x11
    	SetRTCRegister(DATE_REG,0x31);		//  0x06
    	SetRTCRegister(MONTH_REG,0x05);		//   0x12
    	SetRTCRegister(YEAR_REG,0x14);
    }
    
    
    int main(void)
    {
    	SysCtlClockSet(SYSCTL_SYSDIV_1 | SYSCTL_USE_OSC | SYSCTL_OSC_MAIN |
    	                   SYSCTL_XTAL_16MHZ);
    	I2C_Init();
    //	RTCInit();
    	ROM_IntMasterEnable();
    	InitConsole();
    //	DisplayCurrentRTC();
        while(1)
        {
    
        	delay(500);
        	delay(500);
        	delay(500);
        	RTC_FLAG++;
        	if(RTC_FLAG > 2000000)
        	{
        		delay(500);
        		delay(100);
        		for(i = 0;i < 2000000;i++);
        		if(RTC_FLAG1 > 2)
        		{
    
        			delay(500);
        		  	delay(100);
        			sec1 =  GetRTCRegister(0x00);
        			delay(500);
        			delay(100);
        			min1 = GetRTCRegister(0x01);
        			delay(500);
        			delay(100);
        			hr1 = GetRTCRegister(0x02);
        		    delay(500);
        		    delay(100);
        			date1 = GetRTCRegister(0x04);
        		    delay(500);
        		    delay(100);
        			month1 = GetRTCRegister(0x05);
        		    delay(500);
        		    delay(100);
        			year1 = GetRTCRegister(0x06);
        		    delay(500);
        		    delay(100);
        			//    		UARTprintf("******Date = %02x-%02x-20%02x******Hour:Min:Sec = %02x:%02x:%02x********\n",date1,month1,year1,hr1,min1,sec1);
        			UARTprintf("******Date = %02x-%02x-20%02x******Hour:Min:Sec = %x:%x:%x********\n",date1,month1,year1,hr1,min1,sec1);
        			RTC_FLAG1 = 0;
        		}
        		for(i = 0;i < 2000000;i++);
        		RTC_FLAG = 0;
        		RTC_FLAG1++;
        	}
        	delay(500);
        	delay(500);
        	delay(500);
        	delay(500);
    
        }

  • Hi,

    After a quick read of your files, it is purely software error - seems you did not catched up my suggestions - I will come back later with a modified file.

    Petrei

  • hi petrei,

    Thanks for helping me ... i am really stuck with this from past 2 days it will be of great help if a solution comes out.

    And i replaced IC and checked the observation is still the same.

    Regards

    Santosh

  • Hi,

    I modified your RTCGet() function - see how is written and add the missing parts. Added two small arrays. Compile/modify to correspond with the new function. 

    One more advice: do not "learn" anything from PICs, at least not from 8-bits, some "weird" things could not work on Tiva (although I do recommend to read/learn from others).

    Petrei

    
    #include <stdbool.h>
    #include <stdint.h>
    #include "inc/hw_i2c.h"
    #include "inc/hw_ints.h"
    #include "inc/hw_memmap.h"
    #include "inc/hw_types.h"
    #include "driverlib/gpio.h"
    #include "driverlib/i2c.h"
    #include "driverlib/rom.h"
    #include "driverlib/interrupt.h"
    #include "driverlib/pin_map.h"
    #include "driverlib/sysctl.h"
    #include "driverlib/uart.h"
    #include "utils/uartstdio.h"
    #include <stdint.h>
    //#include "inc/tm4c129xnczad.h"
    
    #define SEC_REG    0x00
    #define MIN_REG    0x01
    #define HOUR_REG   0x02
    #define DAY_REG    0x03 //MON, TUE, WED,..
    #define DATE_REG   0x04
    #define MONTH_REG  0x05
    #define YEAR_REG   0x06
    
    void I2C_Init();
    bool SetRTCRegister(uint8_t nReg,uint8_t nVal);
    uint8_t GetRTCRegister(uint8_t nReg);
    void DisplayCurrentRTC();
    void RTCInit();
    void RTC_2_WRITE();
    void delay(int num);
    void DelayMs();
    
    
    uint32_t RTC_FLAG = 0,RTC_FLAG1 = 0,loop,loop1;
    uint32_t i = 0;
    uint8_t hr1 = 0,min1 = 0,sec1 = 0,date1 = 0,month1 = 0,year1 = 0;
    
    #define RTC_SLAVE_ADDR		( 0xD0 >> 1)	//Slave address specific to Bq 32000 (Fixed)
    
    void delay(int num)
    {
    	for(loop = 0;loop < num;loop++)
    	{
    		for(loop1 = 0;loop1 < 200000;loop1++);
    	}
    }
    
    
    void DisplayCurrentRTC()
    {
    	//uint8_t hr,min,sec;
    	//uint8_t date,month,year;
    
    	GetRTCRegister(SEC_REG);
      GetRTCRegister(MIN_REG);
      GetRTCRegister(HOUR_REG);
      GetRTCRegister(DATE_REG);
      GetRTCRegister(MONTH_REG);
      GetRTCRegister(YEAR_REG);
    
    //	
    	UARTprintf("%s\n",&timedate);
    }
    
    void I2C_Init()
    {
    	SysCtlPeripheralEnable(SYSCTL_PERIPH_I2C0);
    
    	SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOB);
    
    	GPIOPinConfigure(GPIO_PB2_I2C0SCL);
    	GPIOPinConfigure(GPIO_PB3_I2C0SDA);
    
    	GPIOPinTypeI2CSCL(GPIO_PORTB_BASE, GPIO_PIN_2);
    	GPIOPinTypeI2C(GPIO_PORTB_BASE, GPIO_PIN_3);
    
    
    	I2CMasterEnable(I2C0_BASE);
    	I2CMasterInitExpClk(I2C0_BASE,16000000,true);
    }
    bool SetRTCRegister(uint8_t nReg,uint8_t nVal)
    {
    	//first set the RTC device address
    	I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,false);
    	//Write the RTC sub address.
    	I2CMasterDataPut(I2C0_BASE,nReg);
    	//Continue transfer..
    	I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_START);
    	//Wait until current byte has been transferred.
    	while(I2CMasterBusy(I2C0_BASE)){}
    	//Write the next byte to the controller
    	I2CMasterDataPut(I2C0_BASE,nVal);
    	//End the transfer
    	I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_FINISH);
    	//Give some delay--
    	SysCtlDelay(50000);
    
    	return true;
    }
    //****************************************************
    static uint8_t timedate[]="yyyy:mm:dd - hh:mm:ss";
    const uint8_t ascii[] = "0123456789ABCD";
    //
    
    void GetRTCRegister(uint8_t nReg)
    {
    	uint8_t nVal = 0;
    	// uint8_t nVal1 = 0;
    	// uint8_t nVal2 = 0;
    	//write the RTC device address first
    	I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,false);
    	//write the sub address/register to be read from
    	I2CMasterDataPut(I2C0_BASE,nReg);
    	//perform a single send, write the register address only
    	I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_START);//I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_SEND);
    	//wait until the current byte has been transferred
    	while(I2CMasterBusy(I2C0_BASE)){}
    	//Put the master in receive mode now
    	I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,true);
    	//start the receive
    	I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_RECEIVE);
    	//wait until the current byte has been read
    	while(I2CMasterBusy(I2C0_BASE)){}
    	//read the received character
    	nVal = I2CMasterDataGet(I2C0_BASE);
    
    	I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_RECEIVE_FINISH);
    
    	switch(nReg)
    	{
    	case MIN_REG:
    		timedate[16] = ascii[(nVal & 0x70)>>4];
    		timedate[17] = ascii[nVal & 0x0F];
    		//
    		//
    		break;
    
    	case HOUR_REG:
    		timedate[13] = ascii[(nVal & 0x30)>>4];
    		timedate[14] = ascii[nVal & 0x0F];                    
    		//
    		break;
    
    	case DATE_REG:
    		//
    		break;
    
    	case MONTH_REG:
    		timedate[5] = ascii[(nVal & 0x10)>>4];
    	  timedate[6] = ascii[nVal & 0x0F];
    	  //
    		break;
    
    	case YEAR_REG:
    		//
    		break;
    		
    	case SEC_REG:
    		timedate[19] = ascii[(nVal & 0x70)>>4];
    	  timedate[20] = ascii[nVal & 0x0F];
    	  //
    		break;
    
    	default:
    		UARTprintf("Wrong RTC register selected");
    	}
    	return;
    }
    
    
    }
    
    

  • HI Pretei,

                       I am really thankful to you for the pain you have taken. Unfortunately my previous experience was on PIC and some of the things which worked on PIC does not work on Tiva even  i have observed this.

    will surely make those changes and will keep you informed.

    Thanks & Regards

    Santosh Prasad S

  • HI,

    one more clarification i require . so delay is not creating problem is it?

    santosh

  • santosh prasad s said:
    delay is not creating problem is it?

    We don't really know that my friend.

    That said - it is unlikely that your external IC (RTC in this instance) will "spoil" its values due to the insertion of any (read or write) delay.  Thus - to maximize your chances for success - add an order of magnitude (i.e.10 times) the specified (or normal/customary) delay - "just in case."  That delay may slow your data harvest from the RTC - but should not cause nor contribute to any error.   Later - once proper operation is achieved - you may systematically reduce all such delays - carefully monitoring for any error or hiccup.

    I'd challenge the statement (likely made in haste) that one can't learn from another MCU.  Indeed when the differences are large - when the architectures are opposing - then great care must be exercised.  However the "methods of attack" - program sequences - and depth of "set-up/config" often prove instructive & useful. 

  • Hi Petrei ,cd_mobile

    i found what what was the issue it was because of these two lines in the GetRTCfunction

    I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_START); and

    I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_RECEIVE_FINISH);

    i replaced I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_START) with  I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_SEND); and commented the Receive finsih . It is working fine now..i have ran the test almost for an hour and i dont see any changes in the reg.

    I am really thankful for the help you provided and probably ascii conversion part played a very huge role.

    Thanks & Regards

    Santosh Prasad S

  • Good for you Santosh.  Record must  show that Petrei deserves the credit - especially for identifying the BCD nature of your RTC.  BCD provided a great simplification when all we had was hardware - most displays and driver ICs did not know "how to react" when you fed them data beyond "9." 

    You gained much appreciation for the importance of focused, tech manual and code example reading - followed then by careful monitoring of the actual hardware to confirm (or oppose) your beliefs...

    Bon chance, mon ami... (and award a "green Verify" to Petrei - much deserved)

  • Hello All,

    The removal of receive finish would mean that only transmit bit was set in I2CMCS, but then how could the control loop go past the I2CMasterBusy. Santosh, it would be good if you can clarify the same with the code post!!!

    "i replaced I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_START) with  I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_SEND); and commented the Receive finsih"

    Though the code is working now, but still having a clarity at it would be of much interest

    Of course, agree with cb1, "Green Verify" for Petrei...

    Regards

    Amit

  • Hello Amit,

                       I am posting the code for you to check...What i feel is that earlier i was doing Burst start and doing a single receive and trying to finish it as burst finish. which was wrong. because i was not sending  the source address continuously it was a one time operation and i was calling GETRTCregister each time for reading seconds minutes hours etc. so it should be single command send and single command receive.The problem what i faced by placing command burst receive finish at the end is the that the master would have already received a stop from slave after single receive yet it use to be waiting again till this burst receive was over so this created delay where when i used to read hour register some time i used to get the register value which is adjacent to hour register. if i had done reading all the register inside a single function in one time then burst will be the right command along with burst receive continued command before giving burst receive finish at the end after reading all the registers.

    
    #include <stdbool.h>
    #include <stdint.h>
    #include "inc/hw_i2c.h"
    #include "inc/hw_ints.h"
    #include "inc/hw_memmap.h"
    #include "inc/hw_types.h"
    #include "driverlib/gpio.h"
    #include "driverlib/i2c.h"
    #include "driverlib/rom.h"
    #include "driverlib/interrupt.h"
    #include "driverlib/pin_map.h"
    #include "driverlib/sysctl.h"
    #include "driverlib/uart.h"
    #include "utils/uartstdio.h"
    #include <stdint.h>
    //#include "inc/tm4c129xnczad.h"
    
    #define SEC_REG    0x00
    #define MIN_REG    0x01
    #define HOUR_REG   0x02
    #define DAY_REG    0x03 //MON, TUE, WED,..
    #define DATE_REG   0x04
    #define MONTH_REG  0x05
    #define YEAR_REG   0x06
    
    void I2C_Init();
    bool SetRTCRegister(uint8_t nReg,uint8_t nVal);
    void GetRTCRegister(uint8_t nReg);
    void DisplayCurrentRTC();
    void RTCInit();
    void RTC_2_WRITE();
    void delay(int num);
    
    static uint8_t timedate[] = "20yy:mm:dd - hh:mm:ss";
    const uint8_t ascii[] = "0123456789ABCD";
    
    uint32_t RTC_FLAG = 0,RTC_FLAG1 = 0,loop,loop1;
    uint32_t i = 0;
    uint8_t hr1 = 0,min1 = 0,sec1 = 0,date1 = 0,month1 = 0,year1 = 0;
    
    #define RTC_SLAVE_ADDR		( 0xD0 >> 1)	//Slave address specific to Bq 32000 (Fixed)
    
    void delay(int num)
    {
    	for(loop = 0;loop < num;loop++)
    	{
    		for(loop1 = 0;loop1 < 200000;loop1++);
    	}
    }
    void DisplayCurrentRTC()
    {
    	GetRTCRegister(SEC_REG);
    	GetRTCRegister(MIN_REG);
    	GetRTCRegister(HOUR_REG);
    	GetRTCRegister(DATE_REG);
    	GetRTCRegister(MONTH_REG);
    	GetRTCRegister(YEAR_REG);
            UARTprintf("%s\n",&timedate);
    }
    void I2C_Init()
    {
    	SysCtlPeripheralEnable(SYSCTL_PERIPH_I2C0);
    
    	SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOB);
    
    	GPIOPinConfigure(GPIO_PB2_I2C0SCL);
    	GPIOPinConfigure(GPIO_PB3_I2C0SDA);
    
    	GPIOPinTypeI2CSCL(GPIO_PORTB_BASE, GPIO_PIN_2);
    	GPIOPinTypeI2C(GPIO_PORTB_BASE, GPIO_PIN_3);
    
    
    	I2CMasterEnable(I2C0_BASE);
    	I2CMasterInitExpClk(I2C0_BASE,16000000,true);
    }
    bool SetRTCRegister(uint8_t nReg,uint8_t nVal)
    {
    	//first set the RTC device address
    	I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,false);
    	//Write the RTC sub address.
    	I2CMasterDataPut(I2C0_BASE,nReg);
    	//Continue transfer..
    	I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_START);
    	//Wait until current byte has been transferred.
    	while(I2CMasterBusy(I2C0_BASE)){}
    	//Write the next byte to the controller
    	I2CMasterDataPut(I2C0_BASE,nVal);
    	//End the transfer
    	I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_BURST_SEND_FINISH);
    	//Give some delay--
    	SysCtlDelay(50000);
    
    	return true;
    }
    
    void GetRTCRegister(uint8_t nReg)
    {
    	uint8_t nVal = 0;
    	//write the RTC device address first
    	I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,false);
    	//write the sub address/register to be read from
    	I2CMasterDataPut(I2C0_BASE,nReg);
    	//perform a single send, write the register address only
            I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_SEND);
    	//wait until the current byte has been transferred
    	while(I2CMasterBusy(I2C0_BASE)){}
    	//Put the master in receive mode now
    	I2CMasterSlaveAddrSet(I2C0_BASE,RTC_SLAVE_ADDR,true);
    	//start the receive
    	I2CMasterControl(I2C0_BASE,I2C_MASTER_CMD_SINGLE_RECEIVE);
    	//wait until the current byte has been read
    	while(I2CMasterBusy(I2C0_BASE)){}
    	//read the received character
    	nVal = I2CMasterDataGet(I2C0_BASE);
    
    
    	switch(nReg)
    	{
    
    	case SEC_REG:
    		timedate[19] = ascii[(nVal & 0x70) >> 4];
    		timedate[20] = ascii[nVal & 0x0F];
    		break;
    
    	case MIN_REG:
    		timedate[16] = ascii[(nVal & 0x70) >> 4];
    		timedate[17] = ascii[nVal & 0x0F];
    		break;
    
    	case HOUR_REG:
    		timedate[13] = ascii[(nVal & 0x30) >> 4];
    		timedate[14] = ascii[nVal & 0x0F];
    		break;
    
    	case DATE_REG:
    		timedate[8] = ascii[(nVal & 0x30) >> 4];
    	    timedate[9] = ascii[nVal & 0x0F];
    		break;
    
    	case MONTH_REG:
    		timedate[5] = ascii[(nVal & 0x10) >> 4];
    		timedate[6] = ascii[nVal & 0x0F];
    		break;
    
    	case YEAR_REG:
    		timedate[2] = ascii[(nVal & 0xF0) >> 4];
    		timedate[3] = ascii[nVal & 0x0F];
    		break;
    
    	default:
    		UARTprintf("Wrong RTC register selected");
    	}
    	return ;
    }
    void RTCInit()
    {
    	SetRTCRegister(SEC_REG,0x10);		//  0x02
        SetRTCRegister(MIN_REG,0x45);		//  0x10
    	SetRTCRegister(HOUR_REG,0x09);	    //18
    			                            //  0x11
    	SetRTCRegister(DATE_REG,0x01);		//  0x06
    	SetRTCRegister(MONTH_REG,0x06);		//   0x12
    	SetRTCRegister(YEAR_REG,0x14);
    }
    void InitConsole(void)
    {
    
        SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOA);             // UART0 POARTA
    
        GPIOPinConfigure(GPIO_PA0_U0RX);
        GPIOPinConfigure(GPIO_PA1_U0TX);
    
        SysCtlPeripheralEnable(SYSCTL_PERIPH_UART0);
    
        UARTClockSourceSet(UART0_BASE, UART_CLOCK_PIOSC);			//Using!6mhz internal clock source
    
    
        GPIOPinTypeUART(GPIO_PORTA_BASE, GPIO_PIN_0 | GPIO_PIN_1);
    
        UARTStdioConfig(0,115200,16000000);
    
    
    }
    int main(void)
    {
    	SysCtlClockSet(SYSCTL_SYSDIV_1 | SYSCTL_USE_OSC | SYSCTL_OSC_MAIN |
    	                   SYSCTL_XTAL_16MHZ);
    	I2C_Init();
    //	RTCInit();
    	ROM_IntMasterEnable();
    	InitConsole();
    //	DisplayCurrentRTC();
        while(1)
        {
        	delay(500);
        	delay(500);
        	delay(500);
        	RTC_FLAG++;
        	if(RTC_FLAG > 2000000)
        	{
        		for(i = 0;i < 2000000;i++);
        		if(RTC_FLAG1 > 2)
        		{
        			RTC_FLAG1 = 0;
        			DisplayCurrentRTC();
        		}
        		for(i = 0;i < 2000000;i++);
        		RTC_FLAG = 0;
        		RTC_FLAG1++;
        	}
        	delay(500);
        	delay(500);
        	delay(500);
        }
    
    }
    
    
    ntinued.

    Thanks & Regards

    Santosh Prasad S