FastLED 3.9.3
Loading...
Searching...
No Matches
fastpin.h
Go to the documentation of this file.
1#ifndef __INC_FASTPIN_H
2#define __INC_FASTPIN_H
3
4#include "FastLED.h"
5
6#include "led_sysdefs.h"
7#include <stddef.h>
8
9#pragma GCC diagnostic push
10#pragma GCC diagnostic ignored "-Wignored-qualifiers"
11#ifdef ESP32
12// Get rid of the endless volatile warnings in ESP32
13#pragma GCC diagnostic ignored "-Wpragmas"
14#pragma GCC diagnostic ignored "-Wvolatile"
15#endif
16
19
20FASTLED_NAMESPACE_BEGIN
21
24#define NO_PIN 255
25
27//
28// Pin access class - needs to tune for various platforms (naive fallback solution?)
29//
31
34public:
35 virtual void select() = 0;
36 virtual void release() = 0;
37 virtual bool isSelected() = 0;
38};
39
40#if !defined(FASTLED_NO_PINMAP)
41
43class Pin : public Selectable {
44 volatile RwReg *mPort;
45 volatile RoReg *mInPort;
46 RwReg mPinMask;
47 uint8_t mPin;
48
51 void _init() {
52 mPinMask = digitalPinToBitMask(mPin);
53 mPort = (volatile RwReg*)portOutputRegister(digitalPinToPort(mPin));
54 mInPort = (volatile RoReg*)portInputRegister(digitalPinToPort(mPin));
55 }
56
57public:
60 Pin(int pin) : mPin(pin) { _init(); }
61
62 typedef volatile RwReg * port_ptr_t;
63 typedef RwReg port_t;
64
66 inline void setOutput() { pinMode(mPin, OUTPUT); }
67
69 inline void setInput() { pinMode(mPin, INPUT); }
70
72 inline void hi() __attribute__ ((always_inline)) { *mPort |= mPinMask; }
74 inline void lo() __attribute__ ((always_inline)) { *mPort &= ~mPinMask; }
75
77 inline void strobe() __attribute__ ((always_inline)) { toggle(); toggle(); }
80 inline void toggle() __attribute__ ((always_inline)) { *mInPort = mPinMask; }
81
84 inline void hi(FASTLED_REGISTER port_ptr_t port) __attribute__ ((always_inline)) { *port |= mPinMask; }
87 inline void lo(FASTLED_REGISTER port_ptr_t port) __attribute__ ((always_inline)) { *port &= ~mPinMask; }
91 inline void set(FASTLED_REGISTER port_t val) __attribute__ ((always_inline)) { *mPort = val; }
92
96 inline void fastset(FASTLED_REGISTER port_ptr_t port, FASTLED_REGISTER port_t val) __attribute__ ((always_inline)) { *port = val; }
97
99 port_t hival() __attribute__ ((always_inline)) { return *mPort | mPinMask; }
101 port_t loval() __attribute__ ((always_inline)) { return *mPort & ~mPinMask; }
103 port_ptr_t port() __attribute__ ((always_inline)) { return mPort; }
105 port_t mask() __attribute__ ((always_inline)) { return mPinMask; }
106
108 virtual void select() { hi(); }
110 virtual void release() { lo(); }
112 virtual bool isSelected() { return (*mPort & mPinMask) == mPinMask; }
113};
114
116class OutputPin : public Pin {
117public:
119 OutputPin(int pin) : Pin(pin) { setOutput(); }
120};
121
123class InputPin : public Pin {
124public:
126 InputPin(int pin) : Pin(pin) { setInput(); }
127};
128
129#else
130// This is the empty code version of the raw pin class, method bodies should be filled in to Do The Right Thing[tm] when making this
131// available on a new platform
132class Pin : public Selectable {
133 volatile RwReg *mPort;
134 volatile RoReg *mInPort;
135 RwReg mPinMask;
136 uint8_t mPin;
137
138 void _init() {
139 // TODO: fill in init on a new platform
140 mPinMask = 0;
141 mPort = NULL;
142 mInPort = NULL;
143 }
144
145public:
146 Pin(int pin) : mPin(pin) { _init(); }
147
148 void setPin(int pin) { mPin = pin; _init(); }
149
150 typedef volatile RwReg * port_ptr_t;
151 typedef RwReg port_t;
152
153 inline void setOutput() { /* TODO: Set pin output */ }
154 inline void setInput() { /* TODO: Set pin input */ }
155
156 inline void hi() __attribute__ ((always_inline)) { *mPort |= mPinMask; }
157 inline void lo() __attribute__ ((always_inline)) { *mPort &= ~mPinMask; }
158
159 inline void strobe() __attribute__ ((always_inline)) { toggle(); toggle(); }
160 inline void toggle() __attribute__ ((always_inline)) { *mInPort = mPinMask; }
161
162 inline void hi(FASTLED_REGISTER port_ptr_t port) __attribute__ ((always_inline)) { *port |= mPinMask; }
163 inline void lo(FASTLED_REGISTER port_ptr_t port) __attribute__ ((always_inline)) { *port &= ~mPinMask; }
164 inline void set(FASTLED_REGISTER port_t val) __attribute__ ((always_inline)) { *mPort = val; }
165
166 inline void fastset(FASTLED_REGISTER port_ptr_t port, FASTLED_REGISTER port_t val) __attribute__ ((always_inline)) { *port = val; }
167
168 port_t hival() __attribute__ ((always_inline)) { return *mPort | mPinMask; }
169 port_t loval() __attribute__ ((always_inline)) { return *mPort & ~mPinMask; }
170 port_ptr_t port() __attribute__ ((always_inline)) { return mPort; }
171 port_t mask() __attribute__ ((always_inline)) { return mPinMask; }
172
173 virtual void select() { hi(); }
174 virtual void release() { lo(); }
175 virtual bool isSelected() { return (*mPort & mPinMask) == mPinMask; }
176};
177
178class OutputPin : public Pin {
179public:
180 OutputPin(int pin) : Pin(pin) { setOutput(); }
181};
182
183class InputPin : public Pin {
184public:
185 InputPin(int pin) : Pin(pin) { setInput(); }
186};
187
188#endif
189
204#ifdef FASTLED_FORCE_SOFTWARE_PINS
205template<uint8_t PIN> class FastPin {
206 static RwReg sPinMask;
207 static volatile RwReg *sPort;
208 static volatile RoReg *sInPort;
209 static void _init() {
210#if !defined(FASTLED_NO_PINMAP)
211 sPinMask = digitalPinToBitMask(PIN);
212 sPort = portOutputRegister(digitalPinToPort(PIN));
213 sInPort = portInputRegister(digitalPinToPort(PIN));
214#endif
215 }
216
217public:
218 typedef volatile RwReg * port_ptr_t;
219 typedef RwReg port_t;
220
222 inline static void setOutput() { _init(); pinMode(PIN, OUTPUT); }
224 inline static void setInput() { _init(); pinMode(PIN, INPUT); }
225
227 inline static void hi() __attribute__ ((always_inline)) { *sPort |= sPinMask; }
229 inline static void lo() __attribute__ ((always_inline)) { *sPort &= ~sPinMask; }
230
232 inline static void strobe() __attribute__ ((always_inline)) { toggle(); toggle(); }
233
235 inline static void toggle() __attribute__ ((always_inline)) { *sInPort = sPinMask; }
236
238 inline static void hi(FASTLED_REGISTER port_ptr_t port) __attribute__ ((always_inline)) { *port |= sPinMask; }
240 inline static void lo(FASTLED_REGISTER port_ptr_t port) __attribute__ ((always_inline)) { *port &= ~sPinMask; }
242 inline static void set(FASTLED_REGISTER port_t val) __attribute__ ((always_inline)) { *sPort = val; }
243
245 inline static void fastset(FASTLED_REGISTER port_ptr_t port, FASTLED_REGISTER port_t val) __attribute__ ((always_inline)) { *port = val; }
246
248 static port_t hival() __attribute__ ((always_inline)) { return *sPort | sPinMask; }
250 static port_t loval() __attribute__ ((always_inline)) { return *sPort & ~sPinMask; }
252 static port_ptr_t port() __attribute__ ((always_inline)) { return sPort; }
254 static port_t mask() __attribute__ ((always_inline)) { return sPinMask; }
255};
256
257template<uint8_t PIN> RwReg FastPin<PIN>::sPinMask;
258template<uint8_t PIN> volatile RwReg *FastPin<PIN>::sPort;
259template<uint8_t PIN> volatile RoReg *FastPin<PIN>::sInPort;
260
261#else
262
263template<uint8_t PIN> class FastPin {
264 // This is a default implementation. If you are hitting this then FastPin<> has
265 // not be defined for your platform. You need to define a FastPin<> specialization
266 // or change what get's included for your particular build target.
267 constexpr static bool validpin() { return false; }
268 constexpr static bool LowSpeedOnlyRecommended() { // Some implementations assume this exists.
269 // Caller must always determine if high speed use if allowed on a given pin,
270 // because it depends on more than just the chip packaging ... it depends on entire board (and even system) design.
271 return false; // choosing default to be FALSE, to allow users to ATTEMPT to use high-speed on pins where support is not known
272 }
273
274 static_assert(validpin(), "Invalid pin specified");
275
276 static void _init() { }
277
278public:
279 typedef volatile RwReg * port_ptr_t;
280 typedef RwReg port_t;
281
283 inline static void setOutput() { }
285 inline static void setInput() { }
286
288 inline static void hi() __attribute__ ((always_inline)) { }
290 inline static void lo() __attribute__ ((always_inline)) { }
291
293 inline static void strobe() __attribute__ ((always_inline)) { }
294
296 inline static void toggle() __attribute__ ((always_inline)) { }
297
299 inline static void hi(FASTLED_REGISTER port_ptr_t port) __attribute__ ((always_inline)) { }
301 inline static void lo(FASTLED_REGISTER port_ptr_t port) __attribute__ ((always_inline)) { }
303 inline static void set(FASTLED_REGISTER port_t val) __attribute__ ((always_inline)) { }
304
306 inline static void fastset(FASTLED_REGISTER port_ptr_t port, FASTLED_REGISTER port_t val) __attribute__ ((always_inline)) { }
307
309 static port_t hival() __attribute__ ((always_inline)) { return 0; }
311 static port_t loval() __attribute__ ((always_inline)) { return 0;}
313 static port_ptr_t port() __attribute__ ((always_inline)) { return NULL; }
315 static port_t mask() __attribute__ ((always_inline)) { return 0; }
316};
317
318#endif
319
323template<uint8_t PIN> class FastPinBB : public FastPin<PIN> {};
324
325typedef volatile uint32_t & reg32_t;
326typedef volatile uint32_t * ptr_reg32_t;
327
330template<uint8_t port> struct __FL_PORT_INFO {
332 static bool hasPort() { return 0; }
334 static const char *portName() { return "--"; }
336 static const void *portAddr() { return NULL; }
337};
338
339
346#define _FL_DEFINE_PORT(L, BASE) template<> struct __FL_PORT_INFO<L> { \
347 static bool hasPort() { return 1; } \
348 static const char *portName() { return #L; } \
349 typedef BASE __t_baseType; \
350 static const void *portAddr() { return (void*)&__t_baseType::r(); } };
351
362#define _FL_DEFINE_PORT3(L, LC, BASE) template<> struct __FL_PORT_INFO<LC> { \
363 static bool hasPort() { return 1; } \
364 static const char *portName() { return #L; } \
365 typedef BASE __t_baseType; \
366 static const void *portAddr() { return (void*)&__t_baseType::r(); } };
367
368FASTLED_NAMESPACE_END
369
370#pragma GCC diagnostic pop
371
372#endif // __INC_FASTPIN_H
central include file for FastLED, defines the CFastLED class/object
FastPin implementation for bit-banded access.
Definition fastpin.h:323
The simplest level of Pin class.
Definition fastpin.h:205
static port_t hival()
Gets the state of the port with this pin HIGH
Definition fastpin.h:248
RwReg port_t
type for a pin read/write register, non-volatile
Definition fastpin.h:219
static void toggle()
Toggle the pin.
Definition fastpin.h:235
static void hi(FASTLED_REGISTER port_ptr_t port)
Set the same pin on another port to HIGH
Definition fastpin.h:238
static port_t loval()
Gets the state of the port with this pin LOW
Definition fastpin.h:250
static void lo(FASTLED_REGISTER port_ptr_t port)
Set the same pin on another port to LOW
Definition fastpin.h:240
static void set(FASTLED_REGISTER port_t val)
Set the state of the output register.
Definition fastpin.h:242
static port_t mask()
Get the pin mask.
Definition fastpin.h:254
volatile RwReg * port_ptr_t
type for a pin read/write register, volatile
Definition fastpin.h:218
static void lo()
Set the pin state to LOW
Definition fastpin.h:229
static port_ptr_t port()
Get the output state of the port.
Definition fastpin.h:252
static void setOutput()
Set the pin mode as OUTPUT
Definition fastpin.h:222
static void strobe()
Toggle the pin twice to create a short pulse.
Definition fastpin.h:232
static void fastset(FASTLED_REGISTER port_ptr_t port, FASTLED_REGISTER port_t val)
Set the state of a port.
Definition fastpin.h:245
static void hi()
Set the pin state to HIGH
Definition fastpin.h:227
static void setInput()
Set the pin mode as INPUT
Definition fastpin.h:224
I/O pin initially set to INPUT.
Definition fastpin.h:123
InputPin(int pin)
Constructor.
Definition fastpin.h:126
I/O pin initially set to OUTPUT.
Definition fastpin.h:116
OutputPin(int pin)
Constructor.
Definition fastpin.h:119
Naive fallback solution for low level pin access.
Definition fastpin.h:43
void fastset(FASTLED_REGISTER port_ptr_t port, FASTLED_REGISTER port_t val)
Set the state of a port.
Definition fastpin.h:96
void lo(FASTLED_REGISTER port_ptr_t port)
Set the same pin on another port to LOW
Definition fastpin.h:87
virtual void release()
Set the pin state to LOW
Definition fastpin.h:110
void setOutput()
Set the pin mode as OUTPUT
Definition fastpin.h:66
void set(FASTLED_REGISTER port_t val)
Set the state of the output register.
Definition fastpin.h:91
port_t loval()
Gets the state of the port with this pin LOW
Definition fastpin.h:101
void setInput()
Set the pin mode as INPUT
Definition fastpin.h:69
void hi()
Set the pin state to HIGH
Definition fastpin.h:72
void toggle()
Toggle the pin.
Definition fastpin.h:80
void hi(FASTLED_REGISTER port_ptr_t port)
Set the same pin on another port to HIGH
Definition fastpin.h:84
void lo()
Set the pin state to LOW
Definition fastpin.h:74
virtual void select()
Set the pin state to HIGH
Definition fastpin.h:108
volatile RwReg * port_ptr_t
type for a pin read/write register, volatile
Definition fastpin.h:62
virtual bool isSelected()
Checks if the pin is currently HIGH
Definition fastpin.h:112
RwReg port_t
type for a pin read/write register, non-volatile
Definition fastpin.h:63
port_t mask()
Get the pin mask.
Definition fastpin.h:105
port_ptr_t port()
Get the output state of the port.
Definition fastpin.h:103
void strobe()
Toggle the pin twice to create a short pulse.
Definition fastpin.h:77
Pin(int pin)
Constructor.
Definition fastpin.h:60
port_t hival()
Gets the state of the port with this pin HIGH
Definition fastpin.h:99
Abstract class for "selectable" things.
Definition fastpin.h:33
virtual void release()=0
Release this object.
virtual void select()=0
Select this object.
virtual bool isSelected()=0
Check if this object is currently selected.
volatile uint32_t * ptr_reg32_t
Pointer to a 32-bit register, volatile.
Definition fastpin.h:326
volatile uint32_t & reg32_t
Reference to a 32-bit register, volatile.
Definition fastpin.h:325
Determines which platform system definitions to include.
Utility template for tracking down information about pins and ports.
Definition fastpin.h:330
static const void * portAddr()
Gets the raw address of the port.
Definition fastpin.h:336
static bool hasPort()
Checks whether a port exists.
Definition fastpin.h:332
static const char * portName()
Gets the name of the port, as a C-string.
Definition fastpin.h:334