Skip to content

STM32L562RE I2C2 Clock Not Being Set #2764

Closed
@haydenth

Description

@haydenth

This is on a custom board with STM32L562. Here's how my STM32 pins are configured, PB10, BP11 as I2C2.

Image

Here is my SystemClock_Config which sets the I2C2 Clock

WEAK void SystemClock_Config(void)
{
  RCC_OscInitTypeDef RCC_OscInitStruct = {};
  RCC_ClkInitTypeDef RCC_ClkInitStruct = {};
  RCC_PeriphCLKInitTypeDef PeriphClkInit = {};

  /** Configure the main internal regulator output voltage
  */
  if (HAL_PWREx_ControlVoltageScaling(PWR_REGULATOR_VOLTAGE_SCALE2) != HAL_OK)
  {
    Error_Handler();
  }

  /** Configure LSE Drive Capability
  */
  HAL_PWR_EnableBkUpAccess();
  __HAL_RCC_LSEDRIVE_CONFIG(RCC_LSEDRIVE_LOW);

  /** Initializes the RCC Oscillators according to the specified parameters
  * in the RCC_OscInitTypeDef structure.
  */
  RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSI48|RCC_OSCILLATORTYPE_HSE
                              |RCC_OSCILLATORTYPE_LSE;
  RCC_OscInitStruct.HSEState = RCC_HSE_ON;
  RCC_OscInitStruct.LSEState = RCC_LSE_ON;
  RCC_OscInitStruct.HSI48State = RCC_HSI48_ON;
  RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
  RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSE;
  RCC_OscInitStruct.PLL.PLLM = 1;
  RCC_OscInitStruct.PLL.PLLN = 12;
  RCC_OscInitStruct.PLL.PLLP = RCC_PLLP_DIV7;
  RCC_OscInitStruct.PLL.PLLQ = RCC_PLLQ_DIV4;
  RCC_OscInitStruct.PLL.PLLR = RCC_PLLR_DIV4;
  if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK)
  {
    Error_Handler();
  }

  /** Initializes the CPU, AHB and APB buses clocks
  */
  RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK|RCC_CLOCKTYPE_SYSCLK
                              |RCC_CLOCKTYPE_PCLK1|RCC_CLOCKTYPE_PCLK2;
  RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_HSE;
  RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1;
  RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV1;
  RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV1;

  if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_0) != HAL_OK)
  {
    Error_Handler();
  }

  /** Enable MSI Auto calibration
  */
  HAL_RCCEx_EnableMSIPLLMode();

  PeriphClkInit.PeriphClockSelection = RCC_PERIPHCLK_RTC | RCC_PERIPHCLK_SDMMC1
                                      | RCC_PERIPHCLK_UART4 | RCC_PERIPHCLK_USB
                                      | RCC_PERIPHCLK_I2C2;
  PeriphClkInit.RTCClockSelection = RCC_RTCCLKSOURCE_LSE;
  PeriphClkInit.Sdmmc1ClockSelection = RCC_SDMMC1CLKSOURCE_PLLP;
  PeriphClkInit.Uart4ClockSelection = RCC_UART4CLKSOURCE_PCLK1;
  PeriphClkInit.UsbClockSelection = RCC_USBCLKSOURCE_HSI48;
  PeriphClkInit.I2c2ClockSelection = RCC_I2C2CLKSOURCE_HSI;

  if (HAL_RCCEx_PeriphCLKConfig(&PeriphClkInit) != HAL_OK)
  {
    Error_Handler();
  }

}

And here's my PeripheralPins section for I2C2

//*** I2C ***
#ifdef HAL_I2C_MODULE_ENABLED
WEAK const PinMap PinMap_I2C_SDA[] = {
  // {PB_4,       I2C3, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF4_I2C3)},
  // {PB_7,       I2C1, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF4_I2C1)},
  // {PB_7_ALT1,  I2C4, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF5_I2C4)},
  // {PB_9,       I2C1, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF4_I2C1)},
  {PB_11,      I2C2, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF4_I2C2)},
  // {PB_11_ALT1, I2C4, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF3_I2C4)},
  // {PB_14,      I2C2, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF4_I2C2)},
  // {PC_1,       I2C3, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF4_I2C3)},
  // {PC_1_ALT1,  I2C4, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF2_I2C4)},
  // {PC_9,       I2C3, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF6_I2C3)},
  {NC,         NP,   0}
};
#endif

