Update for STM32F103
This commit is contained in:
@@ -1,5 +1,8 @@
|
||||
2016-05-30 NIIBE Yutaka <gniibe@fsij.org>
|
||||
|
||||
* mcu/adc-stm32f103.c: New from NeuG.
|
||||
* mcu/stm32f103.h: New from NeuG.
|
||||
|
||||
* example-cdc: Update.
|
||||
|
||||
2016-05-30 NIIBE Yutaka <gniibe@fsij.org>
|
||||
|
||||
329
mcu/adc-stm32f103.c
Normal file
329
mcu/adc-stm32f103.c
Normal file
@@ -0,0 +1,329 @@
|
||||
/*
|
||||
* adc_stm32f103.c - ADC driver for STM32F103
|
||||
* In this ADC driver, there are NeuG specific parts.
|
||||
* You need to modify to use this as generic ADC driver.
|
||||
*
|
||||
* Copyright (C) 2011, 2012, 2013, 2015, 2016
|
||||
* Free Software Initiative of Japan
|
||||
* Author: NIIBE Yutaka <gniibe@fsij.org>
|
||||
*
|
||||
* This file is a part of NeuG, a True Random Number Generator
|
||||
* implementation based on quantization error of ADC (for STM32F103).
|
||||
*
|
||||
* NeuG is free software: you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* NeuG 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 General Public
|
||||
* License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stdlib.h>
|
||||
#include <chopstx.h>
|
||||
#include <mcu/stm32f103.h>
|
||||
#include "adc.h"
|
||||
|
||||
#define STM32_ADC_ADC1_DMA_PRIORITY 2
|
||||
|
||||
#define ADC_SMPR1_SMP_VREF(n) ((n) << 21)
|
||||
#define ADC_SMPR1_SMP_SENSOR(n) ((n) << 18)
|
||||
|
||||
#define ADC_SMPR1_SMP_AN10(n) ((n) << 0)
|
||||
#define ADC_SMPR1_SMP_AN11(n) ((n) << 3)
|
||||
|
||||
#define ADC_SMPR2_SMP_AN0(n) ((n) << 0)
|
||||
#define ADC_SMPR2_SMP_AN1(n) ((n) << 3)
|
||||
#define ADC_SMPR2_SMP_AN2(n) ((n) << 6)
|
||||
#define ADC_SMPR2_SMP_AN9(n) ((n) << 27)
|
||||
|
||||
#define ADC_SQR1_NUM_CH(n) (((n) - 1) << 20)
|
||||
|
||||
#define ADC_SQR3_SQ1_N(n) ((n) << 0)
|
||||
#define ADC_SQR3_SQ2_N(n) ((n) << 5)
|
||||
#define ADC_SQR3_SQ3_N(n) ((n) << 10)
|
||||
#define ADC_SQR3_SQ4_N(n) ((n) << 15)
|
||||
|
||||
#define ADC_SAMPLE_1P5 0
|
||||
|
||||
#define ADC_CHANNEL_IN0 0
|
||||
#define ADC_CHANNEL_IN1 1
|
||||
#define ADC_CHANNEL_IN2 2
|
||||
#define ADC_CHANNEL_IN9 9
|
||||
#define ADC_CHANNEL_IN10 10
|
||||
#define ADC_CHANNEL_IN11 11
|
||||
#define ADC_CHANNEL_SENSOR 16
|
||||
#define ADC_CHANNEL_VREFINT 17
|
||||
|
||||
#define DELIBARATELY_DO_IT_WRONG_VREF_SAMPLE_TIME
|
||||
#define DELIBARATELY_DO_IT_WRONG_START_STOP
|
||||
|
||||
#ifdef DELIBARATELY_DO_IT_WRONG_VREF_SAMPLE_TIME
|
||||
#define ADC_SAMPLE_VREF ADC_SAMPLE_1P5
|
||||
#define ADC_SAMPLE_SENSOR ADC_SAMPLE_1P5
|
||||
#else
|
||||
#define ADC_SAMPLE_VREF ADC_SAMPLE_239P5
|
||||
#define ADC_SAMPLE_SENSOR ADC_SAMPLE_239P5
|
||||
#endif
|
||||
|
||||
#define NEUG_DMA_CHANNEL STM32_DMA1_STREAM1
|
||||
#define NEUG_DMA_MODE \
|
||||
( STM32_DMA_CR_PL (STM32_ADC_ADC1_DMA_PRIORITY) \
|
||||
| STM32_DMA_CR_MSIZE_WORD | STM32_DMA_CR_PSIZE_WORD \
|
||||
| STM32_DMA_CR_MINC | STM32_DMA_CR_TCIE \
|
||||
| STM32_DMA_CR_TEIE )
|
||||
|
||||
#define NEUG_ADC_SETTING1_SMPR1 ADC_SMPR1_SMP_VREF(ADC_SAMPLE_VREF) \
|
||||
| ADC_SMPR1_SMP_SENSOR(ADC_SAMPLE_SENSOR)
|
||||
#define NEUG_ADC_SETTING1_SMPR2 0
|
||||
#define NEUG_ADC_SETTING1_SQR3 ADC_SQR3_SQ1_N(ADC_CHANNEL_VREFINT) \
|
||||
| ADC_SQR3_SQ2_N(ADC_CHANNEL_SENSOR) \
|
||||
| ADC_SQR3_SQ3_N(ADC_CHANNEL_SENSOR) \
|
||||
| ADC_SQR3_SQ4_N(ADC_CHANNEL_VREFINT)
|
||||
#define NEUG_ADC_SETTING1_NUM_CHANNELS 4
|
||||
|
||||
/*
|
||||
* ADC finish interrupt
|
||||
*/
|
||||
#define INTR_REQ_DMA1_Channel1 11
|
||||
|
||||
static chopstx_intr_t adc_intr;
|
||||
|
||||
/*
|
||||
* Do calibration for both of ADCs.
|
||||
*/
|
||||
int
|
||||
adc_init (void)
|
||||
{
|
||||
RCC->APB2ENR |= (RCC_APB2ENR_ADC1EN | RCC_APB2ENR_ADC2EN);
|
||||
RCC->APB2RSTR = (RCC_APB2RSTR_ADC1RST | RCC_APB2RSTR_ADC2RST);
|
||||
RCC->APB2RSTR = 0;
|
||||
|
||||
ADC1->CR1 = 0;
|
||||
ADC1->CR2 = ADC_CR2_ADON;
|
||||
ADC1->CR2 = ADC_CR2_ADON | ADC_CR2_RSTCAL;
|
||||
while ((ADC1->CR2 & ADC_CR2_RSTCAL) != 0)
|
||||
;
|
||||
ADC1->CR2 = ADC_CR2_ADON | ADC_CR2_CAL;
|
||||
while ((ADC1->CR2 & ADC_CR2_CAL) != 0)
|
||||
;
|
||||
ADC1->CR2 = 0;
|
||||
|
||||
ADC2->CR1 = 0;
|
||||
ADC2->CR2 = ADC_CR2_ADON;
|
||||
ADC2->CR2 = ADC_CR2_ADON | ADC_CR2_RSTCAL;
|
||||
while ((ADC2->CR2 & ADC_CR2_RSTCAL) != 0)
|
||||
;
|
||||
ADC2->CR2 = ADC_CR2_ADON | ADC_CR2_CAL;
|
||||
while ((ADC2->CR2 & ADC_CR2_CAL) != 0)
|
||||
;
|
||||
ADC2->CR2 = 0;
|
||||
RCC->APB2ENR &= ~(RCC_APB2ENR_ADC1EN | RCC_APB2ENR_ADC2EN);
|
||||
|
||||
chopstx_claim_irq (&adc_intr, INTR_REQ_DMA1_Channel1);
|
||||
return 0;
|
||||
}
|
||||
|
||||
#include "board.h"
|
||||
#include "mcu/sys-stm32f103.h"
|
||||
#if defined(HAVE_SYS_H)
|
||||
# define SYS_BOARD_ID sys_board_id
|
||||
#else
|
||||
# define SYS_BOARD_ID BOARD_ID
|
||||
#endif
|
||||
|
||||
static void
|
||||
get_adc_config (uint32_t config[4])
|
||||
{
|
||||
config[2] = ADC_SQR1_NUM_CH(2);
|
||||
switch (SYS_BOARD_ID)
|
||||
{
|
||||
case BOARD_ID_FST_01:
|
||||
config[0] = 0;
|
||||
config[1] = ADC_SMPR2_SMP_AN0(ADC_SAMPLE_1P5)
|
||||
| ADC_SMPR2_SMP_AN9(ADC_SAMPLE_1P5);
|
||||
config[3] = ADC_SQR3_SQ1_N(ADC_CHANNEL_IN0)
|
||||
| ADC_SQR3_SQ2_N(ADC_CHANNEL_IN9);
|
||||
break;
|
||||
|
||||
case BOARD_ID_OLIMEX_STM32_H103:
|
||||
case BOARD_ID_STBEE:
|
||||
config[0] = ADC_SMPR1_SMP_AN10(ADC_SAMPLE_1P5)
|
||||
| ADC_SMPR1_SMP_AN11(ADC_SAMPLE_1P5);
|
||||
config[1] = 0;
|
||||
config[3] = ADC_SQR3_SQ1_N(ADC_CHANNEL_IN10)
|
||||
| ADC_SQR3_SQ2_N(ADC_CHANNEL_IN11);
|
||||
break;
|
||||
|
||||
case BOARD_ID_STBEE_MINI:
|
||||
config[0] = 0;
|
||||
config[1] = ADC_SMPR2_SMP_AN1(ADC_SAMPLE_1P5)
|
||||
| ADC_SMPR2_SMP_AN2(ADC_SAMPLE_1P5);
|
||||
config[3] = ADC_SQR3_SQ1_N(ADC_CHANNEL_IN1)
|
||||
| ADC_SQR3_SQ2_N(ADC_CHANNEL_IN2);
|
||||
break;
|
||||
|
||||
case BOARD_ID_CQ_STARM:
|
||||
case BOARD_ID_FST_01_00:
|
||||
case BOARD_ID_MAPLE_MINI:
|
||||
case BOARD_ID_STM32_PRIMER2:
|
||||
case BOARD_ID_STM8S_DISCOVERY:
|
||||
case BOARD_ID_ST_DONGLE:
|
||||
case BOARD_ID_ST_NUCLEO_F103:
|
||||
case BOARD_ID_NITROKEY_START:
|
||||
default:
|
||||
config[0] = 0;
|
||||
config[1] = ADC_SMPR2_SMP_AN0(ADC_SAMPLE_1P5)
|
||||
| ADC_SMPR2_SMP_AN1(ADC_SAMPLE_1P5);
|
||||
config[3] = ADC_SQR3_SQ1_N(ADC_CHANNEL_IN0)
|
||||
| ADC_SQR3_SQ2_N(ADC_CHANNEL_IN1);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
adc_start (void)
|
||||
{
|
||||
uint32_t config[4];
|
||||
|
||||
get_adc_config (config);
|
||||
|
||||
/* Use DMA channel 1. */
|
||||
RCC->AHBENR |= RCC_AHBENR_DMA1EN;
|
||||
DMA1_Channel1->CCR = STM32_DMA_CCR_RESET_VALUE;
|
||||
DMA1->IFCR = 0xffffffff;
|
||||
|
||||
RCC->APB2ENR |= (RCC_APB2ENR_ADC1EN | RCC_APB2ENR_ADC2EN);
|
||||
|
||||
ADC1->CR1 = (ADC_CR1_DUALMOD_2 | ADC_CR1_DUALMOD_1 | ADC_CR1_DUALMOD_0
|
||||
| ADC_CR1_SCAN);
|
||||
ADC1->CR2 = (ADC_CR2_TSVREFE | ADC_CR2_EXTTRIG | ADC_CR2_SWSTART
|
||||
| ADC_CR2_EXTSEL | ADC_CR2_DMA | ADC_CR2_CONT | ADC_CR2_ADON);
|
||||
ADC1->SMPR1 = NEUG_ADC_SETTING1_SMPR1;
|
||||
ADC1->SMPR2 = NEUG_ADC_SETTING1_SMPR2;
|
||||
ADC1->SQR1 = ADC_SQR1_NUM_CH(NEUG_ADC_SETTING1_NUM_CHANNELS);
|
||||
ADC1->SQR2 = 0;
|
||||
ADC1->SQR3 = NEUG_ADC_SETTING1_SQR3;
|
||||
|
||||
ADC2->CR1 = (ADC_CR1_DUALMOD_2 | ADC_CR1_DUALMOD_1 | ADC_CR1_DUALMOD_0
|
||||
| ADC_CR1_SCAN);
|
||||
ADC2->CR2 = ADC_CR2_EXTTRIG | ADC_CR2_CONT | ADC_CR2_ADON;
|
||||
ADC2->SMPR1 = config[0];
|
||||
ADC2->SMPR2 = config[1];
|
||||
ADC2->SQR1 = config[2];
|
||||
ADC2->SQR2 = 0;
|
||||
ADC2->SQR3 = config[3];
|
||||
|
||||
#ifdef DELIBARATELY_DO_IT_WRONG_START_STOP
|
||||
/*
|
||||
* We could just let ADC run continuously always and only enable DMA
|
||||
* to receive stable data from ADC. But our purpose is not to get
|
||||
* correct data but noise. In fact, we can get more noise when we
|
||||
* start/stop ADC each time.
|
||||
*/
|
||||
ADC2->CR2 = 0;
|
||||
ADC1->CR2 = 0;
|
||||
#else
|
||||
/* Start conversion. */
|
||||
ADC2->CR2 = ADC_CR2_EXTTRIG | ADC_CR2_CONT | ADC_CR2_ADON;
|
||||
ADC1->CR2 = (ADC_CR2_TSVREFE | ADC_CR2_EXTTRIG | ADC_CR2_SWSTART
|
||||
| ADC_CR2_EXTSEL | ADC_CR2_DMA | ADC_CR2_CONT | ADC_CR2_ADON);
|
||||
#endif
|
||||
}
|
||||
|
||||
uint32_t adc_buf[64];
|
||||
|
||||
void
|
||||
adc_start_conversion (int offset, int count)
|
||||
{
|
||||
DMA1_Channel1->CPAR = (uint32_t)&ADC1->DR; /* SetPeripheral */
|
||||
DMA1_Channel1->CMAR = (uint32_t)&adc_buf[offset]; /* SetMemory0 */
|
||||
DMA1_Channel1->CNDTR = count; /* Counter */
|
||||
DMA1_Channel1->CCR = NEUG_DMA_MODE | DMA_CCR1_EN; /* Mode */
|
||||
|
||||
#ifdef DELIBARATELY_DO_IT_WRONG_START_STOP
|
||||
/* Power on */
|
||||
ADC2->CR2 = ADC_CR2_EXTTRIG | ADC_CR2_CONT | ADC_CR2_ADON;
|
||||
ADC1->CR2 = (ADC_CR2_TSVREFE | ADC_CR2_EXTTRIG | ADC_CR2_SWSTART
|
||||
| ADC_CR2_EXTSEL | ADC_CR2_DMA | ADC_CR2_CONT | ADC_CR2_ADON);
|
||||
/*
|
||||
* Start conversion. tSTAB is 1uS, but we don't follow the spec, to
|
||||
* get more noise.
|
||||
*/
|
||||
ADC2->CR2 = ADC_CR2_EXTTRIG | ADC_CR2_CONT | ADC_CR2_ADON;
|
||||
ADC1->CR2 = (ADC_CR2_TSVREFE | ADC_CR2_EXTTRIG | ADC_CR2_SWSTART
|
||||
| ADC_CR2_EXTSEL | ADC_CR2_DMA | ADC_CR2_CONT | ADC_CR2_ADON);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
static void adc_stop_conversion (void)
|
||||
{
|
||||
DMA1_Channel1->CCR &= ~DMA_CCR1_EN;
|
||||
|
||||
#ifdef DELIBARATELY_DO_IT_WRONG_START_STOP
|
||||
ADC2->CR2 = 0;
|
||||
ADC1->CR2 = 0;
|
||||
#endif
|
||||
}
|
||||
|
||||
void
|
||||
adc_stop (void)
|
||||
{
|
||||
ADC1->CR1 = 0;
|
||||
ADC1->CR2 = 0;
|
||||
|
||||
ADC2->CR1 = 0;
|
||||
ADC2->CR2 = 0;
|
||||
|
||||
RCC->AHBENR &= ~RCC_AHBENR_DMA1EN;
|
||||
RCC->APB2ENR &= ~(RCC_APB2ENR_ADC1EN | RCC_APB2ENR_ADC2EN);
|
||||
}
|
||||
|
||||
|
||||
static uint32_t adc_err;
|
||||
|
||||
/*
|
||||
* Return 0 on success.
|
||||
* Return 1 on error.
|
||||
*/
|
||||
int
|
||||
adc_wait_completion (void)
|
||||
{
|
||||
uint32_t flags;
|
||||
|
||||
while (1)
|
||||
{
|
||||
chopstx_poll (NULL, 1, &adc_intr);
|
||||
flags = DMA1->ISR & STM32_DMA_ISR_MASK; /* Channel 1 interrupt cause. */
|
||||
/*
|
||||
* Clear interrupt cause of channel 1.
|
||||
*
|
||||
* Note that CGIFx=0, as CGIFx=1 clears all of GIF, HTIF, TCIF
|
||||
* and TEIF.
|
||||
*/
|
||||
DMA1->IFCR = (flags & ~1);
|
||||
|
||||
if ((flags & STM32_DMA_ISR_TEIF) != 0) /* DMA errors */
|
||||
{
|
||||
/* Should never happened. If any, it's coding error. */
|
||||
/* Access an unmapped address space or alignment violation. */
|
||||
adc_err++;
|
||||
adc_stop_conversion ();
|
||||
return 1;
|
||||
}
|
||||
else if ((flags & STM32_DMA_ISR_TCIF) != 0) /* Transfer complete */
|
||||
{
|
||||
adc_stop_conversion ();
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
204
mcu/stm32f103.h
Normal file
204
mcu/stm32f103.h
Normal file
@@ -0,0 +1,204 @@
|
||||
#define PERIPH_BASE 0x40000000
|
||||
#define APB2PERIPH_BASE (PERIPH_BASE + 0x10000)
|
||||
#define AHBPERIPH_BASE (PERIPH_BASE + 0x20000)
|
||||
|
||||
#define RCC_APB2RSTR_ADC1RST 0x00000200
|
||||
#define RCC_APB2RSTR_ADC2RST 0x00000400
|
||||
|
||||
struct RCC {
|
||||
volatile uint32_t CR;
|
||||
volatile uint32_t CFGR;
|
||||
volatile uint32_t CIR;
|
||||
volatile uint32_t APB2RSTR;
|
||||
volatile uint32_t APB1RSTR;
|
||||
volatile uint32_t AHBENR;
|
||||
volatile uint32_t APB2ENR;
|
||||
volatile uint32_t APB1ENR;
|
||||
volatile uint32_t BDCR;
|
||||
volatile uint32_t CSR;
|
||||
};
|
||||
|
||||
#define RCC_BASE (AHBPERIPH_BASE + 0x1000)
|
||||
static struct RCC *const RCC = ((struct RCC *const)RCC_BASE);
|
||||
|
||||
#define RCC_AHBENR_DMA1EN 0x00000001
|
||||
#define RCC_AHBENR_CRCEN 0x00000040
|
||||
|
||||
#define RCC_APB2ENR_ADC1EN 0x00000200
|
||||
#define RCC_APB2ENR_ADC2EN 0x00000400
|
||||
|
||||
#define CRC_CR_RESET 0x00000001
|
||||
|
||||
struct CRC {
|
||||
volatile uint32_t DR;
|
||||
volatile uint8_t IDR;
|
||||
uint8_t RESERVED0;
|
||||
uint16_t RESERVED1;
|
||||
volatile uint32_t CR;
|
||||
};
|
||||
|
||||
#define CRC_BASE (AHBPERIPH_BASE + 0x3000)
|
||||
static struct CRC *const CRC = ((struct CRC *const)CRC_BASE);
|
||||
|
||||
|
||||
struct ADC {
|
||||
volatile uint32_t SR;
|
||||
volatile uint32_t CR1;
|
||||
volatile uint32_t CR2;
|
||||
volatile uint32_t SMPR1;
|
||||
volatile uint32_t SMPR2;
|
||||
volatile uint32_t JOFR1;
|
||||
volatile uint32_t JOFR2;
|
||||
volatile uint32_t JOFR3;
|
||||
volatile uint32_t JOFR4;
|
||||
volatile uint32_t HTR;
|
||||
volatile uint32_t LTR;
|
||||
volatile uint32_t SQR1;
|
||||
volatile uint32_t SQR2;
|
||||
volatile uint32_t SQR3;
|
||||
volatile uint32_t JSQR;
|
||||
volatile uint32_t JDR1;
|
||||
volatile uint32_t JDR2;
|
||||
volatile uint32_t JDR3;
|
||||
volatile uint32_t JDR4;
|
||||
volatile uint32_t DR;
|
||||
};
|
||||
|
||||
#define ADC1_BASE (APB2PERIPH_BASE + 0x2400)
|
||||
#define ADC2_BASE (APB2PERIPH_BASE + 0x2800)
|
||||
|
||||
static struct ADC *const ADC1 = (struct ADC *const)ADC1_BASE;
|
||||
static struct ADC *const ADC2 = (struct ADC *const)ADC2_BASE;
|
||||
|
||||
#define ADC_CR1_DUALMOD_0 0x00010000
|
||||
#define ADC_CR1_DUALMOD_1 0x00020000
|
||||
#define ADC_CR1_DUALMOD_2 0x00040000
|
||||
#define ADC_CR1_DUALMOD_3 0x00080000
|
||||
|
||||
#define ADC_CR1_SCAN 0x00000100
|
||||
|
||||
#define ADC_CR2_ADON 0x00000001
|
||||
#define ADC_CR2_CONT 0x00000002
|
||||
#define ADC_CR2_CAL 0x00000004
|
||||
#define ADC_CR2_RSTCAL 0x00000008
|
||||
#define ADC_CR2_DMA 0x00000100
|
||||
#define ADC_CR2_ALIGN 0x00000800
|
||||
#define ADC_CR2_EXTSEL 0x000E0000
|
||||
#define ADC_CR2_EXTSEL_0 0x00020000
|
||||
#define ADC_CR2_EXTSEL_1 0x00040000
|
||||
#define ADC_CR2_EXTSEL_2 0x00080000
|
||||
#define ADC_CR2_EXTTRIG 0x00100000
|
||||
#define ADC_CR2_SWSTART 0x00400000
|
||||
#define ADC_CR2_TSVREFE 0x00800000
|
||||
|
||||
struct DMA_Channel {
|
||||
volatile uint32_t CCR;
|
||||
volatile uint32_t CNDTR;
|
||||
volatile uint32_t CPAR;
|
||||
volatile uint32_t CMAR;
|
||||
};
|
||||
|
||||
struct DMA {
|
||||
volatile uint32_t ISR;
|
||||
volatile uint32_t IFCR;
|
||||
};
|
||||
|
||||
#define STM32_DMA_CR_MINC DMA_CCR1_MINC
|
||||
#define STM32_DMA_CR_MSIZE_WORD DMA_CCR1_MSIZE_1
|
||||
#define STM32_DMA_CR_PSIZE_WORD DMA_CCR1_PSIZE_1
|
||||
#define STM32_DMA_CR_TCIE DMA_CCR1_TCIE
|
||||
#define STM32_DMA_CR_TEIE DMA_CCR1_TEIE
|
||||
#define STM32_DMA_CR_HTIE DMA_CCR1_HTIE
|
||||
#define STM32_DMA_ISR_TEIF DMA_ISR_TEIF1
|
||||
#define STM32_DMA_ISR_HTIF DMA_ISR_HTIF1
|
||||
#define STM32_DMA_ISR_TCIF DMA_ISR_TCIF1
|
||||
|
||||
#define STM32_DMA_ISR_MASK 0x0F
|
||||
#define STM32_DMA_CCR_RESET_VALUE 0x00000000
|
||||
#define STM32_DMA_CR_PL_MASK DMA_CCR1_PL
|
||||
#define STM32_DMA_CR_PL(n) ((n) << 12)
|
||||
|
||||
#define DMA_CCR1_EN 0x00000001
|
||||
#define DMA_CCR1_TCIE 0x00000002
|
||||
#define DMA_CCR1_HTIE 0x00000004
|
||||
#define DMA_CCR1_TEIE 0x00000008
|
||||
#define DMA_CCR1_DIR 0x00000010
|
||||
#define DMA_CCR1_CIRC 0x00000020
|
||||
#define DMA_CCR1_PINC 0x00000040
|
||||
#define DMA_CCR1_MINC 0x00000080
|
||||
#define DMA_CCR1_PSIZE 0x00000300
|
||||
#define DMA_CCR1_PSIZE_0 0x00000100
|
||||
#define DMA_CCR1_PSIZE_1 0x00000200
|
||||
#define DMA_CCR1_MSIZE 0x00000C00
|
||||
#define DMA_CCR1_MSIZE_0 0x00000400
|
||||
#define DMA_CCR1_MSIZE_1 0x00000800
|
||||
#define DMA_CCR1_PL 0x00003000
|
||||
#define DMA_CCR1_PL_0 0x00001000
|
||||
#define DMA_CCR1_PL_1 0x00002000
|
||||
#define DMA_CCR1_MEM2MEM 0x00004000
|
||||
|
||||
#define DMA_ISR_GIF1 0x00000001
|
||||
#define DMA_ISR_TCIF1 0x00000002
|
||||
#define DMA_ISR_HTIF1 0x00000004
|
||||
#define DMA_ISR_TEIF1 0x00000008
|
||||
#define DMA_ISR_GIF2 0x00000010
|
||||
#define DMA_ISR_TCIF2 0x00000020
|
||||
#define DMA_ISR_HTIF2 0x00000040
|
||||
#define DMA_ISR_TEIF2 0x00000080
|
||||
#define DMA_ISR_GIF3 0x00000100
|
||||
#define DMA_ISR_TCIF3 0x00000200
|
||||
#define DMA_ISR_HTIF3 0x00000400
|
||||
#define DMA_ISR_TEIF3 0x00000800
|
||||
#define DMA_ISR_GIF4 0x00001000
|
||||
#define DMA_ISR_TCIF4 0x00002000
|
||||
#define DMA_ISR_HTIF4 0x00004000
|
||||
#define DMA_ISR_TEIF4 0x00008000
|
||||
#define DMA_ISR_GIF5 0x00010000
|
||||
#define DMA_ISR_TCIF5 0x00020000
|
||||
#define DMA_ISR_HTIF5 0x00040000
|
||||
#define DMA_ISR_TEIF5 0x00080000
|
||||
#define DMA_ISR_GIF6 0x00100000
|
||||
#define DMA_ISR_TCIF6 0x00200000
|
||||
#define DMA_ISR_HTIF6 0x00400000
|
||||
#define DMA_ISR_TEIF6 0x00800000
|
||||
#define DMA_ISR_GIF7 0x01000000
|
||||
#define DMA_ISR_TCIF7 0x02000000
|
||||
#define DMA_ISR_HTIF7 0x04000000
|
||||
#define DMA_ISR_TEIF7 0x08000000
|
||||
|
||||
#define DMA1_BASE (AHBPERIPH_BASE + 0x0000)
|
||||
static struct DMA *const DMA1 = (struct DMA *const)DMA1_BASE;
|
||||
|
||||
#define DMA1_Channel1_BASE (AHBPERIPH_BASE + 0x0008)
|
||||
static struct DMA_Channel *const DMA1_Channel1 =
|
||||
(struct DMA_Channel *const)DMA1_Channel1_BASE;
|
||||
|
||||
/* System Control Block */
|
||||
struct SCB
|
||||
{
|
||||
volatile uint32_t CPUID;
|
||||
volatile uint32_t ICSR;
|
||||
volatile uint32_t VTOR;
|
||||
volatile uint32_t AIRCR;
|
||||
volatile uint32_t SCR;
|
||||
volatile uint32_t CCR;
|
||||
volatile uint8_t SHP[12];
|
||||
volatile uint32_t SHCSR;
|
||||
volatile uint32_t CFSR;
|
||||
volatile uint32_t HFSR;
|
||||
volatile uint32_t DFSR;
|
||||
volatile uint32_t MMFAR;
|
||||
volatile uint32_t BFAR;
|
||||
volatile uint32_t AFSR;
|
||||
volatile uint32_t PFR[2];
|
||||
volatile uint32_t DFR;
|
||||
volatile uint32_t ADR;
|
||||
volatile uint32_t MMFR[4];
|
||||
volatile uint32_t ISAR[5];
|
||||
uint32_t RESERVED0[5];
|
||||
volatile uint32_t CPACR;
|
||||
};
|
||||
|
||||
#define SCS_BASE 0xE000E000
|
||||
#define SCB_BASE (SCS_BASE + 0x0D00)
|
||||
static struct SCB *const SCB = (struct SCB *const)SCB_BASE;
|
||||
Reference in New Issue
Block a user