雅特力AT32F403A

1、FLSAH算法相关知识

小猫爪:嵌入式小知识08-KEIL/IAR FLASH算法_小猫爪的博客-CSDN博客

        ps:3rd_part 第三方软件

1.1

        外设寄存器访问示例

        寄存器读 i = ADC1-> ctrl1;

        寄存器写 ADC1-> ctrl1 = i;

        bit 5 按位域方式读 i = ADC1-> ctrl1. cceien;

        bit 5 按位域方式写 1 ADC1-> ctrl1. cceien= TRUE;

        bit 5 直接写 1 ADC1-> ctrl1 |= 1 ctrl1&= ~(1<<5) ;

1.2

        DAC的配置:

        雅特力AT32F403A_第1张图片

        系统时钟:

雅特力AT32F403A_第2张图片雅特力AT32F403A_第3张图片

2、DMA固定请求映射与弹性映射

        在调试例程时,使用的是DAC1,DAC1的DMA是固定映射在DMA2通道的ch3通道的,

但是例程中使用的是DMA1的CH1通道。

雅特力AT32F403A_第4张图片

        通过手册知道这里亚特力的DMA弹性映射,DMA 弹性映射请求功能提供了一种更灵活的使用方式,即外设的 DMA 通道不固定,可选择 DMA1 和 DMA2 中,共 14 个通道的任意一个通道。DMA 弹性映射请求功能提供了一种更灵活的使用方式,即外设的 DMA 通道不固定,可选择 DMA1 和 DMA2 中,共 14 个通道的任意一个通道。可以将某外设的 DMA 请求通道指定到 DMA1 或者 DMA2 共 14 个通道中的任意一个通道。(如:可以将 SPI1 接受数据的 DMA 请求指定到 DMA1 的通道 7)。

  dma_flexible_config(DMA1, FLEX_CHANNEL1, DMA_FLEXIBLE_DAC2);
 
    //此处即将固定映射在DMA2\CH4上的DAC2的DMA通道弹性映射到DMA1的CH1通道

雅特力AT32F403A_第5张图片

        参考文章:STM32学习-DMA介绍及一般使用方法_Yahong.W的博客-CSDN博客_stm32 dma

         ps:DMA配置流程

雅特力AT32F403A_第6张图片

        实验:ADC+DMA生成基波为10Khz的方波的三角波;


#include "at32f403a_407_board.h"
#include "at32f403a_407_clock.h"

/** @addtogroup AT32F407_periph_examples
  * @{
  */

/** @addtogroup 407_DAC_double_mode_dma_sinewave DAC_double_mode_dma_sinewave
  * @{
  */

gpio_init_type  gpio_init_struct = {0};
dma_init_type dma_init_struct = {0};
crm_clocks_freq_type crm_clocks_freq_struct = {0};
uint16_t square[512];															
uint32_t dualsine12bit[512];
uint32_t idx = 0;

/**
  * @brief  main function.
  * @param  none
  * @retval none
  */
