From 40f55f8b983bbac5d2bb08785b4c852926567fe5 Mon Sep 17 00:00:00 2001
From: "J.C. Nelson" <32139633+xC0000005@users.noreply.github.com>
Date: Thu, 11 Jun 2020 19:53:26 -0700
Subject: [PATCH] Chitu variant for disk-based update (#18264)

---
 .../share/PlatformIO/boards/chitu_F103.json   |  48 ++++
 .../PlatformIO/variants/CHITU_F103/board.cpp  | 233 +++++++++++++++++
 .../variants/CHITU_F103/board/board.h         | 240 ++++++++++++++++++
 .../variants/CHITU_F103/ld/common.inc         | 220 ++++++++++++++++
 .../variants/CHITU_F103/ld/extra_libs.inc     |   7 +
 .../variants/CHITU_F103/ld/stm32f103z_dfu.ld  |  29 +++
 .../variants/CHITU_F103/ld/stm32f103zc.ld     |  27 ++
 .../variants/CHITU_F103/ld/stm32f103zd.ld     |  27 ++
 .../variants/CHITU_F103/ld/stm32f103ze.ld     |  29 +++
 .../variants/CHITU_F103/ld/vector_symbols.inc |  78 ++++++
 .../variants/CHITU_F103/pins_arduino.h        |   2 +
 .../PlatformIO/variants/CHITU_F103/variant.h  |  17 ++
 .../variants/CHITU_F103/wirish/boards.cpp     | 225 ++++++++++++++++
 .../CHITU_F103/wirish/boards_setup.cpp        | 123 +++++++++
 .../variants/CHITU_F103/wirish/start.S        |  57 +++++
 .../variants/CHITU_F103/wirish/start_c.c      | 144 +++++++++++
 .../variants/CHITU_F103/wirish/syscalls.c     | 176 +++++++++++++
 platformio.ini                                |   5 +-
 18 files changed, 1685 insertions(+), 2 deletions(-)
 create mode 100644 buildroot/share/PlatformIO/boards/chitu_F103.json
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/board.cpp
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/board/board.h
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/ld/common.inc
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/ld/extra_libs.inc
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103z_dfu.ld
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103zc.ld
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103zd.ld
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103ze.ld
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/ld/vector_symbols.inc
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/pins_arduino.h
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/variant.h
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/wirish/boards.cpp
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/wirish/boards_setup.cpp
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/wirish/start.S
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/wirish/start_c.c
 create mode 100755 buildroot/share/PlatformIO/variants/CHITU_F103/wirish/syscalls.c

diff --git a/buildroot/share/PlatformIO/boards/chitu_F103.json b/buildroot/share/PlatformIO/boards/chitu_F103.json
new file mode 100644
index 0000000000..ab772aea07
--- /dev/null
+++ b/buildroot/share/PlatformIO/boards/chitu_F103.json
@@ -0,0 +1,48 @@
+{
+  "build": {
+    "core": "maple",
+    "cpu": "cortex-m3",
+    "extra_flags": "-DSTM32F103xE -DSTM32F1",
+    "f_cpu": "72000000L",
+    "hwids": [
+      [
+        "0x1EAF",
+        "0x0003"
+      ],
+      [
+        "0x1EAF",
+        "0x0004"
+      ]
+    ],
+    "mcu": "stm32f103zet6",
+    "variant": "CHITU_F103",
+    "ldscript": "chitu_f103.ld"
+  },
+  "debug": {
+    "jlink_device": "STM32F103ZE",
+    "openocd_target": "stm32f1x",
+    "svd_path": "STM32F103xx.svd"
+  },
+  "frameworks": [
+    "arduino"
+  ],
+  "name": "CHITU STM32F103Z (64k RAM. 512k Flash)",
+  "upload": {
+    "disable_flushing": false,
+    "maximum_ram_size": 60536,
+    "maximum_size": 480288,
+    "protocol": "stlink",
+    "protocols": [
+      "jlink",
+      "stlink",
+      "blackmagic",
+      "serial",
+      "dfu"
+    ],
+    "require_upload_port": true,
+    "use_1200bps_touch": false,
+    "wait_for_upload_port": false
+  },
+  "url": "http://www.st.com/en/microcontrollers/stm32f103ze.html",
+  "vendor": "Generic"
+}
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/board.cpp b/buildroot/share/PlatformIO/variants/CHITU_F103/board.cpp
new file mode 100755
index 0000000000..fbc5c7df13
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/board.cpp
@@ -0,0 +1,233 @@
+/******************************************************************************
+ * The MIT License
+ *
+ * Copyright (c) 2011 LeafLabs, LLC.
+ *
+ * Permission is hereby granted, free of charge, to any person
+ * obtaining a copy of this software and associated documentation
+ * files (the "Software"), to deal in the Software without
+ * restriction, including without limitation the rights to use, copy,
+ * modify, merge, publish, distribute, sublicense, and/or sell copies
+ * of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
+ * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
+ * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+ * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ *****************************************************************************/
+
+/**
+ * @file   wirish/boards/maple/board.cpp
+ * @author Marti Bolivar <mbolivar@leaflabs.com>
+ * @brief  Maple board file.
+ */
+
+#include <board/board.h>         // For this board's header file
+
+/* Roger Clark. Added next to includes for changes to Serial */
+#include <libmaple/usart.h>
+#include <HardwareSerial.h>
+
+#include <wirish_types.h> // For stm32_pin_info and its contents
+                                 // (these go into PIN_MAP).
+
+#include "boards_private.h"      // For PMAP_ROW(), which makes
+                                 // PIN_MAP easier to read.
+
+// boardInit(): nothing special to do for Maple.
+//
+// When defining your own board.cpp, you can put extra code in this
+// function if you have anything you want done on reset, before main()
+// or setup() are called.
+//
+// If there's nothing special you need done, feel free to leave this
+// function out, as we do here.
+/*
+void boardInit(void) {
+}
+*/
+
+// Pin map: this lets the basic I/O functions (digitalWrite(),
+// analogRead(), pwmWrite()) translate from pin numbers to STM32
+// peripherals.
+//
+// PMAP_ROW() lets us specify a row (really a struct stm32_pin_info)
+// in the pin map. Its arguments are:
+//
+// - GPIO device for the pin (&gpioa, etc.)
+// - GPIO bit for the pin (0 through 15)
+// - Timer device, or NULL if none
+// - Timer channel (1 to 4, for PWM), or 0 if none
+// - ADC device, or NULL if none
+// - ADC channel, or ADCx if none
+
+extern const stm32_pin_info PIN_MAP[BOARD_NR_GPIO_PINS] = {
+  /*
+    gpio_dev *gpio_device;      GPIO device 
+    timer_dev *timer_device;    Pin's timer device, if any.
+    const adc_dev *adc_device;  ADC device, if any. 
+    uint8 gpio_bit;             Pin's GPIO port bit. 
+    uint8 timer_channel;        Timer channel, or 0 if none. 
+    uint8 adc_channel;          Pin ADC channel, or ADCx if none. 
+  */
+
+  {&gpioa, &timer2, &adc1,  0, 1,    0}, /* PA0 */
+  {&gpioa, &timer2, &adc1,  1, 2,    1}, /* PA1 */
+  {&gpioa, &timer2, &adc1,  2, 3,    2}, /* PA2 */
+  {&gpioa, &timer2, &adc1,  3, 4,    3}, /* PA3 */
+  {&gpioa,   NULL, &adc1,  4, 0,    4}, /* PA4 */	
+  {&gpioa,   NULL, &adc1,  5, 0,    5}, /* PA5 */
+  {&gpioa, &timer3, &adc1,  6, 1,    6}, /* PA6 */
+  {&gpioa, &timer3, &adc1,  7, 2,    7}, /* PA7 */
+  {&gpioa, &timer1, NULL,  8, 1, ADCx}, /* PA8 */
+  {&gpioa, &timer1, NULL,  9, 2, ADCx}, /* PA9 */
+  {&gpioa, &timer1, NULL, 10, 3, ADCx}, /* PA10 */
+  {&gpioa,   NULL, NULL, 11, 0, ADCx}, /* PA11 */
+  {&gpioa,   NULL, NULL, 12, 0, ADCx}, /* PA12 */	
+  {&gpioa,   NULL, NULL, 13, 0, ADCx}, /* PA13 */
+  {&gpioa,   NULL, NULL, 14, 0, ADCx}, /* PA14 */
+  {&gpioa,   NULL, NULL, 15, 0, ADCx}, /* PA15 */
+
+  {&gpiob, &timer3, &adc1,  0, 3,    8}, /* PB0 */
+  {&gpiob, &timer3, &adc1,  1, 4,    9}, /* PB1 */
+  {&gpiob, &timer3, &adc1,  2, 4,    9}, /* PB2 */
+  {&gpiob,   NULL, NULL,  3, 0, ADCx}, /* PB3  */
+  {&gpiob,   NULL, NULL,  4, 0, ADCx}, /* PB4  */
+  {&gpiob,   NULL, NULL,  5, 0, ADCx}, /* PB5 */
+  {&gpiob, &timer4, NULL,  6, 1, ADCx}, /* PB6 */
+  {&gpiob, &timer4, NULL,  7, 2, ADCx}, /* PB7 */
+  {&gpiob, &timer4, NULL,  8, 3, ADCx}, /* PB8 */
+  {&gpiob, &timer4, NULL,  9, 4, ADCx}, /* PB9 */
+  {&gpiob,   NULL, NULL, 10, 0, ADCx}, /* PB10 */
+  {&gpiob,   NULL, NULL, 11, 0, ADCx}, /* PB11 */
+  {&gpiob,   NULL, NULL, 12, 0, ADCx}, /* PB12 */
+  {&gpiob,   NULL, NULL, 13, 0, ADCx}, /* PB13 */
+  {&gpiob,   NULL, NULL, 14, 0, ADCx}, /* PB14 */
+  {&gpiob,   NULL, NULL, 15, 0, ADCx}, /* PB15 */
+
+
+  {&gpioc,   NULL, &adc1,  0, 0,   10}, /* PC0 */
+  {&gpioc,   NULL, &adc1,  1, 0,   11}, /* PC1 */
+  {&gpioc,   NULL, &adc1,  2, 0,   12}, /* PC2 */
+  {&gpioc,   NULL, &adc1,  3, 0,   13}, /* PC3 */
+  {&gpioc,   NULL, &adc1,  4, 0,   14}, /* PC4 */
+  {&gpioc,   NULL, &adc1,  5, 0,   15}, /* PC5 */
+  {&gpioc, &timer8, NULL,  6, 1, ADCx}, /* PC6 */	
+  {&gpioc, &timer8, NULL,  7, 2, ADCx}, /* PC7 */
+  {&gpioc, &timer8, NULL,  8, 3, ADCx}, /* PC8 */
+  {&gpioc, &timer8, NULL,  9, 4, ADCx}, /* PC9 */
+  {&gpioc,   NULL, NULL, 10, 0, ADCx}, /* PC10 UART4_TX/SDIO_D2 */
+  {&gpioc,   NULL, NULL, 11, 0, ADCx}, /* PC11 UART4_RX/SDIO_D3 */
+  {&gpioc,   NULL, NULL, 12, 0, ADCx}, /* PC12 UART5_TX/SDIO_CK */	
+  {&gpioc,   NULL, NULL, 13, 0, ADCx}, /* PC13 TAMPER-RTC */
+  {&gpioc,   NULL, NULL, 14, 0, ADCx}, /* PC14 OSC32_IN */
+  {&gpioc,   NULL, NULL, 15, 0, ADCx}, /* PC15 OSC32_OUT */
+
+	{&gpiod,   NULL, NULL,   0, 0, ADCx} , /* PD0 OSC_IN */
+	{&gpiod,   NULL, NULL,   1, 0, ADCx} , /* PD1  OSC_OUT */
+	{&gpiod,   NULL, NULL,   2, 0, ADCx} , /* PD2  TIM3_ETR/UART5_RX SDIO_CMD */
+	
+	{&gpiod,   NULL, NULL,   3, 0, ADCx} , /* PD3  FSMC_CLK */
+	{&gpiod,   NULL, NULL,   4, 0, ADCx} , /* PD4  FSMC_NOE */
+	{&gpiod,   NULL, NULL,   5, 0, ADCx} , /* PD5  FSMC_NWE */
+	{&gpiod,   NULL, NULL,   6, 0, ADCx} , /* PD6  FSMC_NWAIT */
+	{&gpiod,   NULL, NULL,   7, 0, ADCx} , /* PD7  FSMC_NE1/FSMC_NCE2 */
+	{&gpiod,   NULL, NULL,   8, 0, ADCx} , /* PD8  FSMC_D13 */
+	{&gpiod,   NULL, NULL,   9, 0, ADCx} , /* PD9  FSMC_D14 */
+	{&gpiod,   NULL, NULL,  10, 0, ADCx} , /* PD10  FSMC_D15 */
+	{&gpiod,   NULL, NULL,  11, 0, ADCx} , /* PD11  FSMC_A16 */
+	{&gpiod,   NULL, NULL,  12, 0, ADCx} , /* PD12  FSMC_A17 */
+	{&gpiod,   NULL, NULL,  13, 0, ADCx} , /* PD13  FSMC_A18 */	
+	{&gpiod,   NULL, NULL,  14, 0, ADCx} , /* PD14  FSMC_D0 */
+	{&gpiod,   NULL, NULL,  15, 0, ADCx} , /* PD15  FSMC_D1 */
+	
+	{&gpioe,   NULL, NULL,   0, 0, ADCx} , /* PE0   */
+	{&gpioe,   NULL, NULL,   1, 0, ADCx} , /* PE1   */
+	{&gpioe,   NULL, NULL,   2, 0, ADCx} , /* PE2   */
+	{&gpioe,   NULL, NULL,   3, 0, ADCx} , /* PE3   */
+	{&gpioe,   NULL, NULL,   4, 0, ADCx} , /* PE4   */
+	{&gpioe,   NULL, NULL,   5, 0, ADCx} , /* PE5   */
+	{&gpioe,   NULL, NULL,   6, 0, ADCx} , /* PE6   */
+	{&gpioe,   NULL, NULL,   7, 0, ADCx} , /* PE7   */
+	{&gpioe,   NULL, NULL,   8, 0, ADCx} , /* PE8   */
+	{&gpioe,   NULL, NULL,   9, 0, ADCx} , /* PE9   */
+	{&gpioe,   NULL, NULL,  10, 0, ADCx} , /* PE10  */
+	{&gpioe,   NULL, NULL,  11, 0, ADCx} , /* PE11  */
+	{&gpioe,   NULL, NULL,  12, 0, ADCx} , /* PE12  */
+	{&gpioe,   NULL, NULL,  13, 0, ADCx} , /* PE13  */	
+	{&gpioe,   NULL, NULL,  14, 0, ADCx} , /* PE14  */
+	{&gpioe,   NULL, NULL,  15, 0, ADCx} , /* PE15  */	
+
+	{&gpiof,   NULL, NULL,   0, 0, ADCx} , /* PF0   */
+	{&gpiof,   NULL, NULL,   1, 0, ADCx} , /* PF1   */
+	{&gpiof,   NULL, NULL,   2, 0, ADCx} , /* PF2   */
+	{&gpiof,   NULL, NULL,   3, 0, ADCx} , /* PF3   */
+	{&gpiof,   NULL, NULL,   4, 0, ADCx} , /* PF4   */
+	{&gpiof,   NULL, NULL,   5, 0, ADCx} , /* PF5   */
+	{&gpiof,   NULL, NULL,   6, 0, ADCx} , /* PF6   */
+	{&gpiof,   NULL, NULL,   7, 0, ADCx} , /* PF7   */
+	{&gpiof,   NULL, NULL,   8, 0, ADCx} , /* PF8   */
+	{&gpiof,   NULL, NULL,   9, 0, ADCx} , /* PF9   */
+	{&gpiof,   NULL, NULL,  10, 0, ADCx} , /* PF10  */
+	{&gpiof,   NULL, NULL,  11, 0, ADCx} , /* PF11  */
+	{&gpiof,   NULL, NULL,  12, 0, ADCx} , /* PF12  */
+	{&gpiof,   NULL, NULL,  13, 0, ADCx} , /* PF13  */	
+	{&gpiof,   NULL, NULL,  14, 0, ADCx} , /* PF14  */
+	{&gpiof,   NULL, NULL,  15, 0, ADCx} , /* PF15  */		
+	
+	{&gpiog,   NULL, NULL,   0, 0, ADCx} , /* PG0   */
+	{&gpiog,   NULL, NULL,   1, 0, ADCx} , /* PG1   */
+	{&gpiog,   NULL, NULL,   2, 0, ADCx} , /* PG2   */
+	{&gpiog,   NULL, NULL,   3, 0, ADCx} , /* PG3   */
+	{&gpiog,   NULL, NULL,   4, 0, ADCx} , /* PG4   */
+	{&gpiog,   NULL, NULL,   5, 0, ADCx} , /* PG5   */
+	{&gpiog,   NULL, NULL,   6, 0, ADCx} , /* PG6   */
+	{&gpiog,   NULL, NULL,   7, 0, ADCx} , /* PG7   */
+	{&gpiog,   NULL, NULL,   8, 0, ADCx} , /* PG8   */
+	{&gpiog,   NULL, NULL,   9, 0, ADCx} , /* PG9   */
+	{&gpiog,   NULL, NULL,  10, 0, ADCx} , /* PG10  */
+	{&gpiog,   NULL, NULL,  11, 0, ADCx} , /* PG11  */
+	{&gpiog,   NULL, NULL,  12, 0, ADCx} , /* PG12  */
+	{&gpiog,   NULL, NULL,  13, 0, ADCx} , /* PG13  */	
+	{&gpiog,   NULL, NULL,  14, 0, ADCx} , /* PG14  */
+	{&gpiog,   NULL, NULL,  15, 0, ADCx}   /* PG15  */		
+};
+
+/*  Basically everything that is defined as having a timer us PWM */
+extern const uint8 boardPWMPins[BOARD_NR_PWM_PINS] __FLASH__ = {
+  PA0,PA1,PA2,PA3,PA6,PA7,PA8,PA9,PA10,PB0,PB1,PB6,PB7,PB8,PB9,PC6,PC7,PC8,PC9
+};
+
+/*  Basically everything that is defined having ADC */
+extern const uint8 boardADCPins[BOARD_NR_ADC_PINS] __FLASH__ = {
+  PA0,PA1,PA2,PA3,PA4,PA5,PA6,PA7,PB0,PB1,PC0,PC1,PC2,PC3,PC4,PC5
+};
+
+/* not sure what this us used for */
+extern const uint8 boardUsedPins[BOARD_NR_USED_PINS] __FLASH__ = {
+  BOARD_JTMS_SWDIO_PIN,
+  BOARD_JTCK_SWCLK_PIN, BOARD_JTDI_PIN, BOARD_JTDO_PIN, BOARD_NJTRST_PIN
+};
+
+
+#ifdef SERIAL_USB
+	DEFINE_HWSERIAL(Serial1, 1);
+	DEFINE_HWSERIAL(Serial2, 2);
+	DEFINE_HWSERIAL(Serial3, 3);
+	DEFINE_HWSERIAL_UART(Serial4, 4);
+	DEFINE_HWSERIAL_UART(Serial5, 5);
+#else
+	DEFINE_HWSERIAL(Serial, 1);
+	DEFINE_HWSERIAL(Serial1, 2);
+	DEFINE_HWSERIAL(Serial2, 3);
+	DEFINE_HWSERIAL_UART(Serial3, 4);
+	DEFINE_HWSERIAL_UART(Serial4, 5);
+#endif
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/board/board.h b/buildroot/share/PlatformIO/variants/CHITU_F103/board/board.h
new file mode 100755
index 0000000000..20fd9d379f
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/board/board.h
@@ -0,0 +1,240 @@
+/******************************************************************************
+ * The MIT License
+ *
+ * Copyright (c) 2011 LeafLabs, LLC.
+ *
+ * Permission is hereby granted, free of charge, to any person
+ * obtaining a copy of this software and associated documentation
+ * files (the "Software"), to deal in the Software without
+ * restriction, including without limitation the rights to use, copy,
+ * modify, merge, publish, distribute, sublicense, and/or sell copies
+ * of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
+ * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
+ * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+ * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ *****************************************************************************/
+
+/**
+ * @file   maple_RET6.h
+ * @author Marti Bolivar <mbolivar@leaflabs.com>
+ * @brief  Private include file for Maple RET6 Edition in boards.h
+ *
+ * See maple.h for more information on these definitions.
+ */
+
+#ifndef _BOARDS_GENERIC_STM32F103Z_H_
+#define _BOARDS_GENERIC_STM32F103Z_H_
+
+/* A few of these values will seem strange given that it's a
+ * high-density board. */
+
+#define CYCLES_PER_MICROSECOND  72
+#define SYSTICK_RELOAD_VAL     (F_CPU/1000) - 1 /* takes a cycle to reload */
+
+// USARTS
+#define BOARD_NR_USARTS         5
+#define BOARD_USART1_TX_PIN     PA9
+#define BOARD_USART1_RX_PIN     PA10
+
+#define BOARD_USART2_TX_PIN     PA2
+#define BOARD_USART2_RX_PIN     PA3
+
+#define BOARD_USART3_TX_PIN     PB10
+#define BOARD_USART3_RX_PIN     PB11
+
+#define BOARD_USART4_TX_PIN     PC10
+#define BOARD_USART4_RX_PIN     PC11
+
+#define BOARD_USART5_TX_PIN     PC12
+#define BOARD_USART5_RX_PIN     PD2
+
+/* Note:
+ *
+ * SPI3 is unusable due to pin 43 (PB4) and NRST tie-together :(, but
+ * leave the definitions so as not to clutter things up.  This is only
+ * OK since RET6 Ed. is specifically advertised as a beta board. */
+#define BOARD_NR_SPI            3
+#define BOARD_SPI1_NSS_PIN      PA4
+#define BOARD_SPI1_SCK_PIN      PA5
+#define BOARD_SPI1_MISO_PIN     PA6
+#define BOARD_SPI1_MOSI_PIN     PA7
+
+
+
+#define BOARD_SPI2_NSS_PIN      PB12
+#define BOARD_SPI2_SCK_PIN      PB13
+#define BOARD_SPI2_MISO_PIN     PB14
+#define BOARD_SPI2_MOSI_PIN     PB15
+
+
+#define BOARD_SPI3_NSS_PIN      PA15
+#define BOARD_SPI3_SCK_PIN      PB3
+#define BOARD_SPI3_MISO_PIN     PB4
+#define BOARD_SPI3_MOSI_PIN     PB5
+
+
+/* GPIO A to E = 5 * 16  - BOOT1 not used = 79*/
+#define BOARD_NR_GPIO_PINS      112
+/* Note: NOT 19. The missing one is D38 a.k.a. BOARD_BUTTON_PIN, which
+ * isn't broken out to a header and is thus unusable for PWM. */
+#define BOARD_NR_PWM_PINS       19
+#define BOARD_NR_ADC_PINS       16
+#define BOARD_NR_USED_PINS      7
+
+#define BOARD_JTMS_SWDIO_PIN    39
+#define BOARD_JTCK_SWCLK_PIN    40
+#define BOARD_JTDI_PIN          41
+#define BOARD_JTDO_PIN          42
+#define BOARD_NJTRST_PIN        43
+
+/* USB configuration.  BOARD_USB_DISC_DEV is the GPIO port containing
+ * the USB_DISC pin, and BOARD_USB_DISC_BIT is that pin's bit. */
+#define BOARD_USB_DISC_DEV      GPIOC
+#define BOARD_USB_DISC_BIT      12
+
+/*
+ * SDIO Pins
+ */
+#define BOARD_SDIO_D0 			PC8
+#define BOARD_SDIO_D1 			PC9
+#define BOARD_SDIO_D2 			PC10
+#define BOARD_SDIO_D3 			PC11
+#define BOARD_SDIO_CLK 			PC12
+#define BOARD_SDIO_CMD 			PD2
+
+/* Pin aliases: these give the GPIO port/bit for each pin as an
+ * enum. These are optional, but recommended. They make it easier to
+ * write code using low-level GPIO functionality. */
+enum {
+PA0,PA1,PA2,PA3,PA4,PA5,PA6,PA7,PA8,PA9,PA10,PA11,PA12,PA13,PA14,PA15,
+PB0,PB1,PB2,PB3,PB4,PB5,PB6,PB7,PB8,PB9,PB10,PB11,PB12,PB13,PB14,PB15,
+PC0,PC1,PC2,PC3,PC4,PC5,PC6,PC7,PC8,PC9,PC10,PC11,PC12,PC13,PC14,PC15,
+PD0,PD1,PD2,PD3,PD4,PD5,PD6,PD7,PD8,PD9,PD10,PD11,PD12,PD13,PD14,PD15,
+PE0,PE1,PE2,PE3,PE4,PE5,PE6,PE7,PE8,PE9,PE10,PE11,PE12,PE13,PE14,PE15,
+PF0,PF1,PF2,PF3,PF4,PF5,PF6,PF7,PF8,PF9,PF10,PF11,PF12,PF13,PF14,PF15,
+PG0,PG1,PG2,PG3,PG4,PG5,PG6,PG7,PG8,PG9,PG10,PG11,PG12,PG13,PG14,PG15
+};/* Note PB2 is skipped as this is Boot1 and is not going to be much use as its likely to be pulled permanently low */
+/*
+#define PA0 0
+#define PA1 1
+#define PA2 2
+#define PA3 3
+#define PA4 4
+#define PA5 5
+#define PA6 6
+#define PA7 7
+#define PA8 8
+#define PA9 9
+#define PA10 10
+#define PA11 11
+#define PA12 12
+#define PA13 13
+#define PA14 14
+#define PA15 15
+#define PB0 16
+#define PB1 17
+#define PB2 18
+#define PB3 19
+#define PB4 20
+#define PB5 21
+#define PB6 22
+#define PB7 23
+#define PB8 24
+#define PB9 25
+#define PB10 26
+#define PB11 27
+#define PB12 28
+#define PB13 29
+#define PB14 30
+#define PB15 31
+#define PC0 32
+#define PC1 33
+#define PC2 34
+#define PC3 35
+#define PC4 36
+#define PC5 37
+#define PC6 38
+#define PC7 39
+#define PC8 40
+#define PC9 41
+#define PC10 42
+#define PC11 43
+#define PC12 44
+#define PC13 45
+#define PC14 46
+#define PC15 47
+#define PD0 48
+#define PD1 49
+#define PD2 50
+#define PD3 51
+#define PD4 52
+#define PD5 53
+#define PD6 54
+#define PD7 55
+#define PD8 56
+#define PD9 57
+#define PD10 58
+#define PD11 59
+#define PD12 60
+#define PD13 61
+#define PD14 62
+#define PD15 63
+#define PE0 64
+#define PE1 65
+#define PE2 66
+#define PE3 67
+#define PE4 68
+#define PE5 69
+#define PE6 70
+#define PE7 71
+#define PE8 72
+#define PE9 73
+#define PE10 74
+#define PE11 75
+#define PE12 76
+#define PE13 77
+#define PE14 78
+#define PE15 79
+#define PF0 80
+#define PF1 81
+#define PF2 82
+#define PF3 83
+#define PF4 84
+#define PF5 85
+#define PF6 86
+#define PF7 87
+#define PF8 88
+#define PF9 89
+#define PF10 90
+#define PF11 91
+#define PF12 92
+#define PF13 93
+#define PF14 94
+#define PF15 95
+#define PG0 96
+#define PG1 97
+#define PG2 98
+#define PG3 99
+#define PG4 100
+#define PG5 101
+#define PG6 102
+#define PG7 103
+#define PG8 104
+#define PG9 105
+#define PG10 106
+#define PG11 107
+#define PG12 108
+#define PG13 109
+#define PG14 110
+#define PG15 111 */
+#endif
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/ld/common.inc b/buildroot/share/PlatformIO/variants/CHITU_F103/ld/common.inc
new file mode 100755
index 0000000000..e086a58bca
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/ld/common.inc
@@ -0,0 +1,220 @@
+/*
+ * Linker script for libmaple.
+ *
+ * Original author "lanchon" from ST forums, with modifications by LeafLabs.
+ */
+
+OUTPUT_FORMAT ("elf32-littlearm", "elf32-bigarm", "elf32-littlearm")
+
+/*
+ * Configure other libraries we want in the link.
+ *
+ * libgcc, libc, and libm are common across supported toolchains.
+ * However, some toolchains require additional archives which aren't
+ * present everywhere (e.g. ARM's gcc-arm-embedded releases).
+ *
+ * To hack around this, we let the build system specify additional
+ * archives by putting the right extra_libs.inc (in a directory under
+ * toolchains/) in our search path.
+ */
+GROUP(libgcc.a libc.a libm.a)
+INCLUDE extra_libs.inc
+
+/*
+ * These force the linker to search for vector table symbols.
+ *
+ * These symbols vary by STM32 family (and also within families).
+ * It's up to the build system to configure the link's search path
+ * properly for the target MCU.
+ */
+INCLUDE vector_symbols.inc
+
+/* STM32 vector table. */
+EXTERN(__stm32_vector_table)
+
+/* C runtime initialization function. */
+EXTERN(start_c)
+
+/* main entry point */
+EXTERN(main)
+
+/* Initial stack pointer value. */
+EXTERN(__msp_init)
+PROVIDE(__msp_init = ORIGIN(ram) + LENGTH(ram));
+
+/* Reset vector and chip reset entry point */
+EXTERN(__start__)
+ENTRY(__start__)
+PROVIDE(__exc_reset = __start__);
+
+/* Heap boundaries, for libmaple */
+EXTERN(_lm_heap_start);
+EXTERN(_lm_heap_end);
+
+SECTIONS
+{
+    .text :
+      {
+        __text_start__ = .;
+        /*
+         * STM32 vector table.  Leave this here.  Yes, really.
+         */
+        *(.stm32.interrupt_vector)
+
+        /*
+         * Program code and vague linking
+         */
+        *(.text .text.* .gnu.linkonce.t.*)
+        *(.plt)
+        *(.gnu.warning)
+        *(.glue_7t) *(.glue_7) *(.vfp11_veneer)
+
+        *(.ARM.extab* .gnu.linkonce.armextab.*)
+        *(.gcc_except_table)
+        *(.eh_frame_hdr)
+        *(.eh_frame)
+
+        . = ALIGN(4);
+        KEEP(*(.init))
+
+        . = ALIGN(4);
+        __preinit_array_start = .;
+        KEEP (*(.preinit_array))
+        __preinit_array_end = .;
+
+        . = ALIGN(4);
+        __init_array_start = .;
+        KEEP (*(SORT(.init_array.*)))
+        KEEP (*(.init_array))
+        __init_array_end = .;
+
+        . = ALIGN(0x4);
+        KEEP (*crtbegin.o(.ctors))
+        KEEP (*(EXCLUDE_FILE (*crtend.o) .ctors))
+        KEEP (*(SORT(.ctors.*)))
+        KEEP (*crtend.o(.ctors))
+
+        . = ALIGN(4);
+        KEEP(*(.fini))
+
+        . = ALIGN(4);
+        __fini_array_start = .;
+        KEEP (*(.fini_array))
+        KEEP (*(SORT(.fini_array.*)))
+        __fini_array_end = .;
+
+        KEEP (*crtbegin.o(.dtors))
+        KEEP (*(EXCLUDE_FILE (*crtend.o) .dtors))
+        KEEP (*(SORT(.dtors.*)))
+        KEEP (*crtend.o(.dtors))
+      } > REGION_TEXT
+
+    /*
+     * End of text
+     */
+    .text.align :
+      {
+        . = ALIGN(8);
+        __text_end__ = .;
+      } > REGION_TEXT
+
+    /*
+     * .ARM.exidx exception unwinding; mandated by ARM's C++ ABI
+     */
+    __exidx_start = .;
+    .ARM.exidx :
+      {
+        *(.ARM.exidx* .gnu.linkonce.armexidx.*)
+      } > REGION_RODATA
+    __exidx_end = .;
+
+    /*
+     * .data
+     */
+    .data :
+      {
+        __data_start__ = .;
+      	LONG(0)
+        . = ALIGN(8);
+
+        *(.got.plt) *(.got)
+        *(.data .data.* .gnu.linkonce.d.*)
+
+        . = ALIGN(8);
+        __data_end__ = .;
+      } > REGION_DATA AT> REGION_RODATA
+
+    /*
+     * Read-only data
+     */
+    .rodata :
+      {
+        *(.rodata .rodata.* .gnu.linkonce.r.*)
+        /* .USER_FLASH: We allow users to allocate into Flash here */
+        *(.USER_FLASH)
+        /* ROM image configuration; for C startup */
+        . = ALIGN(4);
+        _lm_rom_img_cfgp = .;
+        LONG(LOADADDR(.data));
+        /*
+         * Heap: Linker scripts may choose a custom heap by overriding
+         * _lm_heap_start and _lm_heap_end. Otherwise, the heap is in
+         * internal SRAM, beginning after .bss, and growing towards
+         * the stack.
+         *
+         * I'm shoving these here naively; there's probably a cleaner way
+         * to go about this. [mbolivar]
+         */
+        _lm_heap_start = DEFINED(_lm_heap_start) ? _lm_heap_start : _end;
+        _lm_heap_end   = DEFINED(_lm_heap_end) ? _lm_heap_end : __msp_init;
+      } > REGION_RODATA
+
+    /*
+     * .bss
+     */
+    .bss :
+      {
+        . = ALIGN(8);
+        __bss_start__ = .;
+        *(.bss .bss.* .gnu.linkonce.b.*)
+        *(COMMON)
+        . = ALIGN (8);
+        __bss_end__ = .;
+        _end = __bss_end__;
+      } > REGION_BSS
+
+    /*
+     * Debugging sections
+     */
+    .stab 0 (NOLOAD) : { *(.stab) }
+    .stabstr 0 (NOLOAD) : { *(.stabstr) }
+    /* DWARF debug sections.
+     * Symbols in the DWARF debugging sections are relative to the beginning
+     * of the section so we begin them at 0.  */
+    /* DWARF 1 */
+    .debug          0 : { *(.debug) }
+    .line           0 : { *(.line) }
+    /* GNU DWARF 1 extensions */
+    .debug_srcinfo  0 : { *(.debug_srcinfo) }
+    .debug_sfnames  0 : { *(.debug_sfnames) }
+    /* DWARF 1.1 and DWARF 2 */
+    .debug_aranges  0 : { *(.debug_aranges) }
+    .debug_pubnames 0 : { *(.debug_pubnames) }
+    /* DWARF 2 */
+    .debug_info     0 : { *(.debug_info .gnu.linkonce.wi.*) }
+    .debug_abbrev   0 : { *(.debug_abbrev) }
+    .debug_line     0 : { *(.debug_line) }
+    .debug_frame    0 : { *(.debug_frame) }
+    .debug_str      0 : { *(.debug_str) }
+    .debug_loc      0 : { *(.debug_loc) }
+    .debug_macinfo  0 : { *(.debug_macinfo) }
+    /* SGI/MIPS DWARF 2 extensions */
+    .debug_weaknames 0 : { *(.debug_weaknames) }
+    .debug_funcnames 0 : { *(.debug_funcnames) }
+    .debug_typenames 0 : { *(.debug_typenames) }
+    .debug_varnames  0 : { *(.debug_varnames) }
+
+    .note.gnu.arm.ident 0 : { KEEP (*(.note.gnu.arm.ident)) }
+    .ARM.attributes 0 : { KEEP (*(.ARM.attributes)) }
+    /DISCARD/ : { *(.note.GNU-stack) }
+}
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/ld/extra_libs.inc b/buildroot/share/PlatformIO/variants/CHITU_F103/ld/extra_libs.inc
new file mode 100755
index 0000000000..dd2c84fa45
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/ld/extra_libs.inc
@@ -0,0 +1,7 @@
+/*
+ * Extra archives needed by ARM's GCC ARM Embedded arm-none-eabi-
+ * releases (https://launchpad.net/gcc-arm-embedded/).
+ */
+
+/* This is for the provided newlib. */
+GROUP(libnosys.a)
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103z_dfu.ld b/buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103z_dfu.ld
new file mode 100755
index 0000000000..5cdf24e08c
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103z_dfu.ld
@@ -0,0 +1,29 @@
+/*
+ * libmaple linker script 
+ *
+ * This build puts .text (and .rodata) in Flash, and
+ * .data/.bss/heap (of course) in SRAM, but links starting at the
+ * Flash and SRAM starting addresses (0x08000000 and 0x20000000
+ * respectively). This will wipe out a Maple bootloader if there's one
+ * on the board, so only use this if you know what you're doing.
+ *
+ * This build is perfectly usable for upload over SWD,
+ * the system memory bootloader, etc. The name is just a historical
+ * artifact.
+ */
+
+
+MEMORY
+{
+  ram (rwx) : ORIGIN = 0x20000000, LENGTH = 64K
+  rom (rx)  : ORIGIN = 0x08002000, LENGTH = 504K
+}
+
+/* Provide memory region aliases for common.inc */
+REGION_ALIAS("REGION_TEXT", rom);
+REGION_ALIAS("REGION_DATA", ram);
+REGION_ALIAS("REGION_BSS", ram);
+REGION_ALIAS("REGION_RODATA", rom);
+
+/* Let common.inc handle the real work. */
+INCLUDE common.inc
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103zc.ld b/buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103zc.ld
new file mode 100755
index 0000000000..dbb50a6d01
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103zc.ld
@@ -0,0 +1,27 @@
+/*
+ * libmaple linker script 
+ *
+ * This build puts .text (and .rodata) in Flash, and
+ * .data/.bss/heap (of course) in SRAM, but links starting at the
+ * Flash and SRAM starting addresses (0x08000000 and 0x20000000
+ * respectively). This will wipe out a Maple bootloader if there's one
+ * on the board, so only use this if you know what you're doing.
+ *
+ * This build is perfectly usable for upload over SWD,
+ * the system memory bootloader, etc. The name is just a historical
+ * artifact.
+ */
+MEMORY
+{
+  ram (rwx) : ORIGIN = 0x20000000, LENGTH = 48K
+  rom (rx)  : ORIGIN = 0x08000000, LENGTH = 512K
+}
+
+/* Provide memory region aliases for common.inc */
+REGION_ALIAS("REGION_TEXT", rom);
+REGION_ALIAS("REGION_DATA", ram);
+REGION_ALIAS("REGION_BSS", ram);
+REGION_ALIAS("REGION_RODATA", rom);
+
+/* Let common.inc handle the real work. */
+INCLUDE common.inc
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103zd.ld b/buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103zd.ld
new file mode 100755
index 0000000000..9cbff794fc
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103zd.ld
@@ -0,0 +1,27 @@
+/*
+ * libmaple linker script 
+ *
+ * This build puts .text (and .rodata) in Flash, and
+ * .data/.bss/heap (of course) in SRAM, but links starting at the
+ * Flash and SRAM starting addresses (0x08000000 and 0x20000000
+ * respectively). This will wipe out a Maple bootloader if there's one
+ * on the board, so only use this if you know what you're doing.
+ *
+ * This build is perfectly usable for upload over SWD,
+ * the system memory bootloader, etc. The name is just a historical
+ * artifact.
+ */
+MEMORY
+{
+  ram (rwx) : ORIGIN = 0x20000000, LENGTH = 64K
+  rom (rx)  : ORIGIN = 0x08000000, LENGTH = 512K
+}
+
+/* Provide memory region aliases for common.inc */
+REGION_ALIAS("REGION_TEXT", rom);
+REGION_ALIAS("REGION_DATA", ram);
+REGION_ALIAS("REGION_BSS", ram);
+REGION_ALIAS("REGION_RODATA", rom);
+
+/* Let common.inc handle the real work. */
+INCLUDE common.inc
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103ze.ld b/buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103ze.ld
new file mode 100755
index 0000000000..a7c9c99ad4
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/ld/stm32f103ze.ld
@@ -0,0 +1,29 @@
+/*
+ * libmaple linker script 
+ *
+ * This build puts .text (and .rodata) in Flash, and
+ * .data/.bss/heap (of course) in SRAM, but links starting at the
+ * Flash and SRAM starting addresses (0x08000000 and 0x20000000
+ * respectively). This will wipe out a Maple bootloader if there's one
+ * on the board, so only use this if you know what you're doing.
+ *
+ * This build is perfectly usable for upload over SWD,
+ * the system memory bootloader, etc. The name is just a historical
+ * artifact.
+ */
+
+
+MEMORY
+{
+  ram (rwx) : ORIGIN = 0x20000000, LENGTH = 64K
+  rom (rx)  : ORIGIN = 0x08000000, LENGTH = 512K
+}
+
+/* Provide memory region aliases for common.inc */
+REGION_ALIAS("REGION_TEXT", rom);
+REGION_ALIAS("REGION_DATA", ram);
+REGION_ALIAS("REGION_BSS", ram);
+REGION_ALIAS("REGION_RODATA", rom);
+
+/* Let common.inc handle the real work. */
+INCLUDE common.inc
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/ld/vector_symbols.inc b/buildroot/share/PlatformIO/variants/CHITU_F103/ld/vector_symbols.inc
new file mode 100755
index 0000000000..f8519bba44
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/ld/vector_symbols.inc
@@ -0,0 +1,78 @@
+EXTERN(__msp_init)
+EXTERN(__exc_reset)
+EXTERN(__exc_nmi)
+EXTERN(__exc_hardfault)
+EXTERN(__exc_memmanage)
+EXTERN(__exc_busfault)
+EXTERN(__exc_usagefault)
+EXTERN(__stm32reservedexception7)
+EXTERN(__stm32reservedexception8)
+EXTERN(__stm32reservedexception9)
+EXTERN(__stm32reservedexception10)
+EXTERN(__exc_svc)
+EXTERN(__exc_debug_monitor)
+EXTERN(__stm32reservedexception13)
+EXTERN(__exc_pendsv)
+EXTERN(__exc_systick)
+
+EXTERN(__irq_wwdg)
+EXTERN(__irq_pvd)
+EXTERN(__irq_tamper)
+EXTERN(__irq_rtc)
+EXTERN(__irq_flash)
+EXTERN(__irq_rcc)
+EXTERN(__irq_exti0)
+EXTERN(__irq_exti1)
+EXTERN(__irq_exti2)
+EXTERN(__irq_exti3)
+EXTERN(__irq_exti4)
+EXTERN(__irq_dma1_channel1)
+EXTERN(__irq_dma1_channel2)
+EXTERN(__irq_dma1_channel3)
+EXTERN(__irq_dma1_channel4)
+EXTERN(__irq_dma1_channel5)
+EXTERN(__irq_dma1_channel6)
+EXTERN(__irq_dma1_channel7)
+EXTERN(__irq_adc)
+EXTERN(__irq_usb_hp_can_tx)
+EXTERN(__irq_usb_lp_can_rx0)
+EXTERN(__irq_can_rx1)
+EXTERN(__irq_can_sce)
+EXTERN(__irq_exti9_5)
+EXTERN(__irq_tim1_brk)
+EXTERN(__irq_tim1_up)
+EXTERN(__irq_tim1_trg_com)
+EXTERN(__irq_tim1_cc)
+EXTERN(__irq_tim2)
+EXTERN(__irq_tim3)
+EXTERN(__irq_tim4)
+EXTERN(__irq_i2c1_ev)
+EXTERN(__irq_i2c1_er)
+EXTERN(__irq_i2c2_ev)
+EXTERN(__irq_i2c2_er)
+EXTERN(__irq_spi1)
+EXTERN(__irq_spi2)
+EXTERN(__irq_usart1)
+EXTERN(__irq_usart2)
+EXTERN(__irq_usart3)
+EXTERN(__irq_exti15_10)
+EXTERN(__irq_rtcalarm)
+EXTERN(__irq_usbwakeup)
+
+EXTERN(__irq_tim8_brk)
+EXTERN(__irq_tim8_up)
+EXTERN(__irq_tim8_trg_com)
+EXTERN(__irq_tim8_cc)
+EXTERN(__irq_adc3)
+EXTERN(__irq_fsmc)
+EXTERN(__irq_sdio)
+EXTERN(__irq_tim5)
+EXTERN(__irq_spi3)
+EXTERN(__irq_uart4)
+EXTERN(__irq_uart5)
+EXTERN(__irq_tim6)
+EXTERN(__irq_tim7)
+EXTERN(__irq_dma2_channel1)
+EXTERN(__irq_dma2_channel2)
+EXTERN(__irq_dma2_channel3)
+EXTERN(__irq_dma2_channel4_5)
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/pins_arduino.h b/buildroot/share/PlatformIO/variants/CHITU_F103/pins_arduino.h
new file mode 100755
index 0000000000..d5dce114d5
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/pins_arduino.h
@@ -0,0 +1,2 @@
+// API compatibility
+#include "variant.h"
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/variant.h b/buildroot/share/PlatformIO/variants/CHITU_F103/variant.h
new file mode 100755
index 0000000000..cd10bb3c07
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/variant.h
@@ -0,0 +1,17 @@
+#pragma once
+
+#define digitalPinToPort(P)        ( PIN_MAP[P].gpio_device )
+#define digitalPinToBitMask(P)     ( BIT(PIN_MAP[P].gpio_bit) )
+#define portOutputRegister(port)   ( &(port->regs->ODR) )
+#define portInputRegister(port)    ( &(port->regs->IDR) )
+
+#define portSetRegister(pin)       ( &(PIN_MAP[pin].gpio_device->regs->BSRR) )
+#define portClearRegister(pin)     ( &(PIN_MAP[pin].gpio_device->regs->BRR) )
+
+#define portConfigRegister(pin)    ( &(PIN_MAP[pin].gpio_device->regs->CRL) )
+
+static const uint8_t SS   = BOARD_SPI1_NSS_PIN;
+static const uint8_t SS1  = BOARD_SPI2_NSS_PIN;
+static const uint8_t MOSI = BOARD_SPI1_MOSI_PIN;
+static const uint8_t MISO = BOARD_SPI1_MISO_PIN;
+static const uint8_t SCK  = BOARD_SPI1_SCK_PIN;
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/wirish/boards.cpp b/buildroot/share/PlatformIO/variants/CHITU_F103/wirish/boards.cpp
new file mode 100755
index 0000000000..93ae231518
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/wirish/boards.cpp
@@ -0,0 +1,225 @@
+/******************************************************************************
+ * The MIT License
+ *
+ * Copyright (c) 2010 Perry Hung.
+ * Copyright (c) 2011, 2012 LeafLabs, LLC.
+ *
+ * Permission is hereby granted, free of charge, to any person
+ * obtaining a copy of this software and associated documentation
+ * files (the "Software"), to deal in the Software without
+ * restriction, including without limitation the rights to use, copy,
+ * modify, merge, publish, distribute, sublicense, and/or sell copies
+ * of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
+ * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
+ * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+ * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ *****************************************************************************/
+
+/**
+ * @file wirish/boards.cpp
+ * @brief init() and board routines.
+ *
+ * This file is mostly interesting for the init() function, which
+ * configures Flash, the core clocks, and a variety of other available
+ * peripherals on the board so the rest of Wirish doesn't have to turn
+ * things on before using them.
+ *
+ * Prior to returning, init() calls boardInit(), which allows boards
+ * to perform any initialization they need to. This file includes a
+ * weak no-op definition of boardInit(), so boards that don't need any
+ * special initialization don't have to define their own.
+ *
+ * How init() works is chip-specific. See the boards_setup.cpp files
+ * under e.g. wirish/stm32f1/, wirish/stmf32f2 for the details, but be
+ * advised: their contents are unstable, and can/will change without
+ * notice.
+ */
+
+#include <boards.h>
+#include <libmaple/libmaple_types.h>
+#include <libmaple/flash.h>
+#include <libmaple/nvic.h>
+#include <libmaple/systick.h>
+#include "boards_private.h"
+
+static void setup_flash(void);
+static void setup_clocks(void);
+static void setup_nvic(void);
+static void setup_adcs(void);
+static void setup_timers(void);
+
+/*
+ * Exported functions
+ */
+
+void init(void) {
+    setup_flash();
+    setup_clocks();
+    setup_nvic();
+    systick_init(SYSTICK_RELOAD_VAL);
+    wirish::priv::board_setup_gpio();
+    setup_adcs();
+    setup_timers();
+    wirish::priv::board_setup_usb();
+    wirish::priv::series_init();
+    boardInit();
+}
+
+/* Provide a default no-op boardInit(). */
+__weak void boardInit(void) {
+}
+
+/* You could farm this out to the files in boards/ if e.g. it takes
+ * too long to test on boards with lots of pins. */
+bool boardUsesPin(uint8 pin) {
+    for (int i = 0; i < BOARD_NR_USED_PINS; i++) {
+        if (pin == boardUsedPins[i]) {
+            return true;
+        }
+    }
+    return false;
+}
+
+/*
+ * Auxiliary routines
+ */
+
+static void setup_flash(void) {
+    // Turn on as many Flash "go faster" features as
+    // possible. flash_enable_features() just ignores any flags it
+    // can't support.
+    flash_enable_features(FLASH_PREFETCH | FLASH_ICACHE | FLASH_DCACHE);
+    // Configure the wait states, assuming we're operating at "close
+    // enough" to 3.3V.
+    flash_set_latency(FLASH_SAFE_WAIT_STATES);
+}
+
+static void setup_clocks(void) {
+    // Turn on HSI. We'll switch to and run off of this while we're
+    // setting up the main PLL.
+    rcc_turn_on_clk(RCC_CLK_HSI);
+
+    // Turn off and reset the clock subsystems we'll be using, as well
+    // as the clock security subsystem (CSS). Note that resetting CFGR
+    // to its default value of 0 implies a switch to HSI for SYSCLK.
+    RCC_BASE->CFGR = 0x00000000;
+    rcc_disable_css();
+    rcc_turn_off_clk(RCC_CLK_PLL);
+    rcc_turn_off_clk(RCC_CLK_HSE);
+    wirish::priv::board_reset_pll();
+    // Clear clock readiness interrupt flags and turn off clock
+    // readiness interrupts.
+    RCC_BASE->CIR = 0x00000000;
+#if !USE_HSI_CLOCK
+    // Enable HSE, and wait until it's ready.
+    rcc_turn_on_clk(RCC_CLK_HSE);
+    while (!rcc_is_clk_ready(RCC_CLK_HSE))
+        ;
+#endif
+    // Configure AHBx, APBx, etc. prescalers and the main PLL.
+    wirish::priv::board_setup_clock_prescalers();
+    rcc_configure_pll(&wirish::priv::w_board_pll_cfg);
+
+    // Enable the PLL, and wait until it's ready.
+    rcc_turn_on_clk(RCC_CLK_PLL);
+    while(!rcc_is_clk_ready(RCC_CLK_PLL))
+        ;
+
+    // Finally, switch to the now-ready PLL as the main clock source.
+    rcc_switch_sysclk(RCC_CLKSRC_PLL);
+}
+
+/*
+ * These addresses are where usercode starts when a bootloader is
+ * present. If no bootloader is present, the user NVIC usually starts
+ * at the Flash base address, 0x08000000.
+ */
+#if defined(BOOTLOADER_maple)
+	#define USER_ADDR_ROM 0x08005000
+#else
+	#define USER_ADDR_ROM 0x08000000
+#endif
+#define USER_ADDR_RAM 0x20000C00
+extern char __text_start__;
+
+static void setup_nvic(void) {
+
+nvic_init((uint32)VECT_TAB_ADDR, 0);
+
+/* Roger Clark. We now control nvic vector table in boards.txt using the build.vect paramater
+#ifdef VECT_TAB_FLASH
+    nvic_init(USER_ADDR_ROM, 0);
+#elif defined VECT_TAB_RAM
+    nvic_init(USER_ADDR_RAM, 0);
+#elif defined VECT_TAB_BASE
+    nvic_init((uint32)0x08000000, 0);
+#elif defined VECT_TAB_ADDR
+    // A numerically supplied value
+    nvic_init((uint32)VECT_TAB_ADDR, 0);
+#else
+    // Use the __text_start__ value from the linker script; this
+    // should be the start of the vector table.
+    nvic_init((uint32)&__text_start__, 0);
+#endif
+
+*/
+}
+
+static void adc_default_config(adc_dev *dev) {
+    adc_enable_single_swstart(dev);
+    adc_set_sample_rate(dev, wirish::priv::w_adc_smp);
+}
+
+static void setup_adcs(void) {
+    adc_set_prescaler(wirish::priv::w_adc_pre);
+    adc_foreach(adc_default_config);
+}
+
+static void timer_default_config(timer_dev *dev) {
+    timer_adv_reg_map *regs = (dev->regs).adv;
+    const uint16 full_overflow = 0xFFFF;
+    const uint16 half_duty = 0x8FFF;
+
+    timer_init(dev);
+    timer_pause(dev);
+
+    regs->CR1 = TIMER_CR1_ARPE;
+    regs->PSC = 1;
+    regs->SR = 0;
+    regs->DIER = 0;
+    regs->EGR = TIMER_EGR_UG;
+    switch (dev->type) {
+    case TIMER_ADVANCED:
+        regs->BDTR = TIMER_BDTR_MOE | TIMER_BDTR_LOCK_OFF;
+        // fall-through
+    case TIMER_GENERAL:
+        timer_set_reload(dev, full_overflow);
+        for (uint8 channel = 1; channel <= 4; channel++) {
+            if (timer_has_cc_channel(dev, channel)) {
+                timer_set_compare(dev, channel, half_duty);
+                timer_oc_set_mode(dev, channel, TIMER_OC_MODE_PWM_1,
+                                  TIMER_OC_PE);
+            }
+        }
+        // fall-through
+    case TIMER_BASIC:
+        break;
+    }
+
+    timer_generate_update(dev);
+    timer_resume(dev);
+}
+
+static void setup_timers(void) {
+    timer_foreach(timer_default_config);
+}
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/wirish/boards_setup.cpp b/buildroot/share/PlatformIO/variants/CHITU_F103/wirish/boards_setup.cpp
new file mode 100755
index 0000000000..98b31cf2b0
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/wirish/boards_setup.cpp
@@ -0,0 +1,123 @@
+/******************************************************************************
+ * The MIT License
+ *
+ * Copyright (c) 2012 LeafLabs, LLC.
+ *
+ * Permission is hereby granted, free of charge, to any person
+ * obtaining a copy of this software and associated documentation
+ * files (the "Software"), to deal in the Software without
+ * restriction, including without limitation the rights to use, copy,
+ * modify, merge, publish, distribute, sublicense, and/or sell copies
+ * of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
+ * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
+ * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+ * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+*****************************************************************************/
+
+/**
+ * @file wirish/stm32f1/boards_setup.cpp
+ * @author Marti Bolivar <mbolivar@leaflabs.com>
+ * @brief STM32F1 chip setup.
+ *
+ * This file controls how init() behaves on the STM32F1. Be very
+ * careful when changing anything here. Many of these values depend
+ * upon each other.
+ */
+
+#include "boards_private.h"
+
+#include <libmaple/gpio.h>
+#include <libmaple/timer.h>
+
+#include <boards.h>
+#include <usb_serial.h>
+
+// Allow boards to provide a PLL multiplier. This is useful for
+// e.g. STM32F100 value line MCUs, which use slower multipliers.
+// (We're leaving the default to RCC_PLLMUL_9 for now, since that
+// works for F103 performance line MCUs, which is all that LeafLabs
+// currently officially supports).
+#ifndef BOARD_RCC_PLLMUL
+  #if !USE_HSI_CLOCK
+  #if F_CPU==128000000
+    #define BOARD_RCC_PLLMUL RCC_PLLMUL_16
+  #elif F_CPU==72000000
+    #define BOARD_RCC_PLLMUL RCC_PLLMUL_9
+  #elif F_CPU==48000000
+    #define BOARD_RCC_PLLMUL RCC_PLLMUL_6
+  #elif F_CPU==16000000
+    #define BOARD_RCC_PLLMUL RCC_PLLMUL_2
+  #endif
+  #else
+  #define BOARD_RCC_PLLMUL RCC_PLLMUL_16
+  #endif
+#endif
+
+namespace wirish {
+    namespace priv {
+
+        static stm32f1_rcc_pll_data pll_data = {BOARD_RCC_PLLMUL};
+#if !USE_HSI_CLOCK
+        __weak rcc_pll_cfg w_board_pll_cfg = {RCC_PLLSRC_HSE, &pll_data};
+#else
+        __weak rcc_pll_cfg w_board_pll_cfg = {RCC_PLLSRC_HSI_DIV_2, &pll_data};
+#endif
+        __weak adc_prescaler w_adc_pre = ADC_PRE_PCLK2_DIV_6;
+        __weak adc_smp_rate w_adc_smp = ADC_SMPR_55_5;
+
+        __weak void board_reset_pll(void) {
+            // TODO
+        }
+
+        __weak void board_setup_clock_prescalers(void) {
+            rcc_set_prescaler(RCC_PRESCALER_AHB, RCC_AHB_SYSCLK_DIV_1);
+            rcc_set_prescaler(RCC_PRESCALER_APB1, RCC_APB1_HCLK_DIV_2);
+            rcc_set_prescaler(RCC_PRESCALER_APB2, RCC_APB2_HCLK_DIV_1);
+      rcc_clk_disable(RCC_USB);
+      #if F_CPU == 72000000
+      rcc_set_prescaler(RCC_PRESCALER_USB, RCC_USB_SYSCLK_DIV_1_5);
+      #elif F_CPU == 48000000
+      rcc_set_prescaler(RCC_PRESCALER_USB, RCC_USB_SYSCLK_DIV_1);     
+      #endif  
+        }
+
+        __weak void board_setup_gpio(void) {
+            gpio_init_all();
+        }
+
+        __weak void board_setup_usb(void) {
+      
+
+  
+#ifdef SERIAL_USB 
+#ifdef GENERIC_BOOTLOADER     
+      //Reset the USB interface on generic boards - developed by Victor PV
+      gpio_set_mode(PIN_MAP[PA12].gpio_device, PIN_MAP[PA12].gpio_bit, GPIO_OUTPUT_PP);
+      gpio_write_bit(PIN_MAP[PA12].gpio_device, PIN_MAP[PA12].gpio_bit,0);
+      
+      for(volatile unsigned int i=0;i<512;i++);// Only small delay seems to be needed, and USB pins will get configured in Serial.begin
+      gpio_set_mode(PIN_MAP[PA12].gpio_device, PIN_MAP[PA12].gpio_bit, GPIO_INPUT_FLOATING);
+#endif  
+
+      Serial.begin();// Roger Clark. Changed SerialUSB to Serial for Arduino sketch compatibility
+#endif
+        }
+
+        __weak void series_init(void) {
+            // Initialize AFIO here, too, so peripheral remaps and external
+            // interrupts work out of the box.
+            afio_init();
+        }
+
+    }
+}
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/wirish/start.S b/buildroot/share/PlatformIO/variants/CHITU_F103/wirish/start.S
new file mode 100755
index 0000000000..8b181aa993
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/wirish/start.S
@@ -0,0 +1,57 @@
+/******************************************************************************
+ * The MIT License
+ *
+ * Copyright (c) 2011 LeafLabs, LLC.
+ *
+ * Permission is hereby granted, free of charge, to any person
+ * obtaining a copy of this software and associated documentation
+ * files (the "Software"), to deal in the Software without
+ * restriction, including without limitation the rights to use, copy,
+ * modify, merge, publish, distribute, sublicense, and/or sell copies
+ * of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
+ * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
+ * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+ * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ *****************************************************************************/
+
+/*
+ * This file is a modified version of a file obtained from
+ * CodeSourcery Inc. (now part of Mentor Graphics Corp.), in which the
+ * following text appeared:
+ *
+ * The authors hereby grant permission to use, copy, modify, distribute,
+ * and license this software and its documentation for any purpose, provided
+ * that existing copyright notices are retained in all copies and that this
+ * notice is included verbatim in any distributions. No written agreement,
+ * license, or royalty fee is required for any of the authorized uses.
+ * Modifications to this software may be copyrighted by their authors
+ * and need not follow the licensing terms described here, provided that
+ * the new terms are clearly indicated on the first page of each file where
+ * they apply.
+ */
+
+        .text
+        .code 16
+        .thumb_func
+
+        .globl __start__
+        .type __start__, %function
+__start__:
+        .fnstart
+        ldr r1,=__msp_init
+        mov sp,r1
+        ldr r1,=start_c
+        bx r1
+        .pool
+        .cantunwind
+        .fnend
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/wirish/start_c.c b/buildroot/share/PlatformIO/variants/CHITU_F103/wirish/start_c.c
new file mode 100755
index 0000000000..d305e6d5b9
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/wirish/start_c.c
@@ -0,0 +1,144 @@
+/******************************************************************************
+ * The MIT License
+ *
+ * Copyright (c) 2011 LeafLabs, LLC.
+ *
+ * Permission is hereby granted, free of charge, to any person
+ * obtaining a copy of this software and associated documentation
+ * files (the "Software"), to deal in the Software without
+ * restriction, including without limitation the rights to use, copy,
+ * modify, merge, publish, distribute, sublicense, and/or sell copies
+ * of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
+ * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
+ * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+ * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ *****************************************************************************/
+
+/*
+ * This file is a modified version of a file obtained from
+ * CodeSourcery Inc. (now part of Mentor Graphics Corp.), in which the
+ * following text appeared:
+ *
+ * Copyright (c) 2006, 2007 CodeSourcery Inc
+ *
+ * The authors hereby grant permission to use, copy, modify, distribute,
+ * and license this software and its documentation for any purpose, provided
+ * that existing copyright notices are retained in all copies and that this
+ * notice is included verbatim in any distributions. No written agreement,
+ * license, or royalty fee is required for any of the authorized uses.
+ * Modifications to this software may be copyrighted by their authors
+ * and need not follow the licensing terms described here, provided that
+ * the new terms are clearly indicated on the first page of each file where
+ * they apply.
+ */
+
+#include <stddef.h>
+
+#include <libmaple/rcc.h>
+#include <libmaple/libmaple.h>
+#include <libmaple/bitband.h>
+
+#include "rcc_private.h"
+
+#include <libmaple/usart.h>
+#include <libmaple/gpio.h>
+#include "usart_private.h"
+
+#include <libmaple/sdio.h>
+#include <string.h>
+
+extern void __libc_init_array(void);
+
+extern int main(int, char**, char**);
+
+extern void exit(int) __attribute__((noreturn, weak));
+
+/* The linker must ensure that these are at least 4-byte aligned. */
+extern char __data_start__, __data_end__;
+extern char __bss_start__, __bss_end__;
+
+struct rom_img_cfg {
+    int *img_start;
+};
+
+extern char _lm_rom_img_cfgp;
+extern void __lm_error();
+extern void timer_disable_all();
+
+    /* Turn off ADC */
+extern void adc_disable_all();
+
+    /* Turn off all USARTs */
+extern void usart_disable_all();
+extern void DisableEverything();
+
+void __attribute__((noreturn)) start_c(void) {
+    struct rom_img_cfg *img_cfg = (struct rom_img_cfg*)&_lm_rom_img_cfgp;
+    int *src = img_cfg->img_start;
+    int *dst = (int*)&__data_start__;
+    int exit_code;
+
+    asm("CPSID I");
+    /* Reset the RCC clock configuration to the default reset state(for debug purpose) */
+    /* Set HSION bit */
+    RCC_BASE->CR |= 0x00000001U;
+
+    /* Reset SW, HPRE, PPRE1, PPRE2, ADCPRE and MCO bits */
+    RCC_BASE->CFGR &= 0xF0FF0000U;
+
+    /* Reset HSEON, CSSON and PLLON bits */
+    RCC_BASE->CR &= 0xFEF6FFFFU;
+
+    /* Reset HSEBYP bit */
+    RCC_BASE->CR &= 0xFFFBFFFFU;
+
+    /* Reset PLLSRC, PLLXTPRE, PLLMUL and USBPRE/OTGFSPRE bits */
+    RCC_BASE->CFGR &= 0xFF80FFFFU;
+
+    /* Disable all interrupts and clear pending bits  */
+    RCC_BASE->CIR = 0x009F0000U;
+
+    USART1_BASE->CR1 = 0;
+    USART1_BASE->CR2 = 0;
+    USART1_BASE->CR3 = 0;
+
+    memset(SDIO_BASE, 0, sizeof(sdio_reg_map));
+    asm("CPSIE I");
+
+    /* Initialize .data, if necessary. */
+    if (src != dst) {
+        int *end = (int*)&__data_end__;
+        while (dst < end) {
+            *dst++ = *src++;
+        }
+    }
+
+    /* Zero .bss. */
+    dst = (int*)&__bss_start__;
+    while (dst < (int*)&__bss_end__) {
+        *dst++ = 0;
+    }
+
+    /* Run initializers. */
+    __libc_init_array();
+
+    /* Jump to main. */
+    exit_code = main(0, 0, 0);
+    if (exit) {
+        exit(exit_code);
+    }
+
+    /* If exit is NULL, make sure we don't return. */
+    for (;;)
+        continue;
+}
diff --git a/buildroot/share/PlatformIO/variants/CHITU_F103/wirish/syscalls.c b/buildroot/share/PlatformIO/variants/CHITU_F103/wirish/syscalls.c
new file mode 100755
index 0000000000..ec1c34dbad
--- /dev/null
+++ b/buildroot/share/PlatformIO/variants/CHITU_F103/wirish/syscalls.c
@@ -0,0 +1,176 @@
+/******************************************************************************
+ * The MIT License
+ *
+ * Copyright (c) 2010 Perry Hung.
+ * Copyright (c) 2011, 2012 LeafLabs, LLC.
+ *
+ * Permission is hereby granted, free of charge, to any person
+ * obtaining a copy of this software and associated documentation
+ * files (the "Software"), to deal in the Software without
+ * restriction, including without limitation the rights to use, copy,
+ * modify, merge, publish, distribute, sublicense, and/or sell copies
+ * of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
+ * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
+ * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+ * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ *****************************************************************************/
+
+/**
+ * @file wirish/syscalls.c
+ * @brief newlib stubs
+ *
+ * Low level system routines used by newlib for basic I/O and memory
+ * allocation. You can override most of these.
+ */
+
+#include <libmaple/libmaple.h>
+
+#include <sys/stat.h>
+#include <errno.h>
+#include <stddef.h>
+
+/* If CONFIG_HEAP_START (or CONFIG_HEAP_END) isn't defined, then
+ * assume _lm_heap_start (resp. _lm_heap_end) is appropriately set by
+ * the linker */
+#ifndef CONFIG_HEAP_START
+extern char _lm_heap_start;
+#define CONFIG_HEAP_START               ((void *)&_lm_heap_start)
+#endif
+#ifndef CONFIG_HEAP_END
+extern char _lm_heap_end;
+#define CONFIG_HEAP_END                 ((void *)&_lm_heap_end)
+#endif
+
+/*
+ * _sbrk -- Increment the program break.
+ *
+ * Get incr bytes more RAM (for use by the heap).  malloc() and
+ * friends call this function behind the scenes.
+ */
+void *_sbrk(int incr) {
+    static void * pbreak = NULL; /* current program break */
+    void * ret;
+
+    if (pbreak == NULL) {
+        pbreak = CONFIG_HEAP_START;
+    }
+
+    if ((CONFIG_HEAP_END - pbreak < incr) ||
+        (pbreak - CONFIG_HEAP_START < -incr)) {
+        errno = ENOMEM;
+        return (void *)-1;
+    }
+
+    ret = pbreak;
+    pbreak += incr;
+    return ret;
+}
+
+__weak int _open(const char *path __attribute__((unused)), int flags __attribute__((unused)), ...) {
+    return 1;
+}
+
+__weak int _close(int fd __attribute__((unused))) {
+    return 0;
+}
+
+__weak int _fstat(int fd __attribute__((unused)), struct stat *st) {
+    st->st_mode = S_IFCHR;
+    return 0;
+}
+
+__weak int _isatty(int fd __attribute__((unused))) {
+    return 1;
+}
+
+__weak int isatty(int fd __attribute__((unused))) {
+    return 1;
+}
+
+__weak int _lseek(int fd __attribute__((unused)), off_t pos __attribute__((unused)), int whence __attribute__((unused))) {
+    return -1;
+}
+
+__weak unsigned char getch(void) {
+    return 0;
+}
+
+
+__weak int _read(int fd __attribute__((unused)), char *buf, size_t cnt __attribute__((unused))) {
+    *buf = getch();
+
+    return 1;
+}
+
+__weak void putch(unsigned char c __attribute__((unused))) {
+}
+
+__weak void cgets(char *s, int bufsize) {
+    char *p;
+    int c;
+    int i;
+
+    for (i = 0; i < bufsize; i++) {
+        *(s+i) = 0;
+    }
+//    memset(s, 0, bufsize);
+
+    p = s;
+
+    for (p = s; p < s + bufsize-1;) {
+        c = getch();
+        switch (c) {
+        case '\r' :
+        case '\n' :
+            putch('\r');
+            putch('\n');
+            *p = '\n';
+            return;
+
+        case '\b' :
+            if (p > s) {
+                *p-- = 0;
+                putch('\b');
+                putch(' ');
+                putch('\b');
+            }
+            break;
+
+        default :
+            putch(c);
+            *p++ = c;
+            break;
+        }
+    }
+    return;
+}
+
+__weak int _write(int fd __attribute__((unused)), const char *buf, size_t cnt) {
+    int i;
+
+    for (i = 0; i < cnt; i++)
+        putch(buf[i]);
+
+    return cnt;
+}
+
+/* Override fgets() in newlib with a version that does line editing */
+__weak char *fgets(char *s, int bufsize, void *f __attribute__((unused))) {
+    cgets(s, bufsize);
+    return s;
+}
+
+__weak void _exit(int exitcode __attribute__((unused))) {
+    while (1)
+        ;
+}
diff --git a/platformio.ini b/platformio.ini
index d3a57aee2c..cfd04e26cb 100644
--- a/platformio.ini
+++ b/platformio.ini
@@ -646,8 +646,9 @@ lib_ignore  = LiquidCrystal, LiquidTWI2, Adafruit NeoPixel, TMCStepper, U8glib-H
 [env:chitu_f103]
 platform      = ${common_stm32f1.platform}
 extends       = common_stm32f1
-board         = genericSTM32F103ZE
-#extra_scripts = buildroot/share/PlatformIO/scripts/chitu_crypt.py
+board         = chitu_f103
+extra_scripts = pre:buildroot/share/PlatformIO/scripts/STM32F1_create_variant.py
+  buildroot/share/PlatformIO/scripts/chitu_crypt.py
 build_flags   = ${common_stm32f1.build_flags}
   -DSTM32F1xx -DSTM32_XL_DENSITY
 build_unflags = ${common_stm32f1.build_unflags}
-- 
GitLab