AVR单片机ATMEGA48的EEPROM操作例子
/***************************************************** CodeWizardAVR
http://www.avrdiy.com Panxiaoyi 快速PWM,也可以叫单斜率PWM
*****************************************************/
#include
unsigned char eeprom i=0; //把变量放保存在EEPROM上/赋值与否并不影响i的值
void main(void) {
TCCR0A=0b10000011; //比较匹配时OC0A=0,计数到比较值时OC0A=1,TOP固定等于255
TCCR0B=0b00000001; //时钟=1分频
DDRD.6=1; //PD6必须设置为输出时OC0A输出的PWM才有效 DDRD.2=0;
PORTD.2=1; //PD2接按键输入/上拉电阻使能 while(1) {
if(PIND.2==0) //如果按键按下/简单的按键防抖动 {
while(PIND.2==0); //等待按键松开
i+=10; //更新EEPROM的数据i/重新来电后数据不变 }
OCR0A = i ; //刷新比较值,PWM占空比随之改变 } }
ATMEGA48的USART串口与PC通讯例子
/***************************************************** CodeWizardAVR
http://www.avrdiy.com
Chip type : ATmega48V Clock frequency : 7.372800 MHz Memory model : Small External SRAM size : 0 Data Stack size : 128
波特率9600/8个数据位 /1个停止位 /无校验 M8V20实验板硬件设置
1: J5的2个跳线帽短接,使用外部晶振7.3728MHz
2: J6与J7的4个跳线帽短接,使用MAX232,其他跳线开路 3: DB9接口连接到电脑
请配合串口调试软件SSCOM32或者comdebug进行调试*/
#include
void main(void) {
UCSR0B=0x18; //下面是3条语句是串口初始化语句 UCSR0C=0x06; UBRR0L=0x2F;
while(1) //循环 {
unsigned char data; //定义一个局部变量
data=getchar(); //等待,直到接收到一个数据 putchar(data); //将接收到的数据发送出去 } } //end
ATMEGA48的T/C2与精确时钟例子
/***************************************************** www.avrdiy.com
CodeWizardAVR V1.25.6 Professional Chip type : ATmega48 Clock frequency : 7.372800 MHz Memory model : Small External SRAM size : 0 Data Stack size : 128
计算: 1秒 = 时钟 / ( 分频 * 计数 )
假设时钟 = 7372800 Hz 那么: 1秒 = 7372800 / ( 分频 * 计数 ) 得: 计数 =7372800/分频
由于分频只有 1/8/32/64/128/256/1024 供我们选择,而计数最高只有8位(255)
为了不占用资源,中断次数尽量少一点比较好,并且中断时间越短越好
所以我们可以选择 计数 = 时钟7372800 / 分频1024 / 30次中断 = 240 这个240就是T/C2的计数上限TOP
*****************************************************/
#include
interrupt [TIM2_COMPA] void timer2_compa_isr(void) {
TC2A++;
if(TC2A>=30) TC2A=0;
if(TC2A>25) PORTD.3=1; else PORTD.3=0; }
void main(void)
{
TCCR2A|=2; //工作于CTC模式(比较匹配时计算器清零)
OCR2A=240; //设置TOP的值(计算器的上限值) TCCR2B|=7; //取系统时钟1024分频作为T/C2时钟 TIMSK2=2; //使能计数器的值达到TOP时产生中断 DDRD.3=1; //使用PD3每秒驱动蜂鸣器\嘀\一次 #asm(\插入汇编语句,打开全局中断 while (1) {
#asm(\空操作的汇编代码,等待中断发生 }; }
/****************************************************
假设程序还有一个3位数码管动态扫描任务,这时我们就可以这样计算 1:数码管的扫描频率在75-85Hz比较合适,太低会闪烁,太高占用资源 2:每扫描一次就必须分3次显示,分别是个位/十位/百位
3:这时我们可以计数出显示频率是225-255Hz(中断频率),在这里假设=240Hz
4:这时我们就可以顺便使用这个T/C2定数中断来保证扫描的可靠运行了 5:计算: 计数 = 时钟7372800 / 分频128 / 240次中断 = 240 ***/
ATMEGA48外部电平变化中断PCINT例子
/***************************************************** CodeWizardAVR
http://www.avrdiy.com
Chip type : ATmega48V Clock frequency : 1.000000 MHz Memory model : Small External SRAM size : 0 Data Stack size : 128
外部PCINT0-PCINT7共享一个中断源PCINT0 外部PCINT8-PCINT14共享一个中断源PCINT1 外部PCINT16-PCINT23共享一个中断源PCINT2
没有使用延时/通信语句,所以使用内部/外部时钟都可以 每按动INT0按键一次,PD3的电平就翻转一次
本例子没有考虑太多的按键防抖动功能*******************/
#include
//外部PCINT16-PCINT23共享一个中断源PCINT2
//请参考M48数据手册的48页/75页
interrupt [PCINT2] void PCINT2_isr(void) {
PORTB.0=~PORTB.0; //电平取反
PCIFR|=4; //清除PCINT2中断触发标记,防止按键抖动 }
void main(void) {
PORTD=255;
DDRD=0; //设置PCINT16-PCINT23端口为输入,上拉电阻有效
PORTB.0=0;
DDRB.0 =1; //设置PB0输出低电平,准备驱动蜂鸣器
PCICR|=4; //使能PCINT16-PCINT23外部电平变化中断 PCMSK2|=4; //使能PCINT18有效
#asm(\插入汇编语句,打开全局中断
while (1) //循环,等待中断 {
#asm(\空操作的汇编代码,等待中断发生 }; }
ATMEGA48外部中断INT0例子
/***************************************************** CodeWizardAVR
http://www.avrdiy.com
Chip type : ATmega48V Clock frequency : 1.000000 MHz Memory model : Small External SRAM size : 0 Data Stack size : 128
INT0最好接一个4.7K的上拉电阻,按键对地有效
没有使用延时/通信语句,所以使用内部/外部时钟都可以 每按动INT0按键一次,PD3的电平就翻转一次
本例子没有考虑太多的按键防抖动功能*******************/
#include
interrupt [2] void INT0_isr(void) //INT0的中断向量是2,请参考M48数据手册的48页 {
PORTD.3=~PORTD.3; //电平取反
EIFR|=1; //清除INT0中断触发标记,防止按键抖动 }
void main(void) {
PORTD.2=1;
DDRD.2=0; //设置INT0端口为输入,上拉电阻有效
PORTD.3=0;
DDRD.3 =1; //设置PD3输出低电平,准备驱动蜂鸣器
EIMSK|=1; //打开INT0中断 EICRA|=3; //INT0上升沿触发
#asm(\插入汇编语句,打开全局中断
while (1) //循环,等待中断 {
#asm(\空操作的汇编代码,等待中断发生
}; }
ATMEGA48的ADC模数转换例子//www.avrdiy.com //ADC结果由串口输出到电脑显示 #include
//外部时钟 7.3728MHz (请取消时钟8分频)
//串口初始化,波特率9600Hz,8个数据位,1个停止位,无奇偶校验,无中断使能
UCSR0B=8; UCSR0C=6; UBRR0L=47;
//***************************************************************** ADMUX=96; //设置参考电压为AVCC,结构左对齐(就是8位精度)
ADCSRA|=135; //使能ADC,ADC时钟=系统时钟128分频 while (1) {
unsigned char adc;