wenyangzeng 发表于 2017-2-26 20:15:32

STM32F413 Nucleo评测(DAC)

本帖最后由 wenyangzeng 于 2017-2-26 21:51 编辑

收到《我与STM32共成长》奖品STM32F413 Nucleo,谢谢社区。应该为它发一贴。



STM32F413ZHT6是Cortex-M4内核,
主频:100MHz,125DMIPS
1.5MB Flash,320KB RAM
低功耗:运行模式115μA/MHz,停止模式18μA
增强型批量数据采集模式(eBAM)
更多的外设:10通道UART,3通道CAN, 低功耗定时器,
另外还比F412多了2路DAC。

    未能找到官方演示代码中关于F413 DAC的演示,本次评测与各位分享对F413进行DAC配置的步骤方法。

选用通道:DAC通道1(GPIOA4);
输出信号:1KHZ正弦波
信号处理方式:DMA,12位DAC
触发源:TIM6



STM32F413 Nucleo板上HSE晶振没有焊接,我们选用内部时钟源HSI作为系统时钟源,并配置为100MHZ。



            使能DAC通道1



                     使能TIM6,用它来触发DAC



配置DAC1:
Output Buffer:Enable
Trigger:Timer 6 Trigger Out event
Wave generation mode:disable

配置TIM6
Prescaler(PSC - 16 bits value):0
Counter Mode:Up
Counter Period(AutoReload Registor:0xc40
Trigger Event Selection:Update Event


配置DMA传输
DMARequest:DAC1
Stream  :  DMA1 Stream5
Direction :   Menory To Preipheral
Priority  :  Low
Mode   : Circular
Inceement Address : Memory
Data width  :Half Word

代码:
#include "main.h"
#include "stm32f4xx_hal.h"

const uint16_t Sine12bit = {
                      2047, 2447, 2831, 3185, 3498, 3750, 3939, 4056, 4095, 4056,
                      3939, 3750, 3495, 3185, 2831, 2447, 2047, 1647, 1263, 909,
                      599, 344, 155, 38, 0, 38, 155, 344, 599, 909, 1263, 1647};
DAC_HandleTypeDef hdac;
DMA_HandleTypeDef hdma_dac1;

TIM_HandleTypeDef htim6;

void SystemClock_Config(void);
void Error_Handler(void);
static void MX_GPIO_Init(void);
static void MX_DMA_Init(void);
static void MX_DAC_Init(void);
static void MX_TIM6_Init(void);

int main(void)
{
HAL_Init();
SystemClock_Config();
MX_GPIO_Init();
MX_DMA_Init();
MX_DAC_Init();
MX_TIM6_Init();
while (1)
{
}
}

void SystemClock_Config(void)
{
RCC_OscInitTypeDef RCC_OscInitStruct;
RCC_ClkInitTypeDef RCC_ClkInitStruct;
__HAL_RCC_PWR_CLK_ENABLE();
__HAL_PWR_VOLTAGESCALING_CONFIG(PWR_REGULATOR_VOLTAGE_SCALE1);
RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSI;
RCC_OscInitStruct.HSIState = RCC_HSI_ON;
RCC_OscInitStruct.HSICalibrationValue = 16;
RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSI;
RCC_OscInitStruct.PLL.PLLM = 16;
RCC_OscInitStruct.PLL.PLLN = 200;
RCC_OscInitStruct.PLL.PLLP = RCC_PLLP_DIV2;
RCC_OscInitStruct.PLL.PLLQ = 2;
RCC_OscInitStruct.PLL.PLLR = 2;
if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK)
{
    Error_Handler();
}
RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK|RCC_CLOCKTYPE_SYSCLK
                              |RCC_CLOCKTYPE_PCLK1|RCC_CLOCKTYPE_PCLK2;
RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK;
RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1;
RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV2;
RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV1;

if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_3) != HAL_OK)
{
    Error_Handler();
}

