有没有人做过NRF24L01的mini2440接收的驱动???
自己最近在移植一个NRF24L01的驱动,可以在友善之臂的mini2440上运行,不过测试总是无法接收到发送过来的信号(发送端是好的,用的是51单片机控制的NRF24L01),不知道怎么回事,是驱动程序的问题?还是友善的mini2440上引出的CON4 GPIO引脚不能用(我用的就是它自带的linux系统)? 请大家指教!!!!!!!
下面是原驱动代码:
#ifndef _NRF24L01_H_
#define _NRF24L01_H_
#define DEVICE_NAME "NRF24L01"
#ifndef NRF24L01_MAJOR
#define NRF24L01_MAJOR 248
#endif
#ifndef NRF24L01_MINOR
#define NRF24L01_MINOR 0
#endif
#ifndef NRF24L01_NR_DEVS //
#define NRF24L01_NR_DEVS 1
#endif
//鍜屽紩鑴氱浉鍏崇殑瀹忓畾涔?
#define CSN S3C2410_GPG(0)
#define MOSI S3C2410_GPG(3)
#define IRQ S3C2410_GPG(5)
#define MISO S3C2410_GPG(6)
#define SCK S3C2410_GPG(7)
#define CE S3C2410_GPG(11)
//NRF24L01绔彛瀹氫箟
#define CE_OUTs3c2410_gpio_cfgpin(CE,S3C2410_GPIO_OUTPUT)//
#define CE_UP s3c2410_gpio_pullup(CE, 1) //
#define CE_Ls3c2410_gpio_setpin(CE, 0) //
#define CE_Hs3c2410_gpio_setpin(CE, 1) //
#define SCK_OUTs3c2410_gpio_cfgpin(SCK,S3C2410_GPIO_OUTPUT)//
#define SCK_UP s3c2410_gpio_pullup(SCK, 1) //
#define SCK_Ls3c2410_gpio_setpin(SCK, 0)//
#define SCK_Hs3c2410_gpio_setpin(SCK, 1)//
#define MISO_INs3c2410_gpio_cfgpin(MISO,S3C2410_GPIO_INPUT) /
#define MISO_UP s3c2410_gpio_pullup(MISO, 1) //
#define MISO_STU s3c2410_gpio_getpin(MISO) //
#define IRQ_INs3c2410_gpio_cfgpin(IRQ,S3C2410_GPIO_INPUT) //
#define IRQ_UP s3c2410_gpio_pullup(IRQ, 1) //
#define IRQ_Ls3c2410_gpio_setpin(IRQ, 0) //
#define IRQ_Hs3c2410_gpio_setpin(IRQ, 1) //
#define MOSI_OUT s3c2410_gpio_cfgpin(MOSI,S3C2410_GPIO_OUTPUT) //
#define MOSI_UP s3c2410_gpio_pullup(MOSI, 1) //
#define MOSI_Ls3c2410_gpio_setpin(MOSI, 0)//
#define MOSI_Hs3c2410_gpio_setpin(MOSI, 1)/
#define CSN_OUTs3c2410_gpio_cfgpin(CSN,S3C2410_GPIO_OUTPUT) //
#define CSN_UP s3c2410_gpio_pullup(CSN, 1) //
#define CSN_Ls3c2410_gpio_setpin(CSN, 0)//
#define CSN_Hs3c2410_gpio_setpin(CSN, 1)//
//NRF24L01
#define TX_ADR_WIDTH 5 // 5 uint8s TX address width
#define RX_ADR_WIDTH 5 // 5 uint8s RX address width
#define TX_PLOAD_WIDTH20 // 20 uint8s TX payload
#define RX_PLOAD_WIDTH20 // 20 uint8s TX payload
unsigned char TX_ADDRESS= {0x34,0x43,0x10,0x10,0x01}; //
unsigned charRX_ADDRESS= {0x34,0x43,0x10,0x10,0x01}; //
//NRF24L01瀵勫瓨鍣ㄦ寚浠?
#define READ_REG 0x00 //
#define WRITE_REG 0x20 //
#define RD_RX_PLOAD 0x61 // 璇诲彇鎺ユ敹鏁版嵁鎸囦护
#define WR_TX_PLOAD 0xA0 // 鍐欏緟鍙戞暟鎹寚浠?
#define FLUSH_TX 0xE1 // 鍐叉礂鍙戦€?FIFO鎸囦护
#define FLUSH_RX 0xE2 // 鍐叉礂鎺ユ敹 FIFO鎸囦护
#define REUSE_TX_PL 0xE3 // 瀹氫箟閲嶅瑁呰浇鏁版嵁鎸囦护
#define NOP 0xFF // 淇濈暀
//SPI(nRF24L01)瀵勫瓨鍣ㄥ湴鍧€
#define CONFIG 0x00// 閰嶇疆鏀跺彂鐘舵€侊紝CRC鏍¢獙妯″紡浠ュ強鏀跺彂鐘舵€佸搷搴旀柟寮?
#define EN_AA 0x01// 鑷姩搴旂瓟鍔熻兘璁剧疆
#define EN_RXADDR 0x02// 鍙敤淇¢亾璁剧疆
#define SETUP_AW 0x03// 鏀跺彂鍦板潃瀹藉害璁剧疆
#define SETUP_RETR 0x04// 鑷姩閲嶅彂鍔熻兘璁剧疆
#define RF_CH 0x05// 宸ヤ綔棰戠巼璁剧疆
#define RF_SETUP 0x06// 鍙戝皠閫熺巼銆佸姛鑰楀姛鑳借缃?
#define STATUS 0x07// 鐘舵€佸瘎瀛樺櫒
#define OBSERVE_TX 0x08// 鍙戦€佺洃娴嬪姛鑳?
#define CD 0x09// 鍦板潃妫€娴?
#define RX_ADDR_P0 0x0A// 棰戦亾0鎺ユ敹鏁版嵁鍦板潃
#define RX_ADDR_P1 0x0B// 棰戦亾1鎺ユ敹鏁版嵁鍦板潃
#define RX_ADDR_P2 0x0C// 棰戦亾2鎺ユ敹鏁版嵁鍦板潃
#define RX_ADDR_P3 0x0D// 棰戦亾3鎺ユ敹鏁版嵁鍦板潃
#define RX_ADDR_P4 0x0E// 棰戦亾4鎺ユ敹鏁版嵁鍦板潃
#define RX_ADDR_P5 0x0F// 棰戦亾5鎺ユ敹鏁版嵁鍦板潃
#define TX_ADDR 0x10// 鍙戦€佸湴鍧€瀵勫瓨鍣?
#define RX_PW_P0 0x11// 鎺ユ敹棰戦亾0鎺ユ敹鏁版嵁闀垮害
#define RX_PW_P1 0x12// 鎺ユ敹棰戦亾0鎺ユ敹鏁版嵁闀垮害
#define RX_PW_P2 0x13// 鎺ユ敹棰戦亾0鎺ユ敹鏁版嵁闀垮害
#define RX_PW_P3 0x14// 鎺ユ敹棰戦亾0鎺ユ敹鏁版嵁闀垮害
#define RX_PW_P4 0x15// 鎺ユ敹棰戦亾0鎺ユ敹鏁版嵁闀垮害
#define RX_PW_P5 0x16// 鎺ユ敹棰戦亾0鎺ユ敹鏁版嵁闀垮害
#define FIFO_STATUS 0x17// FIFO鏍堝叆鏍堝嚭鐘舵€佸瘎瀛樺櫒璁剧疆
#endif /* _NRF24L01_H_ */
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/init.h>
#include <linux/mm.h>
#include <linux/fs.h>
#include <linux/types.h>
#include <linux/delay.h>
#include <linux/moduleparam.h>
#include <linux/slab.h>
#include <linux/errno.h>
#include <linux/ioctl.h>
#include <linux/cdev.h>
#include <linux/string.h>
#include <linux/list.h>
#include <linux/pci.h>
#include <linux/gpio.h>
#include <linux/sched.h>
#include <mach/regs-gpio.h>
#include <mach/hardware.h>
#include <asm/uaccess.h>
#include <asm/atomic.h>
#include <asm/unistd.h>
#include <asm/io.h>
#include <asm/system.h>
#include <asm/uaccess.h>
#include <asm/irq.h>
#include "NRF24L01.h"
static int nrf24l01_major=NRF24L01_MAJOR; //涓昏澶囧彿
static int nrf24l01_minor=NRF24L01_MINOR; //娆¤澶囧彿
dev_t dev;
struct cdev nrf24l01;
unsigned char TxBuf={0};
unsigned char RxBuf={0};
unsigned char opencount = 0; //鍏ㄥ眬鍙橀噺
unsigned char flag = 0;
char sta; //鐘舵€佹爣蹇?
void init_NRF24L01(void);
unsigned char SPI_RW(unsigned char tmp);
unsigned char SPI_Read(unsigned char reg);
void SetRX_Mode(void);
unsigned char SPI_RW_Reg(unsigned char reg, unsigned char value);
unsigned char SPI_Read_Buf(unsigned char reg, unsigned char *pBuf, unsigned char uchars);
unsigned charSPI_Write_Buf(unsigned char reg, unsigned char *pBuf, unsigned char uchars);
unsigned char nRF24L01_RxPacket(unsigned char* rx_buf);
void nRF24L01_TxPacket(unsigned char * tx_buf);
void init_NRF24L01(void) //NRF24L01鍒濆鍖?
{
MISO_UP;
CE_OUT;
CSN_OUT;
SCK_OUT;
MOSI_OUT;
MISO_IN;
IRQ_IN;
flag = 1;
udelay(100);
CE_L; // chip enable
// ndelay(60);
CSN_H; // Spi disable
// ndelay(60);
SCK_L; // Spi clock line init high
// ndelay(60);
SPI_Write_Buf(WRITE_REG + TX_ADDR, TX_ADDRESS, TX_ADR_WIDTH); // 鍐欐湰鍦板湴鍧€
SPI_Write_Buf(WRITE_REG + RX_ADDR_P0, RX_ADDRESS, RX_ADR_WIDTH); // 鍐欐帴鏀剁鍦板潃
SPI_RW_Reg(WRITE_REG + EN_AA, 0x01); //棰戦亾0鑷姩 ACK搴旂瓟鍏佽
SPI_RW_Reg(WRITE_REG + EN_RXADDR, 0x01);//鍏佽鎺ユ敹鍦板潃鍙湁棰戦亾0锛屽鏋滈渶瑕佸棰戦亾鍙互鍙傝€働age21
SPI_RW_Reg(WRITE_REG + RF_CH, 0); // 璁剧疆淇¢亾宸ヤ綔涓?.4GHZ锛屾敹鍙戝繀椤讳竴鑷?
SPI_RW_Reg(WRITE_REG + RX_PW_P0, RX_PLOAD_WIDTH); //璁剧疆鎺ユ敹鏁版嵁闀垮害锛屾湰娆¤缃负32瀛楄妭
SPI_RW_Reg(WRITE_REG + RF_SETUP, 0x07); //璁剧疆鍙戝皠閫熺巼涓?MHZ锛屽彂灏勫姛鐜囦负鏈€澶у€?dB
printk("init! \n");
// mdelay(1000);
}
//鍑芥暟锛歶nsigned char SPI_RW(uint8 tmp)
//鍔熻兘锛歂RF24L01鐨凷PI鍐欐椂搴弔mp
unsigned char SPI_RW(unsigned char tmp)
{
unsigned char bit_ctr;
for(bit_ctr=0 ;bit_ctr<8 ;bit_ctr++) // output 8-bit
{
if(tmp & 0x80) // output 'tmp', MSB to MOSI
MOSI_H;
else
MOSI_L;
tmp <<= 1; // shift next bit into MSB..
SCK_H; // Set SCK high..
// ndelay(60);
tmp |= MISO_STU; // capture current MISO bit
SCK_L; // ..then set SCK low again
// ndelay(60);
}
return(tmp); // return read tmp
}
//鍑芥暟锛歶nsigned char SPI_Read(uint8 reg)
//鍔熻兘锛歂RF24L01鐨凷PI鏃跺簭
unsigned char SPI_Read(unsigned char reg)
{
unsigned char reg_val;
CSN_L; // CSN low, initialize SPI communication...
// ndelay(60);
SPI_RW(reg); // Select register to read from..
reg_val = SPI_RW(0); // ..then read registervalue
CSN_H; // CSN high, terminate SPI communication
// ndelay(60);
return(reg_val); // return register value
}
//鍔熻兘锛歂RF24L01璇诲啓瀵勫瓨鍣ㄥ嚱鏁?
unsigned char SPI_RW_Reg(unsigned char reg, unsigned char value)
{
unsigned char status;
CSN_L; // CSN low, init SPI transaction
// ndelay(60);
status = SPI_RW(reg); // select register
SPI_RW(value); // ..and write value to it..
CSN_H; // CSN high again
// ndelay(60);
return(status); // return nRF24L01 status uint8
}
//鍑芥暟锛歶nsigned char SPI_Read_Buf(unsigned char reg, unsigned char *pBuf, unsigned char uchars)
//鍔熻兘: 鐢ㄤ簬璇绘暟鎹紝reg锛氫负瀵勫瓨鍣ㄥ湴鍧€锛宲Buf锛氫负寰呰鍑烘暟鎹湴鍧€锛寀chars锛氳鍑烘暟鎹殑涓暟
unsigned char SPI_Read_Buf(unsigned char reg, unsigned char *pBuf, unsigned char uchars)
{
unsigned char status,bit_ctr;
CSN_L; // Set CSN low, init SPI tranaction
// ndelay(60);
status = SPI_RW(reg); // Select register to write to and read status uint8
for(bit_ctr=0;bit_ctr<uchars;bit_ctr++)
{
pBuf = SPI_RW(0); //
// ndelay(20);
}
CSN_H;
// ndelay(60);
return(status); // return nRF24L01 status uint8
}
//鍑芥暟锛歶nsigned char SPI_Write_Buf(unsigned char reg, unsigned char *pBuf, unsigned char uchars)
//鍔熻兘: 鐢ㄤ簬鍐欐暟鎹細涓哄瘎瀛樺櫒鍦板潃锛宲Buf锛氫负寰呭啓鍏ユ暟鎹湴鍧€锛寀chars锛氬啓鍏ユ暟鎹殑涓暟
unsigned char SPI_Write_Buf(unsigned char reg, unsigned char *pBuf, unsigned char uchars)
{
unsigned char status,bit_ctr;
CSN_L; //SPI浣胯兘
// ndelay(60);
status = SPI_RW(reg);
for(bit_ctr=0; bit_ctr<uchars; bit_ctr++) //
{
SPI_RW(*pBuf++);
//ndelay(20);
}
CSN_H; //鍏抽棴SPI
// ndelay(60);
return(status); //
}
//鍑芥暟锛歷oid SetRX_Mode(void)
//鍔熻兘锛氭暟鎹帴鏀堕厤缃?
void SetRX_Mode(void)
{
CE_L;
// ndelay(60);
SPI_RW_Reg(WRITE_REG + CONFIG, 0x0f); // IRQ鏀跺彂瀹屾垚涓柇鍝嶅簲锛?6浣岰RC 锛屼富鎺ユ敹
CE_H;
udelay(130);
}
//鍑芥暟锛歶nsigned char nRF24L01_RxPacket(unsigned char* rx_buf)
//鍔熻兘锛氭暟鎹鍙栧悗鏀惧rx_buf鎺ユ敹缂撳啿鍖轰腑
unsigned char nRF24L01_RxPacket(unsigned char* rx_buf)
{
unsigned char revale=0;
sta = 0;
sta=SPI_Read(STATUS); // 璇诲彇鐘舵€佸瘎瀛樺叾鏉ュ垽鏂暟鎹帴鏀剁姸鍐?
printk("sta is %d \n",sta);
if(sta&0x40) // 鍒ゆ柇鏄惁鎺ユ敹鍒版暟鎹?
{
CE_L; //SPI浣胯兘
// udelay(50);
SPI_Read_Buf(RD_RX_PLOAD,rx_buf,TX_PLOAD_WIDTH);// read receive payload from RX_FIFO buffer
revale =1; //璇诲彇鏁版嵁瀹屾垚鏍囧織
printk("rx_buf is %s \n",rx_buf);
}
SPI_RW_Reg(WRITE_REG+STATUS,sta); //鎺ユ敹鍒版暟鎹悗RX_DR,TX_DS,MAX_PT閮界疆楂樹负1锛岄€氳繃鍐?鏉ユ竻妤氫腑鏂爣蹇?
return revale;
}
//鍑芥暟锛歷oid nRF24L01_TxPacket(unsigned char * tx_buf)
//鍔熻兘锛氬彂閫?tx_buf涓暟鎹?
void nRF24L01_TxPacket(unsigned char * tx_buf)
{
CE_L; //StandBy I妯″紡
// ndelay(60);
SPI_Write_Buf(WRITE_REG + RX_ADDR_P0, TX_ADDRESS, TX_ADR_WIDTH); // 瑁呰浇鎺ユ敹绔湴鍧€
SPI_Write_Buf(WR_TX_PLOAD, tx_buf, TX_PLOAD_WIDTH); // 瑁呰浇鏁版嵁
SPI_RW_Reg(WRITE_REG + CONFIG, 0x0e); // IRQ鏀跺彂瀹屾垚涓柇鍝嶅簲锛?6浣岰RC锛屼富鍙戦€?
CE_H; //缃珮CE锛屾縺鍙戞暟鎹彂閫?
udelay(10);
}
//鏂囦欢鐨勫啓鍑芥暟
static ssize_t nrf24l01_write(struct file *filp, const char *buffer,
size_t size, loff_t *ppos)
{
if( copy_from_user( &TxBuf, buffer, size ) ); //浠庡唴鏍哥┖闂村鍒跺埌鐢ㄦ埛绌洪棿
{
printk("Can't Send Data !");
return -EFAULT;
}
nRF24L01_TxPacket(TxBuf);
SPI_RW_Reg(WRITE_REG+STATUS,0XFF);
printk("OK! \n");
return(0);
}
//鏂囦欢鐨勮鍑芥暟
static ssize_t nrf24l01_read(struct file *filp, char *buffer,
size_t size, loff_t *ppos)
{
int ret,t;
unsigned char a,b;
SetRX_Mode();
mdelay(10);
nRF24L01_RxPacket(RxBuf);
a = RxBuf;
b = RxBuf;
printk("this is %d \n",a);
printk("this is %d \n",b);
t=b;
t<<=8;
t=t|a; //涓ゅ瓧鑺傚悎鎴愪竴涓暣鍨嬪彉閲忋€?
mdelay(100);
ret=copy_to_user(buffer,&t,size); //鐢卞唴鏍镐紶鍒扮敤鎴风┖闂?
if(ret>0){
return -EFAULT;
}
return 0;
}
static int nrf24l01_open(struct inode *node, struct file *file)
{
if(opencount == 1)
return -EBUSY;
init_NRF24L01();
TxBuf = 1;
TxBuf = 1;
nRF24L01_TxPacket(TxBuf); // Transmit Tx buffer data
mdelay(100);
if(flag == 0)
{
printk("unable to open device!\n");
return -1;
}
else
{
opencount++;
printk("device opened !\n");
return 0;
}
}
static int nrf24l01_release(struct inode *node, struct file *file)
{
opencount--;
printk(DEVICE_NAME " released !\n");
return 0;
}
static struct file_operations nrf24l01_fops = {
.owner = THIS_MODULE,
.open = nrf24l01_open,
.write = nrf24l01_write,
.read = nrf24l01_read,
.release = nrf24l01_release,
};
static int __init nrf24l01_init(void)
{
int result;
printk("Initial driver for NRF24L01......................\n");
if(nrf24l01_major){
dev = MKDEV(nrf24l01_major,nrf24l01_minor);
result = register_chrdev_region(dev,NRF24L01_NR_DEVS,DEVICE_NAME);
}else{
result = alloc_chrdev_region(&dev,nrf24l01_minor,NRF24L01_NR_DEVS,DEVICE_NAME);
nrf24l01_major = MAJOR(dev);
}
if(result<0){
printk("nrf24l01:can't get major %d\n",nrf24l01_major);
return result;
}
cdev_init(&nrf24l01,&nrf24l01_fops);
nrf24l01.owner = THIS_MODULE;
nrf24l01.ops = &nrf24l01_fops;
cdev_add(&nrf24l01,dev,NRF24L01_NR_DEVS);
return 0;
}
static void __exit nrf24l01_exit(void)
{
cdev_del(&nrf24l01);
unregister_chrdev_region(NRF24L01_MAJOR,NRF24L01_NR_DEVS);
printk("NRF24L01 DEVICE REMOVE!\n");
}
module_init(nrf24l01_init);
module_exit(nrf24l01_exit);
MODULE_AUTHOR("XX");
MODULE_DESCRIPTION("nrf24l01 driver for mini2440");
MODULE_LICENSE("GPL");
页:
[1]