2023-08-04 08:08 PM
I am working to get one F767ZI board (master) to send 1 byte to a second F767ZI (slave). I'm using 4k external pull-up resistors on SDA and SCL. I am trapping errors in the master and they are:
After the following code on the master I get "Error 32".
ret = HAL_I2C_IsDeviceReady(&hi2c1, 30,1, 1000);
if ( ret != HAL_OK) {
uint32_t error_code = HAL_I2C_GetError(&hi2c1);
printf("Error %d\r\n", error_code);
}
Then, after the following code on the master I get "Error 4".
ret = HAL_I2C_Master_Transmit(&hi2c1, 30, TX_Buffer, 1, 1000); //up to 1 second to try and send
if ( ret != HAL_OK) {
uint32_t error_code = HAL_I2C_GetError(&hi2c1);
printf("Error %d\r\n", error_code);
}
Since this is my first time ever trying I2C, I'm sure I'm addressing something wrong or some other simple error.
I can't find anything in the HAL/LL reference to tell me what those error codes mean.
thank you, russ
p.s. My master F767 spits printf statements to UART4 so I can watch it. My slave F767 spits them to the terminal window in Ozone using SEGGER_RTT.
Solved! Go to Solution.
2023-08-05 04:34 AM
Simply your slave dont reply and first error 32 timeout
#define HAL_I2C_ERROR_NONE 0x00000000U
#define HAL_I2C_ERROR_BERR 0x00000001U
#define HAL_I2C_ERROR_ARLO 0x00000002U
#define HAL_I2C_ERROR_AF 0x00000004U
#define HAL_I2C_ERROR_OVR 0x00000008U
#define HAL_I2C_ERROR_DMA 0x00000010U
#define HAL_I2C_ERROR_TIMEOUT 0x00000020U
2023-08-04 08:28 PM
I don't think it's a good idea to try to read an error from the I2C port only when receiving a value other than HAL_OK.
typedef enum
{
HAL_OK = 0x00U,
HAL_ERROR = 0x01U,
HAL_BUSY = 0x02U,
HAL_TIMEOUT = 0x03U
} HAL_StatusTypeDef;
When I check a device (STM32F4), I have to shift a bit in the address.
For example, the TMP117 address, which is 0x48, after shifting a bit, becomes 0x90; // 0x48 << 1
2023-08-05 03:21 AM
I thought the HAL I2C functions handle the necessary address adjustments internally, including left-shifting the address by 1 and setting the LSB based on the read/write operation. So, you don't need to left-shift the address manually before passing it to the HAL I2C functions.
2023-08-05 04:34 AM
Simply your slave dont reply and first error 32 timeout
#define HAL_I2C_ERROR_NONE 0x00000000U
#define HAL_I2C_ERROR_BERR 0x00000001U
#define HAL_I2C_ERROR_ARLO 0x00000002U
#define HAL_I2C_ERROR_AF 0x00000004U
#define HAL_I2C_ERROR_OVR 0x00000008U
#define HAL_I2C_ERROR_DMA 0x00000010U
#define HAL_I2C_ERROR_TIMEOUT 0x00000020U
2023-08-05 06:45 PM - edited 2023-08-05 06:46 PM
My assumption here was wrong (that I should not use the left-bit-shifted address in the HAL function call). It requires it. In my case I assigned a "Primary slave address" to my slave F767 of 30 decimal. So, when my master F767 send a byte it should have used an address of 60 (that is 30 left-shifted by 1 bit).
HAL_I2C_Master_Transmit(&hi2c1, 60, TX_Buffer, 1, 1000);
Then my slave could receive it with
HAL_I2C_Slave_Receive(&hi2c1 ,(uint8_t *)RX_Buffer, 1,3000); //Receiving in Blocking mode, wait 3 seconds before giving up
Of course, timing is important as the approach above the slave only waits 3 seconds for the master to send. This can obviously be increased up to HAL_MAX_DELAY which is 49.7 days. ;)
2023-08-05 07:01 PM - edited 2023-08-05 07:03 PM
@RPatt.11 wrote:My assumption here was wrong (that I should not use the left-bit-shifted address in the HAL function call). It requires it. In my case I assigned a "Primary slave address" to my slave F767 of 30 decimal. So, when my master F767 send a byte it should have used an address of 60 (that is 30 left-shifted by 1 bit).
HAL_I2C_Master_Transmit(&hi2c1, 60, TX_Buffer, 1, 1000);Then my slave could receive it with
HAL_I2C_Slave_Receive(&hi2c1 ,(uint8_t *)RX_Buffer, 1,3000); //Receiving in Blocking mode, wait 3 seconds before giving upOf course, timing is important as the approach above the slave only waits 3 seconds for the master to send. This can obviously be increased up to HAL_MAX_DELAY which is 49.7 days. ;)
I use only 5 milliseconds of timeout.
if(MPU6050_send(&hi2c3, MPU6050_ADDR, data, 2, 5) != HAL_OK)
HAL_StatusTypeDef MPU6050_send(I2C_HandleTypeDef *hi2c, uint16_t DevAddress, uint8_t *pData, uint16_t Size, uint32_t Timeout)
{
HAL_StatusTypeDef result = HAL_I2C_Master_Transmit(hi2c, DevAddress, pData, Size, Timeout);
return result;
}