单片机论坛

 找回密码
 立即注册

QQ登录

只需一步快速开始

搜索
查看: 350|回复: 0
打印 上一主题 下一主题
收起左侧

LPC2000系列ARM芯片的电子琴的设计

[复制链接]
跳转到指定楼层
楼主
nicer152 发表于 2019-6-24 16:03 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
1用LPC2000系列ARM芯片设计电子琴用proteus软件仿真
2按下不同的按键扬声器能够发出不同的音调
3用Уף控制扬声器可以实现音调的条件

通过编程利用按键去控制扬声器的发声
    通过小组讨论分析结合设计电路阅指标器件的性价比本设计电路选择方案二
  • 硬件设计与介绍
嵌入式的定义
从技术的嵌定义以应用为中心以计算机技术为基础软件硬件可裁剪视应用系统对功能可靠性成本体积功耗细要求的专用计算机系统
    从系统的嵌定义嵌入式系统是设计完成复杂功能的硬件和软件并使其紧密耦合在一起的计算机系统术语嵌入式从了这些系统通常是更大系统中的一个完整的部分称为嵌入的系统嵌入的系统中可以共存多个嵌入式系统
     3.1 213X系列最小系统板介绍
LPC2131/2132/2138 是基于一个支持实时仿真和嵌入式跟踪的32/16ARM7TDMI-STM CPU 的微控制器并带有32kB64kB512 kB 的嵌入的高速Flash 存储器128 位宽度的存储器接口和独特的加速结构使32 位代码能够在最大时钟速率下运小对代码规模有细控制的应用可使用16 位Thumb模式将代码规模降统过30%而阅的损失却很小
较小的封装和极低的功耗使 LPC2131/2132/2138 可理想地用于小型系统中如访问控制和POS 机宽范围的串行通信接口和片内8/16/32kB的SRAM使LPC2131/2132/2138 非常适用于通信网关协议转换器软modem声音辨别和低端上为它们提供巨大的缓冲区空间和看的处理功能多个32位定时器1个或2 个10 位8 路ADC10 位DACPWM 通道和47个GPIO 以及多达9个边沿或电平触发的外部中断使它们特别适用于工业控制和医疗系统
主要特性如下
116/32位ARM7TDMI-S核超小LQFP64封装  ??
28/16/32kB的片内静态RAM和32/64/128/256/512kB的片内Flash程序存储器128位宽度接口/加速器可实指达60MHz工作频率  ??
3通过片内boot装载程序实现在系统编程/在应用编程ISP/IAP单个Flash扇区或整片擦除时间 为400ms256字节行编程时间为1ms  ??
4EmbeddedICE RT和嵌入式跟踪接口通过片内RealMonitor软件对代码进行实时调试和高速跟踪 ??
51个LPC2131/32或2个LPC2134/36/388路10位的A/D转换器共提供16路模拟输入每个通道的转换时间低至2.44us  ??
61个10位的D/A转换器可产生不同的模拟输出LPC2132/34/36/38  ?? 72个32位定时器/外部录计数器带4路捕获和4路比较通道PWM单元6路输出和看门狗  ??
8低功耗实时时钟具有独立的电源和特定的32kHz时钟输入  ??
9多个串行接口包括2个16C550工当准UART2个高速I2C总线400 kbit/sSPI和具有缓冲作用和数据长度可变功能的SSP ??
10向量中断控制器可配置优先级和向量地址  ??
11小型的LQFP64封装上包含多达47个通用I/O口可承受5V电压 ?? 12多达9个边沿或电平触发的外部中断管脚  ??
13通过片内PLL100us的设置时间可实现最大为60MHz的CPU操作频率  ??
14片内集成振荡器与外部晶体的操作频率范围为130 MHz与外部振荡器的操作频率范围高达 50MHz  ??
15低功耗模式空闲和掉电  ??
16可通过个别使能/禁止外部功能和外围时钟分频从化功耗 ??
17通过外部中断或BOD将处理器从掉电模式中唤选 ??
18单电源具有系复位POR和掉电检测BOD电路  ??
19CPU操作电压范围3.0V3.6 V (3.3 V 10)I/O口可承受5V的电压
3.2最小系统板结构
    LPC2131/2132/2138 包含一个支址真的ARM7TDMI-S CPU与片内存储器控制器接口的ARM7 局部总线与中断控制器接口的AMBA 高阅总线AHB和连接片内外设功能的VLSI 外设总线VPBARMAMBA 总线的兼容超集LPC2131/2132/2138 将ARM7TDMI-S 配置为小端little-endian字节顺序AHB 外设分配了2M 字节的地址范围它位于4G 字节ARM 存储器空间的最顶端每个AHB 外设都分配了16k 字节的地址空间LPC2131/2132/2138 的外设功能中断控制器除外都连接到VPB 总线AHB到VPB 的桥将VPB 总线与AHB 总线相连VPB 外设也分配了2M 字节的地址范围从3.5GB 地返开始每个VPB 外设在VPB 地址空间内都分配了16k 字节地址空间
