Problem reading DS1307

Hi,

I am using the DS1307 library for STM32L152. The original library for STM32F429 is at here:
stm32f4-discovery.com/.../

It seems a complete library however after few modification to STM32L I cant read/write DS1307.
what ever is received is 1.


int main(void)
{
        TM_DS1307_Time_t tim;
        SystemCoreClockSetHSI();
        GPIO_RCC_configuration();
        GPIO_configuration();
        Init_SPI();
        uart1_configuration();
        I2C2_init();
        TIM4_configuration();

        TM_DS1307_SetDateTime(&tim);
        while(1)
        {

                tim.seconds=TM_DS1307_GetSeconds();
                sprintf(str," \r\ns=%u",tim.seconds);
                uart_out_str(str);
                delay_ms(1000);
        }
}


result is

s=1
s=1
s=1
s=1
s=1
s=1


I see signals in scope and there is a delay about 200ms when reading from DS1307 (reading timeout). when I debug, DR changes between 0xD0 and 0xD1. How can I find where the problem is?

Parents
  • The problem is at start function. ((/* Wait till I2C is busy */)) program waits till TM_I2C_Timeout equals zero.

    int16_t TM_I2C_Start(I2C_TypeDef* I2Cx, uint8_t address, uint8_t direction, uint8_t ack) {
            /* Generate I2C start pulse */
            I2Cx->CR1 |= I2C_CR1_START;
    
            /* Wait till I2C is busy */
            TM_I2C_Timeout = TM_I2C_TIMEOUT;
            while (!(I2Cx->SR1 & I2C_SR1_SB)) {
                    if (--TM_I2C_Timeout == 0x00) {
                            return 1;
                    }
            }
    
            /* Enable ack if we select it */
            if (ack) {
                    I2Cx->CR1 |= I2C_CR1_ACK;
            }
    
            /* Send write/read bit */
            if (direction == I2C_TRANSMITTER_MODE) {
                    /* Send address with zero last bit */
                    I2Cx->DR = address & ~I2C_OAR1_ADD0;
    
                    /* Wait till finished */
                    TM_I2C_Timeout = TM_I2C_TIMEOUT;
                    while (!(I2Cx->SR1 & I2C_SR1_ADDR)) {
                            if (--TM_I2C_Timeout == 0x00) {
                                    return 1;
                            }
                    }
            }
            if (direction == I2C_RECEIVER_MODE) {
                    /* Send address with 1 last bit */
                    I2Cx->DR = address | I2C_OAR1_ADD0;
    
                    /* Wait till finished */
                    TM_I2C_Timeout = TM_I2C_TIMEOUT;
                    while (!I2C_CheckEvent(I2Cx, I2C_EVENT_MASTER_RECEIVER_MODE_SELECTED)) {
                            if (--TM_I2C_Timeout == 0x00) {
                                    return 1;
                            }
                    }
            }
    
    

Reply
  • The problem is at start function. ((/* Wait till I2C is busy */)) program waits till TM_I2C_Timeout equals zero.

    int16_t TM_I2C_Start(I2C_TypeDef* I2Cx, uint8_t address, uint8_t direction, uint8_t ack) {
            /* Generate I2C start pulse */
            I2Cx->CR1 |= I2C_CR1_START;
    
            /* Wait till I2C is busy */
            TM_I2C_Timeout = TM_I2C_TIMEOUT;
            while (!(I2Cx->SR1 & I2C_SR1_SB)) {
                    if (--TM_I2C_Timeout == 0x00) {
                            return 1;
                    }
            }
    
            /* Enable ack if we select it */
            if (ack) {
                    I2Cx->CR1 |= I2C_CR1_ACK;
            }
    
            /* Send write/read bit */
            if (direction == I2C_TRANSMITTER_MODE) {
                    /* Send address with zero last bit */
                    I2Cx->DR = address & ~I2C_OAR1_ADD0;
    
                    /* Wait till finished */
                    TM_I2C_Timeout = TM_I2C_TIMEOUT;
                    while (!(I2Cx->SR1 & I2C_SR1_ADDR)) {
                            if (--TM_I2C_Timeout == 0x00) {
                                    return 1;
                            }
                    }
            }
            if (direction == I2C_RECEIVER_MODE) {
                    /* Send address with 1 last bit */
                    I2Cx->DR = address | I2C_OAR1_ADD0;
    
                    /* Wait till finished */
                    TM_I2C_Timeout = TM_I2C_TIMEOUT;
                    while (!I2C_CheckEvent(I2Cx, I2C_EVENT_MASTER_RECEIVER_MODE_SELECTED)) {
                            if (--TM_I2C_Timeout == 0x00) {
                                    return 1;
                            }
                    }
            }
    
    

Children
More questions in this forum