gd32: add new chip series f1x0

GD32F1X0 (X can be 3, 5, 7 and 9) is a series of Cortex-M3 MCUs by
GigaDevice, which features pin-to-pin package compatibility with
STM32F030 MCU line. F150 adds USB support to F130, and F170/F190 adds
CAN support.

Currently the code mainly targets GD32F130 and F150 chips. Some register
are different between F130/150 and F170/190, just like the difference
between STM32F1 Performance line and Connectivity line.

From the perspective of registers and memory map, GD32F1X0 seems like a
mixture between STM32F1 and STM32F0 (because it is designed to be
pin-to-pin compatible with F0, but with Cortex-M3 like F1). A bunch of
code are shared between STM32 and GD32, and these code are specially
processed to include the GD32 headers instead of STM32 headers when meet
GD32F1X0.

Signed-off-by: Icenowy Zheng <icenowy@aosc.io>

Reviewed-by: Karl Palsson <karlp@tweak.net.au>
gd32/rcc.[ch] are forks of stm32f1/rcc
gd32/flash.[ch] are forks of stm32f0/flash
No attempts at deduplicating this have been done at this stage.  We can
see where they move in the future.
This commit is contained in:
Icenowy Zheng 2019-01-30 01:14:06 +08:00 committed by Karl Palsson
parent d109a1ddeb
commit 330d5fd5be
21 changed files with 1873 additions and 0 deletions

View File

@ -29,6 +29,7 @@ SRCLIBDIR:= $(subst $(space),\$(space),$(realpath lib))
TARGETS ?= stm32/f0 stm32/f1 stm32/f2 stm32/f3 stm32/f4 stm32/f7 \
stm32/l0 stm32/l1 stm32/l4 \
gd32/f1x0 \
lpc13xx lpc17xx lpc43xx/m4 lpc43xx/m0 \
lm3s lm4f msp432/e4 \
efm32/tg efm32/g efm32/lg efm32/gg efm32/hg efm32/wg \

View File

@ -21,6 +21,9 @@
#elif defined(STM32L4)
# include <libopencm3/stm32/l4/nvic.h>
#elif defined(GD32F1X0)
# include <libopencm3/gd32/f1x0/nvic.h>
#elif defined(EFM32TG)
# include <libopencm3/efm32/tg/nvic.h>
#elif defined(EFM32G)

View File

@ -0,0 +1,103 @@
/** @defgroup flash_defines FLASH Defines
*
* @brief <b>Defined Constants and Types for the GD32F1x0 Flash memory</b>
*
* @ingroup GD32F1x0_defines
*
* @version 1.0.0
*
* @author @htmlonly &copy; @endhtmlonly 2013
* Frantisek Burian <BuFran@seznam.cz>
*
* @date 14 January 2014
*
* LGPL License Terms @ref lgpl_license
*/
/*
* This file is part of the libopencm3 project.
*
* Copyright (C) 2013 Frantisek Burian <BuFran@seznam.cz>
*
* This library is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this library. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef LIBOPENCM3_FLASH_H
#define LIBOPENCM3_FLASH_H
/**@{*/
#include <libopencm3/stm32/common/flash_common_all.h>
#include <libopencm3/stm32/common/flash_common_f.h>
#include <libopencm3/stm32/common/flash_common_f01.h>
/*****************************************************************************/
/* Register values */
/*****************************************************************************/
/* --- FLASH_ACR values ---------------------------------------------------- */
/** @defgroup flash_latency FLASH Wait States
@ingroup flash_defines
@{*/
#define FLASH_ACR_LATENCY_000_024MHZ 0
#define FLASH_ACR_LATENCY_024_048MHZ 1
#define FLASH_ACR_LATENCY_048_072MHZ 2
#define FLASH_ACR_LATENCY_0WS 0
#define FLASH_ACR_LATENCY_1WS 1
#define FLASH_ACR_LATENCY_2WS 1
/**@}*/
/* --- FLASH_SR values ----------------------------------------------------- */
#define FLASH_SR_EOP (1 << 5)
#define FLASH_SR_WRPRTERR (1 << 4)
#define FLASH_SR_PGERR (1 << 2)
#define FLASH_SR_BSY (1 << 0)
/* --- FLASH_CR values ----------------------------------------------------- */
#define FLASH_CR_OBL_LAUNCH (1 << 13)
/* --- FLASH_OBR values ---------------------------------------------------- */
#define FLASH_OBR_DATA1_SHIFT 24
#define FLASH_OBR_DATA1 (0xFF << FLASH_OBR_DATA1_SHIFT)
#define FLASH_OBR_DATA0_SHIFT 16
#define FLASH_OBR_DATA0 (0xFF << FLASH_OBR_DATA0_SHIFT)
#define FLASH_OBR_USER_SHIFT 8
#define FLASH_OBR_USER (0xFF << FLASH_OBR_USER_SHIFT)
#define FLASH_OBR_RDPRT (3 << FLASH_OBR_RDPRT_SHIFT)
#define FLASH_OBR_RDPRT_L0 (0 << FLASH_OBR_RDPRT_SHIFT)
#define FLASH_OBR_RDPRT_L1 (1 << FLASH_OBR_RDPRT_SHIFT)
#define FLASH_OBR_RDPRT_L2 (3 << FLASH_OBR_RDPRT_SHIFT)
/*****************************************************************************/
/* API definitions */
/*****************************************************************************/
/* Read protection option byte protection level setting */
#define FLASH_RDP_L0 ((uint8_t)0xa5)
#define FLASH_RDP_L1 ((uint8_t)0xf0) /* any value */
#define FLASH_RDP_L2 ((uint8_t)0xcc)
/*****************************************************************************/
/* API Functions */
/*****************************************************************************/
BEGIN_DECLS
END_DECLS
/**@}*/
#endif

View File

@ -0,0 +1,31 @@
/** @defgroup gpio_defines GPIO Defines
*
* @brief <b>Defined Constants and Types for the GD32F1x0 General Purpose I/O</b>
*
* @ingroup GD32F1x0_defines
*
* @version 1.0.0
*
* @date 1 July 2012
*
* LGPL License Terms @ref lgpl_license
*/
/*
* This file is part of the libopencm3 project.
*
* This library is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this library. If not, see <http://www.gnu.org/licenses/>.
*/
#include <libopencm3/stm32/f0/gpio.h>

View File

@ -0,0 +1,59 @@
{
"irqs": [
"wwdg",
"pvd",
"rtc",
"flash",
"rcc",
"exti0_1",
"exti2_3",
"exti4_15",
"tsc",
"dma_channel1",
"dma_channel2_3",
"dma_channel4_5",
"adc_comp",
"tim1_brk_up_trg_com",
"tim1_cc",
"tim2",
"tim3",
"tim6_dac",
"reserved0",
"tim14",
"tim15",
"tim16",
"tim17",
"i2c1_ev",
"i2c2_ev",
"spi1",
"spi2",
"usart1",
"usart2",
"reserved1",
"cec_can",
"reserved2",
"i2c1_er",
"reserved3",
"i2c2_er",
"i2c3_ev",
"i2c3_er",
"usb_lp",
"usb_hp",
"reserved4",
"reserved5",
"reserved6",
"usb_wakeup",
"reserved7",
"reserved8",
"reserved9",
"reserved10",
"reserved11",
"dma_channel6_7",
"reserved12",
"reserved13",
"spi3"
],
"partname_humanreadable": "GD32F1x0 Series",
"partname_doxygen": "GD32F1x0",
"includeguard": "LIBOPENCM3_GD32F1X0_NVIC_H"
}

View File