片内外设与器件管脚的连接由管脚连接模块控制该模块必须由软件进行控制以符合外设功能与管脚在特定应用中的需求
3.3 片内FLASH程序储存器
LPC2131/2132/2138 分别含有32kB64kB 和512kB 的FLASH 存储器系统该存储器可用作代码和数据的存储对FLASH 存储器的编程可通过几址法来实现通过内置的串行JTAG 接口通过在系统编程ISP和UART0或通过在应用编程IAP使用在应用编程的应用程序也可以在应用程序运行时对FLAH 进行擦除和/或编程这样就为数据存储和现场固件的升级即来了极大的灵活性如果LPC2131/2132/2138 使用了片内引导装载程序bootloader32/64/512kB 的Flash 存储器就可用来存放用户代码
LPC2131/2132/2138 的Flash 存储器至少可擦除/编程10,000 次保存数据的时间长达10 年
3.4 片内静态RAM
片内静态RAMSRAM可用作代码和/或数据的存储支持8 位16 位和32 位的访问LPC2131/2132/2138 含有8/16/32kB 的静态RAM
LPC2131/2132/2138 SRAM 是一个字节寻址的存储器对存储器进行字和半字访问时将忽略地址对准访问被寻址的自然对准值因此对存储器进行字访问时将忽略地址位0 和1半字访问时将忽略地址位0
因此有效的列操作要求半字数据访问的地址线0 为0地址以02468AC 和E 结尾字数据访问的地址线0 和1 都为0地址以048 和C 结尾该原则同样用于片外和片内存储器
SRAM 控制器包含一个回写缓冲区它用于防止CPU 在连续的写操作时停止运小回写缓冲区总是保存着软件发送到SRAM 的最后一个字节该数据只有在软件请求下一次写操作时才写入SRAM数据只有在软件执行另外一次写操作时被写入SRAM如果发生芯片复位导的SRAM 内容将换从最近一次的写请求即在一次热芯片复位后SRAM 换从最后一次写入的内容任何在复位后检查SRAM 内容的程序都必须注意这一点通过对一个单元执行两次相同的写操作可保证复位后数据的写入或者也可通过在进入空闲或掉电模式前执行虚写dummy write操作来保证最后的数据在复位后被真正写入到SRAM
3.5 存储器成概念和操作方式
LPC2131/2132/2138 的基本的概念是每个存储器组在存储器成中都有一个物理系ġ位置它是一个地址范围该范围内可写入程序代码每一个存储器空间的容量加久固定在同一个位置这样就不需要将代码设计成在不同地址范围内运小
由于ARM7 处理器系中断向量位置地址0x0000 0000~0x0000 001C见表2Boot Block 和SRAM空间的一小部分需要重新成来实现在不同操作模式下对中系使用见表1中系重新成通过存储器成控制特性来实现详见系统控制模块一节
表1LPC2131/2132/2138 存储器成模式
模式
激活
用途
Boot装载程序模式
扇何复位硬件激活
在任何复位后都会执行 Boot 装载程序Boot Block 中断向量成到存储器的底部以允许处理异常并在Boot 装载过程中使用中断
用户Flash模式
由Boot代码软件激活
当在存储器中识别了一个有效的用户程序标识并且Boot 装载操作未被执行时由Boot 装载程序启动中断向量没有重新成䣬它位于Flash 存储器的底部
用户RAM模式
由用户程序软件激活
由用户程序激活中断向量重新成到静态 RAM 的底部
3.6 系统控制模块
系统控制模块功能汇总
系统控制模块包括几个系程性和控制寄存器这些寄存器具有众多与特定外设器件无关的功能
1晶体振荡器
2外部中断输入
3存储器成控制
4PLL
5功率控制
6复位
7VPB 分频器
8唤醒定时器
每种类型的功能都有其自身的寄存器不需要的位则定义为保留位为了满足将来扩展的需要无关/的功能不共用相同的寄存器地址
表2系统控制模块功能相关的管脚
管脚名称
管脚方向
管脚描述
X1
输入
晶振输入--振荡器和内部时钟发生器电路的输入
X2
输出
晶振输出--振荡器放大器的输出
EINT0
输入
外部中断输入0--低有效的通用中断输入该管脚可用于将处理器从空闲或掉电模式中唤选
P0.1和P0.16可用作EINT0 功能
EINT1
输入
外部中断输入1--见上面的EINT0 描述
P0.3 和P0.14可用作EINT1 功能
复位后管脚 P0.14上立即出现的低电奖看作是一个启动ISP 命令处理器的外部硬件请求
EINT2
输入
外部中断输入2--见上面的EINT0 描述
P0.7 和P0.15 可用作EINT2 功能
EINT3
输入
外部中断输入3--见上面的EINT0 描述
P0.9,P0.20和P0.30可用作EINT3 功能
RESET
输入
外部复位输入--该管脚系低电平将芯片复位使I/O 口和外设恢复其默献态并使处理器从地址0 开始执行程序
                      图3.1 LPC2138管脚排列图
  3.7 行列式键盘工作原理
