当前位置:   article > 正文

【GD32】AD9833模块 DDS模块 提供测试程序 正弦波/方波/三角波信号发生器

【GD32】AD9833模块 DDS模块 提供测试程序 正弦波/方波/三角波信号发生器

2.45 AD9833 DDS模块

2.45.1 模块来源

采购链接:
AD9833模块 DDS模块 提供测试程序 正弦波/方波/三角波信号发生器
资料下载:
https://pan.baidu.com/s/1JZ0ga4uTyXUq5u-Or9BVlg?pwd=GOOD
提取码:GOOD

2.45.2 规格参数
工作电压:2.3 V至5.5 V电源供电
工作电流:12.65 mW(3 V时)
通信方式:3线SPI接口
芯片引脚数量:10引脚MSOP封装
2.45.3 移植过程
我们的目标是在梁山派GD32F470上能够通过模块输出波形的功能。首先要获取资料,查看数据手册应如何实现,再移植至我们的工程。
2.45.3.1 查看资料
模块作用:
可编程波形发生器,能够产生正弦 波、三角波和方波输出。各种类型的检测、信号激励和时 域反射(TDR)应用都需要波形发生器。输出频率和相位可 通过软件进行编程,调整简单。无需外部元件。频率寄存 器为28位:时钟速率为25 MHz时,可以实现0.1 Hz的分辨 率;而时钟速率为1 MHz时,则可以实现0.004 Hz的分辨率。
模块驱动:
AD9833通过一个三线式串行接口写入数据。该串行接口能 够以最高40 MHz的时钟速率工作,并且与DSP和微控制器 标准兼容。该器件采用2.3 V至5.5 V电源供电。注意:在生成方波时会过冲(可以在加入电源滤波电路缓解但不能彻底解决!!!)
2.45.3.2 引脚选择
在这里插入图片描述
2.45.3.3 移植至工程
移植步骤中的导入.c和.h文件与上一节相同,只是将.c和.h文件更改为AD9833.c与ccd.h。见2.2.3.3 移植至工程。这里不再过多讲述。移植完成后面修改相关代码。
在文件AD9833.c中,编写如下代码。

 /********************************************************************************
   * 测试硬件:立创·梁山派开发板GD32F470ZGT6    使用主频200Mhz    晶振25Mhz
   * 版 本 号: V1.0
   * 修改作者: LCKFB
   * 修改日期: 2023年06月12日
   * 功能介绍:      
   ******************************************************************************
 
 *********************************************************************************/

#include "AD9833.h"
#include "gd32f4xx.h"


/******************************************************************
 * 函 数 名 称:Ad9833GpioConfig
 * 函 数 说 明:Ad9833的初始化
 * 函 数 形 参:无
 * 函 数 返 回:无
 * 作       者:LC
 * 备       注:软件SPI的配置
******************************************************************/
void AD9833_GpioConfig(void)
{
        rcu_periph_clock_enable(RCU_SDATA);     //使能SDATA引脚时钟
    rcu_periph_clock_enable(RCU_SCLK);      //使能SCLK引脚时钟
    rcu_periph_clock_enable(RCU_FSNYC);     //使能FSNYC引脚时钟
    
    //配置SDATA为上拉推挽输出
    gpio_mode_set(PORT_SDATA, GPIO_MODE_OUTPUT, GPIO_PUPD_PULLUP, GPIO_SDATA);        
    gpio_output_options_set(PORT_SDATA, GPIO_OTYPE_PP, GPIO_OSPEED_50MHZ, GPIO_SDATA);
    //输出高电平
    gpio_bit_set(PORT_SDATA, GPIO_SDATA); 

    //配置SCLK为上拉推挽输出
        gpio_mode_set(PORT_SCLK, GPIO_MODE_OUTPUT, GPIO_PUPD_PULLUP,  GPIO_SCLK);        
    gpio_output_options_set(PORT_SCLK, GPIO_OTYPE_PP, GPIO_OSPEED_50MHZ,  GPIO_SCLK); 
    //输出高电平
    gpio_bit_set(PORT_SCLK,  GPIO_SCLK); 

    //配置FSNYC为上拉推挽输出
        gpio_mode_set(PORT_FSNYC, GPIO_MODE_OUTPUT, GPIO_PUPD_PULLUP, GPIO_FSNYC);       
    gpio_output_options_set(PORT_FSNYC, GPIO_OTYPE_PP, GPIO_OSPEED_50MHZ, GPIO_FSNYC); 
    //输出高电平
    gpio_bit_set(PORT_FSNYC, GPIO_FSNYC);         
}
     


