From 11baa1c185655692ea3fb7562d1e2fbd66ea1c10 Mon Sep 17 00:00:00 2001 From: Erki Date: Tue, 12 Jul 2022 18:04:40 +0300 Subject: [PATCH] Initial state transitions --- main.cpp | 21 ++++++++ radio/include/radio_hw_instance.hpp | 20 ++++++++ radio/src/radio_hw_instance.cpp | 80 +++++++++++++++++++++++++++-- 3 files changed, 118 insertions(+), 3 deletions(-) diff --git a/main.cpp b/main.cpp index 97db4e9..e5cdfe2 100644 --- a/main.cpp +++ b/main.cpp @@ -35,6 +35,7 @@ int main() App::Logging::setup(); radio::HwInstance radio_hw; + SKULLC_LOG_DEBUG("Begin."); /* Replace with your application code */ while (true) @@ -51,6 +52,26 @@ int main() SKULLC_LOG_INFO("Status: %d", radio_status); + static int transitioned = 0; + if (radio_status == 0x08 && transitioned == 0) + { + SKULLC_LOG_DEBUG("Transitioning..."); + radio_hw.set_current_state(radio::HwInstance::States::PLL_ON); + transitioned = 1; + } + else if (radio_status == 0x09 && transitioned == 1) + { + SKULLC_LOG_DEBUG("Transitioning 2..."); + radio_hw.set_current_state(radio::HwInstance::States::RX_ON); + transitioned = 2; + } + else if (radio_status == 0x09 && transitioned == 1) + { + SKULLC_LOG_DEBUG("Transitioning 2..."); + radio_hw.set_current_state(radio::HwInstance::States::RX_ON); + transitioned = 2; + } + delay_ms(1000); } } diff --git a/radio/include/radio_hw_instance.hpp b/radio/include/radio_hw_instance.hpp index fff2dca..b19b70a 100644 --- a/radio/include/radio_hw_instance.hpp +++ b/radio/include/radio_hw_instance.hpp @@ -14,6 +14,22 @@ namespace radio struct HwInstance { + enum class States : std::uint8_t + { + P_ON = 0, + BUSY_RX, + BUSY_TX, + RX_ON, + TRX_OFF, + PLL_ON, + SLEEP, + PREP_DEEP_SLEEP, + BUSY_RX_AACK, + BUSY_TX_ARET, + RX_AACK_ON, + TX_ARET_ON + }; + static HwInstance* instance(); HwInstance(); @@ -26,9 +42,13 @@ struct HwInstance uint8_t register_read(const Registers& address); void register_write(const Registers& address, const uint8_t value); + + States current_state() const; + bool set_current_state(const States& new_state); private: spi_m_sync_descriptor* m_spi = nullptr; io_descriptor* m_spi_io = nullptr; + States m_current_state = States::P_ON; void m_wait_transition_complete(); }; diff --git a/radio/src/radio_hw_instance.cpp b/radio/src/radio_hw_instance.cpp index a4358c2..f47a32f 100644 --- a/radio/src/radio_hw_instance.cpp +++ b/radio/src/radio_hw_instance.cpp @@ -7,11 +7,13 @@ #include "radio_hardware_instance.h" #include "radio_gpio.h" #include "radio_spi.h" +#include "utility_logging.hpp" #include #include #include #include +#include namespace { @@ -53,6 +55,7 @@ HwInstance::HwInstance() ext_irq_enable(IN_RADIO_IRQ); ext_irq_register(IN_RADIO_IRQ, _irq_handler); + ext_irq_register(0, _irq_handler); gpio_set_pin_level(OUT_RADIO_RST, true); delay_ms(10); @@ -72,13 +75,12 @@ HwInstance::HwInstance() // clear interrupts. register_read(Registers::IRQ_STATUS); - m_wait_transition_complete(); - - register_write(Registers::TRX_STATE, 0x08); + set_current_state(States::TRX_OFF); } void HwInstance::irq_handler() { + SKULLC_LOG_DEBUG("IRQ set."); } uint8_t HwInstance::register_read(const Registers& address) @@ -111,6 +113,78 @@ void HwInstance::register_write(const Registers& address, const uint8_t value) gpio_set_pin_level(OUT_RADIO_CS, true); } +bool HwInstance::set_current_state(const States& new_state) +{ + if (new_state == m_current_state) + return true; + + m_wait_transition_complete(); + bool can_transition = false; + std::optional trx_state_value = std::nullopt; + + switch (m_current_state) + { + case States::P_ON: + if (new_state == States::TRX_OFF) + { + can_transition = true; + trx_state_value = 0x08; + } + break; + case States::TRX_OFF: + if (new_state == States::RX_ON) + { + can_transition = true; + trx_state_value = 0x06; + } + else if (new_state == States::PLL_ON) + { + can_transition = true; + trx_state_value = 0x09; + } + break; + case States::RX_ON: + if (new_state == States::PLL_ON) + { + can_transition = true; + trx_state_value = 0x09; + } + else if (new_state == States::TRX_OFF) + { + can_transition = true; + trx_state_value = 0x08; + } + break; + case States::PLL_ON: + if (new_state == States::RX_ON) + { + can_transition = true; + trx_state_value = 0x06; + } + else if (new_state == States::TRX_OFF) + { + can_transition = true; + trx_state_value = 0x08; + } + break; + default: + SKULLC_ASSERT_DEBUG(false); + return false; + } + + if (can_transition) + { + register_write(Registers::TRX_STATE, *trx_state_value); + m_wait_transition_complete(); + m_current_state = new_state; + return true; + } + else + { + return false; + } +} + void HwInstance::m_wait_transition_complete() { while (true)