From 3cbadad05b0e1e223ebccfe429014ec7cfb3e1fc Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Lo=C3=AFc=20Dauphin?= <astralien3000@yahoo.fr>
Date: Wed, 17 Jan 2018 18:12:19 +0100
Subject: [PATCH] boards/teensy31: initial support

---
 boards/teensy31/Makefile              |   3 +
 boards/teensy31/Makefile.dep          |   1 +
 boards/teensy31/Makefile.features     |  11 ++
 boards/teensy31/Makefile.include      |  28 +++++
 boards/teensy31/board.c               |  36 ++++++
 boards/teensy31/doc.txt               |  37 ++++++
 boards/teensy31/include/board.h       |  74 +++++++++++
 boards/teensy31/include/periph_conf.h | 172 ++++++++++++++++++++++++++
 8 files changed, 362 insertions(+)
 create mode 100644 boards/teensy31/Makefile
 create mode 100644 boards/teensy31/Makefile.dep
 create mode 100644 boards/teensy31/Makefile.features
 create mode 100644 boards/teensy31/Makefile.include
 create mode 100644 boards/teensy31/board.c
 create mode 100644 boards/teensy31/doc.txt
 create mode 100644 boards/teensy31/include/board.h
 create mode 100644 boards/teensy31/include/periph_conf.h