@ -0,0 +1,109 @@
/*
* This file is part of the libopencm3 project.
*
* Copyright (C) 2019 Iceonwy Zheng <icenowy@aosc.io>
*
* This library is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this library. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef LIBOPENCM3_MEMORYMAP_H
#define LIBOPENCM3_MEMORYMAP_H
#include <libopencm3/cm3/memorymap.h>
/* --- GD32 specific peripheral definitions ------------------------------- */
/* Memory map for all buses */
#define FLASH_BASE (0x08000000U)
#define PERIPH_BASE (0x40000000U)
#define INFO_BASE (0x1ffff000U)
#define PERIPH_BASE_APB1 (PERIPH_BASE + 0x00000)
#define PERIPH_BASE_APB2 (PERIPH_BASE + 0x10000)
#define PERIPH_BASE_AHB1 (PERIPH_BASE + 0x20000)
#define PERIPH_BASE_AHB2 (PERIPH_BASE + 0x8000000)
/* Register boundary addresses */
/* APB1 */
#define TIM2_BASE (PERIPH_BASE_APB1 + 0x0000)
#define TIM3_BASE (PERIPH_BASE_APB1 + 0x0400)
#define TIM6_BASE (PERIPH_BASE_APB1 + 0x1000)
#define TIM14_BASE (PERIPH_BASE_APB1 + 0x2000)
/* PERIPH_BASE_APB1 + 0x2400 (0x4000 2400 - 0x4000 27FF): Reserved */
#define RTC_BASE (PERIPH_BASE_APB1 + 0x2800)
#define WWDG_BASE (PERIPH_BASE_APB1 + 0x2c00)
#define IWDG_BASE (PERIPH_BASE_APB1 + 0x3000)
/* PERIPH_BASE_APB1 + 0x3400 (0x4000 3400 - 0x4000 37FF): Reserved */
#define SPI2_BASE (PERIPH_BASE_APB1 + 0x3800)
/* PERIPH_BASE_APB1 + 0x4000 (0x4000 4000 - 0x4000 3FFF): Reserved */
#define USART2_BASE (PERIPH_BASE_APB1 + 0x4400)
#define I2C1_BASE (PERIPH_BASE_APB1 + 0x5400)
#define I2C2_BASE (PERIPH_BASE_APB1 + 0x5800)
#define USB_DEV_FS_BASE (PERIPH_BASE_APB1 + 0x5c00)
#define USB_PMA_BASE (PERIPH_BASE_APB1 + 0x6000)
#define USB_SRAM_BASE (PERIPH_BASE_APB1 + 0x6000)
#define BACKUP_REGS_BASE (RTC_BASE + 0x50)
#define POWER_CONTROL_BASE (PERIPH_BASE_APB1 + 0x7000)
#define DAC_BASE (PERIPH_BASE_APB1 + 0x7400)
#define CEC_BASE (PERIPH_BASE_APB1 + 0x7800)
/* PERIPH_BASE_APB1 + 0x7c00 (0x4000 7c00 - 0x4000 FFFF): Reserved */
/* APB2 */
#define SYSCFG_COMP_BASE (PERIPH_BASE_APB2 + 0x0000)
#define EXTI_BASE (PERIPH_BASE_APB2 + 0x0400)
#define ADC1_BASE (PERIPH_BASE_APB2 + 0x2400)
#define TIM1_BASE (PERIPH_BASE_APB2 + 0x2c00)
#define SPI1_BASE (PERIPH_BASE_APB2 + 0x3000)
#define USART1_BASE (PERIPH_BASE_APB2 + 0x3800)
#define TIM15_BASE (PERIPH_BASE_APB2 + 0x4000)
#define TIM16_BASE (PERIPH_BASE_APB2 + 0x4400)
#define TIM17_BASE (PERIPH_BASE_APB2 + 0x4800)
/* PERIPH_BASE_APB2 + 0x5800 (0x4001 5800 - 0x4001 7FFF): Reserved */
/* AHB1 */
#define DMA1_BASE (PERIPH_BASE_AHB1 + 0x00000)
#define RCC_BASE (PERIPH_BASE_AHB1 + 0x01000)
#define FLASH_MEM_INTERFACE_BASE (PERIPH_BASE_AHB1 + 0x02000)
#define CRC_BASE (PERIPH_BASE_AHB1 + 0x03000)
#define TSC_BASE (PERIPH_BASE_AHB1 + 0x03000)
/* AHB 2 */
#define GPIO_PORT_A_BASE (PERIPH_BASE_AHB2 + 0x0000)
#define GPIO_PORT_B_BASE (PERIPH_BASE_AHB2 + 0x0400)
#define GPIO_PORT_C_BASE (PERIPH_BASE_AHB2 + 0x0800)
#define GPIO_PORT_D_BASE (PERIPH_BASE_AHB2 + 0x0c00)
#define GPIO_PORT_F_BASE (PERIPH_BASE_AHB2 + 0x1400)
/* Device Electronic Signature */
#define DESIG_FLASH_SIZE_BASE (INFO_BASE + 0x7e0)
#define DESIG_UNIQUE_ID_BASE (INFO_BASE + 0x7ac)
/* Ignore the "reserved for future use" half of the first word */
#define DESIG_UNIQUE_ID0 MMIO32(DESIG_UNIQUE_ID_BASE)
#define DESIG_UNIQUE_ID1 MMIO32(DESIG_UNIQUE_ID_BASE + 4)
#define DESIG_UNIQUE_ID2 MMIO32(DESIG_UNIQUE_ID_BASE + 8)
#endif

View File

@ -0,0 +1,526 @@
/** @defgroup rcc_defines RCC Defines
*
* @brief <b>Defined Constants and Types for the GD32F1x0 Reset and Clock
* Control</b>
*
* @ingroup GD32F1x0_defines
*
* @version 1.0.0
*
* @author @htmlonly &copy; @endhtmlonly 2009
* Federico Ruiz-Ugalde \<memeruiz at gmail dot com\>
* @author @htmlonly &copy; @endhtmlonly 2009
* Uwe Hermann <uwe@hermann-uwe.de>
*
* @date 18 August 2012
*
* LGPL License Terms @ref lgpl_license
* */
/*
* This file is part of the libopencm3 project.
*
* Copyright (C) 2019 Icenowy Zheng <icenowy@aosc.io>
* Copyright (C) 2009 Uwe Hermann <uwe@hermann-uwe.de>
* Copyright (C) 2009 Federico Ruiz-Ugalde <memeruiz at gmail dot com>
*
* This library is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this library. If not, see <http://www.gnu.org/licenses/>.
*/
/**@{*/
#ifndef LIBOPENCM3_RCC_H
#define LIBOPENCM3_RCC_H
/* --- RCC registers ------------------------------------------------------- */
#define RCC_CR MMIO32(RCC_BASE + 0x00)
#define RCC_CFGR MMIO32(RCC_BASE + 0x04)
#define RCC_CIR MMIO32(RCC_BASE + 0x08)
#define RCC_APB2RSTR MMIO32(RCC_BASE + 0x0c)
#define RCC_APB1RSTR MMIO32(RCC_BASE + 0x10)
#define RCC_AHBENR MMIO32(RCC_BASE + 0x14)
#define RCC_APB2ENR MMIO32(RCC_BASE + 0x18)
#define RCC_APB1ENR MMIO32(RCC_BASE + 0x1c)
#define RCC_BDCR MMIO32(RCC_BASE + 0x20)
#define RCC_CSR MMIO32(RCC_BASE + 0x24)
#define RCC_AHBRSTR MMIO32(RCC_BASE + 0x28)
#define RCC_CFGR2 MMIO32(RCC_BASE + 0x2c)
#define RCC_CFGR3 MMIO32(RCC_BASE + 0x30)
#define RCC_CR2 MMIO32(RCC_BASE + 0x34)
/* --- RCC_CR values ------------------------------------------------------- */
#define RCC_CR_PLLRDY (1 << 25)
#define RCC_CR_PLLON (1 << 24)
#define RCC_CR_CSSON (1 << 19)
#define RCC_CR_HSEBYP (1 << 18)
#define RCC_CR_HSERDY (1 << 17)
#define RCC_CR_HSEON (1 << 16)
/* HSICAL: [15:8] */
/* HSITRIM: [7:3] */
#define RCC_CR_HSIRDY (1 << 1)
#define RCC_CR_HSION (1 << 0)
/* --- RCC_CFGR values ----------------------------------------------------- */
#define RCC_CFGR_PLLNODIV (1 << 31)
#define RCC_CFGR_MCOPRE_SHIFT 28
#define RCC_CFGR_MCOPRE (7 << RCC_CFGR_MCOPRE_SHIFT)
#define RCC_CFGR_MCOPRE_DIV1 (0 << RCC_CFGR_MCOPRE_SHIFT)
#define RCC_CFGR_MCOPRE_DIV2 (1 << RCC_CFGR_MCOPRE_SHIFT)
#define RCC_CFGR_MCOPRE_DIV4 (2 << RCC_CFGR_MCOPRE_SHIFT)
#define RCC_CFGR_MCOPRE_DIV8 (3 << RCC_CFGR_MCOPRE_SHIFT)
#define RCC_CFGR_MCOPRE_DIV16 (4 << RCC_CFGR_MCOPRE_SHIFT)
#define RCC_CFGR_MCOPRE_DIV32 (5 << RCC_CFGR_MCOPRE_SHIFT)
#define RCC_CFGR_MCOPRE_DIV64 (6 << RCC_CFGR_MCOPRE_SHIFT)
#define RCC_CFGR_MCOPRE_DIV128 (7 << RCC_CFGR_MCOPRE_SHIFT)
#define RCC_CFGR_PLLMUL_4_SHIFT 27
#define RCC_CFGR_PLLMUL_4 (1 << RCC_CFGR_PLLMUL_4_SHIFT)
#define RCC_CFGR_MCO_SHIFT 24
#define RCC_CFGR_MCO_MASK 0x7
#define RCC_CFGR_MCO_NOCLK 0
#define RCC_CFGR_MCO_HSI14 1
#define RCC_CFGR_MCO_LSI 2
#define RCC_CFGR_MCO_LSE 3
#define RCC_CFGR_MCO_SYSCLK 4
#define RCC_CFGR_MCO_HSI 5
#define RCC_CFGR_MCO_HSE 6
#define RCC_CFGR_MCO_PLL 7
#define RCC_CFGR_USBPRE_SHIFT 22
#define RCC_CFGR_USBPRE (3 << RCC_CFGR_USBPRE_SHIFT)
#define RCC_CFGR_PLLMUL_0_3_SHIFT 18
#define RCC_CFGR_PLLMUL_0_3 (0xF << RCC_CFGR_PLLMUL_0_3_SHIFT)
#define RCC_CFGR_PLLXTPRE (1 << 17)
#define RCC_CFGR_PLLSRC (1 << 16)
#define RCC_CFGR_ADCPRE_SHIFT 14
#define RCC_CFGR_ADCPRE (3 << RCC_CFGR_ADCPRE_SHIFT)
#define RCC_CFGR_PPRE2_SHIFT 11
#define RCC_CFGR_PPRE2 (7 << RCC_CFGR_PPRE2_SHIFT)
#define RCC_CFGR_PPRE1_SHIFT 8
#define RCC_CFGR_PPRE1 (7 << RCC_CFGR_PPRE1_SHIFT)
#define RCC_CFGR_HPRE_SHIFT 4
#define RCC_CFGR_HPRE (0xF << RCC_CFGR_HPRE_SHIFT)
#define RCC_CFGR_SWS_SHIFT 2
#define RCC_CFGR_SWS (3 << RCC_CFGR_SWS_SHIFT)
#define RCC_CFGR_SW_SHIFT 0
#define RCC_CFGR_SW (3 << RCC_CFGR_SW_SHIFT)
/* USBPRE: USB prescaler (RCC_CFGR[23:22]) */
#define RCC_CFGR_USBPRE_PLL_CLK_DIV1_5 0x0
#define RCC_CFGR_USBPRE_PLL_CLK_NODIV 0x1
#define RCC_CFGR_USBPRE_PLL_CLK_DIV2_5 0x2
#define RCC_CFGR_USBPRE_PLL_CLK_DIV2 0x3
/* PLLMUL: PLL multiplication factor */
#define RCC_CFGR_PLLMUL_PLL_CLK_MUL2 0x0
#define RCC_CFGR_PLLMUL_PLL_CLK_MUL3 0x1
#define RCC_CFGR_PLLMUL_PLL_CLK_MUL4 0x2
#define RCC_CFGR_PLLMUL_PLL_CLK_MUL5 0x3
#define RCC_CFGR_PLLMUL_PLL_CLK_MUL6 0x4
#define RCC_CFGR_PLLMUL_PLL_CLK_MUL7 0x5
#define RCC_CFGR_PLLMUL_PLL_CLK_MUL8 0x6
#define RCC_CFGR_PLLMUL_PLL_CLK_MUL9 0x7
#define RCC_CFGR_PLLMUL_PLL_CLK_MUL10 0x8
#define RCC_CFGR_PLLMUL_PLL_CLK_MUL11 0x9
#define RCC_CFGR_PLLMUL_PLL_CLK_MUL12 0xa
#define RCC_CFGR_PLLMUL_PLL_CLK_MUL13 0xb
#define RCC_CFGR_PLLMUL_PLL_CLK_MUL14 0xc
#define RCC_CFGR_PLLMUL_PLL_CLK_MUL15 0xd
#define RCC_CFGR_PLLMUL_PLL_CLK_MUL16 0xe
/* PLLXTPRE: HSE divider for PLL entry */
#define RCC_CFGR_PLLXTPRE_HSE_CLK 0x0
#define RCC_CFGR_PLLXTPRE_HSE_CLK_DIV2 0x1
/* PLLSRC: PLL entry clock source */
#define RCC_CFGR_PLLSRC_HSI_CLK_DIV2 0x0
#define RCC_CFGR_PLLSRC_HSE_CLK 0x1
/* ADCPRE: ADC prescaler */
/****************************************************************************/
#define RCC_CFGR_ADCPRE_PCLK2_DIV2 0x0
#define RCC_CFGR_ADCPRE_PCLK2_DIV4 0x1
#define RCC_CFGR_ADCPRE_PCLK2_DIV6 0x2
#define RCC_CFGR_ADCPRE_PCLK2_DIV8 0x3
/* PPRE2: APB high-speed prescaler (APB2) */
#define RCC_CFGR_PPRE2_HCLK_NODIV 0x0
#define RCC_CFGR_PPRE2_HCLK_DIV2 0x4
#define RCC_CFGR_PPRE2_HCLK_DIV4 0x5
#define RCC_CFGR_PPRE2_HCLK_DIV8 0x6
#define RCC_CFGR_PPRE2_HCLK_DIV16 0x7
/* PPRE1: APB low-speed prescaler (APB1) */
#define RCC_CFGR_PPRE1_HCLK_NODIV 0x0
#define RCC_CFGR_PPRE1_HCLK_DIV2 0x4
#define RCC_CFGR_PPRE1_HCLK_DIV4 0x5
#define RCC_CFGR_PPRE1_HCLK_DIV8 0x6
#define RCC_CFGR_PPRE1_HCLK_DIV16 0x7
/* HPRE: AHB prescaler */
#define RCC_CFGR_HPRE_SYSCLK_NODIV 0x0
#define RCC_CFGR_HPRE_SYSCLK_DIV2 0x8
#define RCC_CFGR_HPRE_SYSCLK_DIV4 0x9
#define RCC_CFGR_HPRE_SYSCLK_DIV8 0xa
#define RCC_CFGR_HPRE_SYSCLK_DIV16 0xb
#define RCC_CFGR_HPRE_SYSCLK_DIV64 0xc
#define RCC_CFGR_HPRE_SYSCLK_DIV128 0xd
#define RCC_CFGR_HPRE_SYSCLK_DIV256 0xe
#define RCC_CFGR_HPRE_SYSCLK_DIV512 0xf
/* SWS: System clock switch status */
#define RCC_CFGR_SWS_SYSCLKSEL_HSICLK 0x0
#define RCC_CFGR_SWS_SYSCLKSEL_HSECLK 0x1
#define RCC_CFGR_SWS_SYSCLKSEL_PLLCLK 0x2
/* SW: System clock switch */
#define RCC_CFGR_SW_SYSCLKSEL_HSICLK 0x0
#define RCC_CFGR_SW_SYSCLKSEL_HSECLK 0x1
#define RCC_CFGR_SW_SYSCLKSEL_PLLCLK 0x2
/* --- RCC_CIR values ------------------------------------------------------ */
/* Clock security system interrupt clear bit */
#define RCC_CIR_CSSC (1 << 23)
/* OSC ready interrupt clear bits */
#define RCC_CIR_HSI14RDYC (1 << 21)
#define RCC_CIR_PLLRDYC (1 << 20)
#define RCC_CIR_HSERDYC (1 << 19)
#define RCC_CIR_HSIRDYC (1 << 18)
#define RCC_CIR_LSERDYC (1 << 17)
#define RCC_CIR_LSIRDYC (1 << 16)
/* OSC ready interrupt enable bits */
#define RCC_CIR_HSI14RDYIE (1 << 13)
#define RCC_CIR_PLLRDYIE (1 << 12)
#define RCC_CIR_HSERDYIE (1 << 11)
#define RCC_CIR_HSIRDYIE (1 << 10)
#define RCC_CIR_LSERDYIE (1 << 9)
#define RCC_CIR_LSIRDYIE (1 << 8)
/* Clock security system interrupt flag bit */
#define RCC_CIR_CSSF (1 << 7)
/* OSC ready interrupt flag bits */
#define RCC_CIR_HSI14RDYF (1 << 5)
#define RCC_CIR_PLLRDYF (1 << 4)
#define RCC_CIR_HSERDYF (1 << 3)
#define RCC_CIR_HSIRDYF (1 << 2)
#define RCC_CIR_LSERDYF (1 << 1)
#define RCC_CIR_LSIRDYF (1 << 0)
/* --- RCC_APB2RSTR values ------------------------------------------------- */
#define RCC_APB2RSTR_TIM17RST (1 << 18)
#define RCC_APB2RSTR_TIM16RST (1 << 17)
#define RCC_APB2RSTR_TIM15RST (1 << 16)
#define RCC_APB2RSTR_USART1RST (1 << 14)
#define RCC_APB2RSTR_SPI1RST (1 << 12)
#define RCC_APB2RSTR_TIM1RST (1 << 11)
#define RCC_APB2RSTR_ADCRST (1 << 9)
#define RCC_APB2RSTR_SYSCFGRST (1 << 0)
/* --- RCC_APB1RSTR values ------------------------------------------------- */
#define RCC_APB1RSTR_CECRST (1 << 30)
#define RCC_APB1RSTR_DACRST (1 << 29)
#define RCC_APB1RSTR_PWRRST (1 << 28)
#define RCC_APB1RSTR_USBRST (1 << 23)
#define RCC_APB1RSTR_I2C2RST (1 << 22)
#define RCC_APB1RSTR_I2C1RST (1 << 21)
#define RCC_APB1RSTR_USART2RST (1 << 17)
#define RCC_APB1RSTR_SPI3RST (1 << 15)
#define RCC_APB1RSTR_SPI2RST (1 << 14)
#define RCC_APB1RSTR_WWDGRST (1 << 11)
#define RCC_APB1RSTR_TIM14RST (1 << 8)
#define RCC_APB1RSTR_TIM6RST (1 << 4)
#define RCC_APB1RSTR_TIM3RST (1 << 1)
#define RCC_APB1RSTR_TIM2RST (1 << 0)
/* --- RCC_AHBENR values --------------------------------------------------- */
#define RCC_AHBENR_TSCEN (1 << 24)
#define RCC_AHBENR_GPIOFEN (1 << 22)
#define RCC_AHBENR_GPIOEEN (1 << 21)
#define RCC_AHBENR_GPIODEN (1 << 20)
#define RCC_AHBENR_GPIOCEN (1 << 19)
#define RCC_AHBENR_GPIOBEN (1 << 18)
#define RCC_AHBENR_GPIOAEN (1 << 17)
#define RCC_AHBENR_CRCEN (1 << 6)
#define RCC_AHBENR_FLTFEN (1 << 4)
#define RCC_AHBENR_SRAMEN (1 << 2)
#define RCC_AHBENR_DMAEN (1 << 0)
/* --- RCC_APB2ENR values -------------------------------------------------- */
#define RCC_APB2ENR_TIM17EN (1 << 18)
#define RCC_APB2ENR_TIM16EN (1 << 17)
#define RCC_APB2ENR_TIM15EN (1 << 16)
#define RCC_APB2ENR_USART1EN (1 << 14)
#define RCC_APB2ENR_SPI1EN (1 << 12)
#define RCC_APB2ENR_TIM1EN (1 << 11)
#define RCC_APB2ENR_ADCEN (1 << 9)
#define RCC_APB2ENR_SYSCFGCOMPEN (1 << 0)
/* --- RCC_APB1ENR values -------------------------------------------------- */
#define RCC_APB1ENR_CECEN (1 << 30)
#define RCC_APB1ENR_DACEN (1 << 29)
#define RCC_APB1ENR_PWREN (1 << 28)
#define RCC_APB1ENR_USBEN (1 << 23)
#define RCC_APB1ENR_I2C2EN (1 << 22)
#define RCC_APB1ENR_I2C1EN (1 << 21)
#define RCC_APB1ENR_USART2EN (1 << 17)
#define RCC_APB1ENR_SPI3EN (1 << 15)
#define RCC_APB1ENR_SPI2EN (1 << 14)
#define RCC_APB1ENR_WWDGEN (1 << 11)
#define RCC_APB1ENR_TIM14EN (1 << 8)
#define RCC_APB1ENR_TIM6EN (1 << 4)
#define RCC_APB1ENR_TIM3EN (1 << 1)
#define RCC_APB1ENR_TIM2EN (1 << 0)
/* --- RCC_BDCR values ----------------------------------------------------- */
#define RCC_BDCR_BDRST (1 << 16)
#define RCC_BDCR_RTCEN (1 << 15)
/* RCC_BDCR[9:8]: RTCSEL */
#define RCC_BDCR_LSEBYP (1 << 2)
#define RCC_BDCR_LSERDY (1 << 1)
#define RCC_BDCR_LSEON (1 << 0)
/* --- RCC_CSR values ------------------------------------------------------ */
#define RCC_CSR_LPWRRSTF (1 << 31)
#define RCC_CSR_WWDGRSTF (1 << 30)
#define RCC_CSR_IWDGRSTF (1 << 29)
#define RCC_CSR_SFTRSTF (1 << 28)
#define RCC_CSR_PORRSTF (1 << 27)
#define RCC_CSR_PINRSTF (1 << 26)
#define RCC_CSR_RMVF (1 << 24)
#define RCC_CSR_LSIRDY (1 << 1)
#define RCC_CSR_LSION (1 << 0)
/* --- RCC_AHBRSTR values -------------------------------------------------- */
#define RCC_AHBRSTR_ETHMACRST (1 << 14)
#define RCC_AHBRSTR_OTGFSRST (1 << 12)
/* --- RCC_CFGR2 values ---------------------------------------------------- */
#define RCC_CFGR2_PREDIV 0xf
#define RCC_CFGR2_PREDIV_NODIV 0x0
#define RCC_CFGR2_PREDIV_DIV2 0x1
#define RCC_CFGR2_PREDIV_DIV3 0x2
#define RCC_CFGR2_PREDIV_DIV4 0x3
#define RCC_CFGR2_PREDIV_DIV5 0x4
#define RCC_CFGR2_PREDIV_DIV6 0x5
#define RCC_CFGR2_PREDIV_DIV7 0x6
#define RCC_CFGR2_PREDIV_DIV8 0x7
#define RCC_CFGR2_PREDIV_DIV9 0x8
#define RCC_CFGR2_PREDIV_DIV10 0x9
#define RCC_CFGR2_PREDIV_DIV11 0xa
#define RCC_CFGR2_PREDIV_DIV12 0xb
#define RCC_CFGR2_PREDIV_DIV13 0xc
#define RCC_CFGR2_PREDIV_DIV14 0xd
#define RCC_CFGR2_PREDIV_DIV15 0xe
#define RCC_CFGR2_PREDIV_DIV16 0xf
/* --- RCC_CFGR3 values ---------------------------------------------------- */
#define RCC_CFGR3_USART2SW_SHIFT 16
#define RCC_CFGR3_USART2SW (3 << RCC_CFGR3_USART2SW_SHIFT)
#define RCC_CFGR3_USART2SW_PCLK (0 << RCC_CFGR3_USART2SW_SHIFT)
#define RCC_CFGR3_USART2SW_SYSCLK (1 << RCC_CFGR3_USART2SW_SHIFT)
#define RCC_CFGR3_USART2SW_LSE (2 << RCC_CFGR3_USART2SW_SHIFT)
#define RCC_CFGR3_USART2SW_HSI (3 << RCC_CFGR3_USART2SW_SHIFT)
#define RCC_CFGR3_ADCSW (1 << 8)
#define RCC_CFGR3_CECSW (1 << 6)
/* --- Variable definitions ------------------------------------------------ */
extern uint32_t rcc_ahb_frequency;
extern uint32_t rcc_apb1_frequency;
extern uint32_t rcc_apb2_frequency;
/* --- Function prototypes ------------------------------------------------- */
enum rcc_clock_hsi {
RCC_CLOCK_HSI_48MHZ,
RCC_CLOCK_HSI_64MHZ,
RCC_CLOCK_HSI_END
};
enum rcc_clock_hse8 {
RCC_CLOCK_HSE8_72MHZ,
RCC_CLOCK_HSE8_END
};
struct rcc_clock_scale {
uint8_t pllmul;
uint8_t hpre;
uint8_t ppre1;
uint8_t ppre2;
uint8_t adcpre;
uint8_t usbpre; /* Only valid if HSE used */
bool use_hse; /* PLL source is HSE if set, HSI/2 if unset */
uint8_t pll_hse_prediv; /* Only valid if HSE used */
uint32_t ahb_frequency;
uint32_t apb1_frequency;
uint32_t apb2_frequency;
};
extern const struct rcc_clock_scale rcc_hsi_configs[RCC_CLOCK_HSI_END];
extern const struct rcc_clock_scale rcc_hse8_configs[RCC_CLOCK_HSE8_END];
enum rcc_osc {
RCC_PLL, RCC_HSE, RCC_HSI, RCC_LSE, RCC_LSI
};
#define _REG_BIT(base, bit) (((base) << 5) + (bit))
/* V = value line F100
* N = standard line F101, F102, F103
* C = communication line F105, F107
*/
enum rcc_periph_clken {
/* AHB peripherals */
RCC_DMA = _REG_BIT(0x14, 0),
RCC_SRAM = _REG_BIT(0x14, 2),
RCC_FLTF = _REG_BIT(0x14, 4),
RCC_CRC = _REG_BIT(0x14, 6),
RCC_GPIOA = _REG_BIT(0x14, 17),
RCC_GPIOB = _REG_BIT(0x14, 18),
RCC_GPIOC = _REG_BIT(0x14, 19),
RCC_GPIOD = _REG_BIT(0x14, 20),
RCC_GPIOF = _REG_BIT(0x14, 22),
RCC_TSC = _REG_BIT(0x14, 24),
/* APB2 peripherals */
RCC_SYSCFG_COMP = _REG_BIT(0x18, 0),
RCC_ADC = _REG_BIT(0x18, 9),
RCC_TIM1 = _REG_BIT(0x18, 11),
RCC_SPI1 = _REG_BIT(0x18, 12),
RCC_USART1 = _REG_BIT(0x18, 14),
RCC_TIM15 = _REG_BIT(0x18, 16),
RCC_TIM16 = _REG_BIT(0x18, 17),
RCC_TIM17 = _REG_BIT(0x18, 18),
/* APB1 peripherals */
RCC_TIM2 = _REG_BIT(0x1C, 0),
RCC_TIM3 = _REG_BIT(0x1C, 1),
RCC_TIM6 = _REG_BIT(0x1C, 4),
RCC_TIM14 = _REG_BIT(0x1C, 8),
RCC_WWDG = _REG_BIT(0x1C, 11),
RCC_SPI2 = _REG_BIT(0x1C, 14),
RCC_SPI3 = _REG_BIT(0x1C, 15),
RCC_USART2 = _REG_BIT(0x1C, 17),
RCC_I2C1 = _REG_BIT(0x1C, 21),
RCC_I2C2 = _REG_BIT(0x1C, 22),
RCC_USB = _REG_BIT(0x1C, 23),
RCC_PWR = _REG_BIT(0x1C, 28),
RCC_DAC = _REG_BIT(0x1C, 29),
RCC_CEC = _REG_BIT(0x1C, 30),
};
enum rcc_periph_rst {
/* Advanced peripherals */
RST_BACKUPDOMAIN = _REG_BIT(0x20, 16),/* BDCR[16] */
/* AHB peripherals */
RST_GPIOA = _REG_BIT(0x28, 17),
RST_GPIOB = _REG_BIT(0x28, 18),
RST_GPIOC = _REG_BIT(0x28, 19),
RST_GPIOD = _REG_BIT(0x28, 20),
RST_GPIOE = _REG_BIT(0x28, 21),
RST_GPIOF = _REG_BIT(0x28, 22),
RST_TSC = _REG_BIT(0x28, 24),
/* APB2 peripherals */
RST_SYSCFG = _REG_BIT(0x0C, 0),
RST_ADC = _REG_BIT(0x0C, 9),
RST_TIM1 = _REG_BIT(0x0C, 11),
RST_SPI1 = _REG_BIT(0x0C, 12),
RST_USART1 = _REG_BIT(0x0C, 14),
RST_TIM15 = _REG_BIT(0x0C, 16),
RST_TIM16 = _REG_BIT(0x0C, 17),
RST_TIM17 = _REG_BIT(0x0C, 18),
/* APB1 peripherals */
RST_TIM2 = _REG_BIT(0x10, 0),
RST_TIM3 = _REG_BIT(0x10, 1),
RST_TIM6 = _REG_BIT(0x10, 4),
RST_TIM14 = _REG_BIT(0x10, 8),
RST_WWDG = _REG_BIT(0x10, 11),
RST_SPI2 = _REG_BIT(0x10, 14),
RST_SPI3 = _REG_BIT(0x10, 15),
RST_USART2 = _REG_BIT(0x10, 17),
RST_I2C1 = _REG_BIT(0x10, 21),
RST_I2C2 = _REG_BIT(0x10, 22),
RST_USB = _REG_BIT(0x10, 23),
RST_PWR = _REG_BIT(0x10, 28),
RST_DAC = _REG_BIT(0x10, 29),
RST_CEC = _REG_BIT(0x10, 30),
};
#include <libopencm3/stm32/common/rcc_common_all.h>
BEGIN_DECLS
void rcc_osc_ready_int_clear(enum rcc_osc osc);
void rcc_osc_ready_int_enable(enum rcc_osc osc);
void rcc_osc_ready_int_disable(enum rcc_osc osc);
int rcc_osc_ready_int_flag(enum rcc_osc osc);
void rcc_css_int_clear(void);
int rcc_css_int_flag(void);
void rcc_osc_on(enum rcc_osc osc);
void rcc_osc_off(enum rcc_osc osc);
void rcc_css_enable(void);
void rcc_css_disable(void);
void rcc_set_sysclk_source(uint32_t clk);
void rcc_set_pll_multiplication_factor(uint32_t mul);
void rcc_set_pll_source(uint32_t pllsrc);
void rcc_set_pllxtpre(uint32_t pllxtpre);
uint32_t rcc_rtc_clock_enabled_flag(void);
void rcc_enable_rtc_clock(void);
void rcc_set_rtc_clock_source(enum rcc_osc clock_source);
void rcc_set_adcpre(uint32_t adcpre);
void rcc_set_ppre2(uint32_t ppre1);
void rcc_set_ppre1(uint32_t ppre1);
void rcc_set_hpre(uint32_t hpre);
void rcc_set_usbpre(uint32_t usbpre);
void rcc_set_prediv(uint32_t prediv);
uint32_t rcc_system_clock_source(void);
void rcc_clock_setup_pll(const struct rcc_clock_scale *clock);
void rcc_backupdomain_reset(void);
END_DECLS
#endif
/**@}*/