#ifdef HAL_I2C_MODULE_ENABLED
WEAK const PinMap PinMap_I2C_SCL[] = {
  // {PA_7,       I2C3, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF4_I2C3)},
  // {PB_6,       I2C1, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF4_I2C1)},
  // {PB_6_ALT1,  I2C4, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF5_I2C4)},
  // {PB_8,       I2C1, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF4_I2C1)},
  {PB_10,      I2C2, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF4_I2C2)},
  // {PB_10_ALT1, I2C4, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF3_I2C4)},
  // {PB_13,      I2C2, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF4_I2C2)},
  // {PC_0,       I2C3, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF4_I2C3)},
  // {PC_0_ALT1,  I2C4, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_NOPULL, GPIO_AF2_I2C4)},
  {NC,         NP,   0}
};

Yet, when I compile an .ino file with this code:

// Define register addresses from the reference manual
#define I2C2_BASE           0x40005800U
#define I2C2_CR1            (*(volatile uint32_t*)(I2C2_BASE + 0x00))
#define I2C2_ISR            (*(volatile uint32_t*)(I2C2_BASE + 0x18))
#define I2C2_TIMINGR        (*(volatile uint32_t*)(I2C2_BASE + 0x10))

#define RCC_BASE            0x40021000U // For L5, adjust if needed for L4
#define RCC_APB1ENR1        (*(volatile uint32_t*)(RCC_BASE + 0x58))
#define RCC_CCIPR1          (*(volatile uint32_t*)(RCC_BASE + 0x88)) // L5 specific, L4 is RCC_CCIPR

#define GPIOB_BASE          0x42020400U // For L5, adjust if needed for L4
#define GPIOB_MODER         (*(volatile uint32_t*)(GPIOB_BASE + 0x00))
#define GPIOB_OTYPER        (*(volatile uint32_t*)(GPIOB_BASE + 0x04))
#define GPIOB_PUPDR         (*(volatile uint32_t*)(GPIOB_BASE + 0x0C))
#define GPIOB_AFRH          (*(volatile uint32_t*)(GPIOB_BASE + 0x24))
#define GPIOB_IDR           (*(volatile uint32_t*)(GPIOB_BASE + 0x10))

log_printf(DEBUG_INFO, "----- I2C Pre-Scan Debug -----");

// 1. Check if I2C2 clock is enabled in the RCC
log_printf(DEBUG_INFO, "RCC APB1ENR1: 0x%08X (I2C2EN is bit 22)", RCC_APB1ENR1);
if (!(RCC_APB1ENR1 & (1 << 22))) {
    log_printf(DEBUG_ERR, "ERROR: I2C2 peripheral clock is NOT enabled!");
}

It seems like the clock source isn't being set

(8029) RCC APB1ENR1: 0x10400420 (I2C2EN is bit 22)

(8031) I2C2 Clock Source (RCC_CCIPR1): 0 (0=PCLK, 1=SYSCLK, 2=HSI16)

(8033) System Clock Freq: 8000000 Hz

(8035) PCLK1 Freq: 8000000 Hz

(8037) GPIOB MODER: 0xFFFFDEBF (should be Alternate Function '10')

(8038) GPIOB OTYPER: 0x00000000 (should be Open-Drain '1')

(8041) GPIOB AFRH: 0x00000000 (should be AF4 for I2C2)

I'm on 2.10.1

Used platform            Version Path
atmosphericiq:stm32      1.0.6   /home/tom/.arduino15/packages/atmosphericiq/hardware/stm32/1.0.6
STMicroelectronics:stm32 2.10.1  /home/tom/.arduino15/packages/STMicroelectronics/hardware/stm32/2.10.1

I don't see any errors, etc in the build logs. Anything else I should check?

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions