www.openedv.com
您好,欢迎您!    会员注册 | 登入 
公告:欢迎访问www.openedv.com开源电子网,开源共享共同进步,祝您新年快乐,万事如意!
设为首页 | 加入收藏
论坛首页 » 其他CM0,CM3系列 前往: 
我用一个LPC1114控制一对Nrf24l01通信,结果怎么没反应呀,望高手指点,调试了好几天了,快绝望了
发表人 内容
[Down] [Up]
[楼主位] 782861417


等级:NO
注册时间:
2011/06/01 16:02
文章: 5
来自: 江苏 
离线

。。。。。。
#include "..\config.h"

#define BEEP         ( 3 << 0)
#define BEEP_INIT()  GPIO2DIR  |=  BEEP                                 /*  蜂鸣器初始化P2^0,P2^1                */
#define BEEPOFF()    GPIO2DATA |=  BEEP                                 /*  蜂鸣器关                    */
#define BEEPON()     GPIO2DATA &= ~BEEP                                 /*  蜂鸣器开                    */

#define KEY  (1ul << 0)                                                        //GPIO3-0
                                            
//CE P0^7
#define CE0    (1ul << 7)         
#define CE_INIT()   GPIO0DIR |=  CE0                                /*CE是GPIO0_1且为输出*/
#define CEH()    GPIO0DATA |=  CE0                                  /*  CE为高电平                    */
#define CEL()     GPIO0DATA &= ~CE0                                 /*  CE为低电平                    */
//CSN  = P0^2; 
#define CSN0    (1ul << 2)         
#define  CSN_INIT()   GPIO0DIR |=  CSN0                           /*CSN是GPIO0_2*/
#define CSNH()    GPIO0DATA |=  CSN0                             /*  CE为高电平    */
#define CSNL()     GPIO0DATA &= ~CSN0                             /*  CE为低电平  */
//sbit IRQ  = P0^3; 
#define IRQ0  (1ul << 3)      
#define  IRQ_INIT()   GPIO0DIR &= ~IRQ0                    /*IRQ是GPIO0_3*/
//sbit MISO = P0^4; 
#define MISO0    (1ul << 4)
#define  MISO_INIT()   GPIO0DIR &= ~MISO0                                        /*IRQ是GPIO0_4*/        
//#define  MISO   GPIO0DIR &=  MISO0                                      /*MISO是GPIO0_4*/

//sbit MOSI = P0^5; 
#define MOSI0    (1ul << 5)         
#define MOSI_INIT()   GPIO0DIR |=  MOSI0                                    /*MOSI是GPIO0_5*/
#define MOSIH()     GPIO0DATA |=  MOSI0                                     /*  CE为高电平                    */
#define MOSIL()     GPIO0DATA &= ~MOSI0                                 /*  CE为低电平                    */
//sbit MOSI = P0^6; 
#define SCK0    (1ul <<6)         
#define SCK_INIT()  GPIO0DIR |=  SCK0                                    /*MOSI是GPIO0_6*/
#define SCKH()      GPIO0DATA |=  SCK0                                     /*  CE为高电平                    */
#define SCKL()      GPIO0DATA &= ~SCK0                                    /*  CE为低电平                    */
/***************************************************************************************/
//CE P2^7
#define R_CE0    (1ul << 7)         
#define R_CE_INIT()   GPIO2DIR |=  R_CE0                                /*CE是GPIO0_1且为输出*/
#define R_CEH()     GPIO2DATA |=  R_CE0                                  /*  CE为高电平                    */
#define R_CEL()     GPIO2DATA &= ~R_CE0                                 /*  CE为低电平   */

//CSN  = P2^2; 
#define R_CSN0    (1ul << 2)         
#define  R_CSN_INIT()   GPIO2DIR |=  R_CSN0                           /*CSN是GPIO0_2*/
#define R_CSNH()    GPIO2DATA |=  R_CSN0                             /*  CE为高电平    */
#define R_CSNL()     GPIO2DATA &= ~R_CSN0                             /*  CE为低电平  */
//sbit IRQ  = P2^3; 
#define R_IRQ0  (1ul << 3)      
#define  R_IRQ_INIT()   GPIO2DIR &= ~R_IRQ0                    /*IRQ是GPIO0_3*/
//sbit MISO = P2^4; 
#define R_MISO0    (1ul << 4)
#define  R_MISO_INIT()   GPIO2DIR &= ~R_MISO0                                        /*IRQ是GPIO0_4*/        
//#define  MISO   GPIO0DIR &=  MISO0                                      /*MISO是GPIO0_4*/

