2440 iic 驱动

来源:互联网 发布:软件开发公司排行榜 编辑:程序博客网 时间:2024/05/18 23:27

将一个组中的数据写入到AT24C02中,然后再读出来!

以下为DOME程序!

#include <stdio.h>
#include <fcntl.h>
#include <unistd.h>
#define DEV_NAME  "/dev/2402_RW"
int main()
{ int fd,ret,i;
  intwr_data[5]={0x00,0x10,0x30,0x70,0xf0};
  int ra_data[5];
  fd=open(DEV_NAME,O_RDWR);
  if (fd<0)
   { printf ("the derive isopened fail !!\n");
     return fd;
     }
   else
    { printf("the derive is opened success !!\n");
  write(fd,wr_data,sizeof(wr_data));
    for(i=0;i<5;i++)
     { printf ("write-----data=%x\n",wr_data[i]);
            }
     sleep(2);
   read(fd,ra_data,20);
  for(i=0;i<5;i++)
    printf("read------data=%x\n",ra_data[i]);
             }
       }
   ret=close(fd);
   printf ("theret=%d\n",ret);
   }

以下为驱动源码!


#include <linux/kernel.h>
#include <linux/config.h>
#include <linux/init.h>
#include <linux/module.h>
#include <linux/fs.h>
#include<linux/devfs_fs_kernel.h>
#include <linux/delay.h>
#include<linux/interrupt.h>
#include<asm-generic/errno-base.h>
#include<asm/arch-s3c2410/regs-gpio.h>
#include<asm/arch-s3c2410/regs-iic.h>
#include<asm/arch-s3c2410/irqs.h>
#include <asm/hardware.h>
#include <asm/io.h>
#include <asm/uaccess.h>
#define  DEV_ID  107
#define  DEV_NAME "2402_RW"
#define  IICCON 0x54000000
#define  IICSTAT 0x54000004
#define  IICDS  0x5400000c
#define  IICADD 0x54000008
#define  IICLC  0x54000010
#define  CLKCON 0x4c00000c
static void *S3C2402_IICSTAT;
static void *S3C2402_IICCON;
static void *S3C2402_IICDS;
static void *S3C2402_IICADD;
static void *S3C2402_IICLC;
static void *S3C2440_CLKCON;
static int wr_data[5];
static int ra_data[5];
static int ack=0;
void delay(int t)
{ int i;
  for(;t>0;t--)
   {for(i=0;i<20000;i++);
     }
  }
static int open_2402(struct inode * inode, struct file *file)
  int cmmd;
   writel(0xc0000,S3C2410_GPEUP);
   s3c2410_gpio_cfgpin(S3C2410_GPE14,S3C2410_GPE14_IICSCL);
   s3c2410_gpio_cfgpin(S3C2410_GPE15,S3C2410_GPE15_IICSDA);   
   S3C2402_IICCON=ioremap(IICCON,0x00000004);                
 S3C2402_IICSTAT=ioremap(IICSTAT,0x00000004);
 S3C2402_IICDS=ioremap(IICDS,0x00000004);
 S3C2402_IICADD=ioremap(IICADD,0x00000004);
 S3C2402_IICLC=ioremap(IICLC,0X00000004);
 S3C2440_CLKCON=ioremap(CLKCON,0x00000004);
 writel(0xf3eb70,S3C2440_CLKCON);                          
 cmmd=((S3C2410_IICCON_ACKEN)|(S3C2410_IICCON_TXDIV_16)|(S3C2410_IICCON_IRQEN)|(0x0f));
 writel(cmmd,S3C2402_IICCON);       
 writel(0x10,S3C2402_IICADD);                           
 writel(0x10,S3C2402_IICSTAT);                          
 writel((S3C2410_IICLC_FILTER_ON|S3C2410_IICLC_SDA_DELAY5),S3C2402_IICLC);
 return 0;
    }
static int  write_2402(struct file * file, constchar __user * userbuf,size_t count, loff_t * off)
  int i;
   ack=0;
   if(copy_from_user(wr_data,userbuf,count)!=0)                                                                          
    { printk("write is error!!\n");
      return  EFAULT;
        }
 writel(0xa0,S3C2402_IICDS);                     
 writel(0xf0,S3C2402_IICSTAT);        
 udelay(100);
   while(ack==0);                                  
   ack=0;
 writel(0x00,S3C2402_IICDS);                     
 writel(0xaf,S3C2402_IICCON);     
 udelay(100);
 while(ack==0);
 ack=0;
 for(i=0;i<5;i++)
 
   writel(wr_data[i],S3C2402_IICDS);           
   printk("wr_data=%x\n",wr_data[i]);
   writel((readl(S3C2410_GPFDAT)|wr_data[i]),S3C2410_GPFDAT);
      writel(0xaf,S3C2402_IICCON);
   udelay(100);
   while(ack==0);
   printk("ack=%x\n",ack);
   ack=0;
   }
 writel(0xd0,S3C2402_IICSTAT);                
   writel(0xaf,S3C2402_IICCON);     
 udelay(100);
 
 return count;
  }
static int  read_2402 (struct file * file, char__user * userbuf, size_t count, loff_t * off)
  int i,a;
   ack=0;
   writel(0xa0,S3C2402_IICDS);                    
 writel(0xf0,S3C2402_IICSTAT);                 
 udelay(100);
 while(ack==0);
 ack=0;
   writel(0x00,S3C2402_IICDS);                    
   writel(0xaf,S3C2402_IICCON);
 udelay(100);
 while(ack==0);
 ack=0;
 writel(0xa1,S3C2402_IICDS);                    
   writel(0xb0,S3C2402_IICSTAT);                  
 writel(0xaf,S3C2402_IICCON);
 udelay(100);
 a=readl(S3C2402_IICDS);
 printk("a=%x\n",a);
 for (i=0;i<5;i++)
    {while(ack==0);
  printk("ack=%x\n",ack);
   ack=0;
  writel(0xaf,S3C2402_IICCON);
   udelay(100);
     ra_data[i]=readl(S3C2402_IICDS);             
  writel((readl(S3C2410_GPFDAT)|ra_data[i]),S3C2410_GPFDAT);
  printk("ra_data=%x\n",ra_data[i]);
  }
 writel(0x90,S3C2402_IICSTAT);                
   writel(0xaf,S3C2402_IICCON);
 udelay(100);
 
 if(copy_to_user(userbuf,ra_data,count)!=0)   
    {printk("read is error!!\n");
     return EFAULT;
   }
 return count;
  }
static irqreturn_t iic_interrupt(int irq,void *dev_id,structpt_regs *regs)  
{
  ack=1;
  return IRQ_HANDLED;
  }
static struct file_operations test_2402 ={
.open     open_2402,
.write    write_2402,
.read  read_2402,
};
static int __init init_2402(void)
{ int result,ret;
 result=register_chrdev(DEV_ID,DEV_NAME,&test_2402);
  if (result<0)
   { printk ("the derive registeris fail!!!\n");
     returnENODEV;
     }
  else
   { printk ("the derive registeris succss!!!\n");
     ret=request_irq(IRQ_IIC,&iic_interrupt,SA_INTERRUPT,DEV_NAME,&iic_interrupt);
      if(ret<0)
       { printk("the iic_interrupt is requesttedfail\n");
      return ENODEV;
        }
   else
    { printk("the iic_interrupt is requesttedsccuss!!\n");
      devfs_mk_cdev(MKDEV(DEV_ID,0),S_IFCHR | S_IRUSR |S_IWUSR,"2402_RW");
    returnret;
       }
     returnresult;
     }
   }
static void __exit exit_2402(void)
{ unregister_chrdev(DEV_ID,DEV_NAME);
  disable_irq(IRQ_IIC);
 free_irq(IRQ_IIC,&iic_interrupt);
  devfs_remove(DEV_NAME);
  printk ("the derive is unregister\n");
   }
module_init(init_2402);
module_exit(exit_2402);
MODULE_LICENSE("GPL");
MODULE_AUTHOR("KANG");
MODULE_DESCRIPTION("2402_READ_WRITE");


0 0
原创粉丝点击