实例介绍
【实例简介】
【实例截图】
【核心代码】
/******************************************************************************************** * 文 件 名:SSP_SPI_Slave.c * 功 能:本实验将SSP配置为SPI从机,将SPI0配置为SPI主机。SSP接收SPI0发送的数据,并进行比较, * 若接收正确,则LED1闪烁,LED2熄灭;否则LED2一直点亮。SSP采用中断方式接收数据。 * 说 明:用跳线帽短接74HC595_2的相关跳线。 * 用杜绑线连接P0.17(SCK1)和P0.4(SCK0),P0.18(MISO1)和P0.5(MISO0),P0.19(MOSI1) * 和P0.6(MOSI0),P0.29和P0.20(SSEL1)。 * 调试方法:全速运行程序,如果接收正确,可以看到LED1在闪烁;若拔开P0.19(MOSI1)和P0.6(MOSI0)的 * 连线,LED1停止闪烁,LED2将会点亮。直到重新插上后,LED1恢复闪烁,而LED2熄灭。 * 作 者:POWER * 日 期:2006年7月30号 * 斯凯科技主页:www.armsky.net * 斯凯科技论坛:www.armsky.net/bbs *********************************************************************************************/ #include "config.h" #define SLAVE_CS ((uint32)1<<29) // P0.29口为SPI从机的选择控制引脚 #define H_SLAVE_CS() IO0SET=SLAVE_CS // 作为SPI从机选择控制引脚的P0.29置高 #define L_SLAVE_CS() IO0CLR=SLAVE_CS // 作为SPI从机选择控制引脚的P0.29置低 #define SPI_CS ((uint32)0x01<<20) // P1.20引脚模拟SPI的片选信号 #define SPI_DATA ((uint32)0x01<<22) // P0.22引脚模拟SPI的数据信号 #define SPI_CLK ((uint32)0x01<<25) // P1.25引脚模拟SPI的时钟信号 #define H_SPI_CS() IO1SET=SPI_CS // SPI的片选信号置高 #define L_SPI_CS() IO1CLR=SPI_CS // SPI的片选信号置低 #define H_SPI_DATA() IO0SET=SPI_DATA // SPI的数据信号置高 #define L_SPI_DATA() IO0CLR=SPI_DATA // SPI的数据信号置低 #define H_SPI_CLK() IO1SET=SPI_CLK // SPI的时钟信号置高 #define L_SPI_CLK() IO1CLR=SPI_CLK // SPI的时钟信号置低 volatile uint8 RcvData; // 接收到的数据 volatile uint8 RcvFlag; // 接收到新数据标志 /******************************************************************************************** * 函数名称:SSP_IRQ() * 功 能:SSP中断服务函数 * 入口参数:无 * 出口参数:无 *********************************************************************************************/ void __irq SSP_IRQ(void) { RcvData=SSPDR; // 接收数据 RcvFlag=0x01; // 接收到新数据 SSPICR=0x03; // 清除标志位 VICVectAddr=0x00; // 中断向量处理结束 } /******************************************************************************************** * 函数名称:Delay() * 功 能:软件延时 * 入口参数:count 延时参数,值越大,延时越长 * 出口参数:无 *********************************************************************************************/ void Delay(uint32 count) { uint32 i; for(;count>0;count--) for(i=0;i<50000;i ); } /******************************************************************************************** * 函数名称:SendDataTo74HC595() * 功 能:向74HC595发送一字节数据 * 入口参数:data 要发送的数据 * 出口参数:无 * 注 意:发送数据时,高位先发送 *********************************************************************************************/ void SendDataTo74HC595(uint8 data) { uint8 i; L_SPI_CS(); // SPI_CS=0 for(i=0;i<8;i ) // 发送8位数据(1个字节) { L_SPI_CLK(); // SPI_CLK=0 /* 设置SPI_DATA输出值 */ if((data & 0x80)!=0) H_SPI_DATA(); // SPI_DATA=1 else L_SPI_DATA(); // SPI_DATA=0 data<<=1; // 将要发送的1字节数据左移一位 H_SPI_CLK(); // SPI_CLK=1 } H_SPI_CS(); // SPI_CS=1 } /******************************************************************************************** * 函数名称:SPI_Init() * 功 能:初始化SPI接口,设置为主机 * 入口参数:无 * 出口参数:无 *********************************************************************************************/ void SPI_Init(void) { SPI_SPCCR=0x52; // 设置SPI时钟分频 SPI_SPCR=0x30; // 设置SPI接口模式,MSTR=1,CPOL=1, // CPHA=0,LSBF=0 } /******************************************************************************************** * 函数名称:SSP_Init() * 功 能:将SSP控制器初始化为SPI接口,设置为从机 * 入口参数:无 * 出口参数:无 *********************************************************************************************/ void SSP_Init(void) { SSPCR0=(0x05<<8)| // SCR 设置SPI时钟分频 (0x00<<7)| // CPHA 时钟输出相位:仅SPI模式有效 (0x01<<6)| // CPOL 时钟输出极性:仅SPI模式有效 (0x00<<4)| // FRF 帧格式:00=SPI,01=SSI,10=Microwire,11=保留 (0x07<<0); // DSS 数据长度:0000~0010=保留,0011=4位, // 0111=8位,1111=16位 SSPCR1=(0x00<<3)| // SOD 从机输出禁止:1=禁止;0=允许 (0x01<<2)| // MS 主从选择:0=主机;1=从机 (0x01<<1)| // SSE SSP使能:1=允许SSP与其他设备通信 (0x00<<0); // LBM 回写模式 SSPCPSR=0x52; // pclk分频值 SSPIMSC=0x02; // 中断屏蔽寄存器 SSPICR=0x03; // 中断清零寄存器清零 } /******************************************************************************************** * 函数名称:MSPI_SendData() * 功 能:SPI0接口向SPI总线发送数据 * 入口参数:data 待发送的数据 * 出口参数:返回值为读取的数据 *********************************************************************************************/ uint8 MSPI_SendData(uint8 data) { L_SLAVE_CS(); // 选择SSP为从机 SPI_SPDR=data; while(0==(SPI_SPSR & 0x80)); // 等待SPIF置位,即等待数据发送完毕 H_SLAVE_CS(); return(SPI_SPDR); } /******************************************************************************************** * 函数名称:main() * 功 能:SPI从机演示实验 *********************************************************************************************/ int main(void) { uint8 rcv_data; PINSEL0=0x00000000; // 设置SPI0引脚连接 PINSEL1=0x000002a8; // 设置SSP引脚连接 IO1DIR=0; // 防止数码管干扰 // PINSEL1&=~((uint32)0x03<<26); // 选择P0.29为GPIO // 设置P0.29为输出 PINSEL1&=~((uint32)0x03<<12); // 设置P0.22引脚为GPIO PINSEL2&=~((uint32)0x01<<3); // 设置P1.20和P1.25引脚为GPIO IO0DIR|=SPI_DATA; // 设置P0.22,P1.20,P1.25引脚为输出 IO1DIR|=(SPI_CS | SPI_CLK); SendDataTo74HC595(0xff); // LED8~LED1全部熄灭 IRQEnable(); // IRQ中断使能 // SPI_Init(); // 初始化SPI接口 SSP_Init(); // 初始化SSP接口 /* SSP中断初始化(使用向量中断)*/ VICIntSelect=0x00000000; // 设置所有中断为IRQ VICVectCntl0=0x20 | 11; // 分配SSP中断为中断向量0,即最高优先级 VICVectAddr0=(uint32)(&SSP_IRQ); // 设置中断服务程序地址 VICIntEnable=1<<11; // 允许SSP中断 while(1) { RcvFlag=0; // 清除接收到新数据标志 // rcv_data=MSPI_SendData(0x5a); // 发送数据0x5a Delay(20); // 延时 if(RcvFlag!=0) // 如果接收到新数据 { if(RcvData==0x84) // 判断接收到的数据是否为0x5a { /* 接收的数据与发送的数据相同,LED1闪烁 */ SendDataTo74HC595(0xff); // 接收正确时,LED2熄灭 SendDataTo74HC595(0xfe); Delay(20); SendDataTo74HC595(0xff); Delay(20); } else /* 数据错误,LED2一直点亮 */ SendDataTo74HC595(0xfd); } } return 0; }
好例子网口号:伸出你的我的手 — 分享!
小贴士
感谢您为本站写下的评论,您的评论对其它用户来说具有重要的参考价值,所以请认真填写。
- 类似“顶”、“沙发”之类没有营养的文字,对勤劳贡献的楼主来说是令人沮丧的反馈信息。
- 相信您也不想看到一排文字/表情墙,所以请不要反馈意义不大的重复字符,也请尽量不要纯表情的回复。
- 提问之前请再仔细看一遍楼主的说明,或许是您遗漏了。
- 请勿到处挖坑绊人、招贴广告。既占空间让人厌烦,又没人会搭理,于人于己都无利。
关于好例子网
本站旨在为广大IT学习爱好者提供一个非营利性互相学习交流分享平台。本站所有资源都可以被免费获取学习研究。本站资源来自网友分享,对搜索内容的合法性不具有预见性、识别性、控制性,仅供学习研究,请务必在下载后24小时内给予删除,不得用于其他任何用途,否则后果自负。基于互联网的特殊性,平台无法对用户传输的作品、信息、内容的权属或合法性、安全性、合规性、真实性、科学性、完整权、有效性等进行实质审查;无论平台是否已进行审查,用户均应自行承担因其传输的作品、信息、内容而可能或已经产生的侵权或权属纠纷等法律责任。本站所有资源不代表本站的观点或立场,基于网友分享,根据中国法律《信息网络传播权保护条例》第二十二与二十三条之规定,若资源存在侵权或相关问题请联系本站客服人员,点此联系我们。关于更多版权及免责申明参见 版权及免责申明
网友评论
我要评论