//sbit MOSI = P2^5; 
#define R_MOSI0    (1ul << 5)         
#define R_MOSI_INIT()   GPIO2DIR |=  R_MOSI0                                    /*MOSI是GPIO0_5*/
#define R_MOSIH()     GPIO2DATA |=  R_MOSI0                                     /*  CE为高电平                    */
#define R_MOSIL()     GPIO2DATA &= ~R_MOSI0                                 /*  CE为低电平                    */
//R_SCK=P2^6
#define R_SCK0    (1ul <<6)         
#define R_SCK_INIT()  GPIO2DIR |=  R_SCK0                                    /*MOSI是GPIO0_6*/
#define R_SCKH()      GPIO2DATA |=  R_SCK0                                     /*  CE为高电平                    */
#define R_SCKL()      GPIO2DATA &= ~R_SCK0                                    /*  CE为低电平                    */


// SPI(nRF24L01) commands
#define READ_REG    0x00  // Define read command to register
#define WRITE_REG   0x20  // Define write command to register
#define RD_RX_PLOAD 0x61  // Define RX payload register address
#define WR_TX_PLOAD 0xA0  // Define TX payload register address
#define FLUSH_TX    0xE1  // Define flush TX register command
#define FLUSH_RX    0xE2  // Define flush RX register command
#define REUSE_TX_PL 0xE3  // Define reuse TX payload register command
#define NOP         0xFF  // Define No Operation, might be used to read status register

// SPI(nRF24L01) registers(addresses)
#define CONFIG      0x00  // 'Config' register address
#define EN_AA       0x01  // 'Enable Auto Acknowledgment' register address
#define EN_RXADDR   0x02  // 'Enabled RX addresses' register address
#define SETUP_AW    0x03  // 'Setup address width' register address
#define SETUP_RETR  0x04  // 'Setup Auto. Retrans' register address
#define RF_CH       0x05  // 'RF channel' register address
#define RF_SETUP    0x06  // 'RF setup' register address
#define STATUS      0x07  // 'Status' register address
#define OBSERVE_TX  0x08  // 'Observe TX' register address
#define CD          0x09  // 'Carrier Detect' register address
#define RX_ADDR_P0  0x0A  // 'RX address pipe0' register address
#define RX_ADDR_P1  0x0B  // 'RX address pipe1' register address
#define RX_ADDR_P2  0x0C  // 'RX address pipe2' register address
#define RX_ADDR_P3  0x0D  // 'RX address pipe3' register address
#define RX_ADDR_P4  0x0E  // 'RX address pipe4' register address
#define RX_ADDR_P5  0x0F  // 'RX address pipe5' register address
#define TX_ADDR     0x10  // 'TX address' register address
#define RX_PW_P0    0x11  // 'RX payload width, pipe0' register address
#define RX_PW_P1    0x12  // 'RX payload width, pipe1' register address
#define RX_PW_P2    0x13  // 'RX payload width, pipe2' register address
#define RX_PW_P3    0x14  // 'RX payload width, pipe3' register address
#define RX_PW_P4    0x15  // 'RX payload width, pipe4' register address
#define RX_PW_P5    0x16  // 'RX payload width, pipe5' register address
#define FIFO_STATUS 0x17  // 'FIFO Status Register' register address
/********************************************************************************/
#define  TX_ADR_WIDTH   5
#define  RX_ADR_WIDTH   5
#define TX_PLOAD_WIDTH  8
#define RX_PLOAD_WIDTH  8  //32字节有效数据宽度
uint8 TX_ADDRESS[TX_ADR_WIDTH]  = {0x34,0x43,0x10,0x10,0x01};
uint8 RX_ADDRESS[RX_ADR_WIDTH]  = {0x34,0x43,0x10,0x10,0x01}; //发送地址
//uint8 RX_BUF[TX_PLOAD_WIDTH];
//uint8 TX_BUF[TX_PLOAD_WIDTH];
uint8 flag;
uint8 sta;
uint8 mode;
uint8 Buffer[]={0X00,0X01,0X02,0X03,0X04,0X05,0X06,0X07};
uint8 Buffer1[]={0X00,0X00,0X00,0X00,0X00,0X00,0X00,0X00};
/******   STATUS寄存器bit位定义      *******/
#define MAX_RT   0x10  //达到最大发送次数中断
#define TX_DS    0x20  //TX发送完成中断
#define RX_DR    0x40  //接收到数据中断

/*********************************************************************************/
void myDelay (INT32U ulTime)
{
    uint8 i;  
    i = 0;
    while (ulTime--) {
      for (i = 0; i < 5000; i++);
    }
}
void Delay_10us(void)
{
 uint8 i = 0;
 for( i =100; i>0; i--); 
}
void Delay_130us(void)
{
 INT32U i = 0;
 for( i =1400; i>0; i--); 
  
}
/************************************************************************************/
void INIT_IO(void)
{
 IRQ_INIT();                 //IRQ输入
 MISO_INIT();                //MISO输入
 MOSI_INIT();    //MOSI输出
 SCK_INIT();                 //SCK输出
 CE_INIT();                  //CE输出
 CSN_INIT();                 //CSN输出
 R_IRQ_INIT();               //IRQ输入
 R_MISO_INIT();              //MISO输入
 R_MOSI_INIT();   //MOSI输出
 R_SCK_INIT();               //SCK输出
 R_CE_INIT();                //CE输出
 R_CSN_INIT();               //CSN输出
 BEEP_INIT();                //P2^0,P2^1输出
   CEL();                    //选中24L01
   R_CEL();
   CSNH();        // CSN为高代表SPI禁止,见时序图
   R_CSNH();
   SCKL();        // SPI时钟置低,为后面上升沿读入做准备,下降沿输出 
   R_SCKL();
}

uint8 SPI_RW(uint8 byte,uint8 mode)
{
 uint8 i;
 if(!mode)
 {
  for(i=0; i<8; i++)          // 循环8次
    {
      if(byte & 0x80)   // byte最高位输出到MOSI
    MOSIH();
     else
       MOSIL(); 
     byte = (byte << 1);           // 低一位移位到最高位  
           SCKH();                // 拉高SCK,nRF24L01从MOSI读入1位数据,同时从MISO输出1位数据   
   if( GPIO0DATA & MISO0 )
   byte |= 1;            // 读MISO到byte最低位
           SCKL();             // SCK置低
    }
           return(byte);            // 返回读出的一字节
 }
  else
  {
   for(i=0; i<8; i++)          // 循环8次
    {
      if(byte & 0x80)   // byte最高位输出到MOSI
    R_MOSIH();
     else
       R_MOSIL(); 
     byte = (byte << 1);           // 低一位移位到最高位  
           R_SCKH();                // 拉高SCK,nRF24L01从MOSI读入1位数据,同时从MISO输出1位数据   
   if( GPIO2DATA & R_MISO0 )
   byte |= 1;            // 读MISO到byte最低位
          R_SCKL();             // SCK置低
    }
           return(byte);            // 返回读出的一字节
  
  }
}

uint8 SPI_RW_Reg(uint8 reg, uint8 value ,uint8 mode)
{
 uint8 status;
 if(!mode)
 {
 CSNL();                    // CSN置低,开始传输数据
   status = SPI_RW(reg,mode);      // 选择寄存器,同时返回状态字
   SPI_RW(value,mode);             // 然后写数据到该寄存器
   CSNH();                   // CSN拉高,结束数据传输
 Delay_10us();
   return(status);            // 返回状态寄存器
 }
   else
 {
 R_CSNL();                    // CSN置低,开始传输数据
   status = SPI_RW(reg,mode);      // 选择寄存器,同时返回状态字
   SPI_RW(value,mode);             // 然后写数据到该寄存器
   R_CSNH();                   // CSN拉高,结束数据传输
 Delay_10us();
   return(status);            // 返回状态寄存器
  
 }
}

uint8 SPI_Read(uint8 reg,uint8 mode)
{
 uint8 reg_val;
 if(!mode)
 {  
 CSNL();                     // CSN置低,开始传输数据
   SPI_RW(reg,mode);                // 选择寄存器
   reg_val = SPI_RW(0,mode);        // 然后从该寄存器读数据
   CSNH();                     // CSN拉高,结束数据传输
 Delay_10us();
   return(reg_val);            // 返回寄存器数据
 }
 else
 {
  R_CSNL();                     // CSN置低,开始传输数据
      SPI_RW(reg,mode);                // 选择寄存器
      reg_val = SPI_RW(0,mode);        // 然后从该寄存器读数据
      R_CSNH();                     // CSN拉高,结束数据传输
    Delay_10us();
      return(reg_val);            // 返回  
 }
}