int main(void)
{
  system_clock_config();

  at32_board_init();

  /* turn led2/led3/led4 on */
  at32_led_on(LED2);
  at32_led_on(LED3);
  at32_led_on(LED4);

  /* enable dac/tmr2/gpioa clock */
  crm_periph_clock_enable(CRM_DMA1_PERIPH_CLOCK, TRUE);
  crm_periph_clock_enable(CRM_DAC_PERIPH_CLOCK, TRUE);
  crm_periph_clock_enable(CRM_TMR2_PERIPH_CLOCK, TRUE);
  crm_periph_clock_enable(CRM_GPIOA_PERIPH_CLOCK, TRUE);

  /* once the dac is enabled, the corresponding gpio pin is automatically
     connected to the dac converter. in order to avoid parasitic consumption,
     the gpio pin should be configured in analog */
  gpio_init_struct.gpio_pins = GPIO_PINS_4 | GPIO_PINS_5;
  gpio_init_struct.gpio_mode = GPIO_MODE_ANALOG;
  gpio_init_struct.gpio_out_type = GPIO_OUTPUT_PUSH_PULL;
  gpio_init_struct.gpio_pull = GPIO_PULL_NONE;
  gpio_init_struct.gpio_drive_strength = GPIO_DRIVE_STRENGTH_STRONGER;
  gpio_init(GPIOA, &gpio_init_struct);

  /* get system clock */
  crm_clocks_freq_get(&crm_clocks_freq_struct);

  /* (systemclock/(systemclock/1000000))/100 = 10KHz */
  tmr_base_init(TMR2, 99, (crm_clocks_freq_struct.sclk_freq/1000000 - 1));
  tmr_cnt_dir_set(TMR2, TMR_COUNT_UP);

  /* primary tmr2 output selection */
  tmr_primary_mode_select(TMR2, TMR_PRIMARY_SEL_OVERFLOW);

  /* dac1 and dac2 configuration */
  dac_trigger_select(DAC1_SELECT, DAC_TMR2_TRGOUT_EVENT);
  dac_trigger_select(DAC2_SELECT, DAC_TMR2_TRGOUT_EVENT);

  dac_trigger_enable(DAC1_SELECT, TRUE);
  dac_trigger_enable(DAC2_SELECT, TRUE);

  dac_wave_generate(DAC1_SELECT, DAC_WAVE_GENERATE_NONE);
  dac_wave_generate(DAC2_SELECT, DAC_WAVE_GENERATE_NONE);

  dac_output_buffer_enable(DAC1_SELECT, FALSE);
  dac_output_buffer_enable(DAC2_SELECT, FALSE);

  dac_dma_enable(DAC1_SELECT, TRUE);
  dac_dma_enable(DAC2_SELECT, TRUE);


  /* fill sine32bit table */
  for(idx = 0; idx < 256; idx++)
  {
		square[2*idx]		=	(4095-idx*8);
		square[2*idx+1]	=	 idx * 8;
  }
for(idx = 0; idx < 512; idx++)
  {
		dualsine12bit[idx] = (square[idx] << 16) + (square[idx]);
  }
  /* dma1 channel1 configuration */
  dma_reset(DMA1_CHANNEL1);
  dma_init_struct.buffer_size = 512;
  dma_init_struct.direction = DMA_DIR_MEMORY_TO_PERIPHERAL;
  dma_init_struct.memory_base_addr = (uint32_t)dualsine12bit;
  dma_init_struct.memory_data_width = DMA_MEMORY_DATA_WIDTH_WORD;
  dma_init_struct.memory_inc_enable = TRUE;
  dma_init_struct.peripheral_base_addr = (uint32_t)0x40007420;
  dma_init_struct.peripheral_data_width = DMA_PERIPHERAL_DATA_WIDTH_WORD;
  dma_init_struct.peripheral_inc_enable = FALSE;
  dma_init_struct.priority = DMA_PRIORITY_MEDIUM;
  dma_init_struct.loop_mode_enable = TRUE;
  dma_init(DMA1_CHANNEL1, &dma_init_struct);

  /* enable dma flexible function */
  dma_flexible_config(DMA1, FLEX_CHANNEL1, DMA_FLEXIBLE_DAC1);

  dma_channel_enable(DMA1_CHANNEL1, TRUE);

  /* enable dac1: once the dac1 is enabled, pa.04 is
     automatically connected to the dac converter. */
  dac_enable(DAC1_SELECT, TRUE);

  /* enable dac2: once the dac2 is enabled, pa.05 is
     automatically connected to the dac converter. */
  dac_enable(DAC2_SELECT, TRUE);

  /* enable tmr2 */
  tmr_counter_enable(TMR2, TRUE);

  while(1)
  {
  }
}


雅特力AT32F403A_第7张图片

雅特力AT32F403A_第8张图片

3、读取GPS串口读取GPS定位信息

        3.1方法1动态内存分配

参考文章:stm32与GPS模块的数据传输,最后把数据传回到电脑上_追梦者( '▿ ' )的博客-CSDN博客_g28z2fttl 需要插卡吗

拾取坐标系统

/**
  **************************************************************************
  * @file     main.c
  * @brief    main program 
  *Read GPS information through seral port2 and prin out the information 
  *through serial port1
  **************************************************************************

  */

#include "at32f403a_407_board.h"
#include "at32f403a_407_clock.h"
#include "stdio.h"
#include "string.h"
#include "stdlib.h"
#include "stdbool.h "

typedef struct Data
{
	char GPS_Buffer[200];//数据接收	
	bool isGetData;//接收数据是否完成
	char *UTCTime;//时间戳
	char *latitude;//纬度
	char *N_S;//南北
	char *longitude;//经度
	char *E_W;//东西
	bool isParseData;//是否解析完成
	bool isUsefull;//是否为有效数据位
}Data;

short int point1;
const short int USART2_MAX_RECV_LEN = 200;
char USAR2_RX_BUF[USART2_MAX_RECV_LEN];
const short int GPS_Buffer_Length = 200;
struct Data Save_Data;

/**
  * @brief  initialize uart1
  * @param  baudrate: uart baudrate
  * @retval none
  */