/******************************************************************
 * 函 数 名 称:AD9833_WriteData
 * 函 数 说 明:向AD9833写入16位数据
 * 函 数 形 参:txdata=写入的16位数据
 * 函 数 返 回:无
 * 作       者:LC
 * 备       注:FSNYC低电平有效,数据在时钟的下降沿被采集数据,在时钟的上升沿更新数据
******************************************************************/
void AD9833_WriteData(uint16_t txdata)
{
    int i;
    ADI_FSNYC_OUT(1);
    
    ADI_SCLK_OUT(0);
    ADI_SCLK_OUT(1);
    
    ADI_FSNYC_OUT(0);
    //写16位数据
    for(i=0;i<16;i++)
    {  
        if (txdata & 0x8000)
        {
           ADI_SDATA_OUT(1);
        }
        else
        {
            ADI_SDATA_OUT(0);
        }
        ADI_SCLK_OUT(0);
        txdata<<=1;
        ADI_SCLK_OUT(1);
        
    }
    ADI_FSNYC_OUT(1);
}
/******************************************************************
 * 函 数 名 称:AD9833_SetFrequency
 * 函 数 说 明:ad9833设置频率寄存器
 * 函 数 形 参:reg=待写入的频率寄存器  fout=频率值
 * 函 数 返 回:无
 * 作       者:LC
 * 备       注:无
******************************************************************/
void AD9833_SetFrequency(unsigned short reg, double fout)
{
    int frequence_LSB=0, frequence_MSB=0;
    double   frequence_mid=0, frequence_DATA=0;
    long int frequence_hex=0;
    /*********************************计算频率的16进制值***********************************/
    //如果时钟频率不为25MHZ,修改该处的频率值,单位MHz ,AD9833最大支持25MHz
    frequence_mid = 268435456/25;//适合25M晶振
    frequence_DATA = fout;
    frequence_DATA = frequence_DATA/1000000;
    frequence_DATA = frequence_DATA*frequence_mid;
    frequence_hex = frequence_DATA;         //这个frequence_hex的值是32位的一个很大的数字,需要拆分成两个14位进行处理;
    frequence_LSB = frequence_hex;          //frequence_hex低16位送给frequence_LSB
    frequence_LSB = frequence_LSB&0x3fff;   //去除最高两位,16位数换去掉高位后变成了14位
    frequence_MSB = frequence_hex>>14;      //frequence_hex高16位送给frequence_HSB
    frequence_MSB = frequence_MSB&0x3fff;   //去除最高两位,16位数换去掉高位后变成了14位
    frequence_LSB = frequence_LSB|reg;
    frequence_MSB = frequence_MSB|reg;
    AD9833_WriteData(0x2100);               //选择数据一次写入,B28位和RESET位为1
    AD9833_WriteData(frequence_LSB);
    AD9833_WriteData(frequence_MSB);
}

/******************************************************************
 * 函 数 名 称:AD9833_SetPhase
 * 函 数 说 明:ad9833设置相位寄存器
 * 函 数 形 参:reg=待写入的相位寄存器    fout=相位值  
 * 函 数 返 回:无
 * 作       者:LC
 * 备       注:无
******************************************************************/
void AD9833_SetPhase(unsigned short reg, unsigned short val)
{
    unsigned short phase = reg;
    phase |= val;
    AD9833_WriteData(phase);
}

/******************************************************************
 * 函 数 名 称:AD9833_SetWave
 * 函 数 说 明:ad9833设置波形
 * 函 数 形 参:WaveMode=输出波形类型 
 *              Freq_SFR=输出的频率寄存器类型
 *              Phase_SFR=输出的相位寄存器类型
 * 函 数 返 回:无
 * 作       者:LC
 * 备       注:无
******************************************************************/
void AD9833_SetWave(unsigned int WaveMode,unsigned int Freq_SFR,unsigned int Phase_SFR)
{
    unsigned int val = 0;
    val = (val | WaveMode | Freq_SFR | Phase_SFR);
    AD9833_WriteData(val);
}

