📄 i2c.c
字号:
/****************************************Copyright (c)**************************************************
** Guangzou ZLG-MCU Development Co.,LTD.
** graduate school
** http://www.zlgmcu.com
**
**--------------File Info-------------------------------------------------------------------------------
** File name: i2c.c
** Last modified Date: 2005-05-17
** Last Version: 1.0
** Descriptions: This is a Kernel module for uClinux 2.4.x .** This module let uClinux 2.4.x can use I2C.
**------------------------------------------------------------------------------------------------------
** Created by: Chenmingji
** Created date: 2005-05-17
** Version: 1.0
** Descriptions: The original version
**
**------------------------------------------------------------------------------------------------------
** Modified by:
** Modified date:
** Version:
** Descriptions:
**
********************************************************************************************************/
#define IN_I2C#include "config.h"/********************************************************************************************************
function announce********************************************************************************************************/
#if 0static loff_t i2c_llseek(struct file *filp, loff_t off, int whence);#endif
static ssize_t i2c_write(struct file *filp, const char *buf, size_t count, loff_t *f_pos);static ssize_t i2c_read(struct file *filp, char *buf, size_t count, loff_t *f_pos);static int i2c_open(struct inode *inode, struct file *filp);static int i2c_release(struct inode *inode, struct file *filp); static int i2c_ioctl(struct inode *inode, struct file *filp, unsigned int cmd, unsigned long param);static void i2c_irq_handle(int irq, void *dev_id, struct pt_regs *regs);
int i2c_init(void);void i2c_cleanup(void);
/********************************************************************************************************
define announce********************************************************************************************************/
#define MAJOR_NR majormodule_init(i2c_init);module_exit(i2c_cleanup);MODULE_PARM(major, "i");MODULE_LICENSE("Proprietary");MODULE_DESCRIPTION("Guangzou ZLG-MCU Development Co.,LTD.\ngraduate school\nhttp://www.zlgmcu.com");MODULE_SUPPORTED_DEVICE("uClinux2.4.x LPC2200 i2c");MODULE_AUTHOR("chenmingji");/*********************************************************************************************************
** "全局和静态变量在这里定义"
** global variables and static variables define here
********************************************************************************************************/
unsigned int usage; /* device using count */struct semaphore sem, irq_sem; /* mutual exclusion semaphore */
static int major = I2C_MAJOR_NR;
static u32 PinSel0Save;
static u8 *I2cBuf;
static size_t I2cNbyte;
static u8 I2cAddr;
/********************************************************************************************************/
static struct file_operations i2c_fops = /* driver info */{ owner: THIS_MODULE,#if 0 llseek: i2c_llseek,#endif write: i2c_write, read: i2c_read, ioctl: i2c_ioctl, open: i2c_open, release: i2c_release,};#if 0/*********************************************************************************************************
** Function name: i2c_llseek
** Descriptions: move read and write point
** Input: filp: pointer of file
** off: ofset
** whence: move mode
** 0: seek set
** 1: seek file' current point
** 2: seek file' end
** Output : new point
** Created by: Chenmingji
** Created Date: 2005-5-17
**-------------------------------------------------------------------------------------------------------
** Modified by:
** Modified Date:
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
static loff_t i2c_llseek(struct file *filp, loff_t off, int whence){ return 0;}#endif
/*********************************************************************************************************
** Function name: i2c_read
** Descriptions: read device
** Input: filp: pointer of file
** buf: buf for save data
** count: size for read
** f_pos: *f_pos = read point
** Output : read size
** Created by: Chenmingji
** Created Date: 2005-5-17
**-------------------------------------------------------------------------------------------------------
** Modified by:
** Modified Date:
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
static ssize_t i2c_read(struct file *filp, char *buf, size_t count, loff_t *f_pos){
unsigned long flag;
unsigned int num;
if (!access_ok(VERIFY_WRITE, (void *)buf, _IOC_SIZE(cmd)))
{
return -EFAULT; }
if (down_interruptible(&sem))
{ return -ERESTARTSYS;
}
num = (unsigned int)filp->private_data;
local_irq_save(flag);
outl(0x6C, I2CONCLR);
outl(0x40, I2CONSET); /* 使能I2c */
I2cAddr = num | 0x01; /* 存储发送地址 */
I2cNbyte = count; /* 存储读字节数 */
I2cBuf = (u8 *)buf; /* 存储读到的数据 */
outl(0x24, I2CONSET); /* 设置为主机,并启动总线 */
local_irq_restore(flag);
if (down_interruptible(&irq_sem))
{ up(&sem);
return -ERESTARTSYS;
} up(&sem);
return count - I2cNbyte;
}
/*********************************************************************************************************
** Function name: i2c_write
** Descriptions: write device
** Input: filp: pointer of file
** buf: buf to write data
** count: size for write
** f_pos: *f_pos = write point
** Output : write size
** Created by: Chenmingji
** Created Date: 2005-5-17
**-------------------------------------------------------------------------------------------------------
** Modified by:
** Modified Date:
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
static ssize_t i2c_write(struct file *filp, const char *buf, size_t count, loff_t *f_pos){ unsigned long flag;
unsigned int num;
if (!access_ok(VERIFY_READ, (void *)buf, count))
{
return -EFAULT; }
num = (unsigned int)filp->private_data;
if (down_interruptible(&sem))
{ return -ERESTARTSYS;
}
local_irq_save(flag);
outl(0x6C, I2CONCLR);
outl(0x40, I2CONSET); /* 使能I2c */
I2cAddr = num & 0xfe; /* 存储发送地址 */
I2cNbyte = count; /* 存储写字节数 */
I2cBuf = (u8 *)buf; /* 存储写的数据的指针 */
outl(0x24, I2CONSET); /* 设置为主机,并启动总线 */
local_irq_restore(flag);
if (down_interruptible(&irq_sem))
{ up(&sem);
return -ERESTARTSYS;
} up(&sem);
return count - I2cNbyte;
} /*********************************************************************************************************
** Function name: i2c_open
** Descriptions: open device
** Input:inode: information of device
** filp: pointer of file
** Output 0: OK
** other: not OK
** Created by: Chenmingji
** Created Date: 2005-5-17
**-------------------------------------------------------------------------------------------------------
** Modified by:
** Modified Date:
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
static int i2c_open(struct inode *inode, struct file *filp){
unsigned long flag;
unsigned int num; u32 temp;
num = MINOR(inode->i_rdev);
if (usage == 0)
{
request_irq(IRQ_I2C, i2c_irq_handle, SA_INTERRUPT, "my" DEVICE_NAME, NULL);
local_irq_save(flag);
temp = inl(PINSEL0);
PinSel0Save = temp & (0x0f << 4);
temp &= ~(0xf << 4);
temp |= (0x05 << 4);
outl(temp, PINSEL0);
outl(0x6C, I2CONCLR); /* 清除控制寄存器 */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -