cancel
Showing results for 
Search instead for 
Did you mean: 

Cannot I^2C to ST-nucleo-IKS01A3 in a normal I2C setting

CWang.14
Associate II

Hi I recently bought a IKS01A3 and want to do research related to human activities. I already have a nucleo-wb55 with me so basically I just connect them via arduino uno V3 ports and willing to set up I2C communication between those two boards. I know there are higher-level drivers and software packs for IKS01A3 board together with fancy UI, but is there a way that we can directly retrieve data according to each sensor unit's datasheet?

I've connected the board's outside connection I2C SCL and SDA (Arduino connector CN10 pin 10 and pin 9) to IC2_1 on IKS01A3 (DIL24 socket pin 20 and pin 21 respectively), and since I2C bus routing are connected as 1-2/3-4(default setting), which means I2C_1=I2C_2 with all devices are on the same bus.

#define I2C_SLAVE_ADDR 			  0x94 << 1
#define CODY_MAX_TRIAL				 50

I define the slave address of the STTS temperature sensor on IKS01A3, and since it's given by the datasheet as 0x94, which mean 0b'10010100, I believe we need to shift leftwise 1-bit (actually I've tried both left shift and right shift and both doesn't work).

Later I go into the communication test steps.

  ret = HAL_I2C_IsDeviceReady(&hi2c1, I2C_SLAVE_ADDR, CODY_MAX_TRIAL, HAL_MAX_DELAY);

But I always get ret as HAL_ERROR which means the device doesn't exist or doesn't support I2C currently. I've checked my wb55 development boar I2C functionalities and it could successfully communicate with other single sensors like Adafruit Si7021or other similar sensors, so right now I have no idea why the slave could never been seen by my microcontroller. I put all main function code below, it would be great if someone can help me out, I've struggled on this issue for about a week already.

#define I2C_SLAVE_ADDR 			  0x94 << 1
#define CODY_MAX_TRIAL				 50
 
/* USER CODE END Header */
/* Includes ------------------------------------------------------------------*/
#include "main.h"
 
/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
 
#include <stdio.h>
#include <unistd.h>
#include <string.h>
/* USER CODE END Includes */
 
/* Private typedef -----------------------------------------------------------*/
/* USER CODE BEGIN PTD */
 
/* USER CODE END PTD */
 
/* Private define ------------------------------------------------------------*/
/* USER CODE BEGIN PD */
/* USER CODE END PD */
 
/* Private macro -------------------------------------------------------------*/
/* USER CODE BEGIN PM */
 
/* USER CODE END PM */
 
/* Private variables ---------------------------------------------------------*/
CRC_HandleTypeDef hcrc;
 
I2C_HandleTypeDef hi2c1;
 
UART_HandleTypeDef huart1;
 
/* USER CODE BEGIN PV */
/* USER CODE END PV */
 
/* Private function prototypes -----------------------------------------------*/
void SystemClock_Config(void);
void PeriphCommonClock_Config(void);
static void MX_GPIO_Init(void);
static void MX_USART1_UART_Init(void);
static void MX_I2C1_Init(void);
static void MX_CRC_Init(void);
/* USER CODE BEGIN PFP */
 
/* USER CODE END PFP */
 
/* Private user code ---------------------------------------------------------*/
/* USER CODE BEGIN 0 */
 
static uint16_t convert_to_uint16(uint8_t bytes[])
{
  return (uint16_t)((bytes[0]<<8) | bytes[1]);
}
 
static float process_temp_code(uint16_t temp_code)
{
  return (float)(((175.72 * temp_code) / 65536.0) - 46.85);
}
 
 
 
 
/* USER CODE END 0 */
 
/**
  * @brief  The application entry point.
  * @retval int
  */
