Use gpio event driver in gpio driver
This commit is contained in:
parent
df0e302bf8
commit
5f6e468c8e
@ -10,11 +10,14 @@ class GpioInterface
|
||||
public:
|
||||
enum class direction {IN, OUT};
|
||||
|
||||
virtual void set_direction(direction) = 0;
|
||||
virtual void set_direction(direction, bool) = 0;
|
||||
virtual uint32_t get() = 0;
|
||||
virtual void set() = 0;
|
||||
virtual void clear() = 0;
|
||||
virtual void toggle() = 0;
|
||||
|
||||
virtual void handle() = 0;
|
||||
virtual uint32_t pin_number() = 0;
|
||||
};
|
||||
|
||||
}
|
||||
|
@ -7,6 +7,7 @@
|
||||
#include "platform/cm4/SystemTick.h"
|
||||
|
||||
#include "platform/nrf52/gpio.h"
|
||||
#include "platform/nrf52/gpiote.h"
|
||||
#include "platform/nrf52/InterruptHandler.h"
|
||||
#include "platform/nrf52/InterruptGuardian.h"
|
||||
|
||||
@ -15,6 +16,18 @@
|
||||
using namespace pinetime::platform;
|
||||
using namespace pinetime::virtual_timer;
|
||||
|
||||
// IRQs
|
||||
nrf52::InterruptGuardian nrf52::InterruptGuardian::instance;
|
||||
cm4::InterruptGuardian cm4::InterruptGuardian::instance;
|
||||
|
||||
// GPIO events
|
||||
nrf52::Gpiote gpiote;
|
||||
|
||||
// Timer
|
||||
cm4::SystemTick system_tick;
|
||||
VirtualTimerDistributor virtual_timer_distributor(system_tick.instance());
|
||||
pinetime::Delay delay;
|
||||
|
||||
enum {
|
||||
PIN_NUMBER_LED_1 = 17,
|
||||
PIN_NUMBER_LED_2 = 18,
|
||||
@ -29,15 +42,6 @@ nrf52::Gpio led_3(PIN_NUMBER_LED_3);
|
||||
nrf52::Gpio led_4(PIN_NUMBER_LED_4);
|
||||
std::array<nrf52::Gpio *, 4> leds = {&led_1, &led_2, &led_3, &led_4};
|
||||
|
||||
// IRQs
|
||||
nrf52::InterruptGuardian nrf52::InterruptGuardian::instance;
|
||||
cm4::InterruptGuardian cm4::InterruptGuardian::instance;
|
||||
|
||||
// Timer
|
||||
cm4::SystemTick system_tick;
|
||||
VirtualTimerDistributor virtual_timer_distributor(system_tick.instance());
|
||||
pinetime::Delay delay;
|
||||
|
||||
int main(void)
|
||||
{
|
||||
cm4::InterruptGuardian::enable_interrupts();
|
||||
|
@ -1,22 +1,33 @@
|
||||
#include "platform/nrf52/gpio.h"
|
||||
|
||||
extern "C" {
|
||||
#include "nrf52.h"
|
||||
#include "nrf52_bitfields.h"
|
||||
|
||||
NRF_GPIO_Type *const GPIO_REGS = reinterpret_cast<NRF_GPIO_Type *>(NRF_P0_BASE);
|
||||
NRF_GPIOTE_Type *const GPIOTE_REGS = reinterpret_cast<NRF_GPIOTE_Type *>(NRF_GPIOTE_BASE);
|
||||
}
|
||||
|
||||
#include "platform/nrf52/gpiote.h"
|
||||
#include "platform/nrf52/gpio.h"
|
||||
|
||||
using namespace pinetime::platform::nrf52;
|
||||
|
||||
Gpio::Gpio()
|
||||
: pin(0)
|
||||
, blocking(false)
|
||||
, wait_for_event(false)
|
||||
{
|
||||
}
|
||||
|
||||
Gpio::Gpio(uint32_t pin)
|
||||
: pin_number(pin)
|
||||
: pin(pin)
|
||||
, blocking(false)
|
||||
, wait_for_event(false)
|
||||
{
|
||||
this->set_direction(direction::OUT);
|
||||
this->clear();
|
||||
}
|
||||
|
||||
void Gpio::set_direction(direction dir)
|
||||
void Gpio::set_direction(direction dir, bool blocking_read)
|
||||
{
|
||||
uint32_t direct = GPIO_PIN_CNF_DIR_Output << GPIO_PIN_CNF_DIR_Pos;
|
||||
uint32_t input = GPIO_PIN_CNF_INPUT_Disconnect << GPIO_PIN_CNF_INPUT_Pos;
|
||||
@ -33,36 +44,60 @@ void Gpio::set_direction(direction dir)
|
||||
// GPIO_PIN_CNF_PULL_Pullup, ///< Pin pull-up resistor enabled.
|
||||
pull = GPIO_PIN_CNF_PULL_Pullup << GPIO_PIN_CNF_PULL_Pos;
|
||||
drive = GPIO_PIN_CNF_DRIVE_S0S1 << GPIO_PIN_CNF_DRIVE_Pos;
|
||||
sense = GPIO_PIN_CNF_SENSE_Disabled << GPIO_PIN_CNF_SENSE_Pos;
|
||||
sense = GPIO_PIN_CNF_SENSE_Low << GPIO_PIN_CNF_SENSE_Pos;
|
||||
|
||||
gpiote.instance().register_handler(this);
|
||||
|
||||
this->blocking = blocking_read;
|
||||
|
||||
gpiote.instance().enable();
|
||||
}
|
||||
GPIO_REGS->PIN_CNF[pin_number] = direct | input | pull | drive | sense;
|
||||
GPIO_REGS->PIN_CNF[pin] = direct | input | pull | drive | sense;
|
||||
}
|
||||
|
||||
void Gpio::set_pin_number(uint32_t pin)
|
||||
void Gpio::pin_number(uint32_t pin)
|
||||
{
|
||||
this->pin_number = pin;
|
||||
this->pin = pin;
|
||||
}
|
||||
|
||||
uint32_t Gpio::pin_number()
|
||||
{
|
||||
return this->pin;
|
||||
}
|
||||
|
||||
uint32_t Gpio::get()
|
||||
{
|
||||
uint32_t res = (GPIO_REGS->IN >> pin_number) & 1UL;
|
||||
if(this->blocking) {
|
||||
this->wait_for_event = true;
|
||||
while(this->wait_for_event == true) {
|
||||
// FIXME: Low Power
|
||||
asm volatile("nop");
|
||||
}
|
||||
}
|
||||
uint32_t res = (GPIO_REGS->IN >> pin) & 1UL;
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
void Gpio::set()
|
||||
{
|
||||
GPIO_REGS->OUTSET = 1UL << (this->pin_number);
|
||||
GPIO_REGS->OUTSET = 1UL << (this->pin);
|
||||
}
|
||||
|
||||
void Gpio::clear()
|
||||
{
|
||||
GPIO_REGS->OUTCLR = 1UL << (this->pin_number);
|
||||
GPIO_REGS->OUTCLR = 1UL << (this->pin);
|
||||
}
|
||||
|
||||
void Gpio::toggle()
|
||||
{
|
||||
uint32_t state = GPIO_REGS->OUT;
|
||||
|
||||
GPIO_REGS->OUTSET = (~state & (1UL << (this->pin_number)));
|
||||
GPIO_REGS->OUTCLR = (state & (1UL << (this->pin_number)));
|
||||
GPIO_REGS->OUTSET = (~state & (1UL << (this->pin)));
|
||||
GPIO_REGS->OUTCLR = (state & (1UL << (this->pin)));
|
||||
}
|
||||
|
||||
void Gpio::handle()
|
||||
{
|
||||
this->wait_for_event = false;
|
||||
}
|
@ -3,22 +3,30 @@
|
||||
|
||||
#include "gpio_interface.h"
|
||||
|
||||
#include "platform/nrf52/InterruptHandler.h"
|
||||
|
||||
namespace pinetime::platform::nrf52 {
|
||||
|
||||
class Gpio : public pinetime::interfaces::GpioInterface
|
||||
{
|
||||
public:
|
||||
inline Gpio() {}
|
||||
public:
|
||||
Gpio();
|
||||
Gpio(uint32_t);
|
||||
void set_pin_number(uint32_t);
|
||||
void set_direction(direction) override;
|
||||
void pin_number(uint32_t);
|
||||
uint32_t pin_number() override;
|
||||
|
||||
void set_direction(direction, bool blocking_read=false) override;
|
||||
uint32_t get() override;
|
||||
void set() override;
|
||||
void clear() override;
|
||||
void toggle() override;
|
||||
|
||||
private:
|
||||
uint32_t pin_number;
|
||||
void handle() override;
|
||||
|
||||
private:
|
||||
uint32_t pin;
|
||||
bool blocking;
|
||||
volatile bool wait_for_event;
|
||||
};
|
||||
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user