Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add ADC and timer for mcu stm32wbaxx #328

Merged
merged 2 commits into from
Jun 18, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
45 changes: 23 additions & 22 deletions hal_st/stm32fxxx/AdcDmaStm.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -11,41 +11,42 @@ namespace hal
TransferDone();
})
, analogPin(pin)
#if defined(STM32G0)
, timer(3, timing, { TimerBaseStm::CounterMode::up, infra::MakeOptional<TimerBaseStm::Trigger>({ TimerBaseStm::Trigger::TriggerOutput::update, false }) })
#else
#ifdef TIM2
, timer(2, timing, { TimerBaseStm::CounterMode::up, infra::MakeOptional<TimerBaseStm::Trigger>({ TimerBaseStm::Trigger::TriggerOutput::update, false }) })
#else
, timer(3, timing, { TimerBaseStm::CounterMode::up, infra::MakeOptional<TimerBaseStm::Trigger>({ TimerBaseStm::Trigger::TriggerOutput::update, false }) })
#endif
{
ADC_ChannelConfTypeDef channelConfig;
ADC_ChannelConfTypeDef channelConfig{};
channelConfig.Channel = adc.Channel(analogPin);
#if !defined(STM32WB)
#ifdef ADC_REGULAR_RANK_1
channelConfig.Rank = ADC_REGULAR_RANK_1;
#else
channelConfig.Rank = 1;
#endif

#ifdef ADC_SMPR_SMP1
channelConfig.SamplingTime = ADC_SAMPLINGTIME_COMMON_1;
#else
channelConfig.Rank = ADC_REGULAR_RANK_1;
channelConfig.SamplingTime = hal::detail::AdcStmChannelConfig().samplingTime;
#endif
#if defined(STM32F0) || defined(STM32F3)
channelConfig.SamplingTime = ADC_SAMPLETIME_7CYCLES_5;
#elif defined(STM32WB)
channelConfig.SingleDiff = ADC_SINGLE_ENDED;
channelConfig.SamplingTime = ADC_SAMPLETIME_92CYCLES_5;
channelConfig.Offset = 0;
#ifdef ADC_OFFSET_NONE
channelConfig.OffsetNumber = ADC_OFFSET_NONE;
#elif defined(STM32G0)
channelConfig.SamplingTime = ADC_SAMPLETIME_3CYCLES_5;
#elif defined(STM32G4)
channelConfig.SamplingTime = ADC_SAMPLETIME_3CYCLES_5;
channelConfig.Offset = 0;
#else
channelConfig.SamplingTime = ADC_SAMPLETIME_3CYCLES;
#endif
#ifdef ADC_SINGLE_ENDED
channelConfig.SingleDiff = ADC_SINGLE_ENDED;
#endif
#ifdef ADC_OFFSET_1
channelConfig.Offset = 0;
#endif
ReconfigureTrigger();

auto result = HAL_ADC_ConfigChannel(&adc.Handle(), &channelConfig);
assert(result == HAL_OK);

#ifdef ADC_SINGLE_ENDED
result = HAL_ADCEx_Calibration_Start(&adc.Handle(), ADC_SINGLE_ENDED);
#endif
assert(result == HAL_OK);
}

Expand All @@ -63,14 +64,14 @@ namespace hal
{
HAL_ADC_Stop(&adc.Handle());

#if defined(STM32F4) || defined(STM32F7)
#if defined(ADC_EXTERNALTRIGCONV_T2_TRGO)
LL_ADC_REG_SetTriggerSource(adc.Handle().Instance, ADC_EXTERNALTRIGCONV_T2_TRGO);
#elif defined(STM32G0)
#elif defined(ADC_EXTERNALTRIG_T3_TRGO)
LL_ADC_REG_SetTriggerSource(adc.Handle().Instance, ADC_EXTERNALTRIG_T3_TRGO);
#else
LL_ADC_REG_SetTriggerSource(adc.Handle().Instance, ADC_EXTERNALTRIG_T2_TRGO);
#endif
LL_ADC_REG_SetTriggerEdge(adc.Handle().Instance, LL_ADC_REG_TRIG_EXT_RISING);
LL_ADC_REG_SetTriggerEdge(adc.Handle().Instance, ADC_EXTERNALTRIGCONVEDGE_RISING);
}