int main(void)
{
  /* USER CODE BEGIN 1 */
  /* USER CODE END 1 */
 
  /* MCU Configuration--------------------------------------------------------*/
 
  /* Reset of all peripherals, Initializes the Flash interface and the Systick. */
  HAL_Init();
 
  /* USER CODE BEGIN Init */
 
  /* USER CODE END Init */
 
  /* Configure the system clock */
  SystemClock_Config();
 
/* Configure the peripherals common clocks */
  PeriphCommonClock_Config();
 
  /* USER CODE BEGIN SysInit */
 
  /* USER CODE END SysInit */
 
  /* Initialize all configured peripherals */
  MX_GPIO_Init();
  MX_USART1_UART_Init();
  MX_I2C1_Init();
  MX_CRC_Init();
  /* USER CODE BEGIN 2 */
 
  HAL_StatusTypeDef ret;
  char word_buffer[50];
  uint8_t temp_buffer[2];
  uint16_t temp_code;
  float temp_double;
 
  //check the status of the device first
  ret = HAL_I2C_IsDeviceReady(&hi2c1, I2C_SLAVE_ADDR, CODY_MAX_TRIAL, HAL_MAX_DELAY);
 
  /* USER CODE END 2 */
 
  /* Infinite loop */
  /* USER CODE BEGIN WHILE */
  while (1)
  {
 
	  /**HAL_StatusTypeDef HAL_I2C_Master_Receive (I2C_HandleTypeDef * hi2c, uint16_t DevAddress,
	    																								uint8_t * pData, uint16_t Size, uint32_t Timeout)**/
 
 
 
 
	  /** HAL_StatusTypeDef HAL_I2C_Mem_Write (I2C_HandleTypeDef * hi2c,
																										 uint16_t DevAddress,
																									    uint16_t MemAddress,
																									    uint16_t MemAddSize,
																													 uint8_t * pData,
																														 uint16_t Size,
																												  uint32_t Timeout)**/
 
	  /**HAL_StatusTypeDef HAL_I2C_IsDeviceReady(I2C_HandleTypeDef *hi2c, uint16_t DevAddress,
	   	   	   	   	   	   	   	   	   	   	   	   	   	   	   	   	   	   	   	   	   	   	   	   	uint32_t Trials, uint32_t Timeout);**/
 
 
	  //1st MASTER START---->MASTER transmit SLAVE_ADDR + WRITE bit---->SLAVE ACK---->transmit command(0xF3)---->SLAVE ACK
	  uint8_t command = 0xE3;
	  ret = HAL_I2C_Master_Transmit(&hi2c1, I2C_SLAVE_ADDR, &command, 1, HAL_MAX_DELAY);
 
	  //2nd MASTER START---->MASTER transmit SLAVE_ADDR + READ bit---->SLAVE ACK---->SLAVE transmit 2 bytes temp reading
	  //---->MASTER save into register and ACK
	  ret = HAL_I2C_Master_Receive(&hi2c1, I2C_SLAVE_ADDR, temp_buffer, 2, HAL_MAX_DELAY); //read into MSByte of temp_returned
 
	  //concat two 8-bit into one 16-bit
	  temp_code = (uint16_t)convert_to_uint16(temp_buffer);
	  //call helper function to do the calculation
	  temp_double  = (float)process_temp_code(temp_code);
	  //print the value into word buffer for UART to mac
	  sprintf((char *)word_buffer, "current temperature: %2f'C\n", temp_double);
	  //UART the current temperature reading to mac
 
	  HAL_UART_Transmit(&huart1, word_buffer, strlen((char * )word_buffer), HAL_MAX_DELAY);
  	  HAL_Delay(1000);
 
 
 
//	  	  int16_t temp_celcius_int = high_temp << 4 + low_temp >> 4;
//	  	  double temp_celcius_double = temp_celcius_int / 16;
//
//	  	sprintf((char*)buffer, "cur temp: %2f'C\n", temp_celcius_double);
//
//		HAL_UART_Transmit(&huart1, buffer, strlen((char *)buffer), HAL_MAX_DELAY);
 
  }
 
    /* USER CODE END WHILE */
 
    /* USER CODE BEGIN 3 */
 
  /* USER CODE END 3 */
}

1 REPLY 1
Foued_KH
ST Employee

Hello @Community member​,

welcome to the Community =)

I made the test with the Address given in the datasheet: 0x94 (without shift) and it works correctly.

For example, I managed to read the content of the register " Manufacturer ID " (address: 0xFE) and I get 0x53 as value.

/*

uint8_t check;

  HAL_I2C_Mem_Read_IT (&hi2c1, 0x94,0xFE,1, &check, 1);

  

  while (HAL_I2C_GetState(&hi2c1) != HAL_I2C_STATE_READY)

  {

  }

*/

Verify first the STM32CubeMX configuration:

  • I2C_SCL: PB8
  • I2C_SDA: PB9

Also, make sure to connect JP13 on the Shield IKS01A3.

0693W00000Unjx2QAB.jpg0693W00000UnjysQAB.png 

To give better visibility on the answered topics, please click on Accept as Solution on the reply which solved your issue or answered your question.