一乐电子

一乐电子百科

 找回密码
 请使用微信账号登录和注册会员

QQ登录

只需一步,快速开始

快捷登录

手机号码,快捷登录

搜索
楼主: xjw01
收起左侧

stm32怎么学

  [复制链接]
 楼主| 发表于 2012-12-4 18:45 | 显示全部楼层
刚吃完饭,又调试,终于找到原因:
忘了打开DMA钟源
发表于 2012-12-5 21:54 | 显示全部楼层
哦 stm32  ---我这只会几句汇编的就杯具了, 不打算跟这潮流了, 不是吃这碗饭的 没一点基础,不再自寻烦恼 ,还是坐等欣赏大家的作品惬意。
 楼主| 发表于 2012-12-7 22:47 | 显示全部楼层
仿STC的LCR程序,用PWM生成正弦波。
stm32频率高,且PWM分辨力也高,生成正弦波的质量比原来的好很多。

/************************
实验目标:
生成正弦波
*************************/
#include "stm32f10x.h"
#include "math.h"
//================================================================
//========================常用函数================================
//================================================================
void delay(u32 n){ u32 i; for(i=0;i<n;i++); } //延时
void PAinit(u16 n,GPIOMode_TypeDef mo){//PA端口设置
  //GPIO_Mode_IPU 上拉输入
  //GPIO_Mode_IPD 下拉输入
  //GPIO_Mode_Out_PP 推挽输出
  GPIO_InitTypeDef g;
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);  //PA钟源
  g.GPIO_Speed = GPIO_Speed_50MHz; //端口速度
  g.GPIO_Mode = mo;                //端口模式
  g.GPIO_Pin =  n;                //脚位
  GPIO_Init(GPIOA, &g);
}
void PBinit(u16 n,GPIOMode_TypeDef mo){//PB端口设置
  GPIO_InitTypeDef g;
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE);  //PB钟源
  g.GPIO_Speed = GPIO_Speed_50MHz; //端口速度
  g.GPIO_Mode = mo;                //端口模式
  g.GPIO_Pin =  n;                //脚位
  GPIO_Init(GPIOB, &g);
}
//================================================================
//=========================dds函数================================
//================================================================
u16 DDSbuf[2400] = {0};
void DDS_cnf(int f) //f=DDS输出频率
{
//DDS时钟=72MHz/m,输出频率=72MHz/m/n
u16 m = 1000,n =3,i;
if(f==10000) m=40, n=180;  //分频参数
if(f==1000)  m=200,n=360;  //分频参数
if(f==100)   m=300,n=2400; //分频参数
for(i=0;i<n;i++) //创建DDS查询表
   DDSbuf[i] = (sin(2*3.1415926535*i/n)+1)*(m-2)/2+1.5;
{//端口及钟源设置
  RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA1, ENABLE);     //DMA钟源
  RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);   //TIM3钟源
  PAinit(GPIO_Pin_6, GPIO_Mode_AF_PP); //TM3 CH1脚位是PA6,置为复用推挽输出
}
{//DMA设置,详见函数库手册第90页解释
  DMA_InitTypeDef D;
  DMA_DeInit(DMA1_Channel3); //DMA1_3通道初始化
  D.DMA_PeripheralBaseAddr = 0x40000434;           //DMA外设基址 TIM3_CCR1_Address
  D.DMA_MemoryBaseAddr = (u32)DDSbuf;              //DMA内存基址
  D.DMA_DIR = DMA_DIR_PeripheralDST;               //DST:外设作为数据传送目的地址,SRC:外设作为传送源地址
  D.DMA_BufferSize = n;                            //DMA缓存大小
  D.DMA_PeripheralInc = DMA_PeripheralInc_Disable; //外设地址寄存器不自增
  D.DMA_MemoryInc = DMA_MemoryInc_Enable;          //内存地址寄存器自增
  D.DMA_PeripheralDataSize = DMA_PeripheralDataSize_HalfWord; //外存字宽16bit
  D.DMA_MemoryDataSize = DMA_MemoryDataSize_HalfWord;       //内存字宽16bit
  D.DMA_Mode = DMA_Mode_Circular;   //工作在循环模式
  D.DMA_Priority = DMA_Priority_High; //DMA置为高优先级
  D.DMA_M2M = DMA_M2M_Disable;    //不置为内存到内存传输
  DMA_Init(DMA1_Channel3, &D);    //初始化DMA1
  DMA_Cmd(DMA1_Channel3, ENABLE);     //DMA1_3使能
}
{//定时器设置
  TIM_TimeBaseInitTypeDef  tm;
  TIM_OCInitTypeDef  tc;
  tm.TIM_Period = m-1;      //当定时器从0计数到m-1,即为m次,为一个定时周期
  tm.TIM_Prescaler = 0;     //设置预分频:不预分频,即为36MHz
  tm.TIM_ClockDivision = 0; //设置时钟分频系数:不分频
  tm.TIM_CounterMode = TIM_CounterMode_Up;  //向上计数模式
  TIM_TimeBaseInit(TIM3, &tm); //初始化TIM3
  //PWM通道1模式设置
  tc.TIM_OCMode = TIM_OCMode_PWM1;         //配置为PWM模式1
  tc.TIM_OutputState = TIM_OutputState_Enable;
  tc.TIM_Pulse = DDSbuf[0];                 //设置跳变值,当计数器计数到这个值时,电平发生跳变
  tc.TIM_OCPolarity = TIM_OCPolarity_High;  //当定时器计数值小于CCR1_Val时为高电平
  TIM_OC1Init(TIM3, &tc);                   //初始化TIM3的通道1
  TIM_DMACmd(TIM3, TIM_DMA_Update, ENABLE); //TIM3 DMA请求使能,注:TIM3_Update请求对应DMA1_chanel3通道
  TIM_Cmd(TIM3, ENABLE); //TIM3使能
}
}

        
int main(void)
{
  u8 kn=0,bk=0;
  SystemInit();  //配置系统时钟为72MHz
  PAinit(GPIO_Pin_0, GPIO_Mode_IPU); //PA0置为上拉输入
  DDS_cnf(100);  //设置DDS输出
  while (1){
    if((GPIOA->IDR&1)==0) { if(kn<255) kn++; }
else kn=0;
if(kn==3){
   bk=(bk+1)%3;
   if(bk==0) DDS_cnf(100);
   if(bk==1) DDS_cnf(1000);
   if(bk==2) DDS_cnf(10000);
}
    delay(10000);
  }
}
 楼主| 发表于 2012-12-7 22:59 | 显示全部楼层
