[FL-2392] FuriHal: refactor interrupts subsystem (#1066)

* FuriHal: refactor interrupts subsystem

* Furi,FuriHal: gather all ISRs under interrupt API, improve crtitical section and cleanup garbage

* FuriHal: mirgate ipcc and hsem to LL

* Format Sources

* FuriHal,BleGlue: move to new critical section

* Format Sources

* FuriHal: correct flash locking

* FuriHal: replace critical section with interrupt disable in OS routine, minor fixex
This commit is contained in:
あく 2022-03-29 20:37:23 +03:00 committed by GitHub
parent bdba15b366
commit 489caa8e77
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
27 changed files with 360 additions and 715 deletions

View File

@ -1,8 +1,6 @@
#include "input_i.h" #include "input_i.h"
#define GPIO_Read(input_pin) \ #define GPIO_Read(input_pin) (hal_gpio_read(input_pin.pin->pin) ^ input_pin.pin->inverted)
(HAL_GPIO_ReadPin((GPIO_TypeDef*)input_pin.pin->port, input_pin.pin->pin) ^ \
input_pin.pin->inverted)
static Input* input = NULL; static Input* input = NULL;
@ -81,8 +79,7 @@ int32_t input_srv() {
input->pin_states = malloc(input_pins_count * sizeof(InputPinState)); input->pin_states = malloc(input_pins_count * sizeof(InputPinState));
for(size_t i = 0; i < input_pins_count; i++) { for(size_t i = 0; i < input_pins_count; i++) {
GpioPin gpio = {(GPIO_TypeDef*)input_pins[i].port, (uint16_t)input_pins[i].pin}; hal_gpio_add_int_callback(input_pins[i].pin, input_isr, NULL);
hal_gpio_add_int_callback(&gpio, input_isr, NULL);
input->pin_states[i].pin = &input_pins[i]; input->pin_states[i].pin = &input_pins[i];
input->pin_states[i].state = GPIO_Read(input->pin_states[i]); input->pin_states[i].state = GPIO_Read(input->pin_states[i]);
input->pin_states[i].debounce = INPUT_DEBOUNCE_TICKS_HALF; input->pin_states[i].debounce = INPUT_DEBOUNCE_TICKS_HALF;

View File

@ -1,11 +1,12 @@
#include "check.h" #include "check.h"
#include "furi_hal_task.h" #include "common_defines.h"
#include <furi_hal_console.h> #include <furi_hal_console.h>
#include <furi_hal_rtc.h> #include <furi_hal_rtc.h>
#include <stdio.h> #include <stdio.h>
void __furi_print_name() { void __furi_print_name() {
if(task_is_isr_context()) { if(FURI_IS_ISR()) {
furi_hal_console_puts("[ISR] "); furi_hal_console_puts("[ISR] ");
} else { } else {
const char* name = osThreadGetName(osThreadGetId()); const char* name = osThreadGetName(osThreadGetId());

34
core/furi/common_defines.h Executable file → Normal file
View File

@ -1,5 +1,8 @@
#pragma once #pragma once
#include <stdbool.h>
#include <cmsis_os2.h>
#ifndef MAX #ifndef MAX
#define MAX(a, b) \ #define MAX(a, b) \
({ \ ({ \
@ -75,12 +78,35 @@
#define FURI_BIT(x, n) ((x) >> (n)&1) #define FURI_BIT(x, n) ((x) >> (n)&1)
#endif #endif
#ifndef FURI_IS_IRQ_MASKED
#define FURI_IS_IRQ_MASKED() (__get_PRIMASK() != 0U)
#endif
#ifndef FURI_IS_IRQ_MODE
#define FURI_IS_IRQ_MODE() (__get_IPSR() != 0U)
#endif
#ifndef FURI_IS_ISR
#define FURI_IS_ISR() \
(FURI_IS_IRQ_MODE() || (FURI_IS_IRQ_MASKED() && (osKernelGetState() == osKernelRunning)))
#endif
#ifndef FURI_CRITICAL_ENTER #ifndef FURI_CRITICAL_ENTER
#define FURI_CRITICAL_ENTER() \ #define FURI_CRITICAL_ENTER() \
uint32_t primask_bit = __get_PRIMASK(); \ uint32_t __isrm = 0; \
__disable_irq() bool __from_isr = FURI_IS_ISR(); \
if(__from_isr) { \
__isrm = taskENTER_CRITICAL_FROM_ISR(); \
} else { \
taskENTER_CRITICAL(); \
}
#endif #endif
#ifndef FURI_CRITICAL_EXIT #ifndef FURI_CRITICAL_EXIT
#define FURI_CRITICAL_EXIT() __set_PRIMASK(primask_bit) #define FURI_CRITICAL_EXIT() \
if(__from_isr) { \
taskEXIT_CRITICAL_FROM_ISR(__isrm); \
} else { \
taskEXIT_CRITICAL(); \
}
#endif #endif

View File

@ -41,7 +41,6 @@
#include <stm32wbxx.h> #include <stm32wbxx.h>
#include <furi_hal_console.h> #include <furi_hal_console.h>
#include <furi/common_defines.h> #include <furi/common_defines.h>
#include <furi_hal_task.h>
/* Defining MPU_WRAPPERS_INCLUDED_FROM_API_FILE prevents task.h from redefining /* Defining MPU_WRAPPERS_INCLUDED_FROM_API_FILE prevents task.h from redefining
all the API functions to use the MPU wrappers. That should only be done when all the API functions to use the MPU wrappers. That should only be done when

View File

@ -5,117 +5,112 @@ extern "C" {
#endif #endif
#include "stm32wbxx_hal.h" #include "stm32wbxx_hal.h"
#include "stm32wbxx_ll_gpio.h"
void Error_Handler(void); void Error_Handler(void);
#define BUTTON_BACK_EXTI_IRQn EXTI15_10_IRQn
#define BUTTON_BACK_GPIO_Port GPIOC #define BUTTON_BACK_GPIO_Port GPIOC
#define BUTTON_BACK_Pin GPIO_PIN_13 #define BUTTON_BACK_Pin LL_GPIO_PIN_13
#define BUTTON_DOWN_EXTI_IRQn EXTI6_IRQn
#define BUTTON_DOWN_GPIO_Port GPIOC #define BUTTON_DOWN_GPIO_Port GPIOC
#define BUTTON_DOWN_Pin GPIO_PIN_6 #define BUTTON_DOWN_Pin LL_GPIO_PIN_6
#define BUTTON_LEFT_EXTI_IRQn EXTI15_10_IRQn
#define BUTTON_LEFT_GPIO_Port GPIOB #define BUTTON_LEFT_GPIO_Port GPIOB
#define BUTTON_LEFT_Pin GPIO_PIN_11 #define BUTTON_LEFT_Pin LL_GPIO_PIN_11
#define BUTTON_OK_EXTI_IRQn EXTI3_IRQn
#define BUTTON_OK_GPIO_Port GPIOH #define BUTTON_OK_GPIO_Port GPIOH
#define BUTTON_OK_Pin GPIO_PIN_3 #define BUTTON_OK_Pin LL_GPIO_PIN_3
#define BUTTON_RIGHT_EXTI_IRQn EXTI15_10_IRQn
#define BUTTON_RIGHT_GPIO_Port GPIOB #define BUTTON_RIGHT_GPIO_Port GPIOB
#define BUTTON_RIGHT_Pin GPIO_PIN_12 #define BUTTON_RIGHT_Pin LL_GPIO_PIN_12
#define BUTTON_UP_EXTI_IRQn EXTI15_10_IRQn
#define BUTTON_UP_GPIO_Port GPIOB #define BUTTON_UP_GPIO_Port GPIOB
#define BUTTON_UP_Pin GPIO_PIN_10 #define BUTTON_UP_Pin LL_GPIO_PIN_10
#define CC1101_CS_GPIO_Port GPIOD #define CC1101_CS_GPIO_Port GPIOD
#define CC1101_CS_Pin GPIO_PIN_0 #define CC1101_CS_Pin LL_GPIO_PIN_0
#define CC1101_G0_GPIO_Port GPIOA #define CC1101_G0_GPIO_Port GPIOA
#define CC1101_G0_Pin GPIO_PIN_1 #define CC1101_G0_Pin LL_GPIO_PIN_1
#define DISPLAY_CS_GPIO_Port GPIOC #define DISPLAY_CS_GPIO_Port GPIOC
#define DISPLAY_CS_Pin GPIO_PIN_11 #define DISPLAY_CS_Pin LL_GPIO_PIN_11
#define DISPLAY_DI_GPIO_Port GPIOB #define DISPLAY_DI_GPIO_Port GPIOB
#define DISPLAY_DI_Pin GPIO_PIN_1 #define DISPLAY_DI_Pin LL_GPIO_PIN_1
#define DISPLAY_RST_GPIO_Port GPIOB #define DISPLAY_RST_GPIO_Port GPIOB
#define DISPLAY_RST_Pin GPIO_PIN_0 #define DISPLAY_RST_Pin LL_GPIO_PIN_0
#define IR_RX_GPIO_Port GPIOA #define IR_RX_GPIO_Port GPIOA
#define IR_RX_Pin GPIO_PIN_0 #define IR_RX_Pin LL_GPIO_PIN_0
#define IR_TX_GPIO_Port GPIOB #define IR_TX_GPIO_Port GPIOB
#define IR_TX_Pin GPIO_PIN_9 #define IR_TX_Pin LL_GPIO_PIN_9
#define NFC_CS_GPIO_Port GPIOE #define NFC_CS_GPIO_Port GPIOE
#define NFC_CS_Pin GPIO_PIN_4 #define NFC_CS_Pin LL_GPIO_PIN_4
#define PA4_GPIO_Port GPIOA #define PA4_GPIO_Port GPIOA
#define PA4_Pin GPIO_PIN_4 #define PA4_Pin LL_GPIO_PIN_4
#define PA6_GPIO_Port GPIOA #define PA6_GPIO_Port GPIOA
#define PA6_Pin GPIO_PIN_6 #define PA6_Pin LL_GPIO_PIN_6
#define PA7_GPIO_Port GPIOA #define PA7_GPIO_Port GPIOA
#define PA7_Pin GPIO_PIN_7 #define PA7_Pin LL_GPIO_PIN_7
#define PB2_GPIO_Port GPIOB #define PB2_GPIO_Port GPIOB
#define PB2_Pin GPIO_PIN_2 #define PB2_Pin LL_GPIO_PIN_2
#define PB3_GPIO_Port GPIOB #define PB3_GPIO_Port GPIOB
#define PB3_Pin GPIO_PIN_3 #define PB3_Pin LL_GPIO_PIN_3
#define PC0_GPIO_Port GPIOC #define PC0_GPIO_Port GPIOC
#define PC0_Pin GPIO_PIN_0 #define PC0_Pin LL_GPIO_PIN_0
#define PC1_GPIO_Port GPIOC #define PC1_GPIO_Port GPIOC
#define PC1_Pin GPIO_PIN_1 #define PC1_Pin LL_GPIO_PIN_1
#define PC3_GPIO_Port GPIOC #define PC3_GPIO_Port GPIOC
#define PC3_Pin GPIO_PIN_3 #define PC3_Pin LL_GPIO_PIN_3
#define PERIPH_POWER_GPIO_Port GPIOA #define PERIPH_POWER_GPIO_Port GPIOA
#define PERIPH_POWER_Pin GPIO_PIN_3 #define PERIPH_POWER_Pin LL_GPIO_PIN_3
#define QUARTZ_32MHZ_IN_GPIO_Port GPIOC #define QUARTZ_32MHZ_IN_GPIO_Port GPIOC
#define QUARTZ_32MHZ_IN_Pin GPIO_PIN_14 #define QUARTZ_32MHZ_IN_Pin LL_GPIO_PIN_14
#define QUARTZ_32MHZ_OUT_GPIO_Port GPIOC #define QUARTZ_32MHZ_OUT_GPIO_Port GPIOC
#define QUARTZ_32MHZ_OUT_Pin GPIO_PIN_15 #define QUARTZ_32MHZ_OUT_Pin LL_GPIO_PIN_15
#define RFID_OUT_GPIO_Port GPIOB #define RFID_OUT_GPIO_Port GPIOB
#define RFID_OUT_Pin GPIO_PIN_13 #define RFID_OUT_Pin LL_GPIO_PIN_13
#define RFID_PULL_GPIO_Port GPIOA #define RFID_PULL_GPIO_Port GPIOA
#define RFID_PULL_Pin GPIO_PIN_2 #define RFID_PULL_Pin LL_GPIO_PIN_2
#define RFID_RF_IN_GPIO_Port GPIOC #define RFID_RF_IN_GPIO_Port GPIOC
#define RFID_RF_IN_Pin GPIO_PIN_5 #define RFID_RF_IN_Pin LL_GPIO_PIN_5
#define RFID_CARRIER_GPIO_Port GPIOA #define RFID_CARRIER_GPIO_Port GPIOA
#define RFID_CARRIER_Pin GPIO_PIN_15 #define RFID_CARRIER_Pin LL_GPIO_PIN_15
#define RF_SW_0_GPIO_Port GPIOC #define RF_SW_0_GPIO_Port GPIOC
#define RF_SW_0_Pin GPIO_PIN_4 #define RF_SW_0_Pin LL_GPIO_PIN_4
#define SD_CD_GPIO_Port GPIOC #define SD_CD_GPIO_Port GPIOC
#define SD_CD_Pin GPIO_PIN_10 #define SD_CD_Pin LL_GPIO_PIN_10
#define SD_CS_GPIO_Port GPIOC #define SD_CS_GPIO_Port GPIOC
#define SD_CS_Pin GPIO_PIN_12 #define SD_CS_Pin LL_GPIO_PIN_12
#define SPEAKER_GPIO_Port GPIOB #define SPEAKER_GPIO_Port GPIOB
#define SPEAKER_Pin GPIO_PIN_8 #define SPEAKER_Pin LL_GPIO_PIN_8
#define VIBRO_GPIO_Port GPIOA #define VIBRO_GPIO_Port GPIOA
#define VIBRO_Pin GPIO_PIN_8 #define VIBRO_Pin LL_GPIO_PIN_8
#define iBTN_GPIO_Port GPIOB #define iBTN_GPIO_Port GPIOB
#define iBTN_Pin GPIO_PIN_14 #define iBTN_Pin LL_GPIO_PIN_14
#define USART1_TX_Pin GPIO_PIN_6 #define USART1_TX_Pin LL_GPIO_PIN_6
#define USART1_TX_Port GPIOB #define USART1_TX_Port GPIOB
#define USART1_RX_Pin GPIO_PIN_7 #define USART1_RX_Pin LL_GPIO_PIN_7
#define USART1_RX_Port GPIOB #define USART1_RX_Port GPIOB
#define SPI_D_MISO_GPIO_Port GPIOC #define SPI_D_MISO_GPIO_Port GPIOC
#define SPI_D_MISO_Pin GPIO_PIN_2 #define SPI_D_MISO_Pin LL_GPIO_PIN_2
#define SPI_D_MOSI_GPIO_Port GPIOB #define SPI_D_MOSI_GPIO_Port GPIOB
#define SPI_D_MOSI_Pin GPIO_PIN_15 #define SPI_D_MOSI_Pin LL_GPIO_PIN_15
#define SPI_D_SCK_GPIO_Port GPIOD #define SPI_D_SCK_GPIO_Port GPIOD
#define SPI_D_SCK_Pin GPIO_PIN_1 #define SPI_D_SCK_Pin LL_GPIO_PIN_1
#define SPI_R_MISO_GPIO_Port GPIOB #define SPI_R_MISO_GPIO_Port GPIOB
#define SPI_R_MISO_Pin GPIO_PIN_4 #define SPI_R_MISO_Pin LL_GPIO_PIN_4
#define SPI_R_MOSI_GPIO_Port GPIOB #define SPI_R_MOSI_GPIO_Port GPIOB
#define SPI_R_MOSI_Pin GPIO_PIN_5 #define SPI_R_MOSI_Pin LL_GPIO_PIN_5
#define SPI_R_SCK_GPIO_Port GPIOA #define SPI_R_SCK_GPIO_Port GPIOA
#define SPI_R_SCK_Pin GPIO_PIN_5 #define SPI_R_SCK_Pin LL_GPIO_PIN_5
#define NFC_IRQ_Pin RFID_PULL_Pin #define NFC_IRQ_Pin RFID_PULL_Pin
#define NFC_IRQ_GPIO_Port RFID_PULL_GPIO_Port #define NFC_IRQ_GPIO_Port RFID_PULL_GPIO_Port

View File

@ -37,7 +37,7 @@ extern "C" {
#define HAL_CRYP_MODULE_ENABLED #define HAL_CRYP_MODULE_ENABLED
/*#define HAL_COMP_MODULE_ENABLED */ /*#define HAL_COMP_MODULE_ENABLED */
/*#define HAL_CRC_MODULE_ENABLED */ /*#define HAL_CRC_MODULE_ENABLED */
#define HAL_HSEM_MODULE_ENABLED /*#define HAL_HSEM_MODULE_ENABLED */
/*#define HAL_I2C_MODULE_ENABLED */ /*#define HAL_I2C_MODULE_ENABLED */
/*#define HAL_IPCC_MODULE_ENABLED */ /*#define HAL_IPCC_MODULE_ENABLED */
/*#define HAL_IRDA_MODULE_ENABLED */ /*#define HAL_IRDA_MODULE_ENABLED */

View File

@ -1,69 +0,0 @@
/* USER CODE BEGIN Header */
/**
******************************************************************************
* @file stm32wbxx_it.h
* @brief This file contains the headers of the interrupt handlers.
******************************************************************************
* @attention
*
* <h2><center>&copy; Copyright (c) 2020 STMicroelectronics.
* All rights reserved.</center></h2>
*
* This software component is licensed by ST under Ultimate Liberty license
* SLA0044, the "License"; You may not use this file except in compliance with
* the License. You may obtain a copy of the License at:
* www.st.com/SLA0044
*
******************************************************************************
*/
/* USER CODE END Header */
/* Define to prevent recursive inclusion -------------------------------------*/
#ifndef __STM32WBxx_IT_H
#define __STM32WBxx_IT_H
#ifdef __cplusplus
extern "C" {
#endif
/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
/* USER CODE END Includes */
/* Exported types ------------------------------------------------------------*/
/* USER CODE BEGIN ET */
/* USER CODE END ET */
/* Exported constants --------------------------------------------------------*/
/* USER CODE BEGIN EC */
/* USER CODE END EC */
/* Exported macro ------------------------------------------------------------*/
/* USER CODE BEGIN EM */
/* USER CODE END EM */
/* Exported functions prototypes ---------------------------------------------*/
void SysTick_Handler(void);
void ADC1_IRQHandler(void);
void USB_LP_IRQHandler(void);
void COMP_IRQHandler(void);
void TIM1_UP_TIM16_IRQHandler(void);
void TIM1_TRG_COM_TIM17_IRQHandler(void);
void TIM1_CC_IRQHandler(void);
void TIM2_IRQHandler(void);
void HSEM_IRQHandler(void);
/* USER CODE BEGIN EFP */
/* USER CODE END EFP */
#ifdef __cplusplus
}
#endif
#endif /* __STM32WBxx_IT_H */
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@ -1,11 +0,0 @@
#include "main.h"
void HAL_MspInit(void) {
HAL_NVIC_SetPriority(PendSV_IRQn, 15, 0);
HAL_NVIC_SetPriority(RCC_IRQn, 5, 0);
HAL_NVIC_EnableIRQ(RCC_IRQn);
HAL_NVIC_SetPriority(HSEM_IRQn, 5, 0);
HAL_NVIC_EnableIRQ(HSEM_IRQn);
}

View File

@ -1,31 +0,0 @@
#include "main.h"
#include "stm32wbxx_it.h"
#include "FreeRTOS.h"
#include "task.h"
#include "usbd_core.h"
extern usbd_device udev;
extern void HW_TS_RTC_Wakeup_Handler();
extern void HW_IPCC_Tx_Handler();
extern void HW_IPCC_Rx_Handler();
void SysTick_Handler(void) {
HAL_IncTick();
}
void USB_LP_IRQHandler(void) {
usbd_poll(&udev);
}
void HSEM_IRQHandler(void) {
HAL_HSEM_IRQHandler();
}
void IPCC_C1_TX_IRQHandler(void) {
HW_IPCC_Tx_Handler();
}
void IPCC_C1_RX_IRQHandler(void) {
HW_IPCC_Rx_Handler();
}

View File

@ -1,126 +1,5 @@
/**
******************************************************************************
* @file system_stm32wbxx.c
* @author MCD Application Team
* @brief CMSIS Cortex Device Peripheral Access Layer System Source File
*
* This file provides two functions and one global variable to be called from
* user application:
* - SystemInit(): This function is called at startup just after reset and
* before branch to main program. This call is made inside
* the "startup_stm32wbxx.s" file.
*
* - SystemCoreClock variable: Contains the core clock (HCLK), it can be used
* by the user application to setup the SysTick
* timer or configure other parameters.
*
* - SystemCoreClockUpdate(): Updates the variable SystemCoreClock and must
* be called whenever the core clock is changed
* during program execution.
*
* After each device reset the MSI (4 MHz) is used as system clock source.
* Then SystemInit() function is called, in "startup_stm32wbxx.s" file, to
* configure the system clock before to branch to main program.
*
* This file configures the system clock as follows:
*=============================================================================
*-----------------------------------------------------------------------------
* System Clock source | MSI
*-----------------------------------------------------------------------------
* SYSCLK(Hz) | 4000000
*-----------------------------------------------------------------------------
* HCLK(Hz) | 4000000
*-----------------------------------------------------------------------------
* AHB Prescaler | 1
*-----------------------------------------------------------------------------
* APB1 Prescaler | 1
*-----------------------------------------------------------------------------
* APB2 Prescaler | 1
*-----------------------------------------------------------------------------
* PLL_M | 1
*-----------------------------------------------------------------------------
* PLL_N | 8
*-----------------------------------------------------------------------------
* PLL_P | 7
*-----------------------------------------------------------------------------
* PLL_Q | 2
*-----------------------------------------------------------------------------
* PLL_R | 2
*-----------------------------------------------------------------------------
* PLLSAI1_P | NA
*-----------------------------------------------------------------------------
* PLLSAI1_Q | NA
*-----------------------------------------------------------------------------
* PLLSAI1_R | NA
*-----------------------------------------------------------------------------
* Require 48MHz for USB OTG FS, | Disabled
* SDIO and RNG clock |
*-----------------------------------------------------------------------------
*=============================================================================
******************************************************************************
* @attention
*
* <h2><center>&copy; Copyright (c) 2019 STMicroelectronics.
* All rights reserved.</center></h2>
*
* This software component is licensed by ST under BSD 3-Clause license,
* the "License"; You may not use this file except in compliance with the
* License. You may obtain a copy of the License at:
* opensource.org/licenses/BSD-3-Clause
*
******************************************************************************
*/
/** @addtogroup CMSIS
* @{
*/
/** @addtogroup stm32WBxx_system
* @{
*/
/** @addtogroup stm32WBxx_System_Private_Includes
* @{
*/
#include "stm32wbxx.h" #include "stm32wbxx.h"
#if !defined(HSE_VALUE)
#define HSE_VALUE (32000000UL) /*!< Value of the External oscillator in Hz */
#endif /* HSE_VALUE */
#if !defined(MSI_VALUE)
#define MSI_VALUE (4000000UL) /*!< Value of the Internal oscillator in Hz*/
#endif /* MSI_VALUE */
#if !defined(HSI_VALUE)
#define HSI_VALUE (16000000UL) /*!< Value of the Internal oscillator in Hz*/
#endif /* HSI_VALUE */
#if !defined(LSI_VALUE)
#define LSI_VALUE (32000UL) /*!< Value of LSI in Hz*/
#endif /* LSI_VALUE */
#if !defined(LSE_VALUE)
#define LSE_VALUE (32768UL) /*!< Value of LSE in Hz*/
#endif /* LSE_VALUE */
/**
* @}
*/
/** @addtogroup STM32WBxx_System_Private_TypesDefinitions
* @{
*/
/**
* @}
*/
/** @addtogroup STM32WBxx_System_Private_Defines
* @{
*/
/*!< Uncomment the following line if you need to relocate your vector Table in /*!< Uncomment the following line if you need to relocate your vector Table in
Internal SRAM. */ Internal SRAM. */
/* #define VECT_TAB_SRAM */ /* #define VECT_TAB_SRAM */
@ -131,21 +10,7 @@
#define VECT_TAB_BASE_ADDRESS \ #define VECT_TAB_BASE_ADDRESS \
SRAM1_BASE /*!< Vector Table base offset field. SRAM1_BASE /*!< Vector Table base offset field.
This value must be a multiple of 0x200. */ This value must be a multiple of 0x200. */
/**
* @}
*/
/** @addtogroup STM32WBxx_System_Private_Macros
* @{
*/
/**
* @}
*/
/** @addtogroup STM32WBxx_System_Private_Variables
* @{
*/
/* The SystemCoreClock variable is updated in three ways: /* The SystemCoreClock variable is updated in three ways:
1) by calling CMSIS function SystemCoreClockUpdate() 1) by calling CMSIS function SystemCoreClockUpdate()
2) by calling HAL API function HAL_RCC_GetHCLKFreq() 2) by calling HAL API function HAL_RCC_GetHCLKFreq()
@ -179,30 +44,6 @@ const uint32_t MSIRangeTable[16UL] = {
0UL, 0UL,
0UL}; /* 0UL values are incorrect cases */ 0UL}; /* 0UL values are incorrect cases */
#if defined(STM32WB55xx) || defined(STM32WB5Mxx) || defined(STM32WB35xx)
const uint32_t SmpsPrescalerTable[4UL][6UL] = {
{1UL, 3UL, 2UL, 2UL, 1UL, 2UL},
{2UL, 6UL, 4UL, 3UL, 2UL, 4UL},
{4UL, 12UL, 8UL, 6UL, 4UL, 8UL},
{4UL, 12UL, 8UL, 6UL, 4UL, 8UL}};
#endif
/**
* @}
*/
/** @addtogroup STM32WBxx_System_Private_FunctionPrototypes
* @{
*/
/**
* @}
*/
/** @addtogroup STM32WBxx_System_Private_Functions
* @{
*/
/** /**
* @brief Setup the microcontroller system. * @brief Setup the microcontroller system.
* @param None * @param None
@ -254,118 +95,3 @@ void SystemInit(void) {
/* Disable all interrupts */ /* Disable all interrupts */
RCC->CIER = 0x00000000; RCC->CIER = 0x00000000;
} }
/**
* @brief Update SystemCoreClock variable according to Clock Register Values.
* The SystemCoreClock variable contains the core clock (HCLK), it can
* be used by the user application to setup the SysTick timer or configure
* other parameters.
*
* @note Each time the core clock (HCLK) changes, this function must be called
* to update SystemCoreClock variable value. Otherwise, any configuration
* based on this variable will be incorrect.
*
* @note - The system frequency computed by this function is not the real
* frequency in the chip. It is calculated based on the predefined
* constant and the selected clock source:
*
* - If SYSCLK source is MSI, SystemCoreClock will contain the MSI_VALUE(*)
*
* - If SYSCLK source is HSI, SystemCoreClock will contain the HSI_VALUE(**)
*
* - If SYSCLK source is HSE, SystemCoreClock will contain the HSE_VALUE(***)
*
* - If SYSCLK source is PLL, SystemCoreClock will contain the HSE_VALUE(***)
* or HSI_VALUE(*) or MSI_VALUE(*) multiplied/divided by the PLL factors.
*
* (*) MSI_VALUE is a constant defined in stm32wbxx_hal.h file (default value
* 4 MHz) but the real value may vary depending on the variations
* in voltage and temperature.
*
* (**) HSI_VALUE is a constant defined in stm32wbxx_hal_conf.h file (default value
* 16 MHz) but the real value may vary depending on the variations
* in voltage and temperature.
*
* (***) HSE_VALUE is a constant defined in stm32wbxx_hal_conf.h file (default value
* 32 MHz), user has to ensure that HSE_VALUE is same as the real
* frequency of the crystal used. Otherwise, this function may
* have wrong result.
*
* - The result of this function could be not correct when using fractional
* value for HSE crystal.
*
* @param None
* @retval None
*/
void SystemCoreClockUpdate(void) {
uint32_t tmp, msirange, pllvco, pllr, pllsource, pllm;
/* Get MSI Range frequency--------------------------------------------------*/
/*MSI frequency range in Hz*/
msirange = MSIRangeTable[(RCC->CR & RCC_CR_MSIRANGE) >> RCC_CR_MSIRANGE_Pos];
/* Get SYSCLK source -------------------------------------------------------*/
switch(RCC->CFGR & RCC_CFGR_SWS) {
case 0x00: /* MSI used as system clock source */
SystemCoreClock = msirange;
break;
case 0x04: /* HSI used as system clock source */
/* HSI used as system clock source */
SystemCoreClock = HSI_VALUE;
break;
case 0x08: /* HSE used as system clock source */
SystemCoreClock = HSE_VALUE;
break;
case 0x0C: /* PLL used as system clock source */
/* PLL_VCO = (HSE_VALUE or HSI_VALUE or MSI_VALUE/ PLLM) * PLLN
SYSCLK = PLL_VCO / PLLR
*/
pllsource = (RCC->PLLCFGR & RCC_PLLCFGR_PLLSRC);
pllm = ((RCC->PLLCFGR & RCC_PLLCFGR_PLLM) >> RCC_PLLCFGR_PLLM_Pos) + 1UL;
if(pllsource == 0x02UL) /* HSI used as PLL clock source */
{
pllvco = (HSI_VALUE / pllm);
} else if(pllsource == 0x03UL) /* HSE used as PLL clock source */
{
pllvco = (HSE_VALUE / pllm);
} else /* MSI used as PLL clock source */
{
pllvco = (msirange / pllm);
}
pllvco = pllvco * ((RCC->PLLCFGR & RCC_PLLCFGR_PLLN) >> RCC_PLLCFGR_PLLN_Pos);
pllr = (((RCC->PLLCFGR & RCC_PLLCFGR_PLLR) >> RCC_PLLCFGR_PLLR_Pos) + 1UL);
SystemCoreClock = pllvco / pllr;
break;
default:
SystemCoreClock = msirange;
break;
}
/* Compute HCLK clock frequency --------------------------------------------*/
/* Get HCLK1 prescaler */
tmp = AHBPrescTable[((RCC->CFGR & RCC_CFGR_HPRE) >> RCC_CFGR_HPRE_Pos)];
/* HCLK clock frequency */
SystemCoreClock = SystemCoreClock / tmp;
}
/**
* @}
*/
/**
* @}
*/
/**
* @}
*/
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@ -29,15 +29,14 @@ extern "C" {
#include "cmsis_compiler.h" #include "cmsis_compiler.h"
#include "string.h" #include "string.h"
#include <furi.h>
/****************************************************************************** /******************************************************************************
* common * common
******************************************************************************/ ******************************************************************************/
#define UTILS_ENTER_CRITICAL_SECTION() \ #define UTILS_ENTER_CRITICAL_SECTION() FURI_CRITICAL_ENTER()
uint32_t primask_bit = __get_PRIMASK(); \
__disable_irq()
#define UTILS_EXIT_CRITICAL_SECTION() __set_PRIMASK(primask_bit) #define UTILS_EXIT_CRITICAL_SECTION() FURI_CRITICAL_EXIT()
#define UTILS_MEMSET8(dest, value, size) memset(dest, value, size); #define UTILS_MEMSET8(dest, value, size) memset(dest, value, size);

View File

@ -82,8 +82,8 @@ void furi_hal_bt_init() {
} }
// Explicitly tell that we are in charge of CLK48 domain // Explicitly tell that we are in charge of CLK48 domain
if(!HAL_HSEM_IsSemTaken(CFG_HW_CLK48_CONFIG_SEMID)) { if(!LL_HSEM_IsSemaphoreLocked(HSEM, CFG_HW_CLK48_CONFIG_SEMID)) {
HAL_HSEM_FastTake(CFG_HW_CLK48_CONFIG_SEMID); furi_assert(LL_HSEM_1StepLock(HSEM, CFG_HW_CLK48_CONFIG_SEMID) == 0);
} }
// Start Core2 // Start Core2
@ -124,8 +124,8 @@ bool furi_hal_bt_start_radio_stack() {
osMutexAcquire(furi_hal_bt_core2_mtx, osWaitForever); osMutexAcquire(furi_hal_bt_core2_mtx, osWaitForever);
// Explicitly tell that we are in charge of CLK48 domain // Explicitly tell that we are in charge of CLK48 domain
if(!HAL_HSEM_IsSemTaken(CFG_HW_CLK48_CONFIG_SEMID)) { if(!LL_HSEM_IsSemaphoreLocked(HSEM, CFG_HW_CLK48_CONFIG_SEMID)) {
HAL_HSEM_FastTake(CFG_HW_CLK48_CONFIG_SEMID); furi_assert(LL_HSEM_1StepLock(HSEM, CFG_HW_CLK48_CONFIG_SEMID) == 0);
} }
do { do {
@ -283,13 +283,13 @@ void furi_hal_bt_set_key_storage_change_callback(
} }
void furi_hal_bt_nvm_sram_sem_acquire() { void furi_hal_bt_nvm_sram_sem_acquire() {
while(HAL_HSEM_FastTake(CFG_HW_BLE_NVM_SRAM_SEMID) != HAL_OK) { while(LL_HSEM_1StepLock(HSEM, CFG_HW_BLE_NVM_SRAM_SEMID)) {
osDelay(1); osThreadYield();
} }
} }
void furi_hal_bt_nvm_sram_sem_release() { void furi_hal_bt_nvm_sram_sem_release() {
HAL_HSEM_Release(CFG_HW_BLE_NVM_SRAM_SEMID, 0); LL_HSEM_ReleaseLock(HSEM, CFG_HW_BLE_NVM_SRAM_SEMID, 0);
} }
bool furi_hal_bt_clear_white_list() { bool furi_hal_bt_clear_white_list() {

View File

@ -87,8 +87,8 @@ static void furi_hal_flash_lock(void) {
static void furi_hal_flash_begin_with_core2(bool erase_flag) { static void furi_hal_flash_begin_with_core2(bool erase_flag) {
// Take flash controller ownership // Take flash controller ownership
while(HAL_HSEM_FastTake(CFG_HW_FLASH_SEMID) != HAL_OK) { while(LL_HSEM_1StepLock(HSEM, CFG_HW_FLASH_SEMID) != 0) {
taskYIELD(); osThreadYield();
} }
// Unlock flash operation // Unlock flash operation
@ -97,27 +97,35 @@ static void furi_hal_flash_begin_with_core2(bool erase_flag) {
// Erase activity notification // Erase activity notification
if(erase_flag) SHCI_C2_FLASH_EraseActivity(ERASE_ACTIVITY_ON); if(erase_flag) SHCI_C2_FLASH_EraseActivity(ERASE_ACTIVITY_ON);
// 64mHz 5us core2 flag protection
for(volatile uint32_t i = 0; i < 35; i++)
;
while(true) { while(true) {
// Wait till flash controller become usable // Wait till flash controller become usable
while(LL_FLASH_IsActiveFlag_OperationSuspended()) { while(LL_FLASH_IsActiveFlag_OperationSuspended()) {
taskYIELD(); osThreadYield();
}; };
// Just a little more love // Just a little more love
taskENTER_CRITICAL(); taskENTER_CRITICAL();
// Actually we already have mutex for it, but specification is specification // Actually we already have mutex for it, but specification is specification
if(HAL_HSEM_IsSemTaken(CFG_HW_BLOCK_FLASH_REQ_BY_CPU1_SEMID)) { if(LL_HSEM_IsSemaphoreLocked(HSEM, CFG_HW_BLOCK_FLASH_REQ_BY_CPU1_SEMID)) {
taskEXIT_CRITICAL(); taskEXIT_CRITICAL();
continue; continue;
} }
// Take sempahopre and prevent core2 from anyting funky //
if(!HAL_HSEM_IsSemTaken(CFG_HW_BLOCK_FLASH_REQ_BY_CPU2_SEMID)) { if(LL_HSEM_IsSemaphoreLocked(HSEM, CFG_HW_BLOCK_FLASH_REQ_BY_CPU2_SEMID)) {
if(HAL_HSEM_FastTake(CFG_HW_BLOCK_FLASH_REQ_BY_CPU2_SEMID) != HAL_OK) { taskEXIT_CRITICAL();
taskEXIT_CRITICAL(); continue;
continue; }
}
// Take sempahopre and prevent core2 from anything funky
if(LL_HSEM_1StepLock(HSEM, CFG_HW_BLOCK_FLASH_REQ_BY_CPU2_SEMID) != 0) {
taskEXIT_CRITICAL();
continue;
} }
break; break;
@ -138,14 +146,14 @@ static void furi_hal_flash_begin(bool erase_flag) {
static void furi_hal_flash_end_with_core2(bool erase_flag) { static void furi_hal_flash_end_with_core2(bool erase_flag) {
// Funky ops are ok at this point // Funky ops are ok at this point
HAL_HSEM_Release(CFG_HW_BLOCK_FLASH_REQ_BY_CPU2_SEMID, 0); LL_HSEM_ReleaseLock(HSEM, CFG_HW_BLOCK_FLASH_REQ_BY_CPU2_SEMID, 0);
// Task switching is ok // Task switching is ok
taskEXIT_CRITICAL(); taskEXIT_CRITICAL();
// Doesn't make much sense, does it? // Doesn't make much sense, does it?
while(__HAL_FLASH_GET_FLAG(FLASH_FLAG_BSY)) { while(__HAL_FLASH_GET_FLAG(FLASH_FLAG_BSY)) {
taskYIELD(); osThreadYield();
} }
// Erase activity over, core2 can continue // Erase activity over, core2 can continue
@ -155,7 +163,7 @@ static void furi_hal_flash_end_with_core2(bool erase_flag) {
furi_hal_flash_lock(); furi_hal_flash_lock();
// Release flash controller ownership // Release flash controller ownership
HAL_HSEM_Release(CFG_HW_FLASH_SEMID, 0); LL_HSEM_ReleaseLock(HSEM, CFG_HW_FLASH_SEMID, 0);
} }
static void furi_hal_flash_end(bool erase_flag) { static void furi_hal_flash_end(bool erase_flag) {

View File

@ -8,7 +8,7 @@
#include <furi.h> #include <furi.h>
#define FURI_HAL_IBUTTON_TIMER TIM1 #define FURI_HAL_IBUTTON_TIMER TIM1
#define FURI_HAL_IBUTTON_TIMER_IRQ TIM1_UP_TIM16_IRQn #define FURI_HAL_IBUTTON_TIMER_IRQ FuriHalInterruptIdTim1UpTim16
typedef enum { typedef enum {
FuriHalIbuttonStateIdle, FuriHalIbuttonStateIdle,
@ -50,10 +50,7 @@ void furi_hal_ibutton_emulate_start(
LL_TIM_DeInit(FURI_HAL_IBUTTON_TIMER); LL_TIM_DeInit(FURI_HAL_IBUTTON_TIMER);
FURI_CRITICAL_EXIT(); FURI_CRITICAL_EXIT();
furi_hal_interrupt_set_timer_isr(FURI_HAL_IBUTTON_TIMER, furi_hal_ibutton_emulate_isr); furi_hal_interrupt_set_isr(FURI_HAL_IBUTTON_TIMER_IRQ, furi_hal_ibutton_emulate_isr, NULL);
NVIC_SetPriority(
FURI_HAL_IBUTTON_TIMER_IRQ, NVIC_EncodePriority(NVIC_GetPriorityGrouping(), 5, 0));
NVIC_EnableIRQ(FURI_HAL_IBUTTON_TIMER_IRQ);
LL_TIM_SetPrescaler(FURI_HAL_IBUTTON_TIMER, 0); LL_TIM_SetPrescaler(FURI_HAL_IBUTTON_TIMER, 0);
LL_TIM_SetCounterMode(FURI_HAL_IBUTTON_TIMER, LL_TIM_COUNTERMODE_UP); LL_TIM_SetCounterMode(FURI_HAL_IBUTTON_TIMER, LL_TIM_COUNTERMODE_UP);
@ -85,7 +82,7 @@ void furi_hal_ibutton_emulate_stop() {
LL_TIM_DeInit(FURI_HAL_IBUTTON_TIMER); LL_TIM_DeInit(FURI_HAL_IBUTTON_TIMER);
FURI_CRITICAL_EXIT(); FURI_CRITICAL_EXIT();
furi_hal_interrupt_set_timer_isr(FURI_HAL_IBUTTON_TIMER, NULL); furi_hal_interrupt_set_isr(FURI_HAL_IBUTTON_TIMER_IRQ, NULL, NULL);
furi_hal_ibutton->callback = NULL; furi_hal_ibutton->callback = NULL;
furi_hal_ibutton->context = NULL; furi_hal_ibutton->context = NULL;

View File

@ -166,7 +166,7 @@ void furi_hal_infrared_async_rx_start(void) {
LL_TIM_IC_SetActiveInput(TIM2, LL_TIM_CHANNEL_CH2, LL_TIM_ACTIVEINPUT_INDIRECTTI); LL_TIM_IC_SetActiveInput(TIM2, LL_TIM_CHANNEL_CH2, LL_TIM_ACTIVEINPUT_INDIRECTTI);
LL_TIM_IC_SetPrescaler(TIM2, LL_TIM_CHANNEL_CH2, LL_TIM_ICPSC_DIV1); LL_TIM_IC_SetPrescaler(TIM2, LL_TIM_CHANNEL_CH2, LL_TIM_ICPSC_DIV1);
furi_hal_interrupt_set_timer_isr(TIM2, furi_hal_infrared_tim_rx_isr); furi_hal_interrupt_set_isr(FuriHalInterruptIdTIM2, furi_hal_infrared_tim_rx_isr, NULL);
furi_hal_infrared_state = InfraredStateAsyncRx; furi_hal_infrared_state = InfraredStateAsyncRx;
LL_TIM_EnableIT_CC1(TIM2); LL_TIM_EnableIT_CC1(TIM2);
@ -176,9 +176,6 @@ void furi_hal_infrared_async_rx_start(void) {
LL_TIM_SetCounter(TIM2, 0); LL_TIM_SetCounter(TIM2, 0);
LL_TIM_EnableCounter(TIM2); LL_TIM_EnableCounter(TIM2);
NVIC_SetPriority(TIM2_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(), 5, 0));
NVIC_EnableIRQ(TIM2_IRQn);
} }
void furi_hal_infrared_async_rx_stop(void) { void furi_hal_infrared_async_rx_stop(void) {
@ -187,7 +184,7 @@ void furi_hal_infrared_async_rx_stop(void) {
FURI_CRITICAL_ENTER(); FURI_CRITICAL_ENTER();
LL_TIM_DeInit(TIM2); LL_TIM_DeInit(TIM2);
furi_hal_interrupt_set_timer_isr(TIM2, NULL); furi_hal_interrupt_set_isr(FuriHalInterruptIdTIM2, NULL, NULL);
furi_hal_infrared_state = InfraredStateIdle; furi_hal_infrared_state = InfraredStateIdle;
FURI_CRITICAL_EXIT(); FURI_CRITICAL_EXIT();
@ -376,15 +373,15 @@ static void furi_hal_infrared_configure_tim_cmgr2_dma_tx(void) {
dma_config.PeriphRequest = LL_DMAMUX_REQ_TIM1_UP; dma_config.PeriphRequest = LL_DMAMUX_REQ_TIM1_UP;
dma_config.Priority = LL_DMA_PRIORITY_VERYHIGH; dma_config.Priority = LL_DMA_PRIORITY_VERYHIGH;
LL_DMA_Init(DMA1, LL_DMA_CHANNEL_1, &dma_config); LL_DMA_Init(DMA1, LL_DMA_CHANNEL_1, &dma_config);
furi_hal_interrupt_set_dma_channel_isr(
DMA1, LL_DMA_CHANNEL_1, furi_hal_infrared_tx_dma_polarity_isr);
LL_DMA_ClearFlag_TE1(DMA1); LL_DMA_ClearFlag_TE1(DMA1);
LL_DMA_ClearFlag_TC1(DMA1); LL_DMA_ClearFlag_TC1(DMA1);
LL_DMA_EnableIT_TE(DMA1, LL_DMA_CHANNEL_1); LL_DMA_EnableIT_TE(DMA1, LL_DMA_CHANNEL_1);
LL_DMA_EnableIT_TC(DMA1, LL_DMA_CHANNEL_1); LL_DMA_EnableIT_TC(DMA1, LL_DMA_CHANNEL_1);
NVIC_SetPriority(DMA1_Channel1_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(), 4, 0)); furi_hal_interrupt_set_isr_ex(
NVIC_EnableIRQ(DMA1_Channel1_IRQn); FuriHalInterruptIdDma1Ch1, 4, furi_hal_infrared_tx_dma_polarity_isr, NULL);
} }
static void furi_hal_infrared_configure_tim_rcr_dma_tx(void) { static void furi_hal_infrared_configure_tim_rcr_dma_tx(void) {
@ -401,16 +398,17 @@ static void furi_hal_infrared_configure_tim_rcr_dma_tx(void) {
dma_config.PeriphRequest = LL_DMAMUX_REQ_TIM1_UP; dma_config.PeriphRequest = LL_DMAMUX_REQ_TIM1_UP;
dma_config.Priority = LL_DMA_PRIORITY_MEDIUM; dma_config.Priority = LL_DMA_PRIORITY_MEDIUM;
LL_DMA_Init(DMA1, LL_DMA_CHANNEL_2, &dma_config); LL_DMA_Init(DMA1, LL_DMA_CHANNEL_2, &dma_config);
furi_hal_interrupt_set_dma_channel_isr(DMA1, LL_DMA_CHANNEL_2, furi_hal_infrared_tx_dma_isr);
LL_DMA_ClearFlag_TC2(DMA1); LL_DMA_ClearFlag_TC2(DMA1);
LL_DMA_ClearFlag_HT2(DMA1); LL_DMA_ClearFlag_HT2(DMA1);
LL_DMA_ClearFlag_TE2(DMA1); LL_DMA_ClearFlag_TE2(DMA1);
LL_DMA_EnableIT_TC(DMA1, LL_DMA_CHANNEL_2); LL_DMA_EnableIT_TC(DMA1, LL_DMA_CHANNEL_2);
LL_DMA_EnableIT_HT(DMA1, LL_DMA_CHANNEL_2); LL_DMA_EnableIT_HT(DMA1, LL_DMA_CHANNEL_2);
LL_DMA_EnableIT_TE(DMA1, LL_DMA_CHANNEL_2); LL_DMA_EnableIT_TE(DMA1, LL_DMA_CHANNEL_2);
NVIC_SetPriority(DMA1_Channel2_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(), 5, 0)); furi_hal_interrupt_set_isr_ex(
NVIC_EnableIRQ(DMA1_Channel2_IRQn); FuriHalInterruptIdDma1Ch2, 5, furi_hal_infrared_tx_dma_isr, NULL);
} }
static void furi_hal_infrared_tx_fill_buffer_last(uint8_t buf_num) { static void furi_hal_infrared_tx_fill_buffer_last(uint8_t buf_num) {
@ -551,8 +549,8 @@ static void furi_hal_infrared_async_tx_free_resources(void) {
osStatus_t status; osStatus_t status;
hal_gpio_init(&gpio_infrared_tx, GpioModeOutputOpenDrain, GpioPullDown, GpioSpeedLow); hal_gpio_init(&gpio_infrared_tx, GpioModeOutputOpenDrain, GpioPullDown, GpioSpeedLow);
furi_hal_interrupt_set_dma_channel_isr(DMA1, LL_DMA_CHANNEL_1, NULL); furi_hal_interrupt_set_isr(FuriHalInterruptIdDma1Ch1, NULL, NULL);
furi_hal_interrupt_set_dma_channel_isr(DMA1, LL_DMA_CHANNEL_2, NULL); furi_hal_interrupt_set_isr(FuriHalInterruptIdDma1Ch2, NULL, NULL);
LL_TIM_DeInit(TIM1); LL_TIM_DeInit(TIM1);
status = osSemaphoreDelete(infrared_tim_tx.stop_semaphore); status = osSemaphoreDelete(infrared_tim_tx.stop_semaphore);

View File

@ -3,153 +3,201 @@
#include <furi.h> #include <furi.h>
#include <main.h> #include <main.h>
#include <stm32wbxx.h>
#include <stm32wbxx_ll_tim.h> #include <stm32wbxx_ll_tim.h>
#define TAG "FuriHalInterrupt" #define TAG "FuriHalInterrupt"
volatile FuriHalInterruptISR furi_hal_tim_tim2_isr = NULL; #define FURI_HAL_INTERRUPT_DEFAULT_PRIORITY 5
volatile FuriHalInterruptISR furi_hal_tim_tim1_isr = NULL;
#define FURI_HAL_INTERRUPT_DMA_COUNT 2 typedef struct {
#define FURI_HAL_INTERRUPT_DMA_CHANNELS_COUNT 8 FuriHalInterruptISR isr;
void* context;
} FuriHalInterruptISRPair;
volatile FuriHalInterruptISR furi_hal_dma_channel_isr[FURI_HAL_INTERRUPT_DMA_COUNT] FuriHalInterruptISRPair furi_hal_interrupt_isr[FuriHalInterruptIdMax] = {0};
[FURI_HAL_INTERRUPT_DMA_CHANNELS_COUNT] = {0};
const IRQn_Type furi_hal_interrupt_irqn[FuriHalInterruptIdMax] = {
// TIM1, TIM16, TIM17
[FuriHalInterruptIdTim1TrgComTim17] = TIM1_TRG_COM_TIM17_IRQn,
[FuriHalInterruptIdTim1Cc] = TIM1_CC_IRQn,
[FuriHalInterruptIdTim1UpTim16] = TIM1_UP_TIM16_IRQn,
// TIM2
[FuriHalInterruptIdTIM2] = TIM2_IRQn,
// DMA1
[FuriHalInterruptIdDma1Ch1] = DMA1_Channel1_IRQn,
[FuriHalInterruptIdDma1Ch2] = DMA1_Channel2_IRQn,
[FuriHalInterruptIdDma1Ch3] = DMA1_Channel3_IRQn,
[FuriHalInterruptIdDma1Ch4] = DMA1_Channel4_IRQn,
[FuriHalInterruptIdDma1Ch5] = DMA1_Channel5_IRQn,
[FuriHalInterruptIdDma1Ch6] = DMA1_Channel6_IRQn,
[FuriHalInterruptIdDma1Ch7] = DMA1_Channel7_IRQn,
// DMA2
[FuriHalInterruptIdDma2Ch1] = DMA2_Channel1_IRQn,
[FuriHalInterruptIdDma2Ch2] = DMA2_Channel2_IRQn,
[FuriHalInterruptIdDma2Ch3] = DMA2_Channel3_IRQn,
[FuriHalInterruptIdDma2Ch4] = DMA2_Channel4_IRQn,
[FuriHalInterruptIdDma2Ch5] = DMA2_Channel5_IRQn,
[FuriHalInterruptIdDma2Ch6] = DMA2_Channel6_IRQn,
[FuriHalInterruptIdDma2Ch7] = DMA2_Channel7_IRQn,
// RCC
[FuriHalInterruptIdRcc] = RCC_IRQn,
// COMP
[FuriHalInterruptIdCOMP] = COMP_IRQn,
// HSEM
[FuriHalInterruptIdHsem] = HSEM_IRQn,
};
__attribute__((always_inline)) static inline void
furi_hal_interrupt_call(FuriHalInterruptId index) {
furi_assert(furi_hal_interrupt_isr[index].isr);
furi_hal_interrupt_isr[index].isr(furi_hal_interrupt_isr[index].context);
}
__attribute__((always_inline)) static inline void
furi_hal_interrupt_enable(FuriHalInterruptId index, uint16_t priority) {
NVIC_SetPriority(
furi_hal_interrupt_irqn[index],
NVIC_EncodePriority(NVIC_GetPriorityGrouping(), priority, 0));
NVIC_EnableIRQ(furi_hal_interrupt_irqn[index]);
}
__attribute__((always_inline)) static inline void
furi_hal_interrupt_disable(FuriHalInterruptId index) {
NVIC_DisableIRQ(furi_hal_interrupt_irqn[index]);
}
void furi_hal_interrupt_init() { void furi_hal_interrupt_init() {
NVIC_SetPriority(RCC_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(), 0, 0));
NVIC_EnableIRQ(RCC_IRQn);
NVIC_SetPriority( NVIC_SetPriority(
TAMP_STAMP_LSECSS_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(), 0, 0)); TAMP_STAMP_LSECSS_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(), 0, 0));
NVIC_EnableIRQ(TAMP_STAMP_LSECSS_IRQn); NVIC_EnableIRQ(TAMP_STAMP_LSECSS_IRQn);
NVIC_SetPriority(DMA1_Channel1_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(), 5, 0)); NVIC_SetPriority(PendSV_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(), 15, 0));
NVIC_EnableIRQ(DMA1_Channel1_IRQn);
NVIC_SetPriority(HSEM_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(), 5, 0));
HAL_NVIC_EnableIRQ(HSEM_IRQn);
FURI_LOG_I(TAG, "Init OK"); FURI_LOG_I(TAG, "Init OK");
} }
void furi_hal_interrupt_set_timer_isr(TIM_TypeDef* timer, FuriHalInterruptISR isr) { void furi_hal_interrupt_set_isr(FuriHalInterruptId index, FuriHalInterruptISR isr, void* context) {
if(timer == TIM2) { furi_hal_interrupt_set_isr_ex(index, FURI_HAL_INTERRUPT_DEFAULT_PRIORITY, isr, context);
if(isr) {
furi_assert(furi_hal_tim_tim2_isr == NULL);
} else {
furi_assert(furi_hal_tim_tim2_isr != NULL);
}
furi_hal_tim_tim2_isr = isr;
} else if(timer == TIM1) {
if(isr) {
furi_assert(furi_hal_tim_tim1_isr == NULL);
} else {
furi_assert(furi_hal_tim_tim1_isr != NULL);
}
furi_hal_tim_tim1_isr = isr;
} else {
furi_crash(NULL);
}
} }
void furi_hal_interrupt_set_dma_channel_isr( void furi_hal_interrupt_set_isr_ex(
DMA_TypeDef* dma, FuriHalInterruptId index,
uint32_t channel, uint16_t priority,
FuriHalInterruptISR isr) { FuriHalInterruptISR isr,
--channel; // Pascal void* context) {
furi_check(dma); furi_assert(index < FuriHalInterruptIdMax);
furi_check(channel < FURI_HAL_INTERRUPT_DMA_CHANNELS_COUNT); furi_assert(priority < 15);
if(dma == DMA1) { furi_assert(furi_hal_interrupt_irqn[index]);
furi_hal_dma_channel_isr[0][channel] = isr;
} else if(dma == DMA2) { if(isr) {
furi_hal_dma_channel_isr[1][channel] = isr; // Pre ISR set
furi_assert(furi_hal_interrupt_isr[index].isr == NULL);
} else { } else {
furi_crash(NULL); // Pre ISR clear
furi_assert(furi_hal_interrupt_isr[index].isr != NULL);
furi_hal_interrupt_disable(index);
}
furi_hal_interrupt_isr[index].isr = isr;
furi_hal_interrupt_isr[index].context = context;
__DMB();
if(isr) {
// Post ISR set
furi_hal_interrupt_enable(index, priority);
} else {
// Post ISR clear
} }
} }
/* Timer 2 */ /* Timer 2 */
void TIM2_IRQHandler(void) { void TIM2_IRQHandler(void) {
if(furi_hal_tim_tim2_isr) { furi_hal_interrupt_call(FuriHalInterruptIdTIM2);
furi_hal_tim_tim2_isr();
}
} }
/* Timer 1 Update */ /* Timer 1 Update */
void TIM1_UP_TIM16_IRQHandler(void) { void TIM1_UP_TIM16_IRQHandler(void) {
if(furi_hal_tim_tim1_isr) { furi_hal_interrupt_call(FuriHalInterruptIdTim1UpTim16);
furi_hal_tim_tim1_isr();
}
} }
void TIM1_TRG_COM_TIM17_IRQHandler(void) { void TIM1_TRG_COM_TIM17_IRQHandler(void) {
furi_hal_interrupt_call(FuriHalInterruptIdTim1TrgComTim17);
} }
void TIM1_CC_IRQHandler(void) { void TIM1_CC_IRQHandler(void) {
furi_hal_interrupt_call(FuriHalInterruptIdTim1Cc);
} }
/* DMA 1 */ /* DMA 1 */
void DMA1_Channel1_IRQHandler(void) { void DMA1_Channel1_IRQHandler(void) {
if(furi_hal_dma_channel_isr[0][0]) furi_hal_dma_channel_isr[0][0](); furi_hal_interrupt_call(FuriHalInterruptIdDma1Ch1);
} }
void DMA1_Channel2_IRQHandler(void) { void DMA1_Channel2_IRQHandler(void) {
if(furi_hal_dma_channel_isr[0][1]) furi_hal_dma_channel_isr[0][1](); furi_hal_interrupt_call(FuriHalInterruptIdDma1Ch2);
} }
void DMA1_Channel3_IRQHandler(void) { void DMA1_Channel3_IRQHandler(void) {
if(furi_hal_dma_channel_isr[0][2]) furi_hal_dma_channel_isr[0][2](); furi_hal_interrupt_call(FuriHalInterruptIdDma1Ch3);
} }
void DMA1_Channel4_IRQHandler(void) { void DMA1_Channel4_IRQHandler(void) {
if(furi_hal_dma_channel_isr[0][3]) furi_hal_dma_channel_isr[0][3](); furi_hal_interrupt_call(FuriHalInterruptIdDma1Ch4);
} }
void DMA1_Channel5_IRQHandler(void) { void DMA1_Channel5_IRQHandler(void) {
if(furi_hal_dma_channel_isr[0][4]) furi_hal_dma_channel_isr[0][4](); furi_hal_interrupt_call(FuriHalInterruptIdDma1Ch5);
} }
void DMA1_Channel6_IRQHandler(void) { void DMA1_Channel6_IRQHandler(void) {
if(furi_hal_dma_channel_isr[0][5]) furi_hal_dma_channel_isr[0][5](); furi_hal_interrupt_call(FuriHalInterruptIdDma1Ch6);
} }
void DMA1_Channel7_IRQHandler(void) { void DMA1_Channel7_IRQHandler(void) {
if(furi_hal_dma_channel_isr[0][6]) furi_hal_dma_channel_isr[0][6](); furi_hal_interrupt_call(FuriHalInterruptIdDma1Ch7);
}
void DMA1_Channel8_IRQHandler(void) {
if(furi_hal_dma_channel_isr[0][7]) furi_hal_dma_channel_isr[0][7]();
} }
/* DMA 2 */ /* DMA 2 */
void DMA2_Channel1_IRQHandler(void) { void DMA2_Channel1_IRQHandler(void) {
if(furi_hal_dma_channel_isr[1][0]) furi_hal_dma_channel_isr[1][0](); furi_hal_interrupt_call(FuriHalInterruptIdDma2Ch1);
} }
void DMA2_Channel2_IRQHandler(void) { void DMA2_Channel2_IRQHandler(void) {
if(furi_hal_dma_channel_isr[1][1]) furi_hal_dma_channel_isr[1][1](); furi_hal_interrupt_call(FuriHalInterruptIdDma2Ch2);
} }
void DMA2_Channel3_IRQHandler(void) { void DMA2_Channel3_IRQHandler(void) {
if(furi_hal_dma_channel_isr[1][2]) furi_hal_dma_channel_isr[1][2](); furi_hal_interrupt_call(FuriHalInterruptIdDma2Ch3);
} }
void DMA2_Channel4_IRQHandler(void) { void DMA2_Channel4_IRQHandler(void) {
if(furi_hal_dma_channel_isr[1][3]) furi_hal_dma_channel_isr[1][3](); furi_hal_interrupt_call(FuriHalInterruptIdDma2Ch4);
} }
void DMA2_Channel5_IRQHandler(void) { void DMA2_Channel5_IRQHandler(void) {
if(furi_hal_dma_channel_isr[1][4]) furi_hal_dma_channel_isr[1][4](); furi_hal_interrupt_call(FuriHalInterruptIdDma2Ch5);
} }
void DMA2_Channel6_IRQHandler(void) { void DMA2_Channel6_IRQHandler(void) {
if(furi_hal_dma_channel_isr[1][5]) furi_hal_dma_channel_isr[1][5](); furi_hal_interrupt_call(FuriHalInterruptIdDma2Ch6);
} }
void DMA2_Channel7_IRQHandler(void) { void DMA2_Channel7_IRQHandler(void) {
if(furi_hal_dma_channel_isr[1][6]) furi_hal_dma_channel_isr[1][6](); furi_hal_interrupt_call(FuriHalInterruptIdDma2Ch7);
} }
void DMA2_Channel8_IRQHandler(void) { void HSEM_IRQHandler(void) {
if(furi_hal_dma_channel_isr[1][7]) furi_hal_dma_channel_isr[1][7](); furi_hal_interrupt_call(FuriHalInterruptIdHsem);
} }
void TAMP_STAMP_LSECSS_IRQHandler(void) { void TAMP_STAMP_LSECSS_IRQHandler(void) {
@ -165,6 +213,7 @@ void TAMP_STAMP_LSECSS_IRQHandler(void) {
} }
void RCC_IRQHandler(void) { void RCC_IRQHandler(void) {
furi_hal_interrupt_call(FuriHalInterruptIdRcc);
} }
void NMI_Handler(void) { void NMI_Handler(void) {
@ -193,3 +242,26 @@ void UsageFault_Handler(void) {
void DebugMon_Handler(void) { void DebugMon_Handler(void) {
} }
#include "usbd_core.h"
extern usbd_device udev;
extern void HW_IPCC_Tx_Handler();
extern void HW_IPCC_Rx_Handler();
void SysTick_Handler(void) {
HAL_IncTick();
}
void USB_LP_IRQHandler(void) {
usbd_poll(&udev);
}
void IPCC_C1_TX_IRQHandler(void) {
HW_IPCC_Tx_Handler();
}
void IPCC_C1_RX_IRQHandler(void) {
HW_IPCC_Rx_Handler();
}

View File

@ -7,29 +7,71 @@ extern "C" {
#endif #endif
/** Timer ISR */ /** Timer ISR */
typedef void (*FuriHalInterruptISR)(); typedef void (*FuriHalInterruptISR)(void* context);
typedef enum {
// TIM1, TIM16, TIM17
FuriHalInterruptIdTim1TrgComTim17,
FuriHalInterruptIdTim1Cc,
FuriHalInterruptIdTim1UpTim16,
// TIM2
FuriHalInterruptIdTIM2,
// DMA1
FuriHalInterruptIdDma1Ch1,
FuriHalInterruptIdDma1Ch2,
FuriHalInterruptIdDma1Ch3,
FuriHalInterruptIdDma1Ch4,
FuriHalInterruptIdDma1Ch5,
FuriHalInterruptIdDma1Ch6,
FuriHalInterruptIdDma1Ch7,
// DMA2
FuriHalInterruptIdDma2Ch1,
FuriHalInterruptIdDma2Ch2,
FuriHalInterruptIdDma2Ch3,
FuriHalInterruptIdDma2Ch4,
FuriHalInterruptIdDma2Ch5,
FuriHalInterruptIdDma2Ch6,
FuriHalInterruptIdDma2Ch7,
// RCC
FuriHalInterruptIdRcc,
// Comp
FuriHalInterruptIdCOMP,
// HSEM
FuriHalInterruptIdHsem,
// Service value
FuriHalInterruptIdMax,
} FuriHalInterruptId;
/** Initialize interrupt subsystem */ /** Initialize interrupt subsystem */
void furi_hal_interrupt_init(); void furi_hal_interrupt_init();
/** Set DMA Channel ISR /** Set ISR and enable interrupt with default priority
* We don't clear interrupt flags for you, do it by your self. * We don't clear interrupt flags for you, do it by your self.
* @param dma - DMA instance * @param index - interrupt ID
* @param channel - DMA channel
* @param isr - your interrupt service routine or use NULL to clear * @param isr - your interrupt service routine or use NULL to clear
* @param context - isr context
*/ */
void furi_hal_interrupt_set_dma_channel_isr( void furi_hal_interrupt_set_isr(FuriHalInterruptId index, FuriHalInterruptISR isr, void* context);
DMA_TypeDef* dma,
uint32_t channel,
FuriHalInterruptISR isr);
/** Set Timer ISR /** Set ISR and enable interrupt with custom priority
* By default ISR is serviced by ST HAL. Use this function to override it.
* We don't clear interrupt flags for you, do it by your self. * We don't clear interrupt flags for you, do it by your self.
* @param timer - timer instance * @param index - interrupt ID
* @param priority - 0 to 15, 0 highest
* @param isr - your interrupt service routine or use NULL to clear * @param isr - your interrupt service routine or use NULL to clear
* @param context - isr context
*/ */
void furi_hal_interrupt_set_timer_isr(TIM_TypeDef* timer, FuriHalInterruptISR isr); void furi_hal_interrupt_set_isr_ex(
FuriHalInterruptId index,
uint16_t priority,
FuriHalInterruptISR isr,
void* context);
#ifdef __cplusplus #ifdef __cplusplus
} }

View File

@ -115,11 +115,11 @@ void vPortSuppressTicksAndSleep(TickType_t expected_idle_ticks) {
} }
// Stop IRQ handling, no one should disturb us till we finish // Stop IRQ handling, no one should disturb us till we finish
FURI_CRITICAL_ENTER(); __disable_irq();
// Confirm OS that sleep is still possible // Confirm OS that sleep is still possible
if(eTaskConfirmSleepModeStatus() == eAbortSleep) { if(eTaskConfirmSleepModeStatus() == eAbortSleep) {
FURI_CRITICAL_EXIT(); __enable_irq();
return; return;
} }
@ -136,7 +136,7 @@ void vPortSuppressTicksAndSleep(TickType_t expected_idle_ticks) {
} }
// Reenable IRQ // Reenable IRQ
FURI_CRITICAL_EXIT(); __enable_irq();
} }
void vApplicationStackOverflowHook(TaskHandle_t xTask, char* pcTaskName) { void vApplicationStackOverflowHook(TaskHandle_t xTask, char* pcTaskName) {

View File

@ -2,41 +2,6 @@
#include "main.h" #include "main.h"
#include <furi.h> #include <furi.h>
const InputPin input_pins[] = {
{.port = BUTTON_UP_GPIO_Port,
.pin = BUTTON_UP_Pin,
.key = InputKeyUp,
.inverted = true,
.name = "Up"},
{.port = BUTTON_DOWN_GPIO_Port,
.pin = BUTTON_DOWN_Pin,
.key = InputKeyDown,
.inverted = true,
.name = "Down"},
{.port = BUTTON_RIGHT_GPIO_Port,
.pin = BUTTON_RIGHT_Pin,
.key = InputKeyRight,
.inverted = true,
.name = "Right"},
{.port = BUTTON_LEFT_GPIO_Port,
.pin = BUTTON_LEFT_Pin,
.key = InputKeyLeft,
.inverted = true,
.name = "Left"},
{.port = BUTTON_OK_GPIO_Port,
.pin = BUTTON_OK_Pin,
.key = InputKeyOk,
.inverted = false,
.name = "Ok"},
{.port = BUTTON_BACK_GPIO_Port,
.pin = BUTTON_BACK_Pin,
.key = InputKeyBack,
.inverted = true,
.name = "Back"},
};
const size_t input_pins_count = sizeof(input_pins) / sizeof(InputPin);
const GpioPin vibro_gpio = {.port = VIBRO_GPIO_Port, .pin = VIBRO_Pin}; const GpioPin vibro_gpio = {.port = VIBRO_GPIO_Port, .pin = VIBRO_Pin};
const GpioPin ibutton_gpio = {.port = iBTN_GPIO_Port, .pin = iBTN_Pin}; const GpioPin ibutton_gpio = {.port = iBTN_GPIO_Port, .pin = iBTN_Pin};
@ -81,3 +46,21 @@ const GpioPin gpio_i2c_power_sda = {.port = GPIOA, .pin = LL_GPIO_PIN_10};
const GpioPin gpio_i2c_power_scl = {.port = GPIOA, .pin = LL_GPIO_PIN_9}; const GpioPin gpio_i2c_power_scl = {.port = GPIOA, .pin = LL_GPIO_PIN_9};
const GpioPin gpio_speaker = {.port = GPIOB, .pin = LL_GPIO_PIN_8}; const GpioPin gpio_speaker = {.port = GPIOB, .pin = LL_GPIO_PIN_8};
const GpioPin gpio_button_up = {.port = GPIOB, .pin = LL_GPIO_PIN_10};
const GpioPin gpio_button_down = {.port = GPIOC, .pin = LL_GPIO_PIN_6};
const GpioPin gpio_button_right = {.port = GPIOB, .pin = LL_GPIO_PIN_12};
const GpioPin gpio_button_left = {.port = GPIOB, .pin = LL_GPIO_PIN_11};
const GpioPin gpio_button_ok = {.port = GPIOH, .pin = LL_GPIO_PIN_3};
const GpioPin gpio_button_back = {.port = GPIOC, .pin = LL_GPIO_PIN_13};
const InputPin input_pins[] = {
{.pin = &gpio_button_up, .key = InputKeyUp, .inverted = true, .name = "Up"},
{.pin = &gpio_button_down, .key = InputKeyDown, .inverted = true, .name = "Down"},
{.pin = &gpio_button_right, .key = InputKeyRight, .inverted = true, .name = "Right"},
{.pin = &gpio_button_left, .key = InputKeyLeft, .inverted = true, .name = "Left"},
{.pin = &gpio_button_ok, .key = InputKeyOk, .inverted = false, .name = "Ok"},
{.pin = &gpio_button_back, .key = InputKeyBack, .inverted = true, .name = "Back"},
};
const size_t input_pins_count = sizeof(input_pins) / sizeof(InputPin);

View File

@ -32,16 +32,12 @@ typedef enum {
} Light; } Light;
typedef struct { typedef struct {
const GPIO_TypeDef* port; const GpioPin* pin;
const uint16_t pin;
const InputKey key; const InputKey key;
const bool inverted; const bool inverted;
const char* name; const char* name;
} InputPin; } InputPin;
extern const InputPin input_pins[];
extern const size_t input_pins_count;
extern const GpioPin vibro_gpio; extern const GpioPin vibro_gpio;
extern const GpioPin ibutton_gpio; extern const GpioPin ibutton_gpio;
@ -86,6 +82,10 @@ extern const GpioPin gpio_i2c_power_scl;
extern const GpioPin gpio_speaker; extern const GpioPin gpio_speaker;
// Input pins
extern const InputPin input_pins[];
extern const size_t input_pins_count;
#ifdef __cplusplus #ifdef __cplusplus
} }
#endif #endif

View File

@ -13,7 +13,7 @@
#define FURI_HAL_RFID_READ_TIMER_CHANNEL_CONFIG LL_TIM_CHANNEL_CH1 #define FURI_HAL_RFID_READ_TIMER_CHANNEL_CONFIG LL_TIM_CHANNEL_CH1
#define FURI_HAL_RFID_EMULATE_TIMER TIM2 #define FURI_HAL_RFID_EMULATE_TIMER TIM2
#define FURI_HAL_RFID_EMULATE_TIMER_IRQ TIM2_IRQn #define FURI_HAL_RFID_EMULATE_TIMER_IRQ FuriHalInterruptIdTIM2
#define FURI_HAL_RFID_EMULATE_TIMER_CHANNEL LL_TIM_CHANNEL_CH3 #define FURI_HAL_RFID_EMULATE_TIMER_CHANNEL LL_TIM_CHANNEL_CH3
typedef struct { typedef struct {
@ -194,15 +194,7 @@ void furi_hal_rfid_tim_emulate_start(FuriHalRfidEmulateCallback callback, void*
furi_hal_rfid->callback = callback; furi_hal_rfid->callback = callback;
furi_hal_rfid->context = context; furi_hal_rfid->context = context;
// TODO make api for interrupts priority furi_hal_interrupt_set_isr(FURI_HAL_RFID_EMULATE_TIMER_IRQ, furi_hal_rfid_emulate_isr, NULL);
for(size_t i = WWDG_IRQn; i <= DMAMUX1_OVR_IRQn; i++) {
HAL_NVIC_SetPriority(i, 15, 0);
}
furi_hal_interrupt_set_timer_isr(FURI_HAL_RFID_EMULATE_TIMER, furi_hal_rfid_emulate_isr);
NVIC_SetPriority(
FURI_HAL_RFID_EMULATE_TIMER_IRQ, NVIC_EncodePriority(NVIC_GetPriorityGrouping(), 5, 0));
NVIC_EnableIRQ(FURI_HAL_RFID_EMULATE_TIMER_IRQ);
LL_TIM_EnableIT_UPDATE(FURI_HAL_RFID_EMULATE_TIMER); LL_TIM_EnableIT_UPDATE(FURI_HAL_RFID_EMULATE_TIMER);
LL_TIM_EnableAllOutputs(FURI_HAL_RFID_EMULATE_TIMER); LL_TIM_EnableAllOutputs(FURI_HAL_RFID_EMULATE_TIMER);
@ -212,7 +204,7 @@ void furi_hal_rfid_tim_emulate_start(FuriHalRfidEmulateCallback callback, void*
void furi_hal_rfid_tim_emulate_stop() { void furi_hal_rfid_tim_emulate_stop() {
LL_TIM_DisableCounter(FURI_HAL_RFID_EMULATE_TIMER); LL_TIM_DisableCounter(FURI_HAL_RFID_EMULATE_TIMER);
LL_TIM_DisableAllOutputs(FURI_HAL_RFID_EMULATE_TIMER); LL_TIM_DisableAllOutputs(FURI_HAL_RFID_EMULATE_TIMER);
furi_hal_interrupt_set_timer_isr(FURI_HAL_RFID_EMULATE_TIMER, NULL); furi_hal_interrupt_set_isr(FURI_HAL_RFID_EMULATE_TIMER_IRQ, NULL, NULL);
} }
void furi_hal_rfid_tim_reset() { void furi_hal_rfid_tim_reset() {

View File

@ -722,9 +722,7 @@ void furi_hal_subghz_start_async_rx(FuriHalSubGhzCaptureCallback callback, void*
LL_TIM_IC_SetFilter(TIM2, LL_TIM_CHANNEL_CH2, LL_TIM_IC_FILTER_FDIV32_N8); LL_TIM_IC_SetFilter(TIM2, LL_TIM_CHANNEL_CH2, LL_TIM_IC_FILTER_FDIV32_N8);
// ISR setup // ISR setup
furi_hal_interrupt_set_timer_isr(TIM2, furi_hal_subghz_capture_ISR); furi_hal_interrupt_set_isr(FuriHalInterruptIdTIM2, furi_hal_subghz_capture_ISR, NULL);
NVIC_SetPriority(TIM2_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(), 5, 0));
NVIC_EnableIRQ(TIM2_IRQn);
// Interrupts and channels // Interrupts and channels
LL_TIM_EnableIT_CC1(TIM2); LL_TIM_EnableIT_CC1(TIM2);
@ -750,7 +748,7 @@ void furi_hal_subghz_stop_async_rx() {
FURI_CRITICAL_ENTER(); FURI_CRITICAL_ENTER();
LL_TIM_DeInit(TIM2); LL_TIM_DeInit(TIM2);
FURI_CRITICAL_EXIT(); FURI_CRITICAL_EXIT();
furi_hal_interrupt_set_timer_isr(TIM2, NULL); furi_hal_interrupt_set_isr(FuriHalInterruptIdTIM2, NULL, NULL);
hal_gpio_init(&gpio_cc1101_g0, GpioModeAnalog, GpioPullNo, GpioSpeedLow); hal_gpio_init(&gpio_cc1101_g0, GpioModeAnalog, GpioPullNo, GpioSpeedLow);
} }
@ -887,8 +885,7 @@ bool furi_hal_subghz_start_async_tx(FuriHalSubGhzAsyncTxCallback callback, void*
dma_config.PeriphRequest = LL_DMAMUX_REQ_TIM2_UP; dma_config.PeriphRequest = LL_DMAMUX_REQ_TIM2_UP;
dma_config.Priority = LL_DMA_MODE_NORMAL; dma_config.Priority = LL_DMA_MODE_NORMAL;
LL_DMA_Init(DMA1, LL_DMA_CHANNEL_1, &dma_config); LL_DMA_Init(DMA1, LL_DMA_CHANNEL_1, &dma_config);
furi_hal_interrupt_set_dma_channel_isr( furi_hal_interrupt_set_isr(FuriHalInterruptIdDma1Ch1, furi_hal_subghz_async_tx_dma_isr, NULL);
DMA1, LL_DMA_CHANNEL_1, furi_hal_subghz_async_tx_dma_isr);
LL_DMA_EnableIT_TC(DMA1, LL_DMA_CHANNEL_1); LL_DMA_EnableIT_TC(DMA1, LL_DMA_CHANNEL_1);
LL_DMA_EnableIT_HT(DMA1, LL_DMA_CHANNEL_1); LL_DMA_EnableIT_HT(DMA1, LL_DMA_CHANNEL_1);
LL_DMA_EnableChannel(DMA1, LL_DMA_CHANNEL_1); LL_DMA_EnableChannel(DMA1, LL_DMA_CHANNEL_1);
@ -914,9 +911,7 @@ bool furi_hal_subghz_start_async_tx(FuriHalSubGhzAsyncTxCallback callback, void*
LL_TIM_OC_DisableFast(TIM2, LL_TIM_CHANNEL_CH2); LL_TIM_OC_DisableFast(TIM2, LL_TIM_CHANNEL_CH2);
LL_TIM_DisableMasterSlaveMode(TIM2); LL_TIM_DisableMasterSlaveMode(TIM2);
furi_hal_interrupt_set_timer_isr(TIM2, furi_hal_subghz_async_tx_timer_isr); furi_hal_interrupt_set_isr(FuriHalInterruptIdTIM2, furi_hal_subghz_async_tx_timer_isr, NULL);
NVIC_SetPriority(TIM2_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(), 5, 0));
NVIC_EnableIRQ(TIM2_IRQn);
LL_TIM_EnableIT_UPDATE(TIM2); LL_TIM_EnableIT_UPDATE(TIM2);
LL_TIM_EnableDMAReq_UPDATE(TIM2); LL_TIM_EnableDMAReq_UPDATE(TIM2);
@ -953,11 +948,12 @@ void furi_hal_subghz_stop_async_tx() {
// Deinitialize Timer // Deinitialize Timer
FURI_CRITICAL_ENTER(); FURI_CRITICAL_ENTER();
LL_TIM_DeInit(TIM2); LL_TIM_DeInit(TIM2);
furi_hal_interrupt_set_timer_isr(TIM2, NULL); furi_hal_interrupt_set_isr(FuriHalInterruptIdTIM2, NULL, NULL);
// Deinitialize DMA // Deinitialize DMA
LL_DMA_DeInit(DMA1, LL_DMA_CHANNEL_1); LL_DMA_DeInit(DMA1, LL_DMA_CHANNEL_1);
furi_hal_interrupt_set_dma_channel_isr(DMA1, LL_DMA_CHANNEL_1, NULL);
furi_hal_interrupt_set_isr(FuriHalInterruptIdDma1Ch1, NULL, NULL);
// Deinitialize GPIO // Deinitialize GPIO
hal_gpio_init(&gpio_cc1101_g0, GpioModeAnalog, GpioPullNo, GpioSpeedLow); hal_gpio_init(&gpio_cc1101_g0, GpioModeAnalog, GpioPullNo, GpioSpeedLow);

View File

@ -1,53 +0,0 @@
#include "furi_hal_task.h"
//-----------------------------cmsis_os2.c-------------------------------
// helpers to get isr context
// get arch
#ifndef __ARM_ARCH_6M__
#define __ARM_ARCH_6M__ 0
#endif
#ifndef __ARM_ARCH_7M__
#define __ARM_ARCH_7M__ 0
#endif
#ifndef __ARM_ARCH_7EM__
#define __ARM_ARCH_7EM__ 0
#endif
#ifndef __ARM_ARCH_8M_MAIN__
#define __ARM_ARCH_8M_MAIN__ 0
#endif
#ifndef __ARM_ARCH_7A__
#define __ARM_ARCH_7A__ 0
#endif
// get masks
#if((__ARM_ARCH_7M__ == 1U) || (__ARM_ARCH_7EM__ == 1U) || (__ARM_ARCH_8M_MAIN__ == 1U))
#define IS_IRQ_MASKED() ((__get_PRIMASK() != 0U) || (__get_BASEPRI() != 0U))
#elif(__ARM_ARCH_6M__ == 1U)
#define IS_IRQ_MASKED() (__get_PRIMASK() != 0U)
#elif(__ARM_ARCH_7A__ == 1U)
/* CPSR mask bits */
#define CPSR_MASKBIT_I 0x80U
#define IS_IRQ_MASKED() ((__get_CPSR() & CPSR_MASKBIT_I) != 0U)
#else
#define IS_IRQ_MASKED() (__get_PRIMASK() != 0U)
#endif
// get is irq mode
#if(__ARM_ARCH_7A__ == 1U)
/* CPSR mode bitmasks */
#define CPSR_MODE_USER 0x10U
#define CPSR_MODE_SYSTEM 0x1FU
#define IS_IRQ_MODE() ((__get_mode() != CPSR_MODE_USER) && (__get_mode() != CPSR_MODE_SYSTEM))
#else
#define IS_IRQ_MODE() (__get_IPSR() != 0U)
#endif
// added osKernelGetState(), because KernelState is a static var
#define IS_IRQ() (IS_IRQ_MODE() || (IS_IRQ_MASKED() && (osKernelGetState() == osKernelRunning)))
//-------------------------end of cmsis_os2.c----------------------------
bool task_is_isr_context(void) {
return IS_IRQ();
}

View File

@ -1,12 +0,0 @@
#pragma once
#include "main.h"
#include <cmsis_os2.h>
#include <stdbool.h>
// Task stack size in bytes
#define DEFAULT_STACK_SIZE 4096
// Max system tasks count
#define MAX_TASK_COUNT 14
bool task_is_isr_context(void);

View File

@ -55,8 +55,6 @@ C_SOURCES += \
$(CUBE_DIR)/Drivers/STM32WBxx_HAL_Driver/Src/stm32wbxx_hal_cryp.c \ $(CUBE_DIR)/Drivers/STM32WBxx_HAL_Driver/Src/stm32wbxx_hal_cryp.c \
$(CUBE_DIR)/Drivers/STM32WBxx_HAL_Driver/Src/stm32wbxx_hal_exti.c \ $(CUBE_DIR)/Drivers/STM32WBxx_HAL_Driver/Src/stm32wbxx_hal_exti.c \
$(CUBE_DIR)/Drivers/STM32WBxx_HAL_Driver/Src/stm32wbxx_hal_gpio.c \ $(CUBE_DIR)/Drivers/STM32WBxx_HAL_Driver/Src/stm32wbxx_hal_gpio.c \
$(CUBE_DIR)/Drivers/STM32WBxx_HAL_Driver/Src/stm32wbxx_hal_hsem.c \
$(CUBE_DIR)/Drivers/STM32WBxx_HAL_Driver/Src/stm32wbxx_hal_ipcc.c \
$(CUBE_DIR)/Drivers/STM32WBxx_HAL_Driver/Src/stm32wbxx_hal_pcd.c \ $(CUBE_DIR)/Drivers/STM32WBxx_HAL_Driver/Src/stm32wbxx_hal_pcd.c \
$(CUBE_DIR)/Drivers/STM32WBxx_HAL_Driver/Src/stm32wbxx_hal_pcd_ex.c \ $(CUBE_DIR)/Drivers/STM32WBxx_HAL_Driver/Src/stm32wbxx_hal_pcd_ex.c \
$(CUBE_DIR)/Drivers/STM32WBxx_HAL_Driver/Src/stm32wbxx_hal_pwr.c \ $(CUBE_DIR)/Drivers/STM32WBxx_HAL_Driver/Src/stm32wbxx_hal_pwr.c \

View File

@ -22,7 +22,6 @@ template <unsigned int N> struct STOP_EXTERNING_ME {};
#include "furi_hal_gpio.h" #include "furi_hal_gpio.h"
#include "furi_hal_light.h" #include "furi_hal_light.h"
#include "furi_hal_delay.h" #include "furi_hal_delay.h"
#include "furi_hal_task.h"
#include "furi_hal_power.h" #include "furi_hal_power.h"
#include "furi_hal_vcp.h" #include "furi_hal_vcp.h"
#include "furi_hal_interrupt.h" #include "furi_hal_interrupt.h"

View File

@ -87,18 +87,11 @@ void platformUnprotectST25RComm();
#define platformUnprotectST25RIrqStatus() \ #define platformUnprotectST25RIrqStatus() \
platformUnprotectST25RComm() /*!< Unprotect the IRQ status var - IRQ enable on a single thread environment (MCU) ; Mutex unlock on a multi thread environment */ platformUnprotectST25RComm() /*!< Unprotect the IRQ status var - IRQ enable on a single thread environment (MCU) ; Mutex unlock on a multi thread environment */
#define platformGpioSet(port, pin) \ #define platformGpioSet(port, pin) LL_GPIO_SetOutputPin(port, pin)
HAL_GPIO_WritePin(port, pin, GPIO_PIN_SET) /*!< Turns the given GPIO High */
#define platformGpioClear(port, pin) \ #define platformGpioClear(port, pin) LL_GPIO_ResetOutputPin(port, pin)
HAL_GPIO_WritePin( \
port, pin, GPIO_PIN_RESET) /*!< Turns the given GPIO Low */ #define platformGpioIsHigh(port, pin) LL_GPIO_IsInputPinSet(port, pin)
#define platformGpioToogle(port, pin) \
HAL_GPIO_TogglePin(port, pin) /*!< Toogles the given GPIO */
#define platformGpioIsHigh(port, pin) \
(HAL_GPIO_ReadPin(port, pin) == \
GPIO_PIN_SET) /*!< Checks if the given LED is High */
#define platformGpioIsLow(port, pin) \
(!platformGpioIsHigh(port, pin)) /*!< Checks if the given LED is Low */
#define platformTimerCreate(t) \ #define platformTimerCreate(t) \
timerCalculateTimer(t) /*!< Create a timer with the given time (ms) */ timerCalculateTimer(t) /*!< Create a timer with the given time (ms) */