void uart1_print_init(uint32_t baudrate)
{
  gpio_init_type gpio_init_struct;

#if defined (__GNUC__) && !defined (__clang__)
  setvbuf(stdout, NULL, _IONBF, 0);
#endif

  /* enable the uart and gpio clock */
  crm_periph_clock_enable(CRM_USART1_PERIPH_CLOCK, TRUE);
  crm_periph_clock_enable(CRM_GPIOA_PERIPH_CLOCK, TRUE);

  gpio_default_para_init(&gpio_init_struct);

  /* configure the uart tx pin */
  gpio_init_struct.gpio_drive_strength = GPIO_DRIVE_STRENGTH_STRONGER;
  gpio_init_struct.gpio_out_type  = GPIO_OUTPUT_PUSH_PULL;
  gpio_init_struct.gpio_mode = GPIO_MODE_MUX;
  gpio_init_struct.gpio_pins = GPIO_PINS_9;
  gpio_init_struct.gpio_pull = GPIO_PULL_NONE;
  gpio_init(GPIOA, &gpio_init_struct);

  /* configure uart param */
  usart_init(USART1, baudrate, USART_DATA_8BITS, USART_STOP_1_BIT);
  usart_transmitter_enable(USART1, TRUE);
  usart_enable(USART1, TRUE);
	
}
/**
	* @brief initialize uart2  RX:PA3  TX:PA2
	* @param baudrate: uart baudrate
	* @retyal none
*/
void uart2_receive_init(uint32_t baudrate)
{
	gpio_init_type gpio_init_struct;
	
	/* enable the uart and gpio clock*/
	crm_periph_clock_enable(CRM_USART2_PERIPH_CLOCK,TRUE);
	crm_periph_clock_enable(CRM_GPIOA_PERIPH_CLOCK,TRUE);
	
	gpio_default_para_init(&gpio_init_struct);
	
	gpio_init_struct.gpio_drive_strength = GPIO_DRIVE_STRENGTH_STRONGER;
	gpio_init_struct.gpio_mode = GPIO_MODE_INPUT;
	gpio_init_struct.gpio_pins = GPIO_PINS_3;
	gpio_init_struct.gpio_pull = GPIO_PULL_UP;
	gpio_init(GPIOA,&gpio_init_struct);
	
	usart_init(USART2,baudrate,USART_DATA_8BITS,USART_STOP_1_BIT);

	usart_receiver_enable(USART2,TRUE);

	nvic_priority_group_config(NVIC_PRIORITY_GROUP_4);
	nvic_irq_enable(USART2_IRQn,0,0);
	usart_interrupt_enable(USART2,USART_RDBF_INT,TRUE);
	usart_enable(USART2,TRUE);
}


void parseGpsBuffer(void){
	char *subString;
	char *subStringNext;
	int i = 0;
	if(Save_Data.isGetData)
	{
		Save_Data.isGetData = FALSE;
		printf("*****************\r\n");
		printf("%s",Save_Data.GPS_Buffer);
		
		for(i = 0; i <= 6; i++){
			if(i == 0){
				if((subString = strstr(Save_Data.GPS_Buffer, ",")) == NULL)
					printf("解析错误");
				}
				else{
					subString++;//到达解析数据中逗号的下一位
					if((subStringNext = strstr(subString, ",")) != NULL)
					{
						char usefullBuffer[2];
						switch(i){
							case 1: 
								//利用subStringNext和subString的首地址相减来确定指针开辟空间的大小,以防指针不合法。
								Save_Data.UTCTime = (char *)malloc((subStringNext - subString)*sizeof(char));
								memcpy(Save_Data.UTCTime, subString, subStringNext - subString); 
								break;
							case 2: memcpy(usefullBuffer, subString, subStringNext - subString); break;  //定位状态,A=有效定位,V=无效定位 
							case 3: Save_Data.latitude = (char *)malloc((subStringNext - subString)*sizeof(char));
								memcpy(Save_Data.latitude, subString, subStringNext - subString); 
								break;
							case 4: Save_Data.N_S = (char *)malloc((subStringNext - subString)*sizeof(char));
								memcpy(Save_Data.N_S, subString, subStringNext - subString); 
								break;
							case 5: Save_Data.longitude = (char *)malloc((subStringNext - subString)*sizeof(char));
								memcpy(Save_Data.longitude, subString, subStringNext - subString); 
								break;
							case 6: Save_Data.E_W = (char *)malloc((subStringNext - subString)*sizeof(char));
								memcpy(Save_Data.E_W, subString, subStringNext - subString); 
								break;
							default: break;
						}
						subString = subStringNext;
						Save_Data.isParseData = TRUE;
						if(usefullBuffer[0] == 'A')
							Save_Data.isUsefull = TRUE;
						else if(usefullBuffer[0] == 'V')
							Save_Data.isUsefull = FALSE;
					}
					else{
							printf("解析错误2");
					}
				}
			}
		}
}