HAL_SYSTICK_Config(HAL_RCC_GetHCLKFreq()/1000);
HAL_SYSTICK_CLKSourceConfig(SYSTICK_CLKSOURCE_HCLK);
HAL_NVIC_SetPriority(SysTick_IRQn, 0, 0);
}
static void MX_DAC_Init(void)
{
DAC_ChannelConfTypeDef sConfig;
hdac.Instance = DAC;
if (HAL_DAC_Init(&hdac) != HAL_OK)
{
    Error_Handler();
}
sConfig.DAC_Trigger = DAC_TRIGGER_T6_TRGO;
sConfig.DAC_OutputBuffer = DAC_OUTPUTBUFFER_ENABLE;
if (HAL_DAC_ConfigChannel(&hdac, &sConfig, DAC_CHANNEL_1) != HAL_OK)
{
    Error_Handler();
}
         if (HAL_DAC_Start_DMA(&hdac, DAC_CHANNEL_1,(uint32_t *) Sine12bit,32, DAC_ALIGN_12B_R) != HAL_OK)
{
   
Error_Handler();
}
}
static void MX_TIM6_Init(void)
{

TIM_MasterConfigTypeDef sMasterConfig;

htim6.Instance = TIM6;
htim6.Init.Prescaler = 0;
htim6.Init.CounterMode = TIM_COUNTERMODE_UP;
htim6.Init.Period = 0xc40;
if (HAL_TIM_Base_Init(&htim6) != HAL_OK)
{
    Error_Handler();
}

sMasterConfig.MasterOutputTrigger = TIM_TRGO_UPDATE;
sMasterConfig.MasterSlaveMode = TIM_MASTERSLAVEMODE_DISABLE;
if (HAL_TIMEx_MasterConfigSynchronization(&htim6, &sMasterConfig) != HAL_OK)
{
    Error_Handler();
}
HAL_TIM_Base_Start(&htim6);
}
static void MX_DMA_Init(void)
{
__HAL_RCC_DMA1_CLK_ENABLE();
HAL_NVIC_SetPriority(DMA1_Stream5_IRQn, 0, 0);
HAL_NVIC_EnableIRQ(DMA1_Stream5_IRQn);

}
static void MX_GPIO_Init(void)
{
__HAL_RCC_GPIOA_CLK_ENABLE();

}
在函数 MX_DAC_Init()末尾要添加:

if (HAL_DAC_Start_DMA(&hdac, DAC_CHANNEL_1,(uint32_t *) Sine12bit,32, DAC_ALIGN_12B_R) != HAL_OK)
      {
         Error_Handler();
      }
在函数MX_TIM6_Init(()末尾要添加:
HAL_TIM_Base_Start(&htim6);

    不知道为什么ST 不把启动定时器、启动DAC、启动ADC等等语句一并在STM32CUBE MX中添加进去,弄得我们这些菜鸟在老老实实按照STM32CUBE MX配置、编译完后,发现程序不能得到正确运行结果,搞得团团转,最后才知道是这个定时器并没有启动、那个DAC并没有激活。如果是因为某个外设有多种启动方式,至少可以把不同的启动方式注释后加入函数中供菜鸟们选择。让STM32CUBE MX更“傻瓜”点不是更好吗?呵呵!



         运行结果
   现在,PA4可以输出1KHZ正弦波了,而主芯片在运行完外设初始化后竟然没有消耗任何资源在这个DAC上,相比采用PWM输出正弦波更具优势。不错不错!











哈佛祖安智 发表于 2017-2-26 20:39:29

好快呀呀呀

wenyangzeng 发表于 2017-2-26 20:40:43

本帖最后由 wenyangzeng 于 2017-2-27 07:05 编辑

哈佛祖安智 发表于 2017-2-26 20:39
好快呀呀呀
:)。。。。

Paderboy 发表于 2017-2-27 08:51:23

恭喜恭喜。。。:loveliness:

Cube配置后都需要人工启动对应的函数。。。默认都是配置不工作。。

fengchao989 发表于 2017-7-31 10:01:26

顺便试一下 uart10 能不能用?

wenyangzeng 发表于 2017-7-31 21:48:02

fengchao989 发表于 2017-7-31 10:01
顺便试一下 uart10 能不能用?

查官方手册可知,虚拟串口是通过USART3连接的,USART10无法直接通过RS232与PC机连接,必须经过TTL-RS232电路转换。


页: [1]
查看完整版本: STM32F413 Nucleo评测(DAC)