Loading...
Searching...
No Matches
gpio_ll_arch.h
Go to the documentation of this file.
1/*
2 * SPDX-FileCopyrightText: 2016 Freie Universität Berlin
3 * SPDX-FileCopyrightText: 2017 OTA keys S.A.
4 * SPDX-License-Identifier: LGPL-2.1-only
5 */
6
7#pragma once
8
20
21#include "architecture.h"
22#include "periph_cpu.h"
23
24#ifdef __cplusplus
25extern "C" {
26#endif
27
28#ifndef DOXYGEN /* hide implementation specific details from Doxygen */
29
30#define GPIO_PORT_NUMBERING_ALPHABETIC 1
31
32#ifdef GPIOA_BASE
33# define GPIO_PORT_0 GPIOA_BASE
34#endif
35
36#ifdef GPIOB_BASE
37# define GPIO_PORT_1 GPIOB_BASE
38#endif
39
40#ifdef GPIOC_BASE
41# define GPIO_PORT_2 GPIOC_BASE
42#endif
43
44#ifdef GPIOD_BASE
45# define GPIO_PORT_3 GPIOD_BASE
46#endif
47
48#ifdef GPIOE_BASE
49# define GPIO_PORT_4 GPIOE_BASE
50#endif
51
52#ifdef GPIOF_BASE
53# define GPIO_PORT_5 GPIOF_BASE
54#endif
55
56#ifdef GPIOG_BASE
57# define GPIO_PORT_6 GPIOG_BASE
58#endif
59
60#ifdef GPIOH_BASE
61# define GPIO_PORT_7 GPIOH_BASE
62#endif
63
64#ifdef GPIOI_BASE
65# define GPIO_PORT_8 GPIOI_BASE
66#endif
67
68#ifdef GPIOJ_BASE
69# define GPIO_PORT_9 GPIOJ_BASE
70#endif
71
72#ifdef GPIOK_BASE
73# define GPIO_PORT_10 GPIOK_BASE
74#endif
75
76static inline gpio_port_t gpio_port(uword_t num)
77{
78#if defined(CPU_FAM_STM32MP1)
79 return GPIOA_BASE + (num << 12);
80#else
81 return GPIOA_BASE + (num << 10);
82#endif
83}
84
85static inline uword_t gpio_port_num(gpio_port_t port)
86{
87#if defined(CPU_FAM_STM32MP1)
88 return (port - GPIOA_BASE) >> 12;
89#else
90 return (port - GPIOA_BASE) >> 10;
91#endif
92}
93
94static inline uword_t gpio_ll_read(gpio_port_t port)
95{
96 GPIO_TypeDef *p = (GPIO_TypeDef *)port;
97 return p->IDR;
98}
99
100static inline uword_t gpio_ll_read_output(gpio_port_t port)
101{
102 GPIO_TypeDef *p = (GPIO_TypeDef *)port;
103 return p->ODR;
104}
105
106static inline void gpio_ll_set(gpio_port_t port, uword_t mask)
107{
108 GPIO_TypeDef *p = (GPIO_TypeDef *)port;
109 p->BSRR = mask;
110}
111
112static inline void gpio_ll_clear(gpio_port_t port, uword_t mask)
113{
114 GPIO_TypeDef *p = (GPIO_TypeDef *)port;
115 /* The STM32F4 vendor header files do include defines for accessing the
116 * BRR register, but do not have a BRR register.
117 * See https://github.com/STMicroelectronics/cmsis_device_f4/pull/7 */
118#if defined(GPIO_BRR_BR0) && !defined(CPU_FAM_STM32F4)
119 p->BRR = mask;
120#else
121 /* The first half-word sets GPIOs, the second half-world clears GPIOs */
122 volatile uint16_t *brr = (volatile uint16_t *)&(p->BSRR);
123 brr[1] = (uint16_t)mask;
124#endif
125}
126
127static inline void gpio_ll_toggle(gpio_port_t port, uword_t mask)
128{
129 GPIO_TypeDef *p = (GPIO_TypeDef *)port;
130 unsigned irq_state = irq_disable();
131 p->ODR ^= mask;
132 irq_restore(irq_state);
133}
134
135static inline void gpio_ll_write(gpio_port_t port, uword_t value)
136{
137 GPIO_TypeDef *p = (GPIO_TypeDef *)port;
138 p->ODR = value;
139}
140
141#ifdef MODULE_PERIPH_GPIO_LL_SWITCH_DIR
143{
144 /* implementation too large to always inline */
145 extern uword_t gpio_ll_prepare_switch_dir_impl(uword_t mask);
146 return gpio_ll_prepare_switch_dir_impl(mask);
147}
148
149static inline void gpio_ll_switch_dir_output(gpio_port_t port, uword_t pins)
150{
151 GPIO_TypeDef *p = (GPIO_TypeDef *)port;
152 unsigned irq_state = irq_disable();
153 p->MODER |= pins;
154 irq_restore(irq_state);
155}
156
157static inline void gpio_ll_switch_dir_input(gpio_port_t port, uword_t pins)
158{
159 GPIO_TypeDef *p = (GPIO_TypeDef *)port;
160 unsigned irq_state = irq_disable();
161 p->MODER &= ~pins;
162 irq_restore(irq_state);
163}
164#endif
165
166static inline gpio_port_t gpio_get_port(gpio_t pin)
167{
168 return pin & 0xfffffff0LU;
169}
170
171static inline uint8_t gpio_get_pin_num(gpio_t pin)
172{
173 return pin & 0xfLU;
174}
175
176static inline gpio_port_t gpio_port_pack_addr(void *addr)
177{
178 return (gpio_port_t)addr;
179}
180
181static inline void * gpio_port_unpack_addr(gpio_port_t port)
182{
183 if (port < GPIOA_BASE) {
184 return (void *)port;
185 }
186
187 return NULL;
188}
189
190static inline bool is_gpio_port_num_valid(uint_fast8_t num)
191{
192 switch (num) {
193 default:
194 return false;
195#ifdef GPIOA_BASE
196 case 0:
197#endif
198#ifdef GPIOB_BASE
199 case 1:
200#endif
201#ifdef GPIOC_BASE
202 case 2:
203#endif
204#ifdef GPIOD_BASE
205 case 3:
206#endif
207#ifdef GPIOE_BASE
208 case 4:
209#endif
210#ifdef GPIOF_BASE
211 case 5:
212#endif
213#ifdef GPIOG_BASE
214 case 6:
215#endif
216#ifdef GPIOH_BASE
217 case 7:
218#endif
219#ifdef GPIOI_BASE
220 case 8:
221#endif
222#ifdef GPIOJ_BASE
223 case 9:
224#endif
225#ifdef GPIOK_BASE
226 case 10:
227#endif
228#ifdef GPIOL_BASE
229 case 11:
230#endif
231#ifdef GPIOM_BASE
232 case 12:
233#endif
234#ifdef GPION_BASE
235 case 13:
236#endif
237#ifdef GPIOO_BASE
238 case 14:
239#endif
240#ifdef GPIOP_BASE
241 case 15:
242#endif
243#ifdef GPIOQ_BASE
244 case 16:
245#endif
246#ifdef GPIOR_BASE
247 case 17:
248#endif
249#ifdef GPIOS_BASE
250 case 18:
251#endif
252#ifdef GPIOT_BASE
253 case 19:
254#endif
255#ifdef GPIOU_BASE
256 case 20:
257#endif
258#ifdef GPIOV_BASE
259 case 21:
260#endif
261#ifdef GPIOW_BASE
262 case 22:
263#endif
264#ifdef GPIOX_BASE
265 case 23:
266#endif
267#ifdef GPIOY_BASE
268 case 24:
269#endif
270#ifdef GPIOZ_BASE
271 case 25:
272#endif
273 return true;
274 }
275}
276
277#endif /* DOXYGEN */
278#ifdef __cplusplus
279}
280#endif
281
Platform-independent access to architecture details.
MAYBE_INLINE void irq_restore(unsigned state)
This function restores the IRQ disable bit in the status register to the value contained within passe...
MAYBE_INLINE unsigned irq_disable(void)
This function sets the IRQ disable bit in the status register.
static uint8_t gpio_get_pin_num(gpio_t pin)
Extract the pin number from a gpio_t
static void gpio_ll_set(gpio_port_t port, uword_t mask)
Perform an reg |= mask operation on the I/O register of the port.
gpio_port_t gpio_port(uword_t num)
Get the gpio_port_t value of the port number num.
static gpio_port_t gpio_port_pack_addr(void *addr)
Pack a pointer into a gpio_port_t.
static void gpio_ll_switch_dir_output(gpio_port_t port, uword_t pins)
Turn GPIO pins specified by pins (obtained from gpio_ll_prepare_switch_dir) to outputs.
static void gpio_ll_switch_dir_input(gpio_port_t port, uword_t pins)
Turn GPIO pins specified by pins (obtained from gpio_ll_prepare_switch_dir) to inputs.
static uword_t gpio_ll_read(gpio_port_t port)
Get the current input value of all GPIO pins of the given port as bitmask.
static gpio_port_t gpio_get_port(gpio_t pin)
Extract the gpio_port_t from a gpio_t
uword_t gpio_port_num(gpio_port_t port)
Get the number of the GPIO port port refers to.
static uword_t gpio_ll_prepare_switch_dir(uword_t mask)
Prepare bitmask for use with gpio_ll_switch_dir_output and gpio_ll_switch_dir_input.
Definition gpio_ll.h:750
static void * gpio_port_unpack_addr(gpio_port_t port)
Extract a data pointer that was packed by gpio_port_pack_addr.
static bool is_gpio_port_num_valid(uint_fast8_t num)
Check if the given number is a valid argument for gpio_port.
static uword_t gpio_ll_read_output(gpio_port_t port)
Get the current output value of all GPIO pins of the given port as bitmask.
static void gpio_ll_clear(gpio_port_t port, uword_t mask)
Perform an reg &= ~mask operation on the I/O register of the port.
static void gpio_ll_toggle(gpio_port_t port, uword_t mask)
Perform an reg ^= mask operation on the I/O register of the port.
static void gpio_ll_write(gpio_port_t port, uword_t state)
Perform a masked write operation on the I/O register of the port.
uintptr_t gpio_port_t
GPIO port type.
Definition gpio_ll.h:95
uint< NUM > _t uword_t
Word sized unsigned integer.
Shared CPU specific definitions for the STM32 family.