summaryrefslogtreecommitdiff
path: root/nuttx/arch/mips/src/pic32mz/pic32mz-gpio.c
diff options
context:
space:
mode:
Diffstat (limited to 'nuttx/arch/mips/src/pic32mz/pic32mz-gpio.c')
-rw-r--r--nuttx/arch/mips/src/pic32mz/pic32mz-gpio.c344
1 files changed, 344 insertions, 0 deletions
diff --git a/nuttx/arch/mips/src/pic32mz/pic32mz-gpio.c b/nuttx/arch/mips/src/pic32mz/pic32mz-gpio.c
new file mode 100644
index 000000000..c4008a952
--- /dev/null
+++ b/nuttx/arch/mips/src/pic32mz/pic32mz-gpio.c
@@ -0,0 +1,344 @@
+/****************************************************************************
+ * arch/mips/src/pic32mz/pic32mz-gpio.c
+ *
+ * Copyright (C) 2015 Gregory Nutt. All rights reserved.
+ * Author: Gregory Nutt <gnutt@nuttx.org>
+ *
+ * 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 NuttX 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 OWNER 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.
+ *
+ ****************************************************************************/
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include <nuttx/config.h>
+
+#include <stdint.h>
+#include <assert.h>
+#include <errno.h>
+
+#include <nuttx/irq.h>
+#include <nuttx/arch.h>
+#include <arch/board/board.h>
+
+#include "up_arch.h"
+
+#include "chip/pic32mz-ioport.h"
+#include "pic32mz-gpio.h"
+
+#if CHIP_NPORTS > 0
+
+/****************************************************************************
+ * Pre-processor Definitions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Public Data
+ ****************************************************************************/
+
+/****************************************************************************
+ * Private Data
+ ****************************************************************************/
+
+static const uintptr_t g_gpiobase[CHIP_NPORTS] =
+{
+ PIC32MZ_IOPORTA_K1BASE
+#if CHIP_NPORTS > 1
+ , PIC32MZ_IOPORTB_K1BASE
+#endif
+#if CHIP_NPORTS > 2
+ , PIC32MZ_IOPORTC_K1BASE
+#endif
+#if CHIP_NPORTS > 3
+ , PIC32MZ_IOPORTD_K1BASE
+#endif
+#if CHIP_NPORTS > 4
+ , PIC32MZ_IOPORTE_K1BASE
+#endif
+#if CHIP_NPORTS > 5
+ , PIC32MZ_IOPORTF_K1BASE
+#endif
+#if CHIP_NPORTS > 6
+ , PIC32MZ_IOPORTG_K1BASE
+#endif
+#if CHIP_NPORTS > 7
+ , PIC32MZ_IOPORTH_K1BASE
+#endif
+#if CHIP_NPORTS > 8
+ , PIC32MZ_IOPORTJ_K1BASE
+#endif
+#if CHIP_NPORTS > 9
+ , PIC32MZ_IOPORTK_K1BASE
+#endif
+};
+
+/****************************************************************************
+ * Private Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: Inline PIN set field extractors
+ ****************************************************************************/
+
+static inline bool pic32mz_output(uint16_t pinset)
+{
+ return ((pinset & GPIO_OUTPUT) != 0);
+}
+
+static inline bool pic32mz_opendrain(uint16_t pinset)
+{
+ return ((pinset & GPIO_MODE_MASK) == GPIO_OPENDRAN);
+}
+
+static inline bool pic32mz_outputhigh(uint16_t pinset)
+{
+ return ((pinset & GPIO_VALUE_MASK) != 0);
+}
+
+static inline bool pic32mz_value(uint16_t pinset)
+{
+ return ((pinset & GPIO_VALUE_MASK) != GPIO_VALUE_ZERO);
+}
+
+static inline unsigned int pic32mz_portno(uint16_t pinset)
+{
+ return ((pinset & GPIO_PORT_MASK) >> GPIO_PORT_SHIFT);
+}
+
+static inline unsigned int pic32mz_pinno(uint16_t pinset)
+{
+ return ((pinset & GPIO_PIN_MASK) >> GPIO_PIN_SHIFT);
+}
+
+static inline unsigned int pic32mz_analog(uint16_t pinset)
+{
+ return ((pinset & GPIO_ANALOG_MASK) != 0);
+}
+
+/****************************************************************************
+ * Public Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: pic32mz_configgpio
+ *
+ * Description:
+ * Configure a GPIO pin based on bit-encoded description of the pin (the
+ * interrupt will be configured when pic32mz_attach() is called.
+ *
+ * Returned Value:
+ * OK on success; negated errno on failure.
+ *
+ ****************************************************************************/
+
+int pic32mz_configgpio(uint16_t cfgset)
+{
+ unsigned int port = pic32mz_portno(cfgset);
+ unsigned int pin = pic32mz_pinno(cfgset);
+ uint32_t mask = (1 << pin);
+ uintptr_t base;
+
+ /* Verify that the port number is within range */
+
+ if (port < CHIP_NPORTS)
+ {
+ /* Get the base address of the ports */
+
+ base = g_gpiobase[port];
+
+ /* Is this an input or an output? */
+
+ sched_lock();
+ if (pic32mz_output(cfgset))
+ {
+ /* Not analog */
+
+ putreg32(mask, base + PIC32MZ_IOPORT_ANSELCLR_OFFSET);
+
+ /* It is an output; clear the corresponding bit in the TRIS register */
+
+ putreg32(mask, base + PIC32MZ_IOPORT_TRISCLR_OFFSET);
+
+ /* Is it an open drain output? */
+
+ if (pic32mz_opendrain(cfgset))
+ {
+ /* It is an open drain output. Set the corresponding bit in
+ * the ODC register.
+ */
+
+ putreg32(mask, base + PIC32MZ_IOPORT_ODCSET_OFFSET);
+ }
+ else
+ {
+ /* Is is a normal output. Clear the corresponding bit in the
+ * ODC register.
+ */
+
+ putreg32(mask, base + PIC32MZ_IOPORT_ODCCLR_OFFSET);
+ }
+
+ /* Set the initial output value */
+
+ pic32mz_gpiowrite(cfgset, pic32mz_outputhigh(cfgset));
+ }
+ else
+ {
+ /* It is an input; set the corresponding bit in the TRIS register. */
+
+ putreg32(mask, base + PIC32MZ_IOPORT_TRISSET_OFFSET);
+ putreg32(mask, base + PIC32MZ_IOPORT_ODCCLR_OFFSET);
+
+ /* Is it an analog input? */
+
+ if (pic32mz_analog(cfgset))
+ {
+ putreg32(mask, base + PIC32MZ_IOPORT_ANSELSET_OFFSET);
+ }
+ else
+ {
+ putreg32(mask, base + PIC32MZ_IOPORT_ANSELCLR_OFFSET);
+ }
+ }
+
+ sched_unlock();
+ return OK;
+ }
+
+ return -EINVAL;
+}
+
+/****************************************************************************
+ * Name: pic32mz_gpiowrite
+ *
+ * Description:
+ * Write one or zero to the selected GPIO pin
+ *
+ ****************************************************************************/
+
+void pic32mz_gpiowrite(uint16_t pinset, bool value)
+{
+ unsigned int port = pic32mz_portno(pinset);
+ unsigned int pin = pic32mz_pinno(pinset);
+ uintptr_t base;
+
+ /* Verify that the port number is within range */
+
+ if (port < CHIP_NPORTS)
+ {
+ /* Get the base address of the ports */
+
+ base = g_gpiobase[port];
+
+ /* Set or clear the output */
+
+ if (value)
+ {
+ putreg32(1 << pin, base + PIC32MZ_IOPORT_PORTSET_OFFSET);
+ }
+ else
+ {
+ putreg32(1 << pin, base + PIC32MZ_IOPORT_PORTCLR_OFFSET);
+ }
+ }
+}
+
+/****************************************************************************
+ * Name: pic32mz_gpioread
+ *
+ * Description:
+ * Read one or zero from the selected GPIO pin
+ *
+ ****************************************************************************/
+
+bool pic32mz_gpioread(uint16_t pinset)
+{
+ unsigned int port = pic32mz_portno(pinset);
+ unsigned int pin = pic32mz_pinno(pinset);
+ uintptr_t base;
+
+ /* Verify that the port number is within range */
+
+ if (port < CHIP_NPORTS)
+ {
+ /* Get the base address of the ports */
+
+ base = g_gpiobase[port];
+
+ /* Get ane return the input value */
+
+ return (getreg32(base + PIC32MZ_IOPORT_PORT_OFFSET) & (1 << pin)) != 0;
+ }
+
+ return false;
+}
+
+/****************************************************************************
+ * Function: pic32mz_dumpgpio
+ *
+ * Description:
+ * Dump all GPIO registers associated with the provided base address
+ *
+ ****************************************************************************/
+
+#if defined(CONFIG_DEBUG) && defined(CONFIG_DEBUG_VERBOSE) && defined(CONFIG_DEBUG_GPIO)
+void pic32mz_dumpgpio(uint32_t pinset, const char *msg)
+{
+ unsigned int port = pic32mz_portno(pinset);
+ irqstate_t flags;
+ uintptr_t base;
+
+ /* Verify that the port number is within range */
+
+ if (port < CHIP_NPORTS)
+ {
+ /* Get the base address of the ports */
+
+ base = g_gpiobase[port];
+
+ /* The following requires exclusive access to the GPIO registers */
+
+ sched_lock();
+ lldbg("IOPORT%c pinset: %04x base: %08x -- %s\n",
+ 'A'+port, pinset, base, msg);
+ lldbg(" TRIS: %08x PORT: %08x LAT: %08x ODC: %08x\n",
+ getreg32(base + PIC32MZ_IOPORT_TRIS_OFFSET),
+ getreg32(base + PIC32MZ_IOPORT_PORT_OFFSET),
+ getreg32(base + PIC32MZ_IOPORT_LAT_OFFSET),
+ getreg32(base + PIC32MZ_IOPORT_ODC_OFFSET));
+ lldbg(" CNCON: %08x CNEN: %08x CNPUE: %08x\n",
+ getreg32(PIC32MZ_IOPORT_CNCON),
+ getreg32(PIC32MZ_IOPORT_CNEN),
+ getreg32(PIC32MZ_IOPORT_CNPUE));
+ sched_unlock();
+ }
+}
+#endif
+
+#endif /* CHIP_NPORTS > 0 */