feat: auto read adc in SysTick_Handler

This commit is contained in:
liuyihui 2023-04-28 01:59:54 +08:00
parent c9af85ad08
commit 3f22ff1a07
7 changed files with 36 additions and 21 deletions

View File

@ -2,5 +2,10 @@
#include <inttypes.h> #include <inttypes.h>
#define ADC_M 1024
extern int16_t adc_buf[ADC_M];
extern int16_t pADC;
extern uint8_t fADC;
void adc0_Init(); void adc0_Init();
int16_t adc0_TR_DATA(); int16_t adc0_TR_DATA();

View File

@ -27,10 +27,10 @@
PORT##port->PCR[pin] |= PORT_PCR_PE(0x1); \ PORT##port->PCR[pin] |= PORT_PCR_PE(0x1); \
} }
#define ticks_ms (uint32_t)(ticks_10us / 100) #define ticks_ms (uint32_t)(ticks_50us / 20)
extern uint32_t CORCLK; extern uint32_t CORCLK;
extern uint32_t BUSCLK; extern uint32_t BUSCLK;
extern volatile uint32_t ticks_10us; extern volatile uint32_t ticks_50us;
extern void SysTick_Handler(void); extern void SysTick_Handler(void);
extern void UART1_IRQHandler(void); extern void UART1_IRQHandler(void);

View File

@ -16,11 +16,11 @@ static inline bool timer_expired_ms(uint32_t *t, uint32_t prd) {
return true; // Expired, return true return true; // Expired, return true
} }
static inline bool timer_expired_10us(uint32_t *t, uint32_t prd) { static inline bool timer_expired_50us(uint32_t *t, uint32_t prd) {
if (ticks_10us + prd < *t) *t = 0; // Time wrapped? Reset timer if (ticks_50us + prd < *t) *t = 0; // Time wrapped? Reset timer
if (*t == 0) *t = ticks_10us + prd; // First poll? Set expiration if (*t == 0) *t = ticks_50us + prd; // First poll? Set expiration
if (*t > ticks_10us) return false; // Not expired yet, return if (*t > ticks_50us) return false; // Not expired yet, return
*t = (ticks_10us - *t) > prd ? ticks_10us + prd : *t + prd; // Next expiration time *t = (ticks_50us - *t) > prd ? ticks_50us + prd : *t + prd; // Next expiration time
return true; // Expired, return true return true; // Expired, return true
} }
@ -29,7 +29,7 @@ static inline void delay_ms(uint32_t ms) {
while (ticks_ms - start < ms) asm("nop"); while (ticks_ms - start < ms) asm("nop");
} }
static inline void delay_10us(uint32_t us) { static inline void delay_50us(uint32_t us) {
uint32_t start = ticks_10us; uint32_t start = ticks_50us;
while (ticks_10us - start < us) asm("nop"); while (ticks_50us - start < us) asm("nop");
} }

9
main.c
View File

