-
Notifications
You must be signed in to change notification settings - Fork 118
/
RH_ABZ.cpp
123 lines (105 loc) · 5.08 KB
/
RH_ABZ.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
// RH_ABZ.cpp
//
// Copyright (C) 2020 Mike McCauley
// $Id: RH_ABZ.cpp,v 1.1 2020/06/15 23:39:39 mikem Exp $
#if (RH_PLATFORM == RH_PLATFORM_STM32L0) && (defined STM32L082xx || defined STM32L072xx)
#include <RH_ABZ.h>
// Pointer to the _only_ permitted ABZ instance (there is only one radio connected to this device)
RH_ABZ* RH_ABZ::_thisDevice;
// The muRata cmwx1zzabz module has its builtin SX1276 radio connected to the processor's SPI1 port,
// but the Arduino compatible SPI interface in Grumpy Pizzas Arduino Core is configured for SPI1 or SPI2
// depending on the exact board variant selected.
// So here we define our own Arduino compatible SPI interface
// so we are _sure_ to get the one connected to the radio, independent of the board variant selected
#include <stm32l0_spi.h>
static const stm32l0_spi_params_t RADIO_SPI_PARAMS = {
STM32L0_SPI_INSTANCE_SPI1,
0,
STM32L0_DMA_CHANNEL_NONE,
STM32L0_DMA_CHANNEL_NONE,
{
STM32L0_GPIO_PIN_PA7_SPI1_MOSI,
STM32L0_GPIO_PIN_PA6_SPI1_MISO,
STM32L0_GPIO_PIN_PB3_SPI1_SCK,
STM32L0_GPIO_PIN_NONE,
},
};
// Create and configure an Arduino compatible SPI interface. This will be referred to in RHHardwareSPI.cpp
// and used as the SPI interface to the radio.
static stm32l0_spi_t RADIO_SPI;
SPIClass radio_spi(&RADIO_SPI, &RADIO_SPI_PARAMS);
// Glue code between the 'C' DIO0 interrupt and the C++ interrupt handler in RH_RF95
void RH_INTERRUPT_ATTR RH_ABZ::isr()
{
_thisDevice->handleInterrupt();
}
RH_ABZ::RH_ABZ():
RH_RF95(RH_INVALID_PIN, RH_INVALID_PIN)
{
}
bool RH_ABZ::init()
{
_thisDevice = this;
// REVISIT: RESET THE RADIO???
// The SX1276 radio DIO0 is connected to STM32 pin PB4
// It will later be configured as an interrupt
stm32l0_gpio_pin_configure(STM32L0_GPIO_PIN_PB4, (STM32L0_GPIO_PARK_NONE | STM32L0_GPIO_PUPD_PULLDOWN | STM32L0_GPIO_OSPEED_HIGH | STM32L0_GPIO_OTYPE_PUSHPULL | STM32L0_GPIO_MODE_INPUT));
// Here we configure the interrupt handler for DIO0 to call the C++
// interrupt handler in RH_RF95, in a roundabout way
#ifdef STM32L0_EXTI_CONTROL_PRIORITY_CRITICAL
stm32l0_exti_attach(STM32L0_GPIO_PIN_PB4, (STM32L0_EXTI_CONTROL_PRIORITY_CRITICAL | STM32L0_EXTI_CONTROL_EDGE_RISING), (stm32l0_exti_callback_t)isr, NULL); // STM32L0_EXTI_CONTROL_PRIORITY_CRITICAL not in 0.0.10
#else
stm32l0_exti_attach(STM32L0_GPIO_PIN_PB4, STM32L0_EXTI_CONTROL_EDGE_RISING, (stm32l0_exti_callback_t)isr, NULL);
#endif
// The SX1276 radio slave select (NSS) is connected to STM32 pin PA15
stm32l0_gpio_pin_configure(STM32L0_GPIO_PIN_PA15, (STM32L0_GPIO_PARK_HIZ | STM32L0_GPIO_PUPD_NONE | STM32L0_GPIO_OSPEED_HIGH | STM32L0_GPIO_OTYPE_PUSHPULL | STM32L0_GPIO_MODE_OUTPUT));
// muRata cmwx1zzabz module has an antenna switch which must be driven the right way to connect the antenna
// to the appropriate SX1276 pins.
// Antenna switch might be something like NJG180K64, but not sure.
// See Application note: AN-ZZABZ-001 P. 20/20
// in typeABZ_hardware_design_guide_revC.pdf
// with 3 pins connected to STM32L0_GPIO_PIN_PA1, STM32L0_GPIO_PIN_PC2, STM32L0_GPIO_PIN_PC1
// which select RX, RFO or PA_BOOST respecitvely
// See modeWillChange() for implementation of pin twiddling when the transmitter is on
//
// We use native STM32 calls because the various different variants in the Grumpy Pizza
// Arduino core and various forks of that core have inconsistent definitions of the Arduino compatible
// pins. We want to be sure we get the right ones for the muRata modules connections to the Radio
stm32l0_gpio_pin_configure(STM32L0_GPIO_PIN_PA1, (STM32L0_GPIO_PARK_NONE | STM32L0_GPIO_PUPD_NONE | STM32L0_GPIO_OSPEED_LOW | STM32L0_GPIO_OTYPE_PUSHPULL | STM32L0_GPIO_MODE_OUTPUT));
stm32l0_gpio_pin_configure(STM32L0_GPIO_PIN_PC2, (STM32L0_GPIO_PARK_NONE | STM32L0_GPIO_PUPD_NONE | STM32L0_GPIO_OSPEED_LOW | STM32L0_GPIO_OTYPE_PUSHPULL | STM32L0_GPIO_MODE_OUTPUT));
stm32l0_gpio_pin_configure(STM32L0_GPIO_PIN_PC1, (STM32L0_GPIO_PARK_NONE | STM32L0_GPIO_PUPD_NONE | STM32L0_GPIO_OSPEED_LOW | STM32L0_GPIO_OTYPE_PUSHPULL | STM32L0_GPIO_MODE_OUTPUT));
return RH_RF95::init();
}
bool RH_ABZ::deinit()
{
setModeIdle();
stm32l0_exti_detach(STM32L0_GPIO_PIN_PB4);
return true;
}
void RH_ABZ::selectSlave()
{
stm32l0_gpio_pin_write(STM32L0_GPIO_PIN_PA15, 0);
}
void RH_ABZ::deselectSlave()
{
stm32l0_gpio_pin_write(STM32L0_GPIO_PIN_PA15, 1);
}
bool RH_ABZ::modeWillChange(RHMode mode)
{
if (mode == RHModeTx)
{
// Tell the antenna switch to connect to one of the transmitter output pins
stm32l0_gpio_pin_write(STM32L0_GPIO_PIN_PA1, 0); // RX
stm32l0_gpio_pin_write(STM32L0_GPIO_PIN_PC2, _useRFO ? 1 : 0); // RFO
stm32l0_gpio_pin_write(STM32L0_GPIO_PIN_PC1, _useRFO ? 0 : 1); // BOOST
}
else
{
// Enabling the RX from the antenna switch improves reception RSSI by about 5
stm32l0_gpio_pin_write(STM32L0_GPIO_PIN_PA1, 1); // RX
stm32l0_gpio_pin_write(STM32L0_GPIO_PIN_PC2, 0); // RFO
stm32l0_gpio_pin_write(STM32L0_GPIO_PIN_PC1, 0); // BOOST
}
return true;
}
#endif