/******************************************************************
 * 函 数 名 称:AD9833_Setup
 * 函 数 说 明:设置ad9833的输出
 * 函 数 形 参:Freq_SFR =  频率寄存器类型
 *              Freq     =  频率值
 *              Phase_SFR=  相位寄存器类型
 *              Phase    =  相位值
 *              WaveMode =  波形类型
 * 函 数 返 回:无
 * 作       者:LC
 * 备       注:无
******************************************************************/
void AD9833_Setup(unsigned int Freq_SFR,double Freq,unsigned int Phase_SFR,unsigned int Phase,unsigned int WaveMode)
{
    unsigned int Fsel,Psel;
    AD9833_WriteData(0x0100); //复位AD9833,即RESET位为1
    AD9833_WriteData(0x2100); //选择数据一次写入,B28位和RESET位为1
    AD9833_SetFrequency(Freq_SFR,Freq);
    AD9833_SetPhase(Phase_SFR,Phase);
    if(Freq_SFR == AD9833_REG_FREQ0)
    {
        Fsel = AD9833_FSEL0;
    }
    else 
    {
        Fsel = AD9833_FSEL1;
    }
    if(Phase_SFR == AD9833_REG_PHASE0)
    {
        Psel = AD9833_PSEL0;
    }
    else 
    {
        Psel = AD9833_PSEL1;
    }
    AD9833_SetWave(WaveMode,Fsel,Psel);
}

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97
  • 98
  • 99
  • 100
  • 101
  • 102
  • 103
  • 104
  • 105
  • 106
  • 107
  • 108
  • 109
  • 110
  • 111
  • 112
  • 113
  • 114
  • 115
  • 116
  • 117
  • 118
  • 119
  • 120
  • 121
  • 122
  • 123
  • 124
  • 125
  • 126
  • 127
  • 128
  • 129
  • 130
  • 131
  • 132
  • 133
  • 134
  • 135
  • 136
  • 137
  • 138
  • 139
  • 140
  • 141
  • 142
  • 143
  • 144
  • 145
  • 146
  • 147
  • 148
  • 149
  • 150
  • 151
  • 152
  • 153
  • 154
  • 155
  • 156
  • 157
  • 158
  • 159
  • 160
  • 161
  • 162
  • 163
  • 164
  • 165
  • 166
  • 167
  • 168
  • 169
  • 170
  • 171
  • 172
  • 173
  • 174
  • 175
  • 176
  • 177
  • 178
  • 179
  • 180
  • 181
  • 182
  • 183
  • 184
  • 185

在文件AD9833.h中,编写如下代码。

 /********************************************************************************
    * 测试硬件:立创·梁山派开发板GD32F470ZGT6    使用主频200Mhz    晶振25Mhz
    * 版 本 号: V1.0
    * 修改作者: LCKFB
    * 修改日期: 2023年06月12日
    * 功能介绍:      
    ******************************************************************************

  *********************************************************************************/
#ifndef _AD9833_H__
#define _AD9833_H__

#include "GD32F4XX.h"


//引脚定义
#define RCU_SDATA   RCU_GPIOD
#define PORT_SDATA  GPIOD
#define GPIO_SDATA  GPIO_PIN_5

#define RCU_SCLK    RCU_GPIOD
#define PORT_SCLK   GPIOD
#define GPIO_SCLK   GPIO_PIN_4

#define RCU_FSNYC   RCU_GPIOD
#define PORT_FSNYC  GPIOD
#define GPIO_FSNYC  GPIO_PIN_1


//端口输出
#define  ADI_SDATA_OUT(X)       gpio_bit_write(PORT_SDATA, GPIO_SDATA, (X)?SET:RESET) 
#define  ADI_SCLK_OUT(X)        gpio_bit_write(PORT_SCLK, GPIO_SCLK, (X)?SET:RESET) 
#define  ADI_FSNYC_OUT(X)       gpio_bit_write(PORT_FSNYC, GPIO_FSNYC, (X)?SET:RESET) 