uint8 SPI_Read_Buf(uint8 reg, uint8 *pBuf, uint8 bytes,uint8 mode)
{
 uint8 status, i;
 if(!mode)
 {
 CSNL();                    // CSN置低,开始传输数据
   status = SPI_RW(reg,mode);       // 选择寄存器,同时返回状态字
   for(i=0; i<bytes; i++)
    pBuf[i] = SPI_RW(0,mode);    // 写0个字节到nrf24l01,同时逐个字节从nRF24L01读出
   CSNH();                    // CSN拉高,结束数据传输
 Delay_10us();
   return(status);             // 返回状态寄存器
 }
   else
 {
  R_CSNL();                    // CSN置低,开始传输数据
   status = SPI_RW(reg,mode);       // 选择寄存器,同时返回状态字
   for(i=0; i<bytes; i++)
    pBuf[i] = SPI_RW(0,mode);    // 写0个字节到nrf24l01,同时逐个字节从nRF24L01读出
   R_CSNH();                    // CSN拉高,结束数据传输
 Delay_10us();
   return(status);             // 返回状态寄存器
 }
}

uint8 SPI_Write_Buf(uint8 reg, uint8 *pBuf, uint8 bytes,uint8 mode)
{
 uint8 status, i;
 if(!mode)
 {
  CSNL();                    // CSN置低,开始传输数据
   status = SPI_RW(reg,mode);       // 选择寄存器,同时返回状态字
   for(i=0; i<bytes; i++)
     SPI_RW(*pBuf++,mode);        // 逐个字节写入nRF24L01
   CSNH();                    // CSN拉高,结束数据传输
 Delay_10us();
   return(status);             // 返回状态寄存器
 }
   else
 {
   R_CSNL();                    // CSN置低,开始传输数据
   status = SPI_RW(reg,mode);       // 选择寄存器,同时返回状态字
   for(i=0; i<bytes; i++)
     SPI_RW(*pBuf++,mode);        // 逐个字节写入nRF24L01
         R_CSNH();                    // CSN拉高,结束数据传输
    Delay_10us();
       return(status);             // 返回状态寄存器  
 }
}

void RX_Mode(void)
{
 R_CEL();
 Delay_10us();
   SPI_Write_Buf(WRITE_REG + RX_ADDR_P0, TX_ADDRESS, TX_ADR_WIDTH,1);  // 接收设备接收通道0使用和发送设备相同的发送地址
   SPI_RW_Reg(WRITE_REG + EN_AA, 0x01,1);               // 使能接收通道0自动应答
   SPI_RW_Reg(WRITE_REG + EN_RXADDR, 0x01,1);           // 使能接收通道0
   SPI_RW_Reg(WRITE_REG + RF_CH, 40,1);                 // 选择射频通道0x40
   SPI_RW_Reg(WRITE_REG + RX_PW_P0, TX_PLOAD_WIDTH,1);  // 接收通道0选择和发送通道相同有效数据宽度
   SPI_RW_Reg(WRITE_REG + RF_SETUP, 0x07,1);            // 数据传输率1Mbps,发射功率0dBm,低噪声放大器增益
   SPI_RW_Reg(WRITE_REG + CONFIG, 0x0f,1);              // CRC使能,16位CRC校验,上电,接收模式
   R_CEH();  // 拉高CE启动接收设备
 Delay_130us();
 Delay_10us();
}

