Skip to content

Commit 2800920

Browse files
committed
STM32 Spi ISR
1 parent 6897160 commit 2800920

File tree

3 files changed

+135
-53
lines changed

3 files changed

+135
-53
lines changed

src/modm/driver/display/ili9341.lb

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,5 @@ def build(env):
2525
env.outbasepath = "modm/src/modm/driver/display"
2626
env.copy("ili9341.hpp")
2727
env.copy("ili9341_impl.hpp")
28+
env.copy("ili9341_spi.hpp")
2829
env.copy("ili9341_parallel.hpp")
29-
30-
env.substitutions = {'spi_16bit_hardware': env[":target"].has_driver("spi:stm32")}
31-
env.template("ili9341_spi.hpp.in")

src/modm/platform/spi/at90_tiny_mega/spi_master.hpp.in

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -105,7 +105,7 @@ public:
105105
}
106106

107107
template< class SystemClock, baudrate_t baudrate, percent_t tolerance=pct(5) >
108-
static inline void
108+
static void
109109
initialize()
110110
{
111111
constexpr auto result = modm::Prescaler::from_power(SystemClock::Spi, baudrate, 2, 128);
@@ -159,8 +159,9 @@ public:
159159
static modm::ResumableResult<T>
160160
transmit(const T data);
161161

162-
/* static modm::ResumableResult<uint8_t>
163-
transmit(const uint8_t data); */
162+
// OPTIMIZE specialize transmit(byte) without ISR overhead
163+
// static modm::ResumableResult<uint8_t>
164+
// transmit(const uint8_t data);
164165

165166
/**
166167
* @brief

src/modm/platform/spi/stm32/spi_master.hpp.in

Lines changed: 130 additions & 47 deletions
Original file line numberDiff line numberDiff line change
@@ -15,12 +15,12 @@
1515
*/
1616
// ----------------------------------------------------------------------------
1717

18-
#ifndef MODM_STM32_SPI_MASTER{{ id }}_HPP
19-
#define MODM_STM32_SPI_MASTER{{ id }}_HPP
18+
#pragma once
2019

2120
#include <modm/architecture/interface/spi_master.hpp>
2221
#include <modm/platform/gpio/connector.hpp>
2322
#include <modm/math/algorithm/prescaler.hpp>
23+
#include <modm/math/utils/binary.hpp>
2424
#include "spi_hal_{{ id }}.hpp"
2525

2626
namespace modm
@@ -39,12 +39,27 @@ namespace platform
3939
*/
4040
class SpiMaster{{ id }} : public modm::SpiMaster
4141
{
42-
static SpiBase::State_t state;
43-
static std::size_t index;
44-
4542
static uint8_t count;
4643
static void *context;
4744
static ConfigurationHandler configuration;
45+
46+
static Spi::State_t state;
47+
static uint8_t shift;
48+
static uint32_t temp;
49+
50+
union unsigned_types_const {
51+
uint8_t const *u8;
52+
uint16_t const *u16;
53+
uint32_t const *u32;
54+
uint16_t repeat;
55+
};
56+
static unsigned_types_const tx, tx_end;
57+
union unsigned_types {
58+
uint8_t *u8;
59+
uint16_t *u16;
60+
uint32_t *u32;
61+
};
62+
static unsigned_types rx, rx_end;
4863
public:
4964
using Hal = SpiHal{{ id }};
5065

@@ -102,18 +117,19 @@ public:
102117
state = SpiBase::State(0);
103118
}
104119

105-
static modm_always_inline void
120+
static void
106121
setDataMode(DataMode mode)
107122
{
108123
SpiHal{{ id }}::setDataMode(static_cast<SpiHal{{ id }}::DataMode>(mode));
109124
}
110125

111-
static modm_always_inline void
126+
static void
112127
setDataOrder(DataOrder order)
113128
{
114129
SpiHal{{ id }}::setDataOrder(static_cast<SpiHal{{ id }}::DataOrder>(order));
115130
}
116-
static modm_always_inline void
131+
132+
static void
117133
setDataSize(DataSize size)
118134
{
119135
SpiHal{{ id }}::setDataSize(static_cast<SpiHal{{ id }}::DataSize>(size));
@@ -126,86 +142,153 @@ public:
126142
static uint8_t
127143
release(void *ctx);
128144

145+
// TODO Complete the docs
146+
147+
/**
148+
* @brief
149+
*
150+
* @param data
151+
* @return modm::ResumableResult<T>
152+
*/
153+
template <modm::unsigned_integral_max32 T>
154+
static modm::ResumableResult<T>
155+
transmit(const T data);
156+
157+
// OPTIMIZE specialize sole transmit(byte / halfword) without ISR overhead
158+
// static modm::ResumableResult<uint8_t>
159+
// transmit(const uint8_t data);
129160

161+
// static modm::ResumableResult<uint16_t>
162+
// transmit(const uint16_t data);
163+
164+
/**
165+
* @brief
166+
*
167+
* @param data
168+
* @return modm::ResumableResult<T>
169+
*/
170+
template <modm::unsigned_integral_max32 T>
171+
static modm::ResumableResult<void>
172+
transmit(const T data, std::size_t repeat);
173+
174+
/**
175+
* @brief Send and optional receive data in range begin()->end().
176+
* Works with C-array or std::array for tx / rx
177+
*
178+
* @param tx_first Pointer to first element to send. f.e. tx.begin() OR tx.begin() + 1
179+
* @param tx_first Pointer to one after last element to send: f.e. tx.end() OR tx.end() - 4
180+
* @param rx_first Pointer to first element to receive: f.e. rx_data.begin() OR rx_data.begin() + 1
181+
*/
182+
template <modm::unsigned_integral_max32 T>
183+
static modm::ResumableResult<void>
184+
transmit(const T *tx_first, const T *tx_last, T *rx_first = nullptr);
185+
186+
/**
187+
* @brief Send a std::array
188+
*
189+
* @param tx_array std::array with data to send
190+
*/
191+
template <std::ranges::forward_range C>
192+
static modm::ResumableResult<void>
193+
transmit(const C &tx_arr)
194+
{ return transmit(tx_arr.begin(), tx_arr.end()); };
195+
196+
/**
197+
* @brief Transmit and receive an std::array
198+
*
199+
* @param tx_arr std::array with data to send
200+
* @param rx_arr std::array for received data
201+
*/
202+
template <std::ranges::forward_range C>
203+
static modm::ResumableResult<void>
204+
transmit(const C &tx_arr, C &rx_arr)
205+
{ return transmit(tx_arr.begin(), tx_arr.end(), rx_arr.begin()); };
206+
207+
// -- Backwards compatible API --------------------------------------------------------
130208
static uint8_t
131209
transferBlocking(const uint8_t data)
132-
{
133-
return RF_CALL_BLOCKING(transmit<uint8_t>(data));
134-
}
210+
{ return RF_CALL_BLOCKING(transmit(data)); }
135211

136212
static uint16_t
137213
transferBlocking16(const uint16_t data)
138-
{
139-
return RF_CALL_BLOCKING(transmit<uint16_t>(data));
140-
}
214+
{ return RF_CALL_BLOCKING(transmit(data)); }
215+
216+
static uint32_t
217+
transferBlocking32(const uint32_t data)
218+
{ return RF_CALL_BLOCKING(transmit(data)); }
141219

142220
static void
143-
transferBlocking(const uint8_t *tx, std::size_t repeat)
144-
{
145-
RF_CALL_BLOCKING(transmit<uint8_t>(tx, repeat));
146-
}
221+
transferBlocking(const uint8_t data, std::size_t repeat)
222+
{ RF_CALL_BLOCKING(transmit(data, repeat)); }
147223

148224
static void
149-
transferBlocking16(const uint16_t *tx, std::size_t repeat)
150-
{
151-
RF_CALL_BLOCKING(transmit<uint16_t>(tx, repeat));
152-
}
225+
transferBlocking16(const uint16_t data, std::size_t repeat)
226+
{ RF_CALL_BLOCKING(transmit(data, repeat)); }
227+
228+
static void
229+
transferBlocking32(const uint32_t data, std::size_t repeat)
230+
{ RF_CALL_BLOCKING(transmit(data, repeat)); }
153231

154232
static void
155233
transferBlocking(const uint8_t *tx, uint8_t *rx, std::size_t length)
156-
{
157-
RF_CALL_BLOCKING(transmit<uint8_t>(tx, rx, length));
158-
}
234+
{ RF_CALL_BLOCKING(transmit(tx, tx + length, rx)); }
159235

160236
static void
161237
transferBlocking16(const uint16_t *tx, uint16_t *rx, std::size_t length)
162-
{
163-
RF_CALL_BLOCKING(transmit<uint16_t>(tx, rx, length));
164-
}
238+
{ RF_CALL_BLOCKING(transmit(tx, tx + length, rx)); }
239+
240+
static void
241+
transferBlocking32(const uint32_t *tx, uint32_t *rx, std::size_t length)
242+
{ RF_CALL_BLOCKING(transmit(tx, tx + length, rx)); }
165243

166244
static modm::ResumableResult<uint8_t>
167245
transfer(const uint8_t data) {
168-
return transmit<uint8_t>(data);
246+
return transmit(data);
169247
}
170248

171249
static modm::ResumableResult<uint16_t>
172250
transfer16(const uint16_t data) {
173-
return transmit<uint16_t>(data);
251+
return transmit(data);
174252
}
175253

176-
static modm::ResumableResult<void>
177-
transfer(const uint8_t *tx, const std::size_t repeat) {
178-
return transmit<uint8_t>(tx, repeat);
254+
static modm::ResumableResult<uint32_t>
255+
transfer32(const uint32_t data) {
256+
return transmit(data);
179257
}
180258

181259
static modm::ResumableResult<void>
182-
transfer16(const uint16_t *tx, const std::size_t repeat) {
183-
return transmit<uint16_t>(tx, repeat);
260+
transfer(const uint8_t tx, const std::size_t repeat) {
261+
return transmit(tx, repeat);
184262
}
185263

186264
static modm::ResumableResult<void>
187-
transfer(const uint8_t *tx, uint8_t *rx, const std::size_t length) {
188-
return transmit<uint8_t>(tx, rx, length);
265+
transfer16(const uint16_t tx, const std::size_t repeat) {
266+
return transmit(tx, repeat);
189267
}
190268

191269
static modm::ResumableResult<void>
192-
transfer16(const uint16_t *tx, uint16_t *rx, const std::size_t length) {
193-
return transmit<uint16_t>(tx, rx, length);
270+
transfer32(const uint32_t tx, const std::size_t repeat) {
271+
return transmit(tx, repeat);
194272
}
195273

196-
// TODO "transmit" == good?
197-
template <std::unsigned_integral T>
198-
static modm::ResumableResult<T>
199-
transmit(const T data);
274+
static modm::ResumableResult<void>
275+
transfer(const uint8_t *tx, uint8_t *rx, const std::size_t length) {
276+
return transmit(tx, tx + length, rx);
277+
}
200278

201-
template <std::unsigned_integral T>
202279
static modm::ResumableResult<void>
203-
transmit(const T *tx, const std::size_t repeat);
280+
transfer16(const uint16_t *tx, uint16_t *rx, const std::size_t length) {
281+
return transmit(tx, tx + length, rx);
282+
}
204283

205-
template <std::unsigned_integral T>
206284
static modm::ResumableResult<void>
207-
transmit(const T *tx, T *rx, const std::size_t length);
285+
transfer32(const uint32_t *tx, uint32_t *rx, const std::size_t length) {
286+
return transmit(tx, tx + length, rx);
287+
}
208288
// end documentation inherited
289+
290+
// TODO friend with MODM_ISR(SPI_STC) possible?
291+
static void isr_handler();
209292
};
210293

211294
} // namespace platform

0 commit comments

Comments
 (0)