99
1010#include < zephyr/spinlock.h>
1111
12- static const struct gpio_dt_spec arduino_pins[] = {DT_FOREACH_PROP_ELEM_SEP (
12+ static constexpr struct gpio_dt_spec arduino_pins[] = {DT_FOREACH_PROP_ELEM_SEP (
1313 DT_PATH (zephyr_user), digital_pin_gpios, GPIO_DT_SPEC_GET_BY_IDX, (, ))};
1414
1515namespace {
@@ -58,6 +58,18 @@ constexpr const size_t is_first_appearance(const size_t &idx, const size_t &at,
5858 tail...);
5959}
6060
61+ constexpr inline const struct device *local_gpio_port (pin_size_t gpin) {
62+ return arduino_pins[gpin].port ;
63+ }
64+
65+ constexpr inline pin_size_t local_gpio_pin (pin_size_t gpin) {
66+ return arduino_pins[gpin].pin ;
67+ }
68+
69+ inline int global_gpio_pin_configure (pin_size_t pinNumber, int flags) {
70+ return gpio_pin_configure_dt (&arduino_pins[pinNumber], flags);
71+ }
72+
6173#define GET_DEVICE_VARGS (n, p, i, _ ) DEVICE_DT_GET(DT_GPIO_CTLR_BY_IDX(n, p, i))
6274#define FIRST_APPEARANCE (n, p, i ) \
6375 is_first_appearance (0 , i, ((size_t )-1 ), DEVICE_DT_GET(DT_GPIO_CTLR_BY_IDX(n, p, i)), \
@@ -103,10 +115,10 @@ struct gpio_port_callback *find_gpio_port_callback(const struct device *dev)
103115
104116void setInterruptHandler (pin_size_t pinNumber, voidFuncPtr func)
105117{
106- struct gpio_port_callback *pcb = find_gpio_port_callback (arduino_pins[ pinNumber]. port );
118+ struct gpio_port_callback *pcb = find_gpio_port_callback (local_gpio_port ( pinNumber) );
107119
108120 if (pcb) {
109- pcb->handlers [arduino_pins[ pinNumber]. pin ].handler = func;
121+ pcb->handlers [local_gpio_pin ( pinNumber) ].handler = func;
110122 }
111123}
112124
@@ -192,26 +204,36 @@ void yield(void) {
192204 */
193205void pinMode (pin_size_t pinNumber, PinMode pinMode) {
194206 if (pinMode == INPUT) { // input mode
195- gpio_pin_configure_dt (&arduino_pins[ pinNumber] ,
207+ global_gpio_pin_configure ( pinNumber,
196208 GPIO_INPUT | GPIO_ACTIVE_HIGH);
197209 } else if (pinMode == INPUT_PULLUP) { // input with internal pull-up
198- gpio_pin_configure_dt (&arduino_pins[ pinNumber] ,
210+ global_gpio_pin_configure ( pinNumber,
199211 GPIO_INPUT | GPIO_PULL_UP | GPIO_ACTIVE_HIGH);
200212 } else if (pinMode == INPUT_PULLDOWN) { // input with internal pull-down
201- gpio_pin_configure_dt (&arduino_pins[ pinNumber] ,
213+ global_gpio_pin_configure ( pinNumber,
202214 GPIO_INPUT | GPIO_PULL_DOWN | GPIO_ACTIVE_HIGH);
203215 } else if (pinMode == OUTPUT) { // output mode
204- gpio_pin_configure_dt (&arduino_pins[ pinNumber] ,
216+ global_gpio_pin_configure ( pinNumber,
205217 GPIO_OUTPUT_LOW | GPIO_ACTIVE_HIGH);
206218 }
207219}
208220
209221void digitalWrite (pin_size_t pinNumber, PinStatus status) {
210- gpio_pin_set_dt (&arduino_pins[pinNumber], status);
222+ const struct device *port = local_gpio_port (pinNumber);
223+
224+ if (port) {
225+ gpio_pin_set (port, local_gpio_pin (pinNumber), status);
226+ }
211227}
212228
213229PinStatus digitalRead (pin_size_t pinNumber) {
214- return (gpio_pin_get_dt (&arduino_pins[pinNumber]) == 1 ) ? HIGH : LOW;
230+ const struct device *port = local_gpio_port (pinNumber);
231+
232+ if (port) {
233+ return gpio_pin_get (port, local_gpio_pin (pinNumber) == 1 ) ? HIGH : LOW;
234+ } else {
235+ return LOW;
236+ }
215237}
216238
217239#if CONFIG_ARDUINO_MAX_TONES < 0
@@ -264,18 +286,19 @@ static struct pin_timer* find_pin_timer(pin_size_t pinNumber, bool active_only)
264286void tone_expiry_cb (struct k_timer *timer) {
265287 struct pin_timer *pt = CONTAINER_OF (timer, struct pin_timer , timer);
266288 k_spinlock_key_t key = k_spin_lock (&pt->lock );
289+ const struct device *port = local_gpio_port (pt->pin );
267290 pin_size_t pin = pt->pin ;
268291
269292 if (pt->count == 0 && !pt->infinity ) {
270- if (pin != pin_size_t (- 1 ) ) {
271- gpio_pin_set_dt (&arduino_pins[ pin] , 0 );
293+ if (port ) {
294+ gpio_pin_set (port, local_gpio_pin (pt-> pin ) , 0 );
272295 }
273296
274297 k_timer_stop (timer);
275298 pt->pin = pin_size_t (-1 );
276299 } else {
277- if (pin != pin_size_t (- 1 ) ) {
278- gpio_pin_toggle_dt (&arduino_pins[ pin] );
300+ if (port ) {
301+ gpio_pin_toggle (port, local_gpio_pin (pt-> pin ) );
279302 }
280303
281304 pt->count --;
@@ -289,8 +312,10 @@ void tone(pin_size_t pinNumber, unsigned int frequency,
289312 k_spinlock_key_t key;
290313 struct pin_timer *pt;
291314 k_timeout_t timeout;
315+ const struct device *port;
292316
293317 pt = find_pin_timer (pinNumber, false );
318+ port = local_gpio_port (pt->pin );
294319
295320 if (pt == nullptr ) {
296321 return ;
@@ -304,7 +329,9 @@ void tone(pin_size_t pinNumber, unsigned int frequency,
304329 pt->pin = pin_size_t (-1 );
305330 k_spin_unlock (&pt->lock , key);
306331
307- gpio_pin_set_dt (&arduino_pins[pinNumber], 0 );
332+ if (port) {
333+ gpio_pin_set (port, local_gpio_pin (pinNumber), 0 );
334+ }
308335 return ;
309336 }
310337
@@ -321,15 +348,19 @@ void tone(pin_size_t pinNumber, unsigned int frequency,
321348
322349 k_timer_init (&pt->timer , tone_expiry_cb, NULL );
323350
324- gpio_pin_set_dt (&arduino_pins[pinNumber], 0 );
351+ if (port) {
352+ gpio_pin_set (port, local_gpio_pin (pinNumber), 0 );
353+ }
325354 k_timer_start (&pt->timer , timeout, timeout);
326355}
327356
328357void noTone (pin_size_t pinNumber) {
329358 struct pin_timer *pt;
330359 k_spinlock_key_t key;
360+ const struct device *port;
331361
332362 pt = find_pin_timer (pinNumber, true );
363+ port = local_gpio_port (pt->pin );
333364
334365 if (pt == nullptr ) {
335366 return ;
@@ -340,7 +371,9 @@ void noTone(pin_size_t pinNumber) {
340371 pt->pin = pin_size_t (-1 );
341372 k_spin_unlock (&pt->lock , key);
342373
343- gpio_pin_set_dt (&arduino_pins[pinNumber], 0 );
374+ if (port) {
375+ gpio_pin_set (port, local_gpio_pin (pinNumber), 0 );
376+ }
344377}
345378
346379void delay (unsigned long ms) {
@@ -442,6 +475,7 @@ int analogRead(pin_size_t pinNumber)
442475
443476void attachInterrupt (pin_size_t pinNumber, voidFuncPtr callback, PinStatus pinStatus)
444477{
478+ const struct device *port = local_gpio_port (pinNumber);
445479 struct gpio_port_callback *pcb;
446480 gpio_flags_t intmode = 0 ;
447481
@@ -463,16 +497,18 @@ void attachInterrupt(pin_size_t pinNumber, voidFuncPtr callback, PinStatus pinSt
463497 return ;
464498 }
465499
466- pcb = find_gpio_port_callback (arduino_pins[pinNumber]. port );
500+ pcb = find_gpio_port_callback (port);
467501 __ASSERT (pcb != nullptr , " gpio_port_callback not found" );
468502
469- pcb->pins |= BIT (arduino_pins[ pinNumber]. pin );
503+ pcb->pins |= BIT (local_gpio_pin ( pinNumber) );
470504 setInterruptHandler (pinNumber, callback);
471505 enableInterrupt (pinNumber);
472506
473- gpio_pin_interrupt_configure (arduino_pins[pinNumber].port , arduino_pins[pinNumber].pin , intmode);
474- gpio_init_callback (&pcb->callback , handleGpioCallback, pcb->pins );
475- gpio_add_callback (arduino_pins[pinNumber].port , &pcb->callback );
507+ if (port) {
508+ gpio_pin_interrupt_configure (port, local_gpio_pin (pinNumber), intmode);
509+ gpio_init_callback (&pcb->callback , handleGpioCallback, pcb->pins );
510+ gpio_add_callback (port, &pcb->callback );
511+ }
476512}
477513
478514void detachInterrupt (pin_size_t pinNumber)
@@ -500,29 +536,30 @@ long random(long max) {
500536#endif
501537
502538unsigned long pulseIn (pin_size_t pinNumber, uint8_t state, unsigned long timeout) {
539+ const struct device *port = local_gpio_port (pinNumber);
540+ const size_t pin = local_gpio_pin (pinNumber);
503541 struct k_timer timer;
504542 int64_t start, end, delta = 0 ;
505- const struct gpio_dt_spec *spec = &arduino_pins[pinNumber];
506543
507- if (!gpio_is_ready_dt (spec )) {
544+ if (!device_is_ready (port )) {
508545 return 0 ;
509546 }
510547
511548 k_timer_init (&timer, NULL , NULL );
512549 k_timer_start (&timer, K_MSEC (timeout), K_NO_WAIT);
513550
514- while (gpio_pin_get_dt (spec ) == state && k_timer_status_get (&timer) == 0 );
551+ while (gpio_pin_get (port, pin ) == state && k_timer_status_get (&timer) == 0 );
515552 if (k_timer_status_get (&timer) > 0 ) {
516553 goto cleanup;
517554 }
518555
519- while (gpio_pin_get_dt (spec ) != state && k_timer_status_get (&timer) == 0 );
556+ while (gpio_pin_get (port, pin ) != state && k_timer_status_get (&timer) == 0 );
520557 if (k_timer_status_get (&timer) > 0 ) {
521558 goto cleanup;
522559 }
523560
524561 start = k_uptime_ticks ();
525- while (gpio_pin_get_dt (spec ) == state && k_timer_status_get (&timer) == 0 );
562+ while (gpio_pin_get (port, pin ) == state && k_timer_status_get (&timer) == 0 );
526563 if (k_timer_status_get (&timer) > 0 ) {
527564 goto cleanup;
528565 }
@@ -536,18 +573,18 @@ unsigned long pulseIn(pin_size_t pinNumber, uint8_t state, unsigned long timeout
536573}
537574
538575void enableInterrupt (pin_size_t pinNumber) {
539- struct gpio_port_callback *pcb = find_gpio_port_callback (arduino_pins[ pinNumber]. port );
576+ struct gpio_port_callback *pcb = find_gpio_port_callback (local_gpio_port ( pinNumber) );
540577
541578 if (pcb) {
542- pcb->handlers [arduino_pins[ pinNumber]. pin ].enabled = true ;
579+ pcb->handlers [local_gpio_pin ( pinNumber) ].enabled = true ;
543580 }
544581}
545582
546583void disableInterrupt (pin_size_t pinNumber) {
547- struct gpio_port_callback *pcb = find_gpio_port_callback (arduino_pins[ pinNumber]. port );
584+ struct gpio_port_callback *pcb = find_gpio_port_callback (local_gpio_port ( pinNumber) );
548585
549586 if (pcb) {
550- pcb->handlers [arduino_pins[ pinNumber]. pin ].enabled = false ;
587+ pcb->handlers [local_gpio_pin ( pinNumber) ].enabled = false ;
551588 }
552589}
553590
@@ -567,7 +604,7 @@ void noInterrupts(void) {
567604
568605int digitalPinToInterrupt (pin_size_t pin) {
569606 struct gpio_port_callback *pcb =
570- find_gpio_port_callback (arduino_pins[ pin]. port );
607+ find_gpio_port_callback (local_gpio_port ( pin) );
571608
572609 return (pcb) ? pin : -1 ;
573610}
0 commit comments