diff --git a/core/embed/trezorhal/boards/trezor_t.h b/core/embed/trezorhal/boards/trezor_t.h index d4630bb98..e08fdc96b 100644 --- a/core/embed/trezorhal/boards/trezor_t.h +++ b/core/embed/trezorhal/boards/trezor_t.h @@ -12,6 +12,17 @@ #define USE_BACKLIGHT 1 #define USE_DISP_I8080_8BIT_DW 1 +#define BACKLIGHT_PWM_FREQ 50000 +#define BACKLIGHT_PWM_TIM TIM1 +#define BACKLIGHT_PWM_TIM_CLK_EN __HAL_RCC_TIM1_CLK_ENABLE +#define BACKLIGHT_PWM_TIM_AF GPIO_AF1_TIM1 +#define BACKLIGHT_PWM_TIM_OCMODE TIM_OCMODE_PWM2 +#define BACKLIGHT_PWM_TIM_CHANNEL TIM_CHANNEL_1 +#define BACKLIGHT_PWM_TIM_CCR CCR1 +#define BACKLIGHT_PWM_PIN GPIO_PIN_7 +#define BACKLIGHT_PWM_PORT GPIOA +#define BACKLIGHT_PWM_PORT_CLK_EN __HAL_RCC_GPIOA_CLK_ENABLE + #define I2C_COUNT 1 #define I2C_INSTANCE_1 I2C1 #define I2C_INSTANCE_1_CLK_EN __HAL_RCC_I2C1_CLK_ENABLE diff --git a/core/embed/trezorhal/stm32f4/backlight_pwm.c b/core/embed/trezorhal/stm32f4/backlight_pwm.c index b23d729d7..9cddd1972 100644 --- a/core/embed/trezorhal/stm32f4/backlight_pwm.c +++ b/core/embed/trezorhal/stm32f4/backlight_pwm.c @@ -4,27 +4,28 @@ #include STM32_HAL_H #include TREZOR_BOARD -#define LED_PWM_TIM_PERIOD \ - (255) // little less than 4kHz with PSC = (SystemCoreClock / 1000000) - 1) -#define LED_PWM_SLOW_TIM_PERIOD \ - (10000) // about 10Hz (with PSC = (SystemCoreClock / 1000000) - 1) +#define TIM_FREQ 1000000 + +#define LED_PWM_PRESCALER (SystemCoreClock / TIM_FREQ - 1) // 1 MHz + +#define LED_PWM_TIM_PERIOD (TIM_FREQ / BACKLIGHT_PWM_FREQ) static int BACKLIGHT = -1; -static int pwm_period = LED_PWM_TIM_PERIOD; +static int pwm_period = 0; int backlight_pwm_set(int val) { if (BACKLIGHT != val && val >= 0 && val <= 255) { BACKLIGHT = val; - TIM1->CCR1 = pwm_period * val / 255; + BACKLIGHT_PWM_TIM->CCR1 = pwm_period * val / 255; } return BACKLIGHT; } void backlight_pwm_init(void) { // init peripherals - __HAL_RCC_GPIOA_CLK_ENABLE(); - __HAL_RCC_TIM1_CLK_ENABLE(); + BACKLIGHT_PWM_PORT_CLK_EN(); + BACKLIGHT_PWM_TIM_CLK_EN(); GPIO_InitTypeDef GPIO_InitStructure; @@ -32,62 +33,69 @@ void backlight_pwm_init(void) { GPIO_InitStructure.Mode = GPIO_MODE_AF_PP; GPIO_InitStructure.Pull = GPIO_NOPULL; GPIO_InitStructure.Speed = GPIO_SPEED_FREQ_VERY_HIGH; - GPIO_InitStructure.Alternate = GPIO_AF1_TIM1; - GPIO_InitStructure.Pin = GPIO_PIN_7; - HAL_GPIO_Init(GPIOA, &GPIO_InitStructure); + GPIO_InitStructure.Alternate = BACKLIGHT_PWM_TIM_AF; + GPIO_InitStructure.Pin = BACKLIGHT_PWM_PIN; + HAL_GPIO_Init(BACKLIGHT_PWM_PORT, &GPIO_InitStructure); // enable PWM timer - TIM_HandleTypeDef TIM1_Handle; - TIM1_Handle.Instance = TIM1; - TIM1_Handle.Init.Period = LED_PWM_TIM_PERIOD - 1; + TIM_HandleTypeDef TIM_Handle; + TIM_Handle.Instance = BACKLIGHT_PWM_TIM; + TIM_Handle.Init.Period = LED_PWM_TIM_PERIOD - 1; // TIM1/APB2 source frequency equals to SystemCoreClock in our configuration, // we want 1 MHz - TIM1_Handle.Init.Prescaler = SystemCoreClock / 1000000 - 1; - TIM1_Handle.Init.ClockDivision = TIM_CLOCKDIVISION_DIV1; - TIM1_Handle.Init.CounterMode = TIM_COUNTERMODE_UP; - TIM1_Handle.Init.RepetitionCounter = 0; - HAL_TIM_PWM_Init(&TIM1_Handle); + TIM_Handle.Init.Prescaler = LED_PWM_PRESCALER; + TIM_Handle.Init.ClockDivision = TIM_CLOCKDIVISION_DIV1; + TIM_Handle.Init.CounterMode = TIM_COUNTERMODE_UP; + TIM_Handle.Init.RepetitionCounter = 0; + HAL_TIM_PWM_Init(&TIM_Handle); pwm_period = LED_PWM_TIM_PERIOD; TIM_OC_InitTypeDef TIM_OC_InitStructure; TIM_OC_InitStructure.Pulse = 0; - TIM_OC_InitStructure.OCMode = TIM_OCMODE_PWM2; + TIM_OC_InitStructure.OCMode = BACKLIGHT_PWM_TIM_OCMODE; TIM_OC_InitStructure.OCPolarity = TIM_OCPOLARITY_HIGH; TIM_OC_InitStructure.OCFastMode = TIM_OCFAST_DISABLE; TIM_OC_InitStructure.OCNPolarity = TIM_OCNPOLARITY_HIGH; TIM_OC_InitStructure.OCIdleState = TIM_OCIDLESTATE_SET; TIM_OC_InitStructure.OCNIdleState = TIM_OCNIDLESTATE_SET; - HAL_TIM_PWM_ConfigChannel(&TIM1_Handle, &TIM_OC_InitStructure, TIM_CHANNEL_1); + HAL_TIM_PWM_ConfigChannel(&TIM_Handle, &TIM_OC_InitStructure, + BACKLIGHT_PWM_TIM_CHANNEL); backlight_pwm_set(0); - HAL_TIM_PWM_Start(&TIM1_Handle, TIM_CHANNEL_1); - HAL_TIMEx_PWMN_Start(&TIM1_Handle, TIM_CHANNEL_1); + HAL_TIM_PWM_Start(&TIM_Handle, BACKLIGHT_PWM_TIM_CHANNEL); + HAL_TIMEx_PWMN_Start(&TIM_Handle, BACKLIGHT_PWM_TIM_CHANNEL); } void backlight_pwm_reinit(void) { - uint32_t prev_arr = TIM1->ARR; - uint32_t prev_ccr1 = TIM1->CCR1; + uint32_t prev_arr = BACKLIGHT_PWM_TIM->ARR; + uint32_t prev_ccr1 = BACKLIGHT_PWM_TIM->BACKLIGHT_PWM_TIM_CCR; uint8_t prev_val = (prev_ccr1 * 255) / prev_arr; BACKLIGHT = prev_val; pwm_period = LED_PWM_TIM_PERIOD; - TIM1->CR1 |= TIM_CR1_ARPE; - TIM1->CR2 |= TIM_CR2_CCPC; - TIM1->CCR1 = pwm_period * prev_val / 255; - TIM1->ARR = LED_PWM_TIM_PERIOD - 1; + BACKLIGHT_PWM_TIM->CR1 |= TIM_CR1_ARPE; + BACKLIGHT_PWM_TIM->CR2 |= TIM_CR2_CCPC; + BACKLIGHT_PWM_TIM->BACKLIGHT_PWM_TIM_CCR = pwm_period * prev_val / 255; + BACKLIGHT_PWM_TIM->ARR = LED_PWM_TIM_PERIOD - 1; } +#ifdef TREZOR_MODEL_T + +#define LED_PWM_SLOW_TIM_PERIOD \ + (10000) // about 10Hz (with PSC = (SystemCoreClock / 1000000) - 1) + void backlight_pwm_set_slow(void) { - uint32_t prev_arr = TIM1->ARR; - uint32_t prev_ccr1 = TIM1->CCR1; + uint32_t prev_arr = BACKLIGHT_PWM_TIM->ARR; + uint32_t prev_ccr1 = BACKLIGHT_PWM_TIM->CCR1; uint8_t prev_val = (prev_ccr1 * 255) / prev_arr; pwm_period = LED_PWM_SLOW_TIM_PERIOD; - TIM1->CR1 |= TIM_CR1_ARPE; - TIM1->CR2 |= TIM_CR2_CCPC; - TIM1->ARR = LED_PWM_SLOW_TIM_PERIOD - 1; - TIM1->CCR1 = pwm_period * prev_val / 255; + BACKLIGHT_PWM_TIM->CR1 |= TIM_CR1_ARPE; + BACKLIGHT_PWM_TIM->CR2 |= TIM_CR2_CCPC; + BACKLIGHT_PWM_TIM->ARR = LED_PWM_SLOW_TIM_PERIOD - 1; + BACKLIGHT_PWM_TIM->BACKLIGHT_PWM_TIM_CCR = pwm_period * prev_val / 255; } +#endif diff --git a/core/embed/trezorhal/stm32f4/platform.c b/core/embed/trezorhal/stm32f4/platform.c index 2624a7746..1bf44e4e8 100644 --- a/core/embed/trezorhal/stm32f4/platform.c +++ b/core/embed/trezorhal/stm32f4/platform.c @@ -21,6 +21,7 @@ #include "platform.h" #include "rng.h" +#include TREZOR_BOARD const uint8_t AHBPrescTable[16] = {0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 6, 7, 8, 9}; @@ -206,6 +207,8 @@ void drop_privileges(void) { extern void shutdown_privileged(void); void PVD_IRQHandler(void) { - TIM1->CCR1 = 0; // turn off display backlight +#ifdef BACKLIGHT_PWM_TIM + BACKLIGHT_PWM_TIM->BACKLIGHT_PWM_TIM_CCR = 0; // turn off display backlight +#endif shutdown_privileged(); }