//输出波形
#define AD9833_OUT_SINUS    ((0 << 5) | (0 << 1) | (0 << 3))    //正弦波
#define AD9833_OUT_TRIANGLE ((0 << 5) | (1 << 1) | (0 << 3))    //三角波
#define AD9833_OUT_MSB      ((1 << 5) | (0 << 1) | (1 << 3))    //方波
#define AD9833_OUT_MSB2     ((1 << 5) | (0 << 1) | (0 << 3))    //方波

//相关寄存器
#define AD9833_REG_CMD      (0 << 14)
#define AD9833_REG_FREQ0    (1 << 14)
#define AD9833_REG_FREQ1    (2 << 14)
#define AD9833_REG_PHASE0   (6 << 13)
#define AD9833_REG_PHASE1   (7 << 13)

//命令控制位
#define AD9833_B28          (1 << 13)
#define AD9833_HLB          (1 << 12)
#define AD9833_FSEL0        (0 << 11)
#define AD9833_FSEL1        (1 << 11)
#define AD9833_PSEL0        (0 << 10)
#define AD9833_PSEL1        (1 << 10)
#define AD9833_PIN_SW       (1 << 9)
#define AD9833_RESET        (1 << 8)
#define AD9833_CLEAR_RESET  (0 << 8)
#define AD9833_SLEEP1       (1 << 7)
#define AD9833_SLEEP12      (1 << 6)
#define AD9833_OPBITEN      (1 << 5)
#define AD9833_SIGN_PIB     (1 << 4)
#define AD9833_DIV2         (1 << 3)
#define AD9833_MODE         (1 << 1)

//函数声明
void AD9833_GpioConfig(void);
void AD9833_WriteData(uint16_t txdata);
void AD9833_SetFrequency(unsigned short reg, double fout);
void AD9833_SetPhase(unsigned short reg, unsigned short val);
void AD9833_SetWave(unsigned int WaveMode,unsigned int Freq_SFR,unsigned int Phase_SFR);
void AD9833_Setup(unsigned int Freq_SFR,double Freq,unsigned int Phase_SFR,unsigned int Phase,unsigned int WaveMode);

#endif

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74

2.45.4 移植验证

在自己工程中的main主函数中,编写如下。

 /********************************************************************************
   * 测试硬件:立创·梁山派开发板GD32F470ZGT6    使用主频200Mhz    晶振25Mhz
   * 版 本 号: V1.0
   * 修改作者: LCKFB
   * 修改日期: 2023年06月12日
   * 功能介绍:      
   ******************************************************************************
 *********************************************************************************/
#include "gd32f4xx.h"
#include "systick.h"
#include <stdio.h>
#include "main.h"
#include "sys.h"
#include "bsp_usart.h"
#include "AD9833.h"

int main(void)
{       
    systick_config();        
    usart_gpio_config(115200U);    
    AD9833_GpioConfig();
    while(1) 
    {
        //输出 2K 三角波
        AD9833_Setup(AD9833_REG_FREQ0,2000.0,AD9833_REG_PHASE1,1024,AD9833_OUT_TRIANGLE);
        delay_1ms(2000);
        delay_1ms(2000);
        delay_1ms(2000);     
        delay_1ms(2000);     

        //输出 50K 正弦波
        AD9833_Setup(AD9833_REG_FREQ0,50000.0,AD9833_REG_PHASE1,1024,AD9833_OUT_SINUS);
        delay_1ms(2000);
        delay_1ms(2000);     
        delay_1ms(2000);     
        delay_1ms(2000);     

        //输出 1M 方波
        AD9833_Setup(AD9833_REG_FREQ0,1000000.0,AD9833_REG_PHASE1,1024,AD9833_OUT_MSB);
        delay_1ms(2000);
        delay_1ms(2000);     
        delay_1ms(2000);     
        delay_1ms(2000);               
    }
}

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46

移植现象:该实例是产生一个2KHZ的三角波,8秒后产生50K正弦波,8秒后再产生1M方波,将探头连接到示波器上观察!!注意:生成方波有过冲是正常现象。
在这里插入图片描述
在这里插入图片描述
移植成功示例,见文件2.45.4-1

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/AllinToyou/article/detail/540069
推荐阅读
  

闽ICP备14008679号