void printfGpsBuffer(void){
	if(Save_Data.isParseData){
		Save_Data.isParseData = FALSE;
		printf("Save_Data.UTCTime = %s\r\n", Save_Data.UTCTime);//打印数据
		free(Save_Data.UTCTime);//释放空间
		
		if(Save_Data.isUsefull){
			Save_Data.isUsefull = FALSE;
			printf("Save_Data.latitude = %s\r\n", Save_Data.latitude);
			free(Save_Data.latitude);
			printf("Save_Data.N_S = %s\r\n", Save_Data.N_S);
			free(Save_Data.N_S);
			printf("Save_Data.longitude = %s\r\n", Save_Data.longitude);
			free(Save_Data.longitude);
			printf("Save_Data.E_W = %s\r\n", Save_Data.E_W);
			free(Save_Data.E_W);
		}
		else
		{
			printf("GPS DATA is not usefull!\r\n");
		}
	}
}

/**
  * @brief  main function.
  * @param  none
  * @retval none
  */
int main(void)
{
  system_clock_config();
  at32_board_init();
  uart1_print_init(9600);
  uart2_receive_init(9600);
	
  while(1);
}
/**
	* @brief this function handles usart2 handler.
	* @param none
	* @retval none
	*/
void  USART2_IRQHandler(void)
{
	u8 res;
	if(usart_flag_get(USART2,USART_RDBF_FLAG)!=RESET){
		res = usart_data_receive(USART2);
		if(res == '$'){
			point1 = 0;
		}
		USAR2_RX_BUF[point1++] = res;
		if(USAR2_RX_BUF[0] == '$' && USAR2_RX_BUF[4] == 'M' && USAR2_RX_BUF[5] == 'C'){
			if(res == '\n'){	
				memcpy(Save_Data.GPS_Buffer, USAR2_RX_BUF, point1);
				Save_Data.isGetData = TRUE;
				point1 = 0;
				memset(USAR2_RX_BUF, 0, USART2_MAX_RECV_LEN);
				parseGpsBuffer();
				printfGpsBuffer();
			}
		}
	}

}

 雅特力AT32F403A_第9张图片

         3.2方法2固定数组 

/**
  **************************************************************************
  * @file     main.c
  * @brief    main program 
  *Read GPS information through seral port2 and prin out the information 
  *through serial port1
  **************************************************************************

  */

#include "at32f403a_407_board.h"
#include "at32f403a_407_clock.h"
#include "stdio.h"
#include "string.h"
#include "stdlib.h"
#include "stdbool.h "



typedef struct Data
{
	char RawData[200];
	char UTCTime [50];
	char Latitude [50];
	char N_S [10];
	char Longitude [50];
	char E_W [10];
	short int BufPoint;
}Data;

Data GPSdata;


/**
  * @brief  initialize uart1
  * @param  baudrate: uart baudrate
  * @retval none
  */
void uart1_print_init(uint32_t baudrate)
{
  gpio_init_type gpio_init_struct;

#if defined (__GNUC__) && !defined (__clang__)
  setvbuf(stdout, NULL, _IONBF, 0);
#endif

  /* enable the uart and gpio clock */
  crm_periph_clock_enable(CRM_USART1_PERIPH_CLOCK, TRUE);
  crm_periph_clock_enable(CRM_GPIOA_PERIPH_CLOCK, TRUE);

  gpio_default_para_init(&gpio_init_struct);

  /* configure the uart tx pin */
  gpio_init_struct.gpio_drive_strength = GPIO_DRIVE_STRENGTH_STRONGER;
  gpio_init_struct.gpio_out_type  = GPIO_OUTPUT_PUSH_PULL;
  gpio_init_struct.gpio_mode = GPIO_MODE_MUX;
  gpio_init_struct.gpio_pins = GPIO_PINS_9;
  gpio_init_struct.gpio_pull = GPIO_PULL_NONE;
  gpio_init(GPIOA, &gpio_init_struct);

  /* configure uart param */
  usart_init(USART1, baudrate, USART_DATA_8BITS, USART_STOP_1_BIT);
  usart_transmitter_enable(USART1, TRUE);
  usart_enable(USART1, TRUE);
	
}
/**
	* @brief initialize uart2  RX:PA3  Read a row of GPS raw data
	* @param baudrate: uart baudrate
	* @retyal none
*/


