S3C2440-蜂鸣器

哈尔滨理工大学软件工程专业08-7李万鹏原创作品,转载请标明出处

http://blog.csdn.net/woshixingaaa/archive/2010/12/03/6054089.aspx

ARM驱动蜂鸣器的方式有两种:一种是PWM输出口直接驱动,另一种是利用IO定时翻转电平产生驱动波形对蜂鸣器进行驱动。PWM输出口直接驱动是利用PWM输出口本身可以输出一定的方波来进行驱动。在ARM中可以用几个特殊功能寄存器对占空比和周期进行设置。通过设置这些寄存器产生符合蜂鸣器要求的方波后,这个时候利用这个方波就可以对蜂鸣器进行驱动了。使用PWM时,通过TCMPn可以决定脉宽,TCNTn决定频率,TCMPn/TCNTn决定占空比。使用IO口电平翻转时,需要使用定时器来做定时,通过定时翻转产生符合要求频率的波形。由于蜂鸣器一般的工作电流比较大,以至于IO口无法驱动,一般使用放大电路来驱动,一般使用三极管来放大电流就可以了。

使用PWM控制蜂鸣器:

rTCFG0用来设置预分频值,rTCFG1用来设置多路选择器MUX的分频值,TCNTB0也起到分频作用。使用PWM控制蜂鸣器注意设置GPB0为TOUT0。这里设置PWM频率为1HZ,占空比50%,也就是半秒响一次。S3C2440定时器中有双缓冲rTCNTBn,rTCMPBn,他们是可以通过编程访问的,他们会将数据自动装入rTCNTn,rTCMPn,这两个16位计数器对程序员来说是透明的。

一般启动定时器的步骤如下:

  • 将初始值写入到rTCNTn,rTCMPn
  • 设置对应定时器的手动更新位,自动装载
  • 启动定时器,并关闭手动更新位

#define rGPBCON (*(volatile unsigned *)0x56000010) #define rGPBDAT (*(volatile unsigned *)0x56000014) #define rGPBUP (*(volatile unsigned *)0x56000018) #define rTCFG0 (*(volatile unsigned *)0x51000000) #define rTCFG1 (*(volatile unsigned *)0x51000004) #define rTCNTB0 (*(volatile unsigned *)0x5100000C) #define rTCMPB0 (*(volatile unsigned *)0x51000010) #define rTCON (*(volatile unsigned *)0x51000008) int Main(){ rGPBCON &= 0xfffffc; rGPBCON |= 0x2; rTCFG0 &= ~0xff; rTCFG0 |= 0x64; rTCFG1 &= ~0xf; rTCFG1 |= 0x3; rTCNTB0 = 0x7530; rTCMPB0 = rTCNTB0>>1; rTCON &= ~0x1f; rTCON |= (0x1)|(0x1<<1)|(0x1<<3); rTCON &= ~2; while(1); return 0; }

使用定时器产生中断使IO电平翻转,控制蜂鸣器:

定时器注意设置rINTMSK开中断,并在中断处理程序中清除中断请求位。rSRCPND |= 0x1<<10;rINTPND |= 0x1<<10;清除rINTPND通过设置相应为1进行清除。rSTCPND是向相应位写数据清除。如果不清除,会一直响应这个中断。在Main函数中清一下是为了防止以前这个位申请中断,所以清一下,以防万一。定时器接在APB总线上,所以用PCLK时钟。在这里我设预分频为0x64,除法器为16,rTCNTB0为0x7a12,所以 50M/0x64/16/0x7a12为1HZ,所以中断周期为1s,所以每一秒蜂鸣器响一下,然后隔一秒,然后再响。

#define rGPBCON (*(volatile unsigned *)0x56000010) #define rGPBDAT (*(volatile unsigned *)0x56000014) #define rGPBUP (*(volatile unsigned *)0x56000018) #define rSRCPND (*(volatile unsigned *)0x4A000000) #define rINTPND (*(volatile unsigned *)0x4A000010) #define rTCFG0 (*(volatile unsigned *)0x51000000) #define rTCFG1 (*(volatile unsigned *)0x51000004) #define rTCNTB0 (*(volatile unsigned *)0x5100000C) #define rTCON (*(volatile unsigned *)0x51000008) #define rINTMSK (*(volatile unsigned *)0x4A000008) #define U32 unsigned int #define _ISR_STARTADDRESS 0x33ffff00 #define pISR_TIMER0 (*(unsigned *)(_ISR_STARTADDRESS+0x48)) int count; void __irq Timer0_ISR(void){ rSRCPND |= 0x1<<10; rINTPND |= 0x1<<10; count++; if(count %2 == 1) rGPBDAT |= 0x01; else rGPBDAT &= 0xfe; if(count == 1000) count = 0; } int Main(){ count = 0; rGPBCON &= 0xfffffc; rGPBCON |= 0x1; rGPBDAT &= 0xffe; rGPBUP &= 0xfe; pISR_TIMER0 = (U32)Timer0_ISR; rSRCPND |= 0x1<<10; rINTPND |= 0x1<<10; rINTMSK &= ~(0x1<<10); rTCFG0 &= ~0xff; rTCFG0 |= 0x64; rTCFG1 &= ~0xf; rTCFG1 |= 0x3; rTCNTB0 = 0x7a12; rTCON &= ~0x1f; rTCON |= 0xb; rTCON &= ~0x2; while(1); return 0; }

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值