View File

@ -0,0 +1,28 @@
/* This provides unification of code over GD32 subfamilies */
/*
* This file is part of the libopencm3 project.
*
* This library is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this library. If not, see <http://www.gnu.org/licenses/>.
*/
#include <libopencm3/cm3/common.h>
#include <libopencm3/gd32/memorymap.h>
#if defined(GD32F1X0)
# include <libopencm3/gd32/f1x0/flash.h>
#else
# error "gd32 family not defined."
#endif

View File

@ -0,0 +1,28 @@
/* This provides unification of code over GD32 subfamilies */
/*
* This file is part of the libopencm3 project.
*
* This library is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this library. If not, see <http://www.gnu.org/licenses/>.
*/
#include <libopencm3/cm3/common.h>
#include <libopencm3/gd32/memorymap.h>
#if defined(GD32F1X0)
# include <libopencm3/gd32/f1x0/gpio.h>
#else
# error "gd32 family not defined."
#endif

View File

@ -0,0 +1,29 @@
/*
* This file is part of the libopencm3 project.
*
* Copyright (C) 2019 Icenowy Zheng <icenowy@aosc.io>
*
* This library is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this library. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef LIBOPENCM3_MEMORYMAP_COMMON_H
#define LIBOPENCM3_MEMORYMAP_COMMON_H
#if defined(GD32F1X0)
# include <libopencm3/gd32/f1x0/memorymap.h>
#else
# error "gd32 family not defined."
#endif
#endif /* LIBOPENCM3_MEMORYMAP_COMMON_H */

