简单的示例,根据各自的情况修改~
#include <linux/module.h>
#include <linux/kernel.h>
#include <asm/io.h>
#include <linux/delay.h>
#include <linux/gpio.h>
#define GPIO_W_ADDR 0x6a
#define GPIO_R_ADDR (GPIO_W_ADDR | 0x1)
#define GPIO_SDA S5PV210_GPH3(3) //随便写的gpio
#define GPIO_SCL S5PV210_GPH3(4)
#define GPIO_SDA_OUTP s3c_gpio_cfgpin(GPIO_SDA, S3C_GPIO_OUTPUT) //设定SDA输出
#define GPIO_SDA_INP s3c_gpio_cfgpin(GPIO_SDA, S3C_GPIO_INPUT) //设定SDA输入
#define GPIO_SCL_OUTP s3c_gpio_cfgpin(GPIO_SCL, S3C_GPIO_OUTPUT) //设定SCL输出
#define GPIO_SDA_H gpio_set_value(GPIO_SDA, 1)
#define GPIO_SDA_L gpio_set_value(GPIO_SDA, 0)
#define GPIO_SCL_H gpio_set_value(GPIO_SCL, 1)
#define GPIO_SCL_L gpio_set_value(GPIO_SCL, 0)
/************************************
GPIO 初始化
*************************************/
void gpio_init(void)
{
s3c_gpio_setpull(GPIO_SCL, S3C_GPIO_PULL_NONE); //disable pull up&down
s3c_gpio_setpull(GPIO_SDA, S3C_GPIO_PULL_NONE);
GPIO_SDA_OUTP;
GPIO_SCL_OUTP;
}
/************************************
总线初始化
*************************************/
void i2c_init(void)
{
GPIO_SCL_L;
udelay(5);
GPIO_SDA_H;
udelay(5);
GPIO_SCL_H;
udelay(5);
}
/************************************
接收ACK
*************************************/
void receive_ack(void)
{
unsigned long ack;
GPIO_SDA_INP; // Function <- Input (SDA)
GPIO_SCL_L;
udelay(5);
GPIO_SCL_H;
udelay(5);
ack = gpio_get_value(GPIO_SDA);
GPIO_SCL_H;
udelay(5);
while(ack!=0) //接收到非应答信号,等待!这里最好不要写成死循环的形式,因为是示例,我就随意了!
{
GPIO_SCL_L;
udelay(5);
GPIO_SCL_H;
udelay(5);
ack = gpio_get_value(GPIO_SDA);
printk("++++++++there is no ack +++++++++\n");
}
GPIO_SCL_L;
udelay(5);
GPIO_SDA_OUTP; // Function <- Output (SDA)
}
/************************************
起始信号
*************************************/
void i2c_start(void)
{
GPIO_SCL_L;
udelay(5);
GPIO_SDA_H;
udelay(5);
GPIO_SCL_H;
udelay(5);
GPIO_SDA_L;
udelay(5);
}
/************************************
停止信号
*************************************/
void i2c_stop(void)
{
GPIO_SCL_L;
udelay(5);
GPIO_SDA_L;
udelay(5);
GPIO_SCL_H;
udelay(5);
GPIO_SDA_H;
udelay(5);
}
/************************************
写一个字节
*************************************/
void i2c_byte_write(unsigned char dat)
{
unsigned long i;
for(i = 8; i > 0; i--)
{
GPIO_SCL_L; //SCL拉低,使SDA变化有效
udelay(5);
if((dat >> (i-1)) & 0x0001)
GPIO_SDA_H; //SDA变化
else
GPIO_SDA_L;
udelay(5);
GPIO_SCL_H; //SCL拉高, 从机读取SDA
udelay(5);
}
GPIO_SCL_L;
udelay(5);
GPIO_SDA_H; //主机释放SDA,等待从机发送ACK或者NOACK
udelay(5);
receive_ack();
}
/************************************
读一个字节
*************************************/
unsigned char i2c_byte_read(void)
{
unsigned long i, dat = 0;
GPIO_SDA_H; //释放SDA
udelay(5);
GPIO_SDA_INP; // Function <- Input
for(i = 0; i < 8; i++)
{
GPIO_SCL_H; //SCL拉高,等待从机发出SDA
udelay(5);
dat = (dat<<1)|(gpio_get_value(GPIO_SDA)); //读取从机发出的SDA
udelay(5);
GPIO_SCL_L; //SCL拉低,使从机改变或者SDA
udelay(5);
}
GPIO_SCL_H;
udelay(5);
GPIO_SCL_L;
udelay(5);
GPIO_SCL_L;
udelay(5);
GPIO_SCL_H;
udelay(5);
GPIO_SDA_OUTP; // Function <- Output (SDA)
return (unsigned char)dat;
}