/*
This software uses a BSD license.
Copyright (c) 2010, Sean Cross / chumby industries
All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions
are met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above copyright
notice, this list of conditions and the following disclaimer in the
documentation and/or other materials provided with the
distribution.
* Neither the name of Sean Cross / chumby industries nor the names
of its contributors may be used to endorse or promote products
derived from this software without specific prior written
permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY
WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
POSSIBILITY OF SUCH DAMAGE.
*/
#include <stdio.h>
#include <linux/i2c.h>
#include <linux/i2c-dev.h>
#include <fcntl.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/ioctl.h>
#include <string.h>
#define I2C_FILE_NAME "/dev/i2c-1"
#define USAGE_MESSAGE \
"Usage:\n" \
" %s r [addr] [register] " \
"to read value from [register]\n" \
" %s w [addr] [register] [value] " \
"to write a value [value] to register [register]\n" \
""
static int set_i2c_register(int file,
unsigned char addr,
unsigned char reg,
unsigned char value) {
unsigned char outbuf[2];
struct i2c_rdwr_ioctl_data packets;
struct i2c_msg messages[1];
messages[0].addr = addr;
messages[0].flags = 0;
messages[0].len = sizeof(outbuf);
messages[0].buf = outbuf;
/* The first byte indicates which register we'll write */
outbuf[0] = reg;
/*
* The second byte indicates the value to write. Note that for many
* devices, we can write multiple, sequential registers at once by
* simply making outbuf bigger.
*/
outbuf[1] = value;
/* Transfer the i2c packets to the kernel and verify it worked */
packets.msgs = messages;
packets.nmsgs = 1;
if(ioctl(file, I2C_RDWR, &packets) < 0) {
perror("Unable to send data");
return 1;
}
return 0;
}
static int get_i2c_register(int file,
unsigned char addr,
unsigned char reg,
unsigned char *val) {
unsigned char inbuf, outbuf;
struct i2c_rdwr_ioctl_data packets;
struct i2c_msg messages[2];
/*
* In order to read a register, we first do a "dummy write" by writing
* 0 bytes to the register we want to read from. This is similar to
* the packet in set_i2c_register, except it's 1 byte rather than 2.
*/
outbuf = reg;
messages[0].addr = addr;
messages[0].flags = 0;
messages[0].len = sizeof(outbuf);
messages[0].buf = &outbuf;
/* The data will get returned in this structure */
messages[1].addr = addr;
messages[1].flags = I2C_M_RD/* | I2C_M_NOSTART*/;
messages[1].len = sizeof(inbuf);
messages[1].buf = &inbuf;
/* Send the request to the kernel and get the result back */
packets.msgs = messages;
packets.nmsgs = 2;
if(ioctl(file, I2C_RDWR, &packets) < 0) {
perror("Unable to send data");
return 1;
}
*val = inbuf;
return 0;
}
int main(int argc, char **argv) {
int i2c_file;
// Open a connection to the I2C userspace control file.
if ((i2c_file = open(I2C_FILE_NAME, O_RDWR)) < 0) {
perror("Unable to open i2c control file");
exit(1);
}
if(argc > 3 && !strcmp(argv[1], "r")) {
int addr = strtol(argv[2], NULL, 0);
int reg = strtol(argv[3], NULL, 0);
unsigned char value;
if(get_i2c_register(i2c_file, addr, reg, &value)) {
printf("Unable to get register!\n");
}
else {
printf("Register %d: %d (%x)\n", reg, (int)value, (int)value);
}
}
else if(argc > 4 && !strcmp(argv[1], "w")) {
int addr = strtol(argv[2], NULL, 0);
int reg = strtol(argv[3], NULL, 0);
int value = strtol(argv[4], NULL, 0);
if(set_i2c_register(i2c_file, addr, reg, value)) {
printf("Unable to get register!\n");
}
else {
printf("Set register %x: %d (%x)\n", reg, value, value);
}
}
else {
fprintf(stderr, USAGE_MESSAGE, argv[0], argv[0]);
}
close(i2c_file);
return 0;
}
分享到:
相关推荐
用户空间APP测试i2c接口或总线,用于嵌入式设备驱动开发或者应用开发都可以。
通过linux下的i2c设备对at24c08 进行读写
自己写的一个linux驱动及其应用程序,可以访问板子上的任何一个i2c地址。很方便使用的。 this is a i2c-access driver based on linux,easy to understand, now share with you.
这是一个C驱动程序,用于通过Raspberry Pi上的I2C操作Bosch BNO055 IMU传感器。 我将其与GY-BNO055和Adafruit BNO055一起使用。 在GY-BNO055上,我必须桥接两个焊盘以启用I2C模式,因为默认情况下为串行模式。 后来...
《嵌入式Linux应用程序开发标准教程(第2版)》主要分为3个部分,包括Linux基础、搭建嵌入式Linux环境和嵌入式Linux的应用开发。Linux基础部分从Linux基础、基本操作命令讲起,为Linux初学者能快速入门提供了保证。...
本程序是为了测试通过I2C方式读写OV3640的寄存器之用。 请注意:地址值为2个字节。比如:0x3005 address register name default value R/W description 0x3005 RED[7:0] 0x40 RW AWB Red Gain 0x3006 GREEN[7:0] 0x...
目前 IC卡的应用仍然非常广泛,而且大部分 IC...文中给出了在EP7312单片机组成的嵌入式系统中读写AT24C01A卡的具体方法, 同时给出了便携式金融 POS机的部分硬件电路以及在嵌入式Linux系统中实现I2C总线的具体程序代码。
6.4 嵌入式Linux串口应用开发 183 6.4.1 串口概述 183 6.4.2 串口设置详解 184 6.4.3 串口使用详解 191 6.5 标准I/O开发 194 6.5.1 打开和关闭文件 194 6.5.2 文件读写 197 6.5.3 输入输出 ...
13.6.2 高级主题:使用fifo的客户/服务器应用程序 464 13.7 cd数据库应用程序 468 13.7.1 目标 469 13.7.2 实现 469 13.7.3 客户接口函数 472 13.7.4 服务器接口server.c 478 13.7.5 管道 481 13.7.6 对cd...
CHA4 Linux内核I2C驱动 CHA5 usb-skeleton.c USB驱动框架 camera Spcaview相关代码 CHA6 skeleton FrameBuffer驱动框架 2410fb.c S3C2410X LCD驱动 CHA7 button.c 输入形式的按键驱动 LED.c 输入形式的LED灯驱动 ...
13.6.2 高级主题:使用fifo的客户/服务器应用程序 464 13.7 cd数据库应用程序 468 13.7.1 目标 469 13.7.2 实现 469 13.7.3 客户接口函数 472 13.7.4 服务器接口server.c 478 13.7.5 管道 481 13.7.6 对cd...
CHA4 Linux内核I2C驱动 CHA5 usb-skeleton.c USB驱动框架 camera Spcaview相关代码 CHA6 skeleton FrameBuffer驱动框架 2410fb.c S3C2410X LCD驱动 CHA7 button.c 输入形式的按键驱动 LED.c 输入形式的LED灯驱动 ...
D.2 Linux上的C/C++编译器和调试器 238 D.2.1 运行gcc/egcs 238 D.2.2 gcc/egcs的主要选项 240 D.2.3 gdb简介 240 D.2.4 gdb的常用命令 241 D.2.5 gdb使用示例 242 D.3 GNU make和makefile 243 D.3.1 GNU make 243 D...
CHA4 Linux内核I2C驱动 CHA5 usb-skeleton.c USB驱动框架 camera Spcaview相关代码 CHA6 skeleton FrameBuffer驱动框架 2410fb.c S3C2410X LCD驱动 CHA7 button.c 输入形式的按键驱动 LED.c 输入形式的LED灯驱动 usb...
CHA4 Linux内核I2C驱动 CHA5 usb-skeleton.c USB驱动框架 camera Spcaview相关代码 CHA6 skeleton FrameBuffer驱动框架 2410fb.c S3C2410X LCD驱动 CHA7 button.c 输入形式的按键驱动 LED.c 输入形式的LED灯驱动 usb...
CHA4 Linux内核I2C驱动 CHA5 usb-skeleton.c USB驱动框架 camera Spcaview相关代码 CHA6 skeleton FrameBuffer驱动框架 2410fb.c S3C2410X LCD驱动 CHA7 button.c 输入形式的按键驱动 LED.c 输入形式的LED灯驱动 ...
CHA4 Linux内核I2C驱动 CHA5 usb-skeleton.c USB驱动框架 camera Spcaview相关代码 CHA6 skeleton FrameBuffer驱动框架 2410fb.c S3C2410X LCD驱动 CHA7 button.c 输入形式的按键驱动 LED.c 输入形式的LED灯驱动 usb...
CHA4 Linux内核I2C驱动 CHA5 usb-skeleton.c USB驱动框架 camera Spcaview相关代码 CHA6 skeleton FrameBuffer驱动框架 2410fb.c S3C2410X LCD驱动 CHA7 button.c 输入形式的按键驱动 LED.c 输入形式的LED灯驱动 usb...
CHA4 Linux内核I2C驱动 CHA5 usb-skeleton.c USB驱动框架 camera Spcaview相关代码 CHA6 skeleton FrameBuffer驱动框架 2410fb.c S3C2410X LCD驱动 CHA7 button.c 输入形式的按键驱动 LED.c 输入形式的LED灯驱动 usb...