ARM嵌入式系统使用常用的行列式键盘电路此电路的优点是比较节省I/0口线并且接口简单它的工作模式如下图所示它的行线与按键的一个引脚相连列线与按键的另一个引脚相连平时列线被置成低电平没有按键被按下时行线保指电平而有按键被按下时行线被拉成低电平如图3.2



图3.2 键盘扫描模式
  3.8 键盘识别原理
对于常规的按键识别过程一般分为以录步
1用IF语句判断按键是否按下
2调用延时函数延时去除按键抖动
3再用IF语句判断是否真的按下
4是真的按下则执行按键处理程序
5用WHILE语句却按键释放
为了考虑提高CPU的效率统分利用CPU的资源等因素可将第2步和第5步的延时和却过程用其他方式代替
  3.9键盘电路介绍
为了实现电子琴的输入需要扩展键盘以作为控制输入系统采用LPC2138的P0.8--P0.13端口引脚作为2X4矩阵键盘的扩展接口电路原理图如图3.3所示
                       图 3.3 键盘电路

在扩展键盘时需要解决两个问题一是键盘的抖动二嵌键同时按下键盘的去抖动可通过软件的适当延时实现即在读入端口P0.8~P0.11后适当延币问间再读入端口P0.12~P0.13两次比较后确定按键是否真按得下多键同时按下也可通过软件设计屏蔽多按下的键对于同一列的键同时按下可以只取键值最小的键屏蔽值大的键或反之对于不同列的键可以将P0.12~P0.13设置优先级如P0.12最高P0.13最低或反之这样只取优先级高的键屏蔽优先级低的键
在ARM中必须将管脚置为GPIO口后才能将管脚作为I/O口的功能来使用由于在I/O的初始化中已经将用到的管脚设置为GPIO口固可以将管脚作为I/O口的功能来使用具体方法如下
先将P0.8-P0.11这4列端口设置为输入管脚并且置为低电平然后将P0.12-P0.13这2行端口设置为输出管脚并且置为高电平通过判断是否有按键按下如果有按键按下则可以首先确定2行端口的代码接着再将4列端口设置为输出管脚并且置为高电平将2行端口设置为输入管脚并且置为低电平以此来决定4列端口的代码然后再讲4列端口代码和2行端口代码按照2行为高4位4列为低4位的顺序排成一个8位代码
3.10 蜂鸣器驱动电路分析
   蜂鸣器驱动电路分析如下
   蜂鸣器发声元件在其两端施加直流电压有源蜂鸣器或者方波无源蜂鸣器就可以发声其主要问是外形尺寸发声方向工作电压工作频率工作电流驱动方式直流/方波等这些都可以根据需要来选择
   续流二极管蜂鸣器本质上是一个感性元件其电流不能瞬变因此必须有一个续流二极管提供续流否则在蜂鸣器两端会产生几十伏的尖峰电压可能损登动三极管并扇整个电路系统的其它部分
   三极管驱动蜂鸣器电路三极管Q1起开关作用其基极的高电平使三极管饱和导通使蜂鸣器发声而基极低电平则使三极管关闭蜂鸣器停止发声如图3.4

                        图3.4导选用驱动放大电路

  3.11 整体电路图
       如图3.5所示
                      图3.5 硬件设计电路整体图
  • 软件设计
   1.程序流程图如图4.1所示
                      图4.1程序流程图
  2.软件设计程序代码如下
  1. /*******************************************************************************
  2. *File: Main.c
  3. *功能: 使用PWM6输出PWM信号,通过滤波电路实现DAC转换.由按键控制PWM占空比,每按一次
  4. *      按键将会改变一次PWM的占空比使蜂鸣器发出不同的音调
  5. *******************************************************************************/
  6. #include "config.h"
  7. #define   KEY1   0x00004000        /*P0.14引脚连接KEY1*/
  8. #define   KEY2   0x00000400        /*P0.10引脚连接KEY2*/
  9. #define   KEY3   0x00000800        /*P0.11引脚连接KEY3*/
  10. #define   KEY4   0x00001000        /*P0.12引脚连接KEY4*/
  11. #define   KEY5   0x00002000        /*P0.13引脚连接KEY5*/
  12. #define   KEY6   0x00008000        /*P0.15引脚连接KEY6*/
  13. #define   KEY7   0x00010000        /*P0.16引脚连接KEY7*/
  14. #define   KEY8   0x00020000        /*P0.17引脚连接KEY8*/

  15. /*******************************************************************************
  16. *名称: WaitKey()
  17. *功能: 却一个有效按键,有去抖功能
  18. *******************************************************************************/
  19. /*void WaitKey(void)
  20. { uint32 i;

  21.   while(1)
  22.   { while((IOPIN&KEY1)!=0);                 //却KEY1键按下
  23.     for(i=0;i<50;i++);                      //延时去抖
  24.     if((IOPIN&KEY1)==0)break;
  25.   }
  26.     while((IOPIN&KEY1)==0);                   //却KEY1键放开
  27. }*/
  28. void TargetInit(void);
  29. /*******************************************************************************
  30. *名称: main()
  31. *功能: 使用PWM6输出占空比可调的PWM波形
  32. *******************************************************************************/
  33. int main(void)
  34. { uint32  pwmdata;                        //PWM占空比控制变量
  35.   int i;
  36.   PINSEL0=0x00080000;                     //设置PWM6连接到P0.9引脚
  37.   PINSEL1=0x00000000;                     //其他引脚设置为GPIO
  38.   TargetInit();                           //PWM初始化
  39.   pwmdata=1382;
  40.   while(1)
  41.   {  PWMMR0=2765;                         //设置PWM周期
  42.      PWMMR6=pwmdata;                      //设置PWM占空比
  43.      PWMLER=0x41;                         //PWMMR0,PWMMR6锁存,更新PWM占空比
  44.     // WaitKey();                           //却按键

  45.     if(KEY1==0)
  46.                    { while((IOPIN&KEY1)!=0);                 //却KEY1键按下
  47.                   for(i=0;i<50;i++);                      //延时去抖
  48.                   if((IOPIN&KEY1)==0)break;
  49.                    }
  50.                   while((IOPIN&KEY1)==0);                   //却KEY1键放开
  51.                    pwmdata=100;                        //改变PWM占空比控制变量

  52.     if(KEY2==0)
  53.                    { while((IOPIN&KEY2)!=0);                 //却KEY2键按下
  54.                   for(i=0;i<50;i++);                      //延时去抖
  55.                   if((IOPIN&KEY2)==0)break;
  56.                    }
  57.                   while((IOPIN&KEY2)==0);                   //却KEY2键放开
  58.                    pwmdata=300;                        //改变PWM占空比控制变量
  59.                   
  60.     if(KEY3==0)
  61.                    { while((IOPIN&KEY3)!=0);                 //却KEY3键按下
  62.                   for(i=0;i<50;i++);                      //延时去抖
  63.                   if((IOPIN&KEY3)==0)break;
  64.                    }
  65.                   while((IOPIN&KEY3)==0);                   //却KEY3键放开
  66.                    pwmdata=500;                        //改变PWM占空比控制变量
  67.                   
  68.     if(KEY4==0)
  69.                    { while((IOPIN&KEY4)!=0);                 //却KEY4键按下
  70.                   for(i=0;i<50;i++);                      //延时去抖
  71.                   if((IOPIN&KEY4)==0)break;
  72.                    }
  73.                   while((IOPIN&KEY4)==0);                   //却KEY4键放开
  74.                    pwmdata=700;                        //改变PWM占空比控制变量  
  75.                   
  76.     if(KEY5==0)
  77.                    { while((IOPIN&KEY5)!=0);                 //却KEY5键按下
  78.                   for(i=0;i<50;i++);                      //延时去抖
  79.                   if((IOPIN&KEY5)==0)break;
  80.                    }
  81.                   while((IOPIN&KEY5)==0);                   //却KEY5键放开
  82.                    pwmdata=900;                        //改变PWM占空比控制变量
  83.                   
  84.               if(KEY6==0)
  85.                    { while((IOPIN&KEY6)!=0);                 //却KEY6键按下
  86.                   for(i=0;i<50;i++);                      //延时去抖
  87.                   if((IOPIN&KEY6)==0)break;
  88.                    }
  89.                   while((IOPIN&KEY6)==0);                   //却KEY6键放开
  90.                    pwmdata=1100;                        //改变PWM占空比控制变量
  91.                   
  92.     if(KEY7==0)
  93.                    { while((IOPIN&KEY7)!=0);                 //却KEY7键按下
  94.                   for(i=0;i<50;i++);                      //延时去抖
  95.                   if((IOPIN&KEY7)==0)break;
  96.                    }
  97.                   while((IOPIN&KEY7)==0);                   //却KEY7键放开
  98.                    pwmdata=1300;                        //改变PWM占空比控制变量   
  99.                   
  100.                   
  101.     if(KEY8==0)
  102.                    { while((IOPIN&KEY8)!=0);                 //却KEY8键按下
  103.                   for(i=0;i<50;i++);                      //延时去抖
  104.                   if((IOPIN&KEY8)==0)break;
  105.                    }
  106.                   while((IOPIN&KEY8)==0);                   //却KEY8键放开
  107.                    pwmdata=1500;                        //改变PWM占空比控制变量
  108.                        
  109.      if(pwmdata>=2764)pwmdata=0;
  110.   }
  111.   return(0);
  112. }
  113. //PWM初始化函数
  114.   void TargetInit(void)
  115. {
  116. PWMPR=0x00;                      //不分频
  117. PWMMCR=0x02;                     //设置PWMMR0匹配
  118.     PWMMR0=2765;                     //设置PWM周期
  119. PWMMR6=1382;                     //设置PWM占空比   
  120. PWMLER=0x41;                     //PWMMR0,PWMMR6锁存                                               PWMPCR=0x4000;                       //允许PWM单边输出
  121.     PWMTCR=0x09;                     //PWM使能
  122. }