@ -6,8 +6,6 @@
#include <stdio.h> #include <stdio.h>
#include <string.h> #include <string.h>
#define ADC_M 2048
int main(void) { int main(void) {
// Initialize // Initialize
uart_init(UART_MSG, 9600); // Initialize UART1 with PC uart_init(UART_MSG, 9600); // Initialize UART1 with PC
@ -35,13 +33,14 @@ int main(void) {
uint16_t pos[x1 - x0 - 1]; uint16_t pos[x1 - x0 - 1];
uint16_t x = x0 + 1, y; uint16_t x = x0 + 1, y;
uint32_t timer = 0; uint32_t timer = 0;
fADC = 1;
for (;;) { for (;;) {
if (timer_expired_10us(&timer, 5)) { if (timer_expired_50us(&timer, 1)) {
LCD_DrawPoint(x, pos[x - x0 - 1], BACK_COLOR); LCD_DrawPoint(x, pos[x - x0 - 1], BACK_COLOR);
res = adc0_TR_DATA() - 1550; res = adc_buf[pADC];
y = ym + res * (y1 - ym) / ADC_M; y = ym + res * (y1 - ym) / 2048;
LCD_DrawPoint(x, y, RED); LCD_DrawPoint(x, y, RED);
LCD_DrawPoint(x, ym, BLACK); LCD_DrawPoint(x, ym, BLACK);

View File

@ -1,6 +1,10 @@
#include "adc.h" #include "adc.h"
#include "derivative.h" #include "derivative.h"
int16_t adc_buf[ADC_M];
int16_t pADC = 0;
uint8_t fADC = 0;
void adc0_Init() { void adc0_Init() {
// Enable ADC0 and PORTE clock // Enable ADC0 and PORTE clock
SIM->SCGC6 |= SIM_SCGC6_ADC0_MASK; SIM->SCGC6 |= SIM_SCGC6_ADC0_MASK;
@ -9,10 +13,10 @@ void adc0_Init() {
// USE AD0 (ADC0_SE4a) // USE AD0 (ADC0_SE4a)
PORTE->PCR[21] |= PORT_PCR_MUX(0x0); PORTE->PCR[21] |= PORT_PCR_MUX(0x0);
ADC0->CFG1 = ADC_CFG1_ADLSMP_MASK // Sample time 0 = Short, 1 = Long ADC0->CFG1 = ADC_CFG1_ADLSMP(0x01) // Sample time 0 = Short, 1 = Long
| ADC_CFG1_MODE(0x01); // Conversion mode 00 = 8-bit, 01 = 12-bit, 10 = 10-bit, 11 = 16-bit | ADC_CFG1_MODE(0x01); // Conversion mode 00 = 8-bit, 01 = 12-bit, 10 = 10-bit, 11 = 16-bit
ADC0->SC3 = ADC_SC3_ADCO_MASK // Continuous Conversion if AVGE = 1 ADC0->SC3 = ADC_SC3_ADCO(0x01) // Continuous conversion enable
| ADC_SC3_AVGE_MASK // Hardware average | ADC_SC3_AVGE(0x01) // Hardware average
| ADC_SC3_AVGS(0x01); // Hardware average 00 = 4 samples, 01 = 8, 10 = 16, 11 = 32 | ADC_SC3_AVGS(0x01); // Hardware average 00 = 4 samples, 01 = 8, 10 = 16, 11 = 32
ADC0->SC1[0] = ADC_SC1_ADCH(0x04); // Input channel select, AD4a is selected as input ADC0->SC1[0] = ADC_SC1_ADCH(0x04); // Input channel select, AD4a is selected as input
} }

View File

@ -1,12 +1,19 @@
#include "adc.h"
#include "derivative.h" #include "derivative.h"
#include "uart.h" #include "uart.h"
uint32_t CORCLK = CORCLK_DEFAULT; uint32_t CORCLK = CORCLK_DEFAULT;
uint32_t BUSCLK = BUSCLK_DEFAULT; uint32_t BUSCLK = BUSCLK_DEFAULT;
volatile uint32_t ticks_10us; volatile uint32_t ticks_50us;
void SysTick_Handler(void) { ticks_10us++; } void SysTick_Handler(void) {
ticks_50us++;
if (fADC) {
adc_buf[pADC] = adc0_TR_DATA() - 1550;
pADC = (pADC + 1) % ADC_M;
}
}
void UART1_IRQHandler(void) { void UART1_IRQHandler(void) {
if (UART1->S1 & UART_S1_RDRF_MASK) { if (UART1->S1 & UART_S1_RDRF_MASK) {

View File

@ -159,7 +159,7 @@ __attribute__((naked, noreturn)) void _reset(void) {
copy_data(); copy_data();
clock_init(); clock_init();
SysTick_Config(CORCLK / 100000); // Period of systick timer : 10 us SysTick_Config(CORCLK / 100000 * 5); // Period of systick timer : 50 us
main(); main();
for (;;) (void)0; for (;;) (void)0;