void uart2_receive_init(uint32_t baudrate)
{
	gpio_init_type gpio_init_struct;
	
	/* enable the uart and gpio clock*/
	crm_periph_clock_enable(CRM_USART2_PERIPH_CLOCK,TRUE);
	crm_periph_clock_enable(CRM_GPIOA_PERIPH_CLOCK,TRUE);
	
	gpio_default_para_init(&gpio_init_struct);
	
	gpio_init_struct.gpio_drive_strength = GPIO_DRIVE_STRENGTH_STRONGER;
	gpio_init_struct.gpio_mode = GPIO_MODE_INPUT;
	gpio_init_struct.gpio_pins = GPIO_PINS_3;
	gpio_init_struct.gpio_pull = GPIO_PULL_UP;
	gpio_init(GPIOA,&gpio_init_struct);
	
	usart_init(USART2,baudrate,USART_DATA_8BITS,USART_STOP_1_BIT);

	usart_receiver_enable(USART2,TRUE);

	nvic_priority_group_config(NVIC_PRIORITY_GROUP_4);
	nvic_irq_enable(USART2_IRQn,0,0);
	usart_interrupt_enable(USART2,USART_RDBF_INT,TRUE);
	usart_enable(USART2,TRUE);
}
/**
* @brief parseGPSdata function
* @param nono
* @retval none
*/
/* eg. $GPGGA,082559.00,4005.22599,N,11632.58234,E,1,04,3.08,14.6,M,-5.6,M,,*76"*/
void parseGPSdata(void)
{
	int h,m,s;
	float flat,flon;
	char tmp[10];
	if(strstr(GPSdata.RawData,",,,,,")){
		printf("Plase the GPS to open area \r\n");
		return;
	}
	else{	
		sscanf(GPSdata.RawData,"%[^,],%[^,],%[^,],%[^,],%[^,],%[^,]",tmp,
		GPSdata.UTCTime,GPSdata.Latitude,GPSdata.N_S,GPSdata.Longitude,GPSdata.E_W);
		
		sscanf(GPSdata.Latitude+2,"%f",&flat);
		flat = flat / 60;
		flat += (GPSdata.Latitude[0]-'0')*10 + (GPSdata.Latitude[1]-'0');
		sscanf(GPSdata.Longitude+3,"%f",&flon);
		flon = flon / 60;
		flon += (GPSdata.Longitude[0]-'0')*100 + (GPSdata.Longitude[1]-'0')*10 + (GPSdata.Longitude[2] - '0');
		
		h = (GPSdata.UTCTime[0]-'0')*10 + (GPSdata.UTCTime[1]-'0') + 8;
		m = (GPSdata.UTCTime[2]-'0')*10 + (GPSdata.UTCTime[3]-'0') ;
		s = (GPSdata.UTCTime[4]-'0')*10 + (GPSdata.UTCTime[5]-'0') ;
		
		printf("*****************************************\r\n");
		printf("%s\r\n",GPSdata.RawData);
		printf("Time:%d:%d:%d\r\n",h,m,s);
		printf("Longitude:%.6f%s\r\n",flon,GPSdata.E_W);
		printf("Latitude:%.6f%s\r\n",flat,GPSdata.N_S);
	}

}


/**
  * @brief  main function.
  * @param  none
  * @retval none
  */
int main(void)
{

	system_clock_config();
	at32_board_init();
	uart1_print_init(9600);
	uart2_receive_init(9600);
	
	while(1);
}
/**
	* @brief this function handles usart2 handler.
	* @param none
	* @retval none
	*/
void  USART2_IRQHandler(void)
{
	char res;
	if(usart_flag_get(USART2,USART_RDBF_FLAG)!=RESET)
	{
		
		res = usart_data_receive(USART2);
		if(res == '$'){
			GPSdata.BufPoint = 0;
		}
		GPSdata.RawData[GPSdata.BufPoint++] = res;
		if(	GPSdata.RawData[0]  == '$' && GPSdata.RawData[4] == 'G' && GPSdata.RawData[5] == 'A'){
			if(res == '\r' )
			{
				GPSdata.RawData[GPSdata.BufPoint] = '\0';
				GPSdata.BufPoint = 0;
				parseGPSdata();
			}
		}
	}

}

 雅特力AT32F403A_第10张图片

你可能感兴趣的:(单片机,嵌入式硬件)