void TX_Mode(void)
{
 CEL();

   SPI_Write_Buf(WRITE_REG + TX_ADDR, TX_ADDRESS, TX_ADR_WIDTH,0);     // 写入发送地址
   SPI_Write_Buf(WRITE_REG + RX_ADDR_P0, TX_ADDRESS, TX_ADR_WIDTH,0);  // 为了应答接收设备,接收通道0地址和发送地址相同
   SPI_Write_Buf(WR_TX_PLOAD, Buffer, TX_PLOAD_WIDTH,0);                  // 写数据包到TX
 
   SPI_RW_Reg(WRITE_REG + EN_AA, 0x01,0);       // 使能接收通道0自动应答
   SPI_RW_Reg(WRITE_REG + EN_RXADDR, 0x01,0);   // 使能接收通道0
   SPI_RW_Reg(WRITE_REG + SETUP_RETR, 0x01,0);  // 自动重发延时等待250us+86us,自动重发10次
   SPI_RW_Reg(WRITE_REG + RF_CH, 40,0);         // 选择射频通道0x40
   SPI_RW_Reg(WRITE_REG + RF_SETUP, 0x07,0);    // 数据传输率1Mbps,发射功率0dBm,低噪声放大器增益
   SPI_RW_Reg(WRITE_REG + CONFIG, 0x0e,0);      // CRC使能,16位CRC校验,上电
 CEH();
 Delay_10us();
 Delay_10us();
}
      
void CheckButtons()
{
 GPIO3DIR &= ~KEY;
 if((GPIO3DATA&KEY)==0x00)              // 读取P3^0状态
 {
   flag = 1;     
 }
}

int main(void)
{
    targetInit();                                   /*  初始化目标板,切勿删除      */
    pinInit();                                      /*  引脚初始化                  */
       SYSAHBCLKCTRL |= (1ul << 6);                  /*  使能GPIO模块时钟  使能16位定时器计时器0的时钟          */ 
    INIT_IO();                                // 初始化IO
    BEEPOFF();                                      //初始化让P2^0,P2^1小灯熄灭    
   
    TX_Mode();
    RX_Mode();
    while(1)
 {      
  CheckButtons();
  if(flag==1)
  {
    flag = 0;
       TX_Mode();
    myDelay(10);
    if(!(GPIO0DATA&IRQ0))
    {
       sta=SPI_Read(STATUS,0);
    switch(sta & 0x30)
    {
       case 0x10:                //MAX_RT IRQ
    GPIO2DATA &= ~(1<<0);
    SPI_RW_Reg(FLUSH_TX,0,0);break;
    case 0x20:                //TX_DS IRQ
    GPIO2DATA  &= ~(1<<1);break;
    default:GPIO2DATA  &= ~(3<<0);break;
    }
    SPI_RW_Reg(WRITE_REG+STATUS,0xff,0);// clear RX_DR or TX_DS or MAX_RT interrupt flag
    }
   if(!(GPIO2DATA&R_IRQ0))
   {
      sta=SPI_Read(STATUS,1);
   if(sta&RX_DR)     // if renRF24L01_CEive data ready (RX_DR) interrupt
   {
   SPI_Read_Buf(RD_RX_PLOAD,Buffer1,TX_PLOAD_WIDTH,1);// read renRF24L01_CEive payload from RX_FIFO buffer
      //   GPIO2DATA |= 0XFD;
   }
   SPI_RW_Reg(WRITE_REG+STATUS,0xff,1);// clear RX_DR or TX_DS or MAX_RT interrupt flag
            RX_Mode();
   }
    
  }
  
  
     }

}


 



这篇文章被编辑了 1 次. 最近一次更新是在 2011/09/23 02:03

[加为好友] 回复 引用回复
[Down] [Up]
[1楼] 782861417


等级:NO
注册时间:
2011/06/01 16:02
文章: 5
来自: 江苏&nbsp;
离线

顺便说一下,我用的是IO口模拟SPI口得方法通信的


[加为好友] 回复 引用回复
[Down] [Up]
[2楼] 正点原子


等级:NO
注册时间:
2010/12/02 10:41
文章: 8097
来自: 湖南
离线

回复【1楼】 782861417 :
---------------------------------
模拟的你要注意下时序电平了.
NRF24L01好像是要求在空闲时候SCK是低电平的.
 
至于没反应,那就得一步步来了.先看有没有应答.应答有了再看有没有正确写入,正确写入了再看有没有配置正确.总之,方法总是有的.



我的淘宝小店:http://shop62103354.taobao.com
[加为好友] 回复 引用回复
[Down] [Up]
[3楼] 782861417


等级:NO
注册时间:
2011/06/01 16:02
文章: 5
来自: 江苏&nbsp;
离线

回复【2楼】 正点原子 :
---------------------------------
谢谢了,我再检查一下我的时序,希望可以检查出来问题


[加为好友] 回复 引用回复
 
前往: 

Powered by ALIENTEK工作室 © 粤ICP备12000418号-1