AVR笔记13:SPI实验(数码管显示INT0次数)(GCC)
》》点此进入 http://bbs.armavr.com/ ARM-AVR嵌入式开发论坛
一、程序结构
下载 (6.74 KB)
2009-8-11 10:38
二、仿真效果
下载 (213.81 KB)
2009-8-11 10:38
三、程序源码
1、main.c
- /*******************************************************************************
- Platform: AVR mega16学习板(www.iccavr.com)
- Project : 实验十三:SPI实验(数码管显示INT0次数)(GCC)
- Clock F : 3.6864M
- Software: WinAVR-20090313+Proteus7.4
- Author : 林夕依然
- Version : 08.12.10
- Updata : 09.03.10 模块化
- 09.05.04 增加proteus仿真模型,仿真未通过,详见仿真模型。
- 09.07.24 WinAVR-20090313调试通过
- comments:
- 1、以学习板4位数码管和INT0键为硬件电路
- 2、练习SPI的配置和使用
- 3、学习74HC595八位移位寄存器芯片的使用
- 4、理解数据显示取位方式(个,十,百位的算法)
- 5、进行此实验请插上JP1的所有8个短路块,JP6(SPI_EN)短路块。
- 6、参考:...mcu\ICCAVR学习板\旧版例程\M16学习板实验程序\5-中断实验
- *******************************************************************************/
- #include <avr/io.h>
- #include <util/delay.h>
- #include <avr/interrupt.h>
- #include "spi.h"
- #define uchar unsigned char
-
- uchar IntCnt = 0; //记录中断次数
- uchar disp[] = {0xC0,0xF9,0xA4,0xB0,0x99,0x92,0x82,0xF8,0x80,0x90};
-
- ISR(INT0_vect)
- {
- IntCnt++;
- }
-
- /*-----------------------------------------------------------------
- 函数名称: void InitDevices(void)
- 函数功能: 初始化各种信息
- 参 数:
- 返 回 值: 无
- -----------------------------------------------------------------*/
- void InitDevices(void)
- {
- cli(); //关全部中断
- SPIMasterInit(); //SPI初始化为主机
-
- MCUCR = 0x02; //中断0,下降沿触发
- GICR = 0x40; //开中断0,
- sei(); //开中断
- }
-
- int main(void)
- {
- uchar temp;
- port_init();
- InitDevices();
- while (1)
- {
- if( IntCnt > 9) //显示十位和百位
- {
- if( IntCnt > 99) //三位显示情况
- {
- DDRB = 0xff;
- PORTB = 0xff; //关显示
- temp = IntCnt / 100; //取百位
- SPI595Out(disp[temp]);
- PORTB = 0xfb; //将百位显示在右数第3个数码管上
- _delay_ms(1); //显示1ms,此时间决定百位十位显示频率
- PORTB = 0xff; //关显示
- temp = IntCnt%100/10; //取十位
- SPI595Out(disp[temp]);
- PORTB = 0xfd; //将十位显示在右数第2个数码管上
- _delay_ms(1); //显示1ms,此时间决定十位个位显示频率
- PORTB = 0xff; //关显示
- temp = IntCnt%10; //取个位
- SPI595Out(disp[temp]);
- PORTB = 0xfe; //在右数第1个数码管上显示个位
- }
- else //两位显示情况
- {
- DDRB = 0xff;
- PORTB = 0xff; //关显示
- temp = IntCnt/10; //取十位
- SPI595Out(disp[temp]);
- PORTB = 0xfd; //将十位显示在右数第2个数码管上
- _delay_ms(1); //显示时1ms,此时间决定十位个位显示频率
- PORTB = 0xff; //关显示
- temp = IntCnt%10; //取个位
- SPI595Out(disp[temp]);
- PORTB = 0xfe; //在右数第1个数码管上显示个位
- }
- }
- else //一位显示情况
- {
- DDRB = 0xff;
- PORTB = 0xfe; //只有一位数码管点亮
- SPI595Out(disp[IntCnt]);
- }
- _delay_ms(1);
- }
- }
2、spi.c
- #include <avr/io.h>
- #define uchar unsigned char
- /*-----------------------------------------------------------------
- 函数名称: void SPIMasterInit(void)
- 函数功能: SPI初始化为主机
- 参 数:
- 返 回 值: 无
- -----------------------------------------------------------------*/
- void SPIMasterInit(void)
- {
- // MOSI,MISO,SCK等都需要设计的数据方向定义
- DDRB |= (1<<PB5) | (1<<PB7); // 设置MOSI 和SCK 为输出,其他为输入 M16
- // DDRB |= (1<<PB2) | (1<<PB3); // 设置MOSI 和SCK 为输出,其他为输入 M64
- // SPI控制寄存器
- // SPIE SPE DORD MSTR CPOL CPHA SPR1 SPR0
- // SPIE 中断使能 SPE SPI使能 DORD 数据次序 1为LSB首先发送,0为MSB首先发送
- // MSTR 主从选择 1为主,0为从MSTR置位时选择主机模式,否则为从机.如果MSTR为"1",
- // SS配置为输入,但被拉低,则MSTR 被清零,寄存器SPSR 的SPIF 置位.用户必须重新设置
- // MSTR 进入主机模式。
- // CPOL: 时钟极性见ATMEGA16L(中文)P130
- // CPHA: 时钟相位
- // SPR1, SPR0: SPI 时钟速率选择1 与0 SPR1 和SPR0 对从机没有影响。
- // 使能SPI 主机模式,设置时钟速率为fck/128 */
- SPCR = (1<<SPE) | (1<<MSTR) | (1<<SPR1) | (1<<SPR0);
- }
- /*-----------------------------------------------------------------
- 函数名称: void SPIMasterTransmit(unsigned char i)
- 函数功能: SPI数据发送
- 参 数:
- 返 回 值: 无
- -----------------------------------------------------------------*/
- void SPIMasterTransmit(uchar TranData)
- {
- SPDR = TranData; // 启动数据传输
- while (!(SPSR & (1<<SPIF))); // 等待传输结束
- }
- /*-----------------------------------------------------------------
- 函数名称: void SPI595Out(unsigned char i)
- 函数功能: 通过74HC595输出数据
- 参 数:
- 返 回 值: 无
- -----------------------------------------------------------------*/
- void SPI595Out(uchar i)
- {
- PORTB&=~(1<<4); //等待数据传输,595存储寄存器数据不变
- SPIMasterTransmit(i); //传输数据
- PORTB|=(1<<4); //595移位寄存器的数据进入数据存储寄存器,并在数码管上显示
- }
-
- void port_init(void)
- {
- DDRA = 0x00; //方向输入
- PORTA = 0xFF; //打开上拉
- DDRB = 0xFF; //方向输出
- PORTB = 0xF0; //电平设置,MISO输出高电平,关闭595移位寄存器的数据清零功能
- DDRC = 0x00;
- PORTC = 0xFF;
- DDRD = 0xFF;
- PORTD = 0xFF;
- }
3、spi.h
- #define uchar unsigned char
- void SPIMasterInit(void);
- void SPIMasterTransmit(uchar TranData);
- void SPI595Out(uchar i);
- void port_init(void);
四、完整项目文件下载
http://bbs.armavr.com/thread-915-1-3.html
*博客内容为网友个人发布,仅代表博主个人观点,如有侵权请联系工作人员删除。