本帖最后由 xjw01 于 2012-12-7 23:02 编辑

回复 82# 老弹弓


    stm32与STC12C5A60S2单片机,写程序不会相差很多。

主要不同:stm32的端口、模块使用之前要打开时源、参数也多一些,比较啰嗦。所以,写stm32之间,要更加耐心写好各模块的模板函数(相档于各模块的驱动程序)。
驱动程序写好之后,接下来的编程就与STC并不多了,而且比STC更简单,因为STC内存多、速度快,编程比较自如,受约束小,算法上不必斤斤计较。
STC写程序之前,也要写各模块的驱动程序的。

直接网上拷备的模块的模板(驱动程序),通常不合你用,得修改、优化一下。
发表于 2012-12-9 16:17 | 显示全部楼层
回复 25# 199003326

STC的便宜吧
发表于 2013-1-11 13:00 | 显示全部楼层
回复 20# DF2012


    普及下!STM32是12bitadc,1通道16输入端口。
发表于 2013-3-29 16:59 | 显示全部楼层
学习了!!!
发表于 2013-5-19 15:55 | 显示全部楼层
学习下!
发表于 2013-5-22 11:20 | 显示全部楼层
潜水学习
发表于 2017-1-31 17:09 | 显示全部楼层
fujiachun 发表于 2012-11-29 08:55
从51过渡到STM32以您的水平估计就两三天的事情,这个平滑过渡很容易。
如果用建议用STM32F103这个档位的芯 ...

F版新年快乐,F版能提供下正交采样相关的资料么?

另外一个不解的是:10倍的ADC采样,如果是100K,也就是1M,采样100KHZ,一个周期只有10个点,做相位和幅度计算好像不够吧?



本版积分规则

QQ|一淘宝店|手机版|商店|电子DIY套件|一乐电子 ( 粤ICP备09076165号 ) 公安备案粤公网安备 44522102000183号

GMT+8, 2024-4-29 10:32 , Processed in 0.047663 second(s), 30 queries , Gzip On.

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

快速回复 返回顶部 返回列表