View File

@ -0,0 +1,28 @@
/* This provides unification of code over GD32 subfamilies */
/*
* This file is part of the libopencm3 project.
*
* This library is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this library. If not, see <http://www.gnu.org/licenses/>.
*/
#include <libopencm3/cm3/common.h>
#include <libopencm3/gd32/memorymap.h>
#if defined(GD32F1X0)
# include <libopencm3/gd32/f1x0/rcc.h>
#else
# error "gd32 family not defined."
#endif

View File

@ -38,6 +38,8 @@
# include <libopencm3/stm32/l1/flash.h>
#elif defined(STM32L4)
# include <libopencm3/stm32/l4/flash.h>
#elif defined(GD32F1X0)
# include <libopencm3/gd32/f1x0/flash.h>
#else
# error "stm32 family not defined."
#endif

View File

@ -38,6 +38,8 @@
# include <libopencm3/stm32/l1/gpio.h>
#elif defined(STM32L4)
# include <libopencm3/stm32/l4/gpio.h>
#elif defined(GD32F1X0)
# include <libopencm3/gd32/f1x0/gpio.h>
#else
# error "stm32 family not defined."
#endif

View File

@ -38,6 +38,8 @@
# include <libopencm3/stm32/l1/memorymap.h>
#elif defined(STM32L4)
# include <libopencm3/stm32/l4/memorymap.h>
#elif defined(GD32F1X0)
# include <libopencm3/gd32/f1x0/memorymap.h>
#else
# error "stm32 family not defined."
#endif

View File

@ -38,6 +38,8 @@
# include <libopencm3/stm32/l1/rcc.h>
#elif defined(STM32L4)
# include <libopencm3/stm32/l4/rcc.h>
#elif defined(GD32F1X0)
# include <libopencm3/gd32/f1x0/rcc.h>
#else
# error "stm32 family not defined."
#endif

View File

@ -17,6 +17,9 @@
#elif defined(STM32L4)
# include <libopencmsis/stm32/l4/irqhandlers.h>
#elif defined(GD32F1X0)
# include <libopencmsis/gd32/f1x0/irqhandlers.h>
#elif defined(EFM32TG)
# include <libopencmsis/efm32/efm32tg/irqhandlers.h>
#elif defined(EFM32G)

View File

@ -0,0 +1,60 @@
/* This file is part of the libopencm3 project.
*
* It was generated by the irq2nvic_h script.
*
* These definitions bend every interrupt handler that is defined CMSIS style
* to the weak symbol exported by libopencm3.
*/
#define WWDG_IRQHandler wwdg_isr
#define PVD_IRQHandler pvd_isr
#define RTC_IRQHandler rtc_isr
#define FLASH_IRQHandler flash_isr
#define RCC_IRQHandler rcc_isr
#define EXTI0_1_IRQHandler exti0_1_isr
#define EXTI2_3_IRQHandler exti2_3_isr
#define EXTI4_15_IRQHandler exti4_15_isr
#define TSC_IRQHandler tsc_isr
#define DMA_CHANNEL1_IRQHandler dma_channel1_isr
#define DMA_CHANNEL2_3_IRQHandler dma_channel2_3_isr
#define DMA_CHANNEL4_5_IRQHandler dma_channel4_5_isr
#define ADC_COMP_IRQHandler adc_comp_isr
#define TIM1_BRK_UP_TRG_COM_IRQHandler tim1_brk_up_trg_com_isr
#define TIM1_CC_IRQHandler tim1_cc_isr
#define TIM2_IRQHandler tim2_isr
#define TIM3_IRQHandler tim3_isr
#define TIM6_DAC_IRQHandler tim6_dac_isr
#define RESERVED0_IRQHandler reserved0_isr
#define TIM14_IRQHandler tim14_isr
#define TIM15_IRQHandler tim15_isr
#define TIM16_IRQHandler tim16_isr
#define TIM17_IRQHandler tim17_isr
#define I2C1_EV_IRQHandler i2c1_ev_isr
#define I2C2_EV_IRQHandler i2c2_ev_isr
#define SPI1_IRQHandler spi1_isr
#define SPI2_IRQHandler spi2_isr
#define USART1_IRQHandler usart1_isr
#define USART2_IRQHandler usart2_isr
#define RESERVED1_IRQHandler reserved1_isr
#define CEC_CAN_IRQHandler cec_can_isr
#define RESERVED2_IRQHandler reserved2_isr
#define I2C1_ER_IRQHandler i2c1_er_isr
#define RESERVED3_IRQHandler reserved3_isr
#define I2C2_ER_IRQHandler i2c2_er_isr
#define I2C3_EV_IRQHandler i2c3_ev_isr
#define I2C3_ER_IRQHandler i2c3_er_isr
#define USB_LP_IRQHandler usb_lp_isr
#define USB_HP_IRQHandler usb_hp_isr
#define RESERVED4_IRQHandler reserved4_isr
#define RESERVED5_IRQHandler reserved5_isr
#define RESERVED6_IRQHandler reserved6_isr
#define USB_WAKEUP_IRQHandler usb_wakeup_isr
#define RESERVED7_IRQHandler reserved7_isr
#define RESERVED8_IRQHandler reserved8_isr
#define RESERVED9_IRQHandler reserved9_isr
#define RESERVED10_IRQHandler reserved10_isr
#define RESERVED11_IRQHandler reserved11_isr
#define DMA_CHANNEL6_7_IRQHandler dma_channel6_7_isr
#define RESERVED12_IRQHandler reserved12_isr
#define RESERVED13_IRQHandler reserved13_isr
#define SPI3_IRQHandler spi3_isr