void AdcTriggeredByTimerWithDma::Configure()
Expand Down
65 changes: 35 additions & 30 deletions hal_st/stm32fxxx/AnalogToDigitalPinStm.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -38,34 +38,37 @@ namespace

namespace hal
{
AnalogToDigitalPinImplStm::AnalogToDigitalPinImplStm(hal::GpioPinStm& pin, AdcStm& adc)
AnalogToDigitalPinImplStm::AnalogToDigitalPinImplStm(hal::GpioPinStm& pin, AdcStm& adc, const Config& config)
: analogPin(pin)
, adc(adc)
, config(config)
{
HAL_ADC_Stop(&adc.Handle());
LL_ADC_REG_SetTriggerSource(adc.Handle().Instance, ADC_SOFTWARE_START);
}

void AnalogToDigitalPinImplStm::Measure(std::size_t numberOfSamples, const infra::Function<void(infra::MemoryRange<uint16_t>)>& onDone)
{
ADC_ChannelConfTypeDef channelConfig;
ADC_ChannelConfTypeDef channelConfig{};
channelConfig.Channel = adc.Channel(analogPin);
#if defined(STM32WB) || defined(STM32G0) || defined(STM32G4)

#ifdef ADC_REGULAR_RANK_1
channelConfig.Rank = ADC_REGULAR_RANK_1;
#else
channelConfig.Rank = 1;
#endif
#if defined(STM32F0) || defined(STM32F3)
channelConfig.SamplingTime = ADC_SAMPLETIME_7CYCLES_5;
#elif defined(STM32WB) || defined(STM32G4)
channelConfig.SamplingTime = ADC_SAMPLETIME_2CYCLES_5;
channelConfig.Offset = 0;
#ifdef ADC_SMPR_SMP1
channelConfig.SamplingTime = ADC_SAMPLINGTIME_COMMON_1;
#else
channelConfig.SamplingTime = config.samplingTime;
#endif
#ifdef ADC_OFFSET_NONE
channelConfig.OffsetNumber = ADC_OFFSET_NONE;
#endif
#ifdef ADC_SINGLE_ENDED
channelConfig.SingleDiff = ADC_SINGLE_ENDED;
#elif defined(STM32G0) || defined(STM32WBA)
channelConfig.SamplingTime = ADC_SAMPLETIME_3CYCLES_5;
#else
channelConfig.SamplingTime = ADC_SAMPLETIME_3CYCLES;
#endif
#ifdef ADC_OFFSET_1
channelConfig.Offset = 0;
#endif
HAL_StatusTypeDef result = HAL_ADC_ConfigChannel(&adc.Handle(), &channelConfig);
Expand All @@ -84,25 +87,27 @@ namespace hal

void AnalogToDigitalInternalTemperatureStm::Measure(std::size_t numberOfSamples, const infra::Function<void(infra::MemoryRange<uint16_t>)>& onDone)
{
ADC_ChannelConfTypeDef channelConfig;
#if defined(ADC_CHANNEL_TEMPSENSOR)
ADC_ChannelConfTypeDef channelConfig{};
#ifdef ADC_CHANNEL_TEMPSENSOR
channelConfig.Channel = ADC_CHANNEL_TEMPSENSOR;
#else
if (adc.index == 1)
channelConfig.Channel = ADC_CHANNEL_TEMPSENSOR_ADC1;
else
channelConfig.Channel = ADC_CHANNEL_TEMPSENSOR_ADC5;
#endif
#if defined(STM32WB) || defined(STM32G0) || defined(STM32G4)
#ifdef ADC_REGULAR_RANK_1
channelConfig.Rank = ADC_REGULAR_RANK_1;
#else
channelConfig.Rank = 1;
#endif
#if defined(STM32WB) || defined(STM32G4)
#ifdef ADC_OFFSET_NONE
channelConfig.OffsetNumber = ADC_OFFSET_NONE;
#endif
#ifdef ADC_SINGLE_ENDED
channelConfig.SingleDiff = ADC_SINGLE_ENDED;
#endif
#if !defined(STM32F0) && !defined(STM32F3) && !defined(STM32G0) && !defined(STM32WBA)
#ifdef ADC_OFFSET_1
channelConfig.Offset = 0;
#endif
channelConfig.SamplingTime = config.samplingTime;
Expand Down Expand Up @@ -131,37 +136,37 @@ namespace hal
EnableClockAdc(index);

handle.Instance = peripheralAdc[index];
#if !defined(STM32F3) && !defined(STM32WBA)
handle.Init.ClockPrescaler = ADC_CLOCKPRESCALER_PCLK_DIV4;
handle.Init.Resolution = ADC_RESOLUTION_12B;
#elif defined(STM32WBA)
#ifdef ADC_CLOCK_ASYNC_DIV4
handle.Init.ClockPrescaler = ADC_CLOCK_ASYNC_DIV4;
handle.Init.Resolution = ADC_RESOLUTION_12B;
#else
handle.Init.ClockPrescaler = ADC_CLOCKPRESCALER_PCLK_DIV4;
#endif
handle.Init.Resolution = ADC_RESOLUTION_12B;
handle.Init.ScanConvMode = DISABLE;
handle.Init.ContinuousConvMode = DISABLE;
handle.Init.DiscontinuousConvMode = DISABLE;
#if !defined(STM32G0) && !defined(STM32WBA)
#if defined(ADC_CFGR_DISCNUM) || defined(ADC_CR1_DISCNUM)
handle.Init.NbrOfDiscConversion = 0;
#endif
#if !defined(STM32F3)
handle.Init.ExternalTrigConvEdge = ADC_EXTERNALTRIGCONVEDGE_NONE;
handle.Init.DMAContinuousRequests = DISABLE;
#endif
handle.Init.ExternalTrigConv = ADC_SOFTWARE_START;
handle.Init.DataAlign = ADC_DATAALIGN_RIGHT;
handle.Init.NbrOfConversion = 1;
#if defined(STM32WB) || defined(STM32G0) || defined(STM32G4)
handle.Init.EOCSelection = ADC_EOC_SINGLE_CONV;
#ifdef ADC_OVR_DATA_OVERWRITTEN
handle.Init.Overrun = ADC_OVR_DATA_OVERWRITTEN;
#endif
#ifdef IS_ADC_OVERSAMPLING_RATIO
handle.Init.OversamplingMode = DISABLE;
#elif !defined(STM32F3)
handle.Init.EOCSelection = DISABLE;
#endif
#ifdef ADC_SMPR_SMP1
handle.Init.SamplingTimeCommon1 = ADC_SAMPLETIME_79CYCLES_5;
#endif
HAL_StatusTypeDef result = HAL_ADC_Init(&handle);
assert(result == HAL_OK);

#if defined(STM32WB)
#ifdef IS_ADC_SINGLE_DIFFERENTIAL
result = HAL_ADCEx_Calibration_Start(&handle, ADC_SINGLE_ENDED);
assert(result == HAL_OK);
#endif
Expand Down Expand Up @@ -193,7 +198,7 @@ namespace hal
void AdcStm::MeasurementDone()
{
assert(onDone != nullptr);
#if defined(STM32WB) || defined(STM32G4) || defined(STM32G0) || defined(STM32WBA)
#ifdef ADC_ISR_EOC
handle.Instance->ISR |= ADC_ISR_EOC | ADC_ISR_EOS;
#else
handle.Instance->SR &= ~ADC_SR_EOC;
Expand Down
13 changes: 7 additions & 6 deletions hal_st/stm32fxxx/AnalogToDigitalPinStm.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,9 @@ namespace hal
{
struct AdcStmChannelConfig
{
#if defined(STM32F0) || defined(STM32F3)
uint32_t samplingTime{ ADC_SAMPLETIME_7CYCLES_5 };
#elif defined(STM32WB) || defined(STM32G4)
#if defined(ADC_SAMPLETIME_2CYCLES_5)
uint32_t samplingTime{ ADC_SAMPLETIME_2CYCLES_5 };
#elif defined(STM32G0) || defined(STM32WBA)
#elif defined(ADC_SAMPLETIME_3CYCLES_5)
uint32_t samplingTime{ ADC_SAMPLETIME_3CYCLES_5 };
#else
uint32_t samplingTime{ ADC_SAMPLETIME_3CYCLES };
Expand All @@ -31,13 +29,16 @@ namespace hal
: public AnalogToDigitalPinImplBase<uint16_t>
{
public:
explicit AnalogToDigitalPinImplStm(hal::GpioPinStm& pin, AdcStm& adc);
using Config = detail::AdcStmChannelConfig;

AnalogToDigitalPinImplStm(hal::GpioPinStm& pin, AdcStm& adc, const Config& config = Config());

void Measure(std::size_t numberOfSamples, const infra::Function<void(infra::MemoryRange<uint16_t>)>& onDone) override;

private:
AnalogPinStm analogPin;
AdcStm& adc;
Config config;
};

class AnalogToDigitalInternalTemperatureStm
Expand All @@ -46,7 +47,7 @@ namespace hal
public:
using Config = detail::AdcStmChannelConfig;

AnalogToDigitalInternalTemperatureStm(AdcStm& adc, const Config& config = Config());
explicit AnalogToDigitalInternalTemperatureStm(AdcStm& adc, const Config& config = Config());

void Measure(std::size_t numberOfSamples, const infra::Function<void(infra::MemoryRange<uint16_t>)>& onDone) override;

Expand Down
16 changes: 12 additions & 4 deletions hal_st/stm32fxxx/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -15,8 +15,8 @@ target_link_libraries(hal_st.stm32fxxx PUBLIC
)

target_sources(hal_st.stm32fxxx PRIVATE
$<$<STREQUAL:${TARGET_MCU},stm32wb55>:AdcDmaStm.cpp>
$<$<STREQUAL:${TARGET_MCU},stm32wb55>:AdcDmaStm.hpp>
$<$<OR:$<STREQUAL:${TARGET_MCU},stm32wb55>,$<STREQUAL:${TARGET_MCU_FAMILY},stm32wbaxx>>:AdcDmaStm.cpp>
$<$<OR:$<STREQUAL:${TARGET_MCU},stm32wb55>,$<STREQUAL:${TARGET_MCU_FAMILY},stm32wbaxx>>:AdcDmaStm.hpp>
AnalogToDigitalPinStm.cpp
AnalogToDigitalPinStm.hpp
BackupRamStm.cpp
Expand Down Expand Up @@ -123,7 +123,7 @@ if (TARGET_MCU_VENDOR STREQUAL st)
elseif (TARGET_MCU_VARIANT STREQUAL stm32wb55rg)
set(gpio_xml "${CMAKE_CURRENT_SOURCE_DIR}/ip/GPIO-STM32WB55x_gpio_v1_0_Modes.xml")
set(mcu_xml "${CMAKE_CURRENT_SOURCE_DIR}/mcu/STM32WB55RGVx.xml")
elseif (TARGET_MCU_VARIANT STREQUAL stm32wba52cg)
elseif (TARGET_MCU STREQUAL stm32wba52)
set(gpio_xml "${CMAKE_CURRENT_SOURCE_DIR}/ip/GPIO-STM32WBA52x_gpio_v1_0_Modes.xml")
set(mcu_xml "${CMAKE_CURRENT_SOURCE_DIR}/mcu/STM32WBA52CGUx.xml")
else()
Expand All @@ -135,8 +135,16 @@ if (TARGET_MCU_VENDOR STREQUAL st)
generate_xslt(hal_st.stm32fxxx generated/stm32fxxx/PinoutTableDefault.cpp GeneratePinoutTableCpp.xsl "${CMAKE_CURRENT_BINARY_DIR}/generated/stm32fxxx/PinoutTableDefaultStructure.xml")
generate_xslt(hal_st.stm32fxxx generated/stm32fxxx/PinoutTableDefault.hpp GeneratePinoutTableHpp.xsl "${CMAKE_CURRENT_BINARY_DIR}/generated/stm32fxxx/PinoutTableDefaultStructure.xml")

generate_xslt(hal_st.stm32fxxx generated/stm32fxxx/PeripheralTableStructure.xml GeneratePeripheralTableStructure.xsl $<IF:$<OR:$<STREQUAL:${TARGET_MCU_FAMILY},stm32wbaxx>,$<STREQUAL:${TARGET_MCU_FAMILY},stm32wbxx>>,PeripheralTableWbxx.xml,PeripheralTableFxxx.xml>
if (TARGET_MCU_FAMILY STREQUAL stm32wbxx)
generate_xslt(hal_st.stm32fxxx generated/stm32fxxx/PeripheralTableStructure.xml GeneratePeripheralTableStructure.xsl PeripheralTableWbxx.xml
--stringparam mcu-document ${mcu_xml})
elseif (TARGET_MCU_FAMILY STREQUAL stm32wbaxx)
generate_xslt(hal_st.stm32fxxx generated/stm32fxxx/PeripheralTableStructure.xml GeneratePeripheralTableStructure.xsl PeripheralTableWbaxx.xml
--stringparam mcu-document ${mcu_xml})
else()
generate_xslt(hal_st.stm32fxxx generated/stm32fxxx/PeripheralTableStructure.xml GeneratePeripheralTableStructure.xsl PeripheralTableFxxx.xml
--stringparam mcu-document ${mcu_xml})
endif()

generate_xslt(hal_st.stm32fxxx generated/stm32fxxx/PeripheralTable.cpp GeneratePeripheralTableCpp.xsl "${CMAKE_CURRENT_BINARY_DIR}/generated/stm32fxxx/PeripheralTableStructure.xml")
generate_xslt(hal_st.stm32fxxx generated/stm32fxxx/PeripheralTable.hpp GeneratePeripheralTableHpp.xsl "${CMAKE_CURRENT_BINARY_DIR}/generated/stm32fxxx/PeripheralTableStructure.xml")
Expand Down
29 changes: 29 additions & 0 deletions hal_st/stm32fxxx/PeripheralTableWbaxx.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
<?xml version="1.0"?>
<peripherals xmlns:xi="http://www.w3.org/2001/XInclude">
<peripheral name="Uart" type="USART_TypeDef*">
<item name="USART"/>
<interrupt/>
</peripheral>
<peripheral name="Lpuart" type="USART_TypeDef*">
<item name="LPUART"/>
<interrupt/>
</peripheral>
<peripheral name="Spi" type="SPI_TypeDef*"><item name="SPI"/><interrupt/></peripheral>
<peripheral name="I2c" type="I2C_TypeDef*"><item name="I2C"/>
<interrupt name="Ev" postfix="_EV"/>
<interrupt name="Er" postfix="_ER"/>
</peripheral>
<peripheral name="Sai" type="SAI_TypeDef*"><item name="SAI"/>
<interrupt/>
</peripheral>
<peripheral name="Adc" type="ADC_TypeDef*"><item name="ADC"/></peripheral>
<peripheral name="QuadSpi" type="QUADSPI_TypeDef*" base="QUADSPI_R_BASE">
<item name="QUADSPI"/>
<interrupt/>
</peripheral>
<peripheral name="Rng" type="RNG_TypeDef*"><item name="RNG"/></peripheral>
<peripheral name="Rtc" type="RTC_TypeDef*"><item name="RTC"/></peripheral>
<peripheral name="Timer" type="TIM_TypeDef*" prefix="TIM">
<item name="TIM1_8WBA5"/>
</peripheral>
</peripherals>
Loading