diff --git a/boards/teensy31/Makefile b/boards/teensy31/Makefile
new file mode 100644
index 0000000000..f8fcbb53a0
--- /dev/null
+++ b/boards/teensy31/Makefile
@@ -0,0 +1,3 @@
+MODULE = board
+
+include $(RIOTBASE)/Makefile.base
diff --git a/boards/teensy31/Makefile.dep b/boards/teensy31/Makefile.dep
new file mode 100644
index 0000000000..98782c48fb
--- /dev/null
+++ b/boards/teensy31/Makefile.dep
@@ -0,0 +1 @@
+include $(RIOTCPU)/kinetis/Makefile.dep
diff --git a/boards/teensy31/Makefile.features b/boards/teensy31/Makefile.features
new file mode 100644
index 0000000000..acfddffc97
--- /dev/null
+++ b/boards/teensy31/Makefile.features
@@ -0,0 +1,11 @@
+# Put defined MCU peripherals here (in alphabetical order)
+FEATURES_PROVIDED += periph_cpuid
+FEATURES_PROVIDED += periph_gpio
+FEATURES_PROVIDED += periph_pwm
+FEATURES_PROVIDED += periph_timer
+FEATURES_PROVIDED += periph_uart
+
+# The board MPU family (used for grouping by the CI system)
+FEATURES_MCU_GROUP = cortex_m4_2
+
+include $(RIOTCPU)/cortexm_common/Makefile.features
diff --git a/boards/teensy31/Makefile.include b/boards/teensy31/Makefile.include
new file mode 100644
index 0000000000..cf00f50129
--- /dev/null
+++ b/boards/teensy31/Makefile.include
@@ -0,0 +1,28 @@
+# define the cpu used by the Teensy3.1 & 3.2 board
+CPU = kinetis
+CPU_MODEL = mk20dx256vlh7
+
+# custom flasher to use with the bootloader
+TEENSY_LOADER = $(RIOTBASE)/dist/tools/teensy-loader-cli/teensy_loader
+FLASHER = $(TEENSY_LOADER)
+
+OFLAGS = -O ihex
+HEXFILE = $(ELFFILE:.elf=.hex)
+
+FFLAGS ?= --mcu=mk20dx256 $(HEXFILE)
+
+ifeq ($(TEENSY_LOADER),$(FLASHER))
+  FLASHDEPS += $(TEENSY_LOADER)
+endif
+
+# define the default port depending on the host OS
+PORT_LINUX ?= /dev/ttyACM0
+PORT_DARWIN ?= $(firstword $(sort $(wildcard /dev/tty.usbserial-*)))
+
+$(TEENSY_LOADER):
+	@echo "[INFO] teensy_loader binary not found - building it from source now"
+	CC= CFLAGS= make -C $(RIOTBASE)/dist/tools/teensy-loader-cli
+	@echo "[INFO] teensy_loader binary successfully build!"
+
+# setup serial terminal
+include $(RIOTMAKE)/tools/serial.inc.mk
diff --git a/boards/teensy31/board.c b/boards/teensy31/board.c
new file mode 100644
index 0000000000..1486b7c722
--- /dev/null
+++ b/boards/teensy31/board.c
@@ -0,0 +1,36 @@
+/*
+ * Copyright (C) 2017 Inria
+ *
+ * This file is subject to the terms and conditions of the GNU Lesser
+ * General Public License v2.1. See the file LICENSE in the top level
+ * directory for more details.
+ */
+
+/**
+ * @ingroup     boards_teensy31
+ * @{
+ *
+ * @file
+ * @brief       Board specific implementations for the Teensy3.1 & 3.2 boards
+ *
+ * @author      Loïc Dauphin <loic.dauphin@inria.fr>
+ *
+ * @}
+ */
+
+#include <stddef.h>
+#include <stdio.h>
+
+#include "board.h"
+#include "cpu.h"
+#include "periph/gpio.h"
+
+void board_init(void)
+{
+    /* initialize the boards LEDs */
+    gpio_init(LED0_PIN, GPIO_OUT);
+    gpio_set(LED0_PIN);
+
+    /* initialize the CPU */
+    cpu_init();
+}
diff --git a/boards/teensy31/doc.txt b/boards/teensy31/doc.txt
new file mode 100644
index 0000000000..95a93929a6
--- /dev/null
+++ b/boards/teensy31/doc.txt
@@ -0,0 +1,37 @@
+/**
+ * @defgroup    boards_teensy31 Teensy3.1 & 3.2
+ * @ingroup     boards
+ * @brief       Support for the Teensy3.1 & 3.2
+ *
+ * ### General information
+ *
+ * Teensy3.1 & 3.2 boards are development boards made by
+ * [PJRC](https://www.pjrc.com/teensy/teensy31.html).
+ *
+ * Teensy3.1 & 3.2 boards are built based on the Freescale MK20DX256VLH7
+ * microcontroller. See [Datasheet](http://cache.freescale.com/files/32bit/doc/data_sheet/K20P64M72SF1.pdf).
+ *
+ * ### Pinout
+ *
+ * <img src="https://www.pjrc.com/teensy/teensy32_front_pinout.png"
+ *      alt="Teensy 3.2 front pinout" style="width:800px;"/>
+ *
+ * <img src="https://www.pjrc.com/teensy/teensy32_back_pinout.png"
+ *      alt="Teensy 3.2 back pinout" style="width:800px;"/>
+ *
+ * ### Flash the board
+ *
+ * 1. Put the board in bootloader mode by tapping the reset button.<br/>
+ *    The board should remain in bootloader mode until flashed.
+ *
+ * 2. Use `BOARD=teensy31` with the `make` command. This works for Teensy 3.1 & 3.2<br/>
+ *    Example with `hello-world` application:
+ * ```
+ *      make BOARD=teensy31 -C examples/hello-world flash
+ * ```
+ *
+ * ### Accessing STDIO via UART
+ *
+ * To access the STDIO of RIOT, a FTDI to USB converter needs to be plugged to
+ * the RX/TX pins on the board (pins 0 and 1 of the board).
+ */
diff --git a/boards/teensy31/include/board.h b/boards/teensy31/include/board.h
new file mode 100644
index 0000000000..e5d9a50c41
--- /dev/null
+++ b/boards/teensy31/include/board.h
@@ -0,0 +1,74 @@
+/*
+ * Copyright (C) 2017 Inria
+ *
+ * This file is subject to the terms and conditions of the GNU Lesser
+ * General Public License v2.1. See the file LICENSE in the top level
+ * directory for more details.
+ */
+
+/**
+ * @ingroup     boards_teensy31
+ * @brief       Board specific files for Teensy3.1 & 3.2
+ * @{
+ *
+ * @file
+ * @brief       Board specific definitions for the Teensy3.1 & 3.2 board
+ *
+ * @author      Loïc Dauphin <loic.dauphin@inria.fr>
+ */
+
+#ifndef BOARD_H
+#define BOARD_H
+
+#include "cpu.h"
+#include "periph_conf.h"
+#include "mtd.h"
+
+/* Use the on board RTC 32kHz clock for LPTMR clocking. */
+#undef LPTIMER_CLKSRC
+/** @brief Clock source for the LPTMR module */
+#define LPTIMER_CLKSRC LPTIMER_CLKSRC_ERCLK32K
+
+/** Disable hardware watchdog, for debugging purposes, don't use this on production builds. */
+#define DISABLE_WDOG    1
+
+/**
+ * @name   xtimer configuration
+ * @{
+ */
+#define XTIMER_DEV                  (TIMER_PIT_DEV(0))
+#define XTIMER_CHAN                 (0)
+#define XTIMER_BACKOFF              (40)
+#define XTIMER_ISR_BACKOFF          (40)
+#define XTIMER_OVERHEAD             (30)
+/** @} */
+
+/**
+ * @name   LED pin definitions and handlers
+ * @{
+ */
+#define LED_PORT            PTC
+#define LED0_BIT            (5)
+
+#define LED0_PIN            GPIO_PIN(PORT_C, LED0_BIT)
+
+#define LED0_ON             (LED_PORT->PSOR = (1 << LED0_BIT))
+#define LED0_OFF            (LED_PORT->PCOR = (1 << LED0_BIT))
+#define LED0_TOGGLE         (LED_PORT->PTOR = (1 << LED0_BIT))
+/** @} */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/**
+ * @brief Initialize board specific hardware, including clock, LEDs and std-IO
+ */
+void board_init(void);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* BOARD_H */
+/** @} */
diff --git a/boards/teensy31/include/periph_conf.h b/boards/teensy31/include/periph_conf.h
new file mode 100644
index 0000000000..baf56935ce
--- /dev/null
+++ b/boards/teensy31/include/periph_conf.h
@@ -0,0 +1,172 @@
+/*
+ * Copyright (C) 2017 Inria
+ *
+ * This file is subject to the terms and conditions of the GNU Lesser
+ * General Public License v2.1. See the file LICENSE in the top level
+ * directory for more details.
+ */
+
+/**
+ * @ingroup     boards_teensy31
+ * @{
+ *
+ * @file
+ * @name        Peripheral MCU configuration for the Teensy3.1 & 3.2
+ *
+ * @author      Loïc Dauphin <loic.dauphin@inria.fr>
+ */
+
+#ifndef PERIPH_CONF_H
+#define PERIPH_CONF_H
+
+#include "periph_cpu.h"
+
+#ifdef __cplusplus
+extern "C"
+{
+#endif
+
+/**
+ * @name Clock system configuration
+ * @{
+ */
+static const clock_config_t clock_config = {
+    /*
+     * This configuration results in the system running from the FLL output with
+     * the following clock frequencies:
+     * Core:  48 MHz
+     * Bus:   48 MHz
+     * Flex:  24 MHz
+     * Flash: 24 MHz
+     */
+    /* The board has a 16 MHz crystal, though it is not used in this configuration */
+    /* This configuration uses the RTC crystal to provide the base clock, it
+     * should have better accuracy than the internal slow clock, and lower power
+     * consumption than using the 16 MHz crystal and the OSC0 module */
+    .clkdiv1 = SIM_CLKDIV1_OUTDIV1(0) | SIM_CLKDIV1_OUTDIV2(0) |
+               SIM_CLKDIV1_OUTDIV3(2) | SIM_CLKDIV1_OUTDIV4(2),
+    .default_mode = KINETIS_MCG_MODE_FEE,
+    .erc_range = KINETIS_MCG_ERC_RANGE_LOW, /* Input clock is 32768 Hz */
+    .fcrdiv = 0, /* Fast IRC divide by 1 => 4 MHz */
+    .oscsel = 1, /* Use RTC for external clock */
+    /* 16 pF capacitors yield ca 10 pF load capacitance as required by the
+     * onboard xtal, not used when OSC0 is disabled */
+    .clc = 0b0001,
+    .fll_frdiv = 0b000, /* Divide by 1 => FLL input 32768 Hz */
+    .fll_factor_fei = KINETIS_MCG_FLL_FACTOR_1464, /* FLL freq = 48 MHz */
+    .fll_factor_fee = KINETIS_MCG_FLL_FACTOR_1464, /* FLL freq = 48 MHz */
+    /* PLL is unavailable when using a 32768 Hz source clock, so the
+     * configuration below can only be used if the above config is modified to
+     * use the 16 MHz crystal instead of the RTC. */
+    .pll_prdiv = 0b00111, /* Divide by 8 */
+    .pll_vdiv = 0b01100, /* Multiply by 36 => PLL freq = 72 MHz */
+    .enable_oscillator = false, /* the RTC module provides the clock input signal */
+    .select_fast_irc = true, /* Only used for FBI mode */
+    .enable_mcgirclk = false,
+};
+#define CLOCK_CORECLOCK              (48000000ul)
+#define CLOCK_BUSCLOCK               (CLOCK_CORECLOCK / 1)
+/** @} */
+
+/**
+ * @name Timer configuration
+ * @{
+ */
+#define PIT_NUMOF               (2U)
+#define PIT_CONFIG {                 \
+        {                            \
+            .prescaler_ch = 0,       \
+            .count_ch = 1,           \
+        },                           \
+        {                            \
+            .prescaler_ch = 2,       \
+            .count_ch = 3,           \
+        },                           \
+    }
+#define LPTMR_NUMOF             (0U)
+#define LPTMR_CONFIG { \
+    }
+#define TIMER_NUMOF             ((PIT_NUMOF) + (LPTMR_NUMOF))
+
+#define PIT_BASECLOCK           (CLOCK_BUSCLOCK)
+#define PIT_ISR_0               isr_pit1
+#define PIT_ISR_1               isr_pit3
+/** @} */
+
+/**
+ * @name UART configuration
+ * @{
+ */
+static const uart_conf_t uart_config[] = {
+    {
+        .dev    = UART0,
+        .freq   = CLOCK_CORECLOCK,
+        .pin_rx = GPIO_PIN(PORT_B, 16), /* TEENSY PIN 0 */
+        .pin_tx = GPIO_PIN(PORT_B, 17), /* TEENSY PIN 1 */
+        .pcr_rx = PORT_PCR_MUX(3),
+        .pcr_tx = PORT_PCR_MUX(3),
+        .irqn   = UART0_RX_TX_IRQn,
+        .scgc_addr = &SIM->SCGC4,
+        .scgc_bit = SIM_SCGC4_UART0_SHIFT,
+        .mode   = UART_MODE_8N1,
+        .type   = KINETIS_UART,
+    },
+    {
+        .dev    = UART1,
+        .freq   = CLOCK_CORECLOCK,
+        .pin_rx = GPIO_PIN(PORT_C, 3), /* TEENSY PIN 9 */
+        .pin_tx = GPIO_PIN(PORT_C, 4), /* TEENSY PIN 10 */
+        .pcr_rx = PORT_PCR_MUX(3),
+        .pcr_tx = PORT_PCR_MUX(3),
+        .irqn   = UART1_RX_TX_IRQn,
+        .scgc_addr = &SIM->SCGC4,
+        .scgc_bit = SIM_SCGC4_UART1_SHIFT,
+        .mode   = UART_MODE_8N1,
+        .type   = KINETIS_UART,
+    },
+};
+
+#define UART_0_ISR          (isr_uart0_rx_tx)
+#define UART_1_ISR          (isr_uart1_rx_tx)
+
+#define UART_NUMOF          (sizeof(uart_config) / sizeof(uart_config[0]))
+/** @} */
+
+/**
+ * @name    PWM configuration
+ * @{
+ */
+static const pwm_conf_t pwm_config[] = {
+    {
+        .ftm        = FTM0,
+        .chan       = {
+            { .pin = GPIO_PIN(PORT_C, 1), .af = 4, .ftm_chan = 0 }, /* TEENSY PIN 22 */
+            { .pin = GPIO_PIN(PORT_C, 2), .af = 4, .ftm_chan = 1 }, /* TEENSY PIN 23 */
+            { .pin = GPIO_UNDEF,          .af = 0, .ftm_chan = 0 },
+            { .pin = GPIO_UNDEF,          .af = 0, .ftm_chan = 0 }
+        },
+        .chan_numof = 2,
+        .ftm_num    = 0
+    },
+    {
+        .ftm        = FTM1,
+        .chan       = {
+            { .pin = GPIO_PIN(PORT_A, 12), .af = 3, .ftm_chan = 0 }, /* TEENSY PIN 3 */
+            { .pin = GPIO_PIN(PORT_A, 13), .af = 3, .ftm_chan = 1 }, /* TEENSY PIN 4 */
+            { .pin = GPIO_UNDEF,           .af = 0, .ftm_chan = 0 },
+            { .pin = GPIO_UNDEF,           .af = 0, .ftm_chan = 0 }
+        },
+        .chan_numof = 2,
+        .ftm_num    = 1
+    }
+};
+
+#define PWM_NUMOF           (sizeof(pwm_config) / sizeof(pwm_config[0]))
+/** @} */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* PERIPH_CONF_H */
+/** @} */
-- 
GitLab