View File

@ -17,6 +17,9 @@
#elif defined(STM32L4)
# include "../stm32/l4/vector_nvic.c"
#elif defined(GD32F1X0)
# include "../gd32/f1x0/vector_nvic.c"
#elif defined(EFM32TG)
# include "../efm32/tg/vector_nvic.c"
#elif defined(EFM32G)

47
lib/gd32/f1x0/Makefile Executable file
View File

@ -0,0 +1,47 @@
##
## This file is part of the libopencm3 project.
##
## Copyright (C) 2019 Icenowy Zheng <icenowy@aosc.io>
##
## This library is free software: you can redistribute it and/or modify
## it under the terms of the GNU Lesser General Public License as published by
## the Free Software Foundation, either version 3 of the License, or
## (at your option) any later version.
##
## This library is distributed in the hope that it will be useful,
## but WITHOUT ANY WARRANTY; without even the implied warranty of
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
## GNU Lesser General Public License for more details.
##
## You should have received a copy of the GNU Lesser General Public License
## along with this library. If not, see <http://www.gnu.org/licenses/>.
##
LIBNAME = libopencm3_gd32f1x0
SRCLIBDIR ?= ../..
PREFIX ?= arm-none-eabi
CC = $(PREFIX)-gcc
AR = $(PREFIX)-ar
TGT_CFLAGS = -Os \
-Wall -Wextra -Wimplicit-function-declaration \
-Wredundant-decls -Wmissing-prototypes -Wstrict-prototypes \
-Wundef -Wshadow \
-I../../../include -fno-common \
-mcpu=cortex-m3 $(FP_FLAGS) -mthumb -Wstrict-prototypes \
-ffunction-sections -fdata-sections -MD -DGD32F1X0
TGT_CFLAGS += $(DEBUG_FLAGS)
# ARFLAGS = rcsv
ARFLAGS = rcs
OBJS = rcc.o flash.o
OBJS += \
gpio_common_all.o gpio_common_f0234.o \
rcc_common_all.o \
flash_common_all.o flash_common_f.o flash_common_f01.o
VPATH += ../:../../cm3:../common:../../stm32/common
include ../../Makefile.include

153
lib/gd32/f1x0/flash.c Normal file
View File

@ -0,0 +1,153 @@
/** @defgroup flash_file FLASH
*
* @ingroup GD32F1x0
*
* @brief <b>libopencm3 GD32F1x0 FLASH</b>
*
* @version 1.0.0
*
* @author @htmlonly &copy; @endhtmlonly 2013
* Frantisek Burian <BuFran@seznam.cz>
*
* @date 14 January 2014
*
* FLASH memory may be used for data storage as well as code, and may be
* programmatically modified. Note that for firmware upload the GD32F1x0
* provides a built-in bootloader in system memory that can be entered from a
* running program.
*
* FLASH must first be unlocked before programming. In this module a write to
* FLASH is a blocking operation until the end-of-operation flag is asserted.
*
* @note: don't forget to lock it again when all operations are complete.
*
* LGPL License Terms @ref lgpl_license
*/
/*
* This file is part of the libopencm3 project.
*
* Copyright (C) 2013 Frantisek Burian <BuFran@seznam.cz>
*
* This library is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this library. If not, see <http://www.gnu.org/licenses/>.
*/
/**@{*/
#include <libopencm3/gd32/flash.h>
/*---------------------------------------------------------------------------*/
/** @brief Clear All Status Flags
Program error, end of operation, write protect error, busy.
*/
void flash_clear_status_flags(void)
{
flash_clear_pgerr_flag();
flash_clear_eop_flag();
flash_clear_wrprterr_flag();
}
/*---------------------------------------------------------------------------*/
/** @brief Read All Status Flags
The programming error, end of operation, write protect error and busy flags
are returned in the order of appearance in the status register.
@returns uint32_t. bit 0: busy, bit 2: programming error, bit 4: write protect
error, bit 5: end of operation.
*/
uint32_t flash_get_status_flags(void)
{
return FLASH_SR & (FLASH_SR_PGERR |
FLASH_SR_EOP |
FLASH_SR_WRPRTERR |
FLASH_SR_BSY);
}
/*---------------------------------------------------------------------------*/
/** @brief Program a Half Word to FLASH
This performs all operations necessary to program a 16 bit word to FLASH memory.
The program error flag should be checked separately for the event that memory
was not properly erased.
Status bit polling is used to detect end of operation.
@param[in] address Full address of flash half word to be programmed.
@param[in] data half word to write
*/
void flash_program_half_word(uint32_t address, uint16_t data)
{
flash_wait_for_last_operation();
FLASH_CR |= FLASH_CR_PG;
MMIO16(address) = data;
flash_wait_for_last_operation();
FLASH_CR &= ~FLASH_CR_PG;
}
/*---------------------------------------------------------------------------*/
/** @brief Erase a Page of FLASH
This performs all operations necessary to erase a page in FLASH memory.
The page should be checked to ensure that it was properly erased. A page must
first be fully erased before attempting to program it.
Note that the page sizes differ between devices. See the reference manual or
the FLASH programming manual for details.
@param[in] page_address Full address of flash page to be erased.
*/
void flash_erase_page(uint32_t page_address)
{
flash_wait_for_last_operation();
FLASH_CR |= FLASH_CR_PER;
FLASH_AR = page_address;
FLASH_CR |= FLASH_CR_STRT;
flash_wait_for_last_operation();
FLASH_CR &= ~FLASH_CR_PER;
}
/*---------------------------------------------------------------------------*/
/** @brief Erase All FLASH
This performs all operations necessary to erase all user pages in the FLASH
memory. The information block is unaffected.
*/
void flash_erase_all_pages(void)
{
flash_wait_for_last_operation();
FLASH_CR |= FLASH_CR_MER; /* Enable mass erase. */
FLASH_CR |= FLASH_CR_STRT; /* Trigger the erase. */
flash_wait_for_last_operation();
FLASH_CR &= ~FLASH_CR_MER; /* Disable mass erase. */
}
/**@}*/

654
lib/gd32/f1x0/rcc.c Normal file
View File

