2020-07-21 06:44 AM
Dear friends,
I am using STM32f407vgt6 and a DS3231 RTC module and I use I2C1 peripheral to read date from DS3231.
It is working fine but after 10 or 12 minutes the I2C bus is continously BUSY and I do not know what to do.
Is there any way to control the bus and and reset the BUSY flag? I used Delays but it didn't work.
MH_StatusTypeDef MH_DS3231_GetDateTime(mh_ds3231_time_t* time)
{
uint8_t data[7];
uint8_t start_addr = DS3231_SECONDS;
/* Read multi bytes */
#if (useCMSIS_OS_MUTEX == 1)
if(osMutexWait(rtc_mutex_id, MAX_MUTEX_RTC_TIMEOUT) == osOK)
{
#endif
if(HAL_I2C_Master_Transmit(&RTC_HANDLE,DS3231_I2C_READ_ADDR,&start_addr,1,MAX_RTC_TIMEOUT) == HAL_OK){
if(HAL_I2C_Master_Receive(&RTC_HANDLE,DS3231_I2C_READ_ADDR,data,7,MAX_RTC_TIMEOUT) == HAL_OK){
/* Fill data */
time->seconds = MH_Bcd2Dec(data[DS3231_SECONDS]);
time->minutes = MH_Bcd2Dec(data[DS3231_MINUTES]);
time->hours = MH_Bcd2Dec(data[DS3231_HOURS]);
time->day = MH_Bcd2Dec(data[DS3231_DAY]);
time->date = MH_Bcd2Dec(data[DS3231_DATE]);
time->month = MH_Bcd2Dec(data[DS3231_MONTH]);
time->year = MH_Bcd2Dec(data[DS3231_YEAR]);
}
}
else
osDelay(500);
#if (useCMSIS_OS_MUTEX == 1)
osMutexRelease(rtc_mutex_id);
}
else
{
return MH_TIMEOUT;
}
#endif
return MH_OK;
}
and I use freeRTOS and mutex as you see above.
Any helps will be appreciated in advance,
Mujtaba
2020-07-21 03:24 PM
The I2C_CR1_SWRST bit can be used to perform a software reset. From the reference manual:
Bit 15 SWRST: Software reset
When set, the I2C is under reset state. Before resetting this bit, make sure the I2C lines are
released and the bus is free.
0: I2C Peripheral not under reset
1: I2C Peripheral under reset state
Note: This bit can be used to reinitialize the peripheral after an error or a locked state. As an
example, if the BUSY bit is set and remains locked due to a glitch on the bus, the
SWRST bit can be used to exit from this state.
2020-07-21 05:30 PM
You'd perhaps need to clock it out of that state, so the peripheral releases the signal(s)