From b17a936bf75f62e677fbc9d7360800c42dbca1d5 Mon Sep 17 00:00:00 2001 From: Michael LeMay Date: Mon, 22 Aug 2016 16:28:58 -0700 Subject: [PATCH] galileo: Add board-level abstraction layer for GPIO This patch adds a HAL for GPIOs so that users of the API can specify board-level IO pin numbers rather than CPU-level pin numbers. --- examples/galileo/gpio-input.c | 9 +-- examples/galileo/gpio-interrupt.c | 11 ++-- examples/galileo/gpio-output.c | 5 +- platform/galileo/Makefile.galileo | 2 +- platform/galileo/drivers/galileo-gpio.c | 72 +++++++++++++++++++++++ platform/galileo/drivers/galileo-gpio.h | 40 +++++++++++++ platform/galileo/drivers/galileo-pinmux.c | 11 ++-- 7 files changed, 132 insertions(+), 18 deletions(-) create mode 100644 platform/galileo/drivers/galileo-gpio.c create mode 100644 platform/galileo/drivers/galileo-gpio.h diff --git a/examples/galileo/gpio-input.c b/examples/galileo/gpio-input.c index 077055a69..804c9a86e 100644 --- a/examples/galileo/gpio-input.c +++ b/examples/galileo/gpio-input.c @@ -33,10 +33,11 @@ #include "contiki.h" #include "sys/ctimer.h" +#include "galileo-gpio.h" #include "gpio.h" -#define PIN_OUTPUT 5 -#define PIN_INPUT 6 +#define PIN_OUTPUT 2 +#define PIN_INPUT 3 static uint32_t value; static struct ctimer timer; @@ -51,9 +52,9 @@ timeout(void *data) /* toggle pin state */ value = !value; - quarkX1000_gpio_write(PIN_OUTPUT, value); + galileo_gpio_write(PIN_OUTPUT, value); - quarkX1000_gpio_read(PIN_INPUT, &value_in); + galileo_gpio_read(PIN_INPUT, &value_in); if (value == value_in) printf("GPIO pin value match!\n"); diff --git a/examples/galileo/gpio-interrupt.c b/examples/galileo/gpio-interrupt.c index ca4606266..6289fe4f1 100644 --- a/examples/galileo/gpio-interrupt.c +++ b/examples/galileo/gpio-interrupt.c @@ -33,10 +33,11 @@ #include "contiki.h" #include "sys/ctimer.h" +#include "galileo-gpio.h" #include "gpio.h" -#define PIN_OUTPUT 5 -#define PIN_INTR 6 +#define PIN_OUTPUT 2 +#define PIN_INTR 3 static struct ctimer timer; @@ -47,8 +48,8 @@ static void timeout(void *data) { /* emulate an interrupt */ - quarkX1000_gpio_write(PIN_OUTPUT, 0); - quarkX1000_gpio_write(PIN_OUTPUT, 1); + galileo_gpio_write(PIN_OUTPUT, 0); + galileo_gpio_write(PIN_OUTPUT, 1); ctimer_reset(&timer); } @@ -63,7 +64,7 @@ PROCESS_THREAD(gpio_interrupt_process, ev, data) { PROCESS_BEGIN(); - quarkX1000_gpio_config(PIN_INTR, QUARKX1000_GPIO_INT | QUARKX1000_GPIO_ACTIVE_HIGH | QUARKX1000_GPIO_EDGE); + galileo_gpio_config(PIN_INTR, QUARKX1000_GPIO_INT | QUARKX1000_GPIO_ACTIVE_HIGH | QUARKX1000_GPIO_EDGE); quarkX1000_gpio_set_callback(callback); diff --git a/examples/galileo/gpio-output.c b/examples/galileo/gpio-output.c index 4cc50597e..33a1159da 100644 --- a/examples/galileo/gpio-output.c +++ b/examples/galileo/gpio-output.c @@ -33,9 +33,10 @@ #include "contiki.h" #include "sys/ctimer.h" +#include "galileo-gpio.h" #include "gpio.h" -#define PIN 5 /* IO2 */ +#define PIN 2 static uint32_t value; static struct ctimer timer; @@ -48,7 +49,7 @@ timeout(void *data) { /* toggle pin state */ value = !value; - quarkX1000_gpio_write(PIN, value); + galileo_gpio_write(PIN, value); ctimer_reset(&timer); } diff --git a/platform/galileo/Makefile.galileo b/platform/galileo/Makefile.galileo index daada587a..d0ff4b0a8 100644 --- a/platform/galileo/Makefile.galileo +++ b/platform/galileo/Makefile.galileo @@ -5,7 +5,7 @@ LIBGCC_PATH = /usr/lib/gcc/$(shell gcc -dumpmachine)/$(shell gcc -dumpversion) CONTIKI_TARGET_DIRS = . core/sys/ drivers/ net/ CONTIKI_TARGET_MAIN = ${addprefix $(OBJECTDIR)/,contiki-main.o} -CONTIKI_SOURCEFILES += contiki-main.c clock.c rtimer-arch.c gpio-pcal9535a.c pwm-pca9685.c galileo-pinmux.c eth-proc.c eth-conf.c +CONTIKI_SOURCEFILES += contiki-main.c clock.c rtimer-arch.c gpio-pcal9535a.c pwm-pca9685.c galileo-pinmux.c eth-proc.c eth-conf.c galileo-gpio.c ifeq ($(CONTIKI_WITH_IPV6),1) CONTIKI_SOURCEFILES += nbr-table.c packetbuf.c linkaddr.c link-stats.c diff --git a/platform/galileo/drivers/galileo-gpio.c b/platform/galileo/drivers/galileo-gpio.c new file mode 100644 index 000000000..593f7acda --- /dev/null +++ b/platform/galileo/drivers/galileo-gpio.c @@ -0,0 +1,72 @@ +/* + * Copyright (C) 2016, Intel Corporation. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include "galileo-gpio.h" +#include +#include "gpio.h" + +/* Must be implemented in board-specific pinmux file to map a board-level GPIO + * pin number to the corresponding CPU GPIO pin number. + * + * The return value should always be a positive number. An assertion within the + * function should check the validity of the pin number. + */ +int galileo_brd_to_cpu_gpio_pin(unsigned pin, bool *sus); + +static int +brd_to_cpu_pin(unsigned pin) +{ + int cpu_pin; + bool sus; + + cpu_pin = galileo_brd_to_cpu_gpio_pin(pin, &sus); + assert(!sus); + + return cpu_pin; +} + +void galileo_gpio_config(uint8_t pin, int flags) +{ + assert(quarkX1000_gpio_config(brd_to_cpu_pin(pin), flags) == 0); +} + +/** + * \brief Read from GPIO. + * \param pin Board-level IO pin number. + */ +void galileo_gpio_read(uint8_t pin, uint8_t *value) +{ + assert(quarkX1000_gpio_read(brd_to_cpu_pin(pin), value) == 0); +} + +void galileo_gpio_write(uint8_t pin, uint8_t value) +{ + assert(quarkX1000_gpio_write(brd_to_cpu_pin(pin), value) == 0); +} diff --git a/platform/galileo/drivers/galileo-gpio.h b/platform/galileo/drivers/galileo-gpio.h new file mode 100644 index 000000000..07dbc1082 --- /dev/null +++ b/platform/galileo/drivers/galileo-gpio.h @@ -0,0 +1,40 @@ +/* + * Copyright (C) 2016, Intel Corporation. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef PLATFORM_GALILEO_DRIVERS_GALILEO_GPIO_H_ +#define PLATFORM_GALILEO_DRIVERS_GALILEO_GPIO_H_ + +#include + +void galileo_gpio_config(uint8_t pin, int flags); +void galileo_gpio_read(uint8_t pin, uint8_t *value); +void galileo_gpio_write(uint8_t pin, uint8_t value); + +#endif /* PLATFORM_GALILEO_DRIVERS_GALILEO_GPIO_H_ */ diff --git a/platform/galileo/drivers/galileo-pinmux.c b/platform/galileo/drivers/galileo-pinmux.c index c99ccd6c2..f4ea5be30 100644 --- a/platform/galileo/drivers/galileo-pinmux.c +++ b/platform/galileo/drivers/galileo-pinmux.c @@ -571,10 +571,9 @@ flatten_pin_num(galileo_pin_group_t grp, unsigned *pin) assert(*pin < GALILEO_NUM_PINS); } -/* Map a board-level GPIO pin number to the corresponding CPU GPIO pin number. - */ -static int -brd_to_cpu_gpio_pin(unsigned pin, bool *sus) +/* See galileo-gpio.c for the declaration of this function. */ +int +galileo_brd_to_cpu_gpio_pin(unsigned pin, bool *sus) { static const int SUS = 0x100; unsigned pins[GALILEO_NUM_PINS] = { @@ -603,7 +602,7 @@ galileo_pinmux_select_din(galileo_pin_group_t grp, unsigned pin) assert(galileo_pinmux_set_pin(pin, GALILEO_PINMUX_FUNC_B) == 0); - cpu_pin = brd_to_cpu_gpio_pin(pin, &sus); + cpu_pin = galileo_brd_to_cpu_gpio_pin(pin, &sus); /* GPIO_SUS pins are currently unsupported. */ assert(!sus); quarkX1000_gpio_config(cpu_pin, QUARKX1000_GPIO_IN); @@ -618,7 +617,7 @@ galileo_pinmux_select_dout(galileo_pin_group_t grp, unsigned pin) assert(galileo_pinmux_set_pin(pin, GALILEO_PINMUX_FUNC_A) == 0); - cpu_pin = brd_to_cpu_gpio_pin(pin, &sus); + cpu_pin = galileo_brd_to_cpu_gpio_pin(pin, &sus); /* GPIO_SUS pins are currently unsupported. */ assert(!sus); quarkX1000_gpio_config(cpu_pin, QUARKX1000_GPIO_OUT);