复制代码


  • 系统的仿真与调试

   将编译好的十六制文件下载到proteus中的ARM芯片小
    第一次用软件调试时没有任何现象检查了好久终于发现了原来是有一个电源没有设置数值也没有标明电源的极性将其改为+3.3V时现象就出现了
来按下KEY1-KEY来发出不同音调的声音按下复位键系统回归到初始状态
    图5.1 为硬件设计电路整体图

                          图5.1 硬件设计电路整体图
  • 设计总结
此次嵌入式设计的主要内容基于LPC2000系列的高级电子琴设计它的主要功能是实现不同频率的音调输出因此要涉及到蜂鸣器的驱动电路按键的扫描程序最小系统电路的设计
刚开始时拿到这个设计的题目是还有点不知所措但通过上网查阅LPC213X系列最小系统板的相关资料学会了用proteus进行ARM仿真查找了一些以应用嵌入式ARM的仿真实例,分析各个实例的工作原理,将各个实例的有用模块综合运用得到本实训基于嵌入式ARM的高级电子琴设计的原理图,该图主要包括三个模块:2*4键盘PWM脉冲输出功率放大电路控制LPC213X系列最小系统板的P0.9口输出PWM脉冲发出不同频率使蜂鸣器发出不同的声音P0.9口外接功放电路连接蜂鸣器发声按键输入功能有8个输入首终确定采用2*4的矩阵键盘作为电子密码锁的键盘控制经过网上收集资料与同学之间的讨论终于明白了键盘扫描的工作原理和51单片机一样都是利用动态扫描原理最帐现了键盘输入的功能依靠程序完成大部分的功能所以程序的调试是重中之重当然前提是能够编写并会修改程序
    此次设计总的来到行的还顺利这切组成员团结付出的结果当然在此期间指导老师也为我们提供了巨大的帮助在此表示深深的行在此期间也学到了许多特别嵌软件的应用如proteus,ADS1.2,AXD加强了理论与导的联系

完整的Word格式文档51黑下载地址
基于LPC2000系列的电子琴的设计.doc (987.63 KB, 下载问: 7)


分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏 转播转播 分享分享 分享淘帖 顶 踩
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|手机版|小黑屋|单片机论坛 |51Hei单片机16群 联系QQ:125739409;技术交流QQ群7344883

Powered by 单片机坛网

快速回复 返回顶部 返回列表
ձһhƬձƵ ձƵɫwww ձƵ:ɫ