@ -0,0 +1,654 @@
/** @defgroup GD32F1x0-rcc-file RCC
@ingroup GD32F1x0
@brief <b>libopencm3 GD32F1x0 Reset and Clock Control</b>
@version 1.0.0
@author @htmlonly &copy; @endhtmlonly 2009
Federico Ruiz-Ugalde \<memeruiz at gmail dot com\>
@author @htmlonly &copy; @endhtmlonly 2009 Uwe Hermann <uwe@hermann-uwe.de>
@author @htmlonly &copy; @endhtmlonly 2010 Thomas Otto <tommi@viadmin.org>
@date 18 August 2012
This library supports the Reset and Clock Control System in the GD32F1x0
series of ARM Cortex Microcontrollers by GigaDevice.
@note Full support for F170 and F190 devices is not yet provided.
Clock settings and resets for many peripherals are given here rather than in
the corresponding peripheral library.
The library also provides a number of common configurations for the processor
system clock. Not all possible configurations are included.
LGPL License Terms @ref lgpl_license
*/
/*
* This file is part of the libopencm3 project.
*
* Copyright (C) 2019 Icenowy Zheng <icenowy@aosc.io>
* Copyright (C) 2009 Federico Ruiz-Ugalde <memeruiz at gmail dot com>
* Copyright (C) 2009 Uwe Hermann <uwe@hermann-uwe.de>
* Copyright (C) 2010 Thomas Otto <tommi@viadmin.org>
*
* This library is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this library. If not, see <http://www.gnu.org/licenses/>.
*/
/**@{*/
#include <libopencm3/cm3/assert.h>
#include <libopencm3/gd32/rcc.h>
#include <libopencm3/gd32/flash.h>
/** Set the default clock frequencies */
uint32_t rcc_apb1_frequency = 8000000;
uint32_t rcc_apb2_frequency = 8000000;
uint32_t rcc_ahb_frequency = 8000000;
const struct rcc_clock_scale rcc_hsi_configs[] = {
{ /* 48MHz */
.pllmul = RCC_CFGR_PLLMUL_PLL_CLK_MUL12,
.hpre = RCC_CFGR_HPRE_SYSCLK_NODIV,
.ppre1 = RCC_CFGR_PPRE1_HCLK_DIV2,
.ppre2 = RCC_CFGR_PPRE2_HCLK_NODIV,
.adcpre = RCC_CFGR_ADCPRE_PCLK2_DIV8,
.use_hse = false,
.ahb_frequency = 48000000,
.apb1_frequency = 24000000,
.apb2_frequency = 48000000,
},
{ /* 64MHz */
.pllmul = RCC_CFGR_PLLMUL_PLL_CLK_MUL16,
.hpre = RCC_CFGR_HPRE_SYSCLK_NODIV,
.ppre1 = RCC_CFGR_PPRE1_HCLK_DIV2,
.ppre2 = RCC_CFGR_PPRE2_HCLK_NODIV,
.adcpre = RCC_CFGR_ADCPRE_PCLK2_DIV8,
.use_hse = false,
.ahb_frequency = 64000000,
.apb1_frequency = 32000000,
.apb2_frequency = 64000000,
}
};
const struct rcc_clock_scale rcc_hse8_configs[] = {
{ /* 72MHz */
.pllmul = RCC_CFGR_PLLMUL_PLL_CLK_MUL9,
.hpre = RCC_CFGR_HPRE_SYSCLK_NODIV,
.ppre1 = RCC_CFGR_PPRE1_HCLK_DIV2,
.ppre2 = RCC_CFGR_PPRE2_HCLK_NODIV,
.adcpre = RCC_CFGR_ADCPRE_PCLK2_DIV8,
.usbpre = RCC_CFGR_USBPRE_PLL_CLK_DIV1_5,
.use_hse = true,
.pll_hse_prediv = RCC_CFGR2_PREDIV_NODIV,
.ahb_frequency = 72000000,
.apb1_frequency = 36000000,
.apb2_frequency = 72000000,
},
};
/*---------------------------------------------------------------------------*/
/** @brief RCC Clear the Oscillator Ready Interrupt Flag
Clear the interrupt flag that was set when a clock oscillator became ready to
use.
@param[in] osc enum ::osc_t. Oscillator ID
*/
void rcc_osc_ready_int_clear(enum rcc_osc osc)
{
switch (osc) {
case RCC_PLL:
RCC_CIR |= RCC_CIR_PLLRDYC;
break;
case RCC_HSE:
RCC_CIR |= RCC_CIR_HSERDYC;
break;
case RCC_HSI:
RCC_CIR |= RCC_CIR_HSIRDYC;
break;
case RCC_LSE:
RCC_CIR |= RCC_CIR_LSERDYC;
break;
case RCC_LSI:
RCC_CIR |= RCC_CIR_LSIRDYC;
break;
}
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Enable the Oscillator Ready Interrupt
@param[in] osc enum ::osc_t. Oscillator ID
*/
void rcc_osc_ready_int_enable(enum rcc_osc osc)
{
switch (osc) {
case RCC_PLL:
RCC_CIR |= RCC_CIR_PLLRDYIE;
break;
case RCC_HSE:
RCC_CIR |= RCC_CIR_HSERDYIE;
break;
case RCC_HSI:
RCC_CIR |= RCC_CIR_HSIRDYIE;
break;
case RCC_LSE:
RCC_CIR |= RCC_CIR_LSERDYIE;
break;
case RCC_LSI:
RCC_CIR |= RCC_CIR_LSIRDYIE;
break;
}
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Disable the Oscillator Ready Interrupt
@param[in] osc enum ::osc_t. Oscillator ID
*/
void rcc_osc_ready_int_disable(enum rcc_osc osc)
{
switch (osc) {
case RCC_PLL:
RCC_CIR &= ~RCC_CIR_PLLRDYIE;
break;
case RCC_HSE:
RCC_CIR &= ~RCC_CIR_HSERDYIE;
break;
case RCC_HSI:
RCC_CIR &= ~RCC_CIR_HSIRDYIE;
break;
case RCC_LSE:
RCC_CIR &= ~RCC_CIR_LSERDYIE;
break;
case RCC_LSI:
RCC_CIR &= ~RCC_CIR_LSIRDYIE;
break;
}
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Read the Oscillator Ready Interrupt Flag
@param[in] osc enum ::osc_t. Oscillator ID
@returns int. Boolean value for flag set.
*/
int rcc_osc_ready_int_flag(enum rcc_osc osc)
{
switch (osc) {
case RCC_PLL:
return ((RCC_CIR & RCC_CIR_PLLRDYF) != 0);
break;
case RCC_HSE:
return ((RCC_CIR & RCC_CIR_HSERDYF) != 0);
break;
case RCC_HSI:
return ((RCC_CIR & RCC_CIR_HSIRDYF) != 0);
break;
case RCC_LSE:
return ((RCC_CIR & RCC_CIR_LSERDYF) != 0);
break;
case RCC_LSI:
return ((RCC_CIR & RCC_CIR_LSIRDYF) != 0);
break;
}
cm3_assert_not_reached();
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Clear the Clock Security System Interrupt Flag
*/
void rcc_css_int_clear(void)
{
RCC_CIR |= RCC_CIR_CSSC;
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Read the Clock Security System Interrupt Flag
@returns int. Boolean value for flag set.
*/
int rcc_css_int_flag(void)
{
return ((RCC_CIR & RCC_CIR_CSSF) != 0);
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Wait for Oscillator Ready.
@param[in] osc enum ::osc_t. Oscillator ID
*/
void rcc_wait_for_osc_ready(enum rcc_osc osc)
{
switch (osc) {
case RCC_PLL:
while ((RCC_CR & RCC_CR_PLLRDY) == 0);
break;
case RCC_HSE:
while ((RCC_CR & RCC_CR_HSERDY) == 0);
break;
case RCC_HSI:
while ((RCC_CR & RCC_CR_HSIRDY) == 0);
break;
case RCC_LSE:
while ((RCC_BDCR & RCC_BDCR_LSERDY) == 0);
break;
case RCC_LSI:
while ((RCC_CSR & RCC_CSR_LSIRDY) == 0);
break;
}
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Turn on an Oscillator.
Enable an oscillator and power on. Each oscillator requires an amount of time
to settle to a usable state. Refer to datasheets for time delay information. A
status flag is available to indicate when the oscillator becomes ready (see
@ref rcc_osc_ready_int_flag and @ref rcc_wait_for_osc_ready).
@note The LSE clock is in the backup domain and cannot be enabled until the
backup domain write protection has been removed (see @ref
pwr_disable_backup_domain_write_protect).
@param[in] osc enum ::osc_t. Oscillator ID
*/
void rcc_osc_on(enum rcc_osc osc)
{
switch (osc) {
case RCC_PLL:
RCC_CR |= RCC_CR_PLLON;
break;
case RCC_HSE:
RCC_CR |= RCC_CR_HSEON;
break;
case RCC_HSI:
RCC_CR |= RCC_CR_HSION;
break;
case RCC_LSE:
RCC_BDCR |= RCC_BDCR_LSEON;
break;
case RCC_LSI:
RCC_CSR |= RCC_CSR_LSION;
break;
}
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Turn off an Oscillator.
Disable an oscillator and power off.
@note An oscillator cannot be turned off if it is selected as the system clock.
@note The LSE clock is in the backup domain and cannot be disabled until the
backup domain write protection has been removed (see
@ref pwr_disable_backup_domain_write_protect) or the backup domain has been
(see reset @ref rcc_backupdomain_reset).
@param[in] osc enum ::osc_t. Oscillator ID
*/
void rcc_osc_off(enum rcc_osc osc)
{
switch (osc) {
case RCC_PLL:
RCC_CR &= ~RCC_CR_PLLON;
break;
case RCC_HSE:
RCC_CR &= ~RCC_CR_HSEON;
break;
case RCC_HSI:
RCC_CR &= ~RCC_CR_HSION;
break;
case RCC_LSE:
RCC_BDCR &= ~RCC_BDCR_LSEON;
break;
case RCC_LSI:
RCC_CSR &= ~RCC_CSR_LSION;
break;
}
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Enable the Clock Security System.
*/
void rcc_css_enable(void)
{
RCC_CR |= RCC_CR_CSSON;
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Disable the Clock Security System.
*/
void rcc_css_disable(void)
{
RCC_CR &= ~RCC_CR_CSSON;
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Set the Source for the System Clock.
@param[in] clk Unsigned int32. System Clock Selection @ref rcc_cfgr_scs
*/
void rcc_set_sysclk_source(uint32_t clk)
{
RCC_CFGR = (RCC_CFGR & ~RCC_CFGR_SW) |
(clk << RCC_CFGR_SW_SHIFT);
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Set the PLL Multiplication Factor.
@note This only has effect when the PLL is disabled.
@param[in] mul Unsigned int32. PLL multiplication factor @ref rcc_cfgr_pmf
*/
void rcc_set_pll_multiplication_factor(uint32_t mul)
{
RCC_CFGR = (RCC_CFGR & ~RCC_CFGR_PLLMUL_0_3 & ~RCC_CFGR_PLLMUL_4) |
((mul & 0xf) << RCC_CFGR_PLLMUL_0_3_SHIFT) |
((!!(mul & 0x10)) << RCC_CFGR_PLLMUL_4_SHIFT);
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Set the PLL Clock Source.
@note This only has effect when the PLL is disabled.
@param[in] pllsrc Unsigned int32. PLL clock source @ref rcc_cfgr_pcs
*/
void rcc_set_pll_source(uint32_t pllsrc)
{
RCC_CFGR = (RCC_CFGR & ~RCC_CFGR_PLLSRC) |
(pllsrc << 16);
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Set the HSE Frequency Divider used as PLL Clock Source.
@note This only has effect when the PLL is disabled.
@param[in] pllxtpre Unsigned int32. HSE division factor @ref rcc_cfgr_hsepre
*/
void rcc_set_pllxtpre(uint32_t pllxtpre)
{
RCC_CFGR = (RCC_CFGR & ~RCC_CFGR_PLLXTPRE) |
(pllxtpre << 17);
}
/*---------------------------------------------------------------------------*/
/** @brief RCC RTC Clock Enabled Flag
@returns uint32_t. Nonzero if the RTC Clock is enabled.
*/
uint32_t rcc_rtc_clock_enabled_flag(void)
{
return RCC_BDCR & RCC_BDCR_RTCEN;
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Enable the RTC clock
*/
void rcc_enable_rtc_clock(void)
{
RCC_BDCR |= RCC_BDCR_RTCEN;
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Set the Source for the RTC clock
@param[in] clock_source ::rcc_osc. RTC clock source. Only HSE/128, LSE and LSI.
*/
void rcc_set_rtc_clock_source(enum rcc_osc clock_source)
{
uint32_t reg32;
switch (clock_source) {
case RCC_LSE:
/* Turn the LSE on and wait while it stabilises. */
RCC_BDCR |= RCC_BDCR_LSEON;
while ((reg32 = (RCC_BDCR & RCC_BDCR_LSERDY)) == 0);
/* Choose LSE as the RTC clock source. */
RCC_BDCR &= ~((1 << 8) | (1 << 9));
RCC_BDCR |= (1 << 8);
break;
case RCC_LSI:
/* Turn the LSI on and wait while it stabilises. */
RCC_CSR |= RCC_CSR_LSION;
while ((reg32 = (RCC_CSR & RCC_CSR_LSIRDY)) == 0);
/* Choose LSI as the RTC clock source. */
RCC_BDCR &= ~((1 << 8) | (1 << 9));
RCC_BDCR |= (1 << 9);
break;
case RCC_HSE:
/* Turn the HSE on and wait while it stabilises. */
RCC_CR |= RCC_CR_HSEON;
while ((reg32 = (RCC_CR & RCC_CR_HSERDY)) == 0);
/* Choose HSE as the RTC clock source. */
RCC_BDCR &= ~((1 << 8) | (1 << 9));
RCC_BDCR |= (1 << 9) | (1 << 8);
break;
case RCC_PLL:
case RCC_HSI:
/* Unusable clock source, here to prevent warnings. */
/* Turn off clock sources to RTC. */
RCC_BDCR &= ~((1 << 8) | (1 << 9));
break;
}
}
/*---------------------------------------------------------------------------*/
/** @brief ADC Setup the A/D Clock
The ADC's have a common clock prescale setting.
@param[in] adcpre uint32_t. Prescale divider taken from @ref rcc_cfgr_adcpre
*/
void rcc_set_adcpre(uint32_t adcpre)
{
RCC_CFGR = (RCC_CFGR & ~RCC_CFGR_ADCPRE) |
(adcpre << RCC_CFGR_ADCPRE_SHIFT);
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Set the APB2 Prescale Factor.
@param[in] ppre2 Unsigned int32. APB2 prescale factor @ref rcc_cfgr_apb2pre
*/
void rcc_set_ppre2(uint32_t ppre2)
{
RCC_CFGR = (RCC_CFGR & ~RCC_CFGR_PPRE2) |
(ppre2 << RCC_CFGR_PPRE2_SHIFT);
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Set the APB1 Prescale Factor.
@note The APB1 clock frequency must not exceed 36MHz.
@param[in] ppre1 Unsigned int32. APB1 prescale factor @ref rcc_cfgr_apb1pre
*/
void rcc_set_ppre1(uint32_t ppre1)
{
RCC_CFGR = (RCC_CFGR & ~RCC_CFGR_PPRE1) |
(ppre1 << RCC_CFGR_PPRE1_SHIFT);
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Set the AHB Prescale Factor.
@param[in] hpre Unsigned int32. AHB prescale factor @ref rcc_cfgr_ahbpre
*/
void rcc_set_hpre(uint32_t hpre)
{
RCC_CFGR = (RCC_CFGR & ~RCC_CFGR_HPRE) |
(hpre << RCC_CFGR_HPRE_SHIFT);
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Set the USB Prescale Factor.
The prescale factor can be set to 1 (no prescale) for use when the PLL clock is
48MHz, or 1.5 to generate the 48MHz USB clock from a 64MHz PLL clock.
@note This bit cannot be reset while the USB clock is enabled.
@param[in] usbpre Unsigned int32. USB prescale factor @ref rcc_cfgr_usbpre
*/
void rcc_set_usbpre(uint32_t usbpre)
{
RCC_CFGR = (RCC_CFGR & ~RCC_CFGR_USBPRE) | usbpre;
}
void rcc_set_prediv(uint32_t prediv)
{
RCC_CFGR2 = (RCC_CFGR2 & ~RCC_CFGR2_PREDIV) | prediv;
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Get the System Clock Source.
@returns Unsigned int32. System clock source:
@li 00 indicates HSE
@li 01 indicates LSE
@li 02 indicates PLL
*/
uint32_t rcc_system_clock_source(void)
{
/* Return the clock source which is used as system clock. */
return (RCC_CFGR & RCC_CFGR_SWS) >> RCC_CFGR_SWS_SHIFT;
}
/*---------------------------------------------------------------------------*/
/*
* These functions are setting up the whole clock system for the most common
* input clock and output clock configurations.
*/
/*---------------------------------------------------------------------------*/
/**
* Setup clocks to run from PLL.
* The arguments provide the pll source, multipliers, dividers, all that's
* needed to establish a system clock.
* @param clock clock information structure
*/
void rcc_clock_setup_pll(const struct rcc_clock_scale *clock)
{
if (clock->use_hse) {
/* Enable external high-speed oscillator. */
rcc_osc_on(RCC_HSE);
rcc_wait_for_osc_ready(RCC_HSE);
rcc_set_sysclk_source(RCC_CFGR_SW_SYSCLKSEL_HSECLK);
} else {
/* Enable internal high-speed oscillator. */
rcc_osc_on(RCC_HSI);
rcc_wait_for_osc_ready(RCC_HSI);
rcc_set_sysclk_source(RCC_CFGR_SW_SYSCLKSEL_HSICLK);
}
/*
* Set prescalers for AHB, ADC, APB1, APB2 and USB.
* Do this before touching the PLL (TODO: why?).
*/
rcc_set_hpre(clock->hpre);
rcc_set_ppre1(clock->ppre1);
rcc_set_ppre2(clock->ppre2);
rcc_set_adcpre(clock->adcpre);
if (clock->use_hse)
rcc_set_usbpre(clock->usbpre);
/* Set the PLL multiplication factor. */
rcc_set_pll_multiplication_factor(clock->pllmul);
if (clock->use_hse) {
/* Select HSE as PLL source. */
rcc_set_pll_source(RCC_CFGR_PLLSRC_HSE_CLK);
/*
* External frequency undivided before entering PLL
* (only valid/needed for HSE).
*/
rcc_set_prediv(clock->pll_hse_prediv);
} else {
/* Select HSI/2 as PLL source. */
rcc_set_pll_source(RCC_CFGR_PLLSRC_HSI_CLK_DIV2);
}
/* Enable PLL oscillator and wait for it to stabilize. */
rcc_osc_on(RCC_PLL);
rcc_wait_for_osc_ready(RCC_PLL);
/* Select PLL as SYSCLK source. */
rcc_set_sysclk_source(RCC_CFGR_SW_SYSCLKSEL_PLLCLK);
/* Set the peripheral clock frequencies used */
rcc_ahb_frequency = clock->ahb_frequency;
rcc_apb1_frequency = clock->apb1_frequency;
rcc_apb2_frequency = clock->apb2_frequency;
}
/*---------------------------------------------------------------------------*/
/** @brief RCC Reset the Backup Domain
The backup domain registers are reset to disable RTC controls and clear user
data.
*/
void rcc_backupdomain_reset(void)
{
/* Set the backup domain software reset. */
RCC_BDCR |= RCC_BDCR_BDRST;
/* Clear the backup domain software reset. */
RCC_BDCR &= ~RCC_BDCR_BDRST;
}
/**@}*/