为什么i2c_smbus函数不可用?(I2C -嵌入式Linux)

时间:2022-03-15 02:03:18

There are many references to using i2c_smbus_ functions when developing embedded Linux software to communicate on the I2C bus. When i2c_smbus functions such as i2c_smbus_read_word_data are referenced in software project for ARM8 processor errors such as ‘i2c_smbus_read_word_data’ was not declared in this scope are generated at compile.

在开发嵌入式Linux软件以在I2C总线上进行通信时,有许多关于使用i2c_smbus_函数的引用。当在software project中引用i2c_smbus函数(如i2c_smbus_read_word_data)处理ARM8处理器错误(如“i2c_smbus_read_data”在此范围内未声明)时,将在编译时生成。

Investigation of the following header files indicate the absence of most i2c_smbus function definition.

对以下头文件的研究表明,大多数i2c_smbus函数没有定义。

  • /usr/arm-linux-gnueabi/include/linux/i2c.h
  • /usr/arm-linux-gnueabi / include / linux / i2c.h
  • /usr/arm-linux-gnueabi/include/linux/i2c-dev.h
  • /usr/arm-linux-gnueabi / include / linux / i2c-dev.h

Also in that following reference i2c.h file has all the i2c_smbus defined.

也在后面的参考i2c中。h文件定义了所有i2c_smbus。

How can this problem be resolved?

如何解决这个问题?

Research references

研究参考

  1. Using I2C from userspace in Linux
  2. 在Linux中使用来自用户空间的I2C。
  3. I2C Communication from Linux Userspace – Part II
  4. 来自Linux用户空间的I2C通信-第2部分
  5. I2C dev interface
  6. I2C接口开发

3 个解决方案

#1


11  

Because you are using a wrong header file for your application.

因为应用程序使用了错误的头文件。

If you see an extern on the function i2c_smbus_read_word_data() in your header, it's a header file for your kernel, but not for your application. The Linux kernel has i2c_smbus_read_word_data() and other i2c smbus functions for its internal use. But they are a) not system calls, or b) not accessible from your application.

如果您在header中的函数i2c_smbus_read_word_data()上看到一个extern,它是内核的头文件,但不是应用程序的头文件。Linux内核有i2c_smbus_read_word_data()和其他i2c smbus函数供内部使用。但它们是a)非系统调用,或b)无法从您的应用程序访问。

Instead, get i2c-tools from lm-sensors and install it. If you are using Debian, just

相反,从lm传感器中获取i2c工具并安装它。如果你用Debian的话

sudo apt-get install libi2c-dev

and use i2c_smbus_read_word_data() or any other interfaces they offer. i2c-dev is a header only package, meaning that there is no library to link to. All functions are inline functions defined using ioctl().

并使用i2c_smbus_read_word_data()或它们提供的任何其他接口。i2c-dev是一个头文件包,意味着没有要链接的库。所有函数都是使用ioctl()定义的内联函数。

e.g.)

例如。)

static inline __s32 i2c_smbus_access(int file, char read_write, __u8 command,
                                     int size, union i2c_smbus_data *data)
{
        struct i2c_smbus_ioctl_data args;

        args.read_write = read_write;
        args.command = command;
        args.size = size;
        args.data = data;
        return ioctl(file,I2C_SMBUS,&args);
}
   :
static inline __s32 i2c_smbus_read_word_data(int file, __u8 command)
{
        union i2c_smbus_data data;
        if (i2c_smbus_access(file,I2C_SMBUS_READ,command,
                             I2C_SMBUS_WORD_DATA,&data))
                return -1;
        else
                return 0x0FFFF & data.word;
}

#2


2  

I ran into this today. The i2c_smbus_* functions are defined in:

我今天遇到了这个问题。i2c_smbus_*函数定义为:

/usr/include/linux/i2c-dev.h

...but when I would try to cross-compile for ARM on an older version of Ubuntu, I was running into errors such:

…但是当我尝试在旧版本的Ubuntu上交叉编译ARM时,我遇到了一些错误:

i2c_smbus_read_block_data was not declared in this scope

Turns out the functions are not defined in the equivalent ARM-specific location:

结果显示,在等效的arm特定位置中没有定义函数:

/usr/arm-linux-gnueabi/include/linux/i2c-dev.h

When cross-compiling, this 2nd older header file is the one used. Had to re-declare locally a few of the inline i2c_smbus_... functions to get around the problem.

当交叉编译时,使用的是第2个旧的头文件。必须在本地重新声明一些内联i2c_smbus_…函数来解决这个问题。

#3


1  

From the i2c Linux kernel documentation:

来自i2c Linux内核文档:

Please note that there are two files named "i2c-dev.h" out there, one is distributed with the Linux kernel and is meant to be included from kernel driver code, the other one is distributed with i2c-tools and is meant to be included from user-space programs. You obviously want the second one here.

请注意,有两个文件名为“i2c-dev”。h“在那里,一个是与Linux内核一起发布的,它应该包含在内核驱动程序代码中,另一个是与i2c工具一起发布的,并且应该包含在用户空间程序中。显然你想要第二个。

So you need to include the i2c-dev.h from i2c-tools not from the Linux kernel.

所以你需要包含i2c-dev。h来自i2c-tools而不是Linux内核。

#1


11  

Because you are using a wrong header file for your application.

因为应用程序使用了错误的头文件。

If you see an extern on the function i2c_smbus_read_word_data() in your header, it's a header file for your kernel, but not for your application. The Linux kernel has i2c_smbus_read_word_data() and other i2c smbus functions for its internal use. But they are a) not system calls, or b) not accessible from your application.

如果您在header中的函数i2c_smbus_read_word_data()上看到一个extern,它是内核的头文件,但不是应用程序的头文件。Linux内核有i2c_smbus_read_word_data()和其他i2c smbus函数供内部使用。但它们是a)非系统调用,或b)无法从您的应用程序访问。

Instead, get i2c-tools from lm-sensors and install it. If you are using Debian, just

相反,从lm传感器中获取i2c工具并安装它。如果你用Debian的话

sudo apt-get install libi2c-dev

and use i2c_smbus_read_word_data() or any other interfaces they offer. i2c-dev is a header only package, meaning that there is no library to link to. All functions are inline functions defined using ioctl().

并使用i2c_smbus_read_word_data()或它们提供的任何其他接口。i2c-dev是一个头文件包,意味着没有要链接的库。所有函数都是使用ioctl()定义的内联函数。

e.g.)

例如。)

static inline __s32 i2c_smbus_access(int file, char read_write, __u8 command,
                                     int size, union i2c_smbus_data *data)
{
        struct i2c_smbus_ioctl_data args;

        args.read_write = read_write;
        args.command = command;
        args.size = size;
        args.data = data;
        return ioctl(file,I2C_SMBUS,&args);
}
   :
static inline __s32 i2c_smbus_read_word_data(int file, __u8 command)
{
        union i2c_smbus_data data;
        if (i2c_smbus_access(file,I2C_SMBUS_READ,command,
                             I2C_SMBUS_WORD_DATA,&data))
                return -1;
        else
                return 0x0FFFF & data.word;
}

#2


2  

I ran into this today. The i2c_smbus_* functions are defined in:

我今天遇到了这个问题。i2c_smbus_*函数定义为:

/usr/include/linux/i2c-dev.h

...but when I would try to cross-compile for ARM on an older version of Ubuntu, I was running into errors such:

…但是当我尝试在旧版本的Ubuntu上交叉编译ARM时,我遇到了一些错误:

i2c_smbus_read_block_data was not declared in this scope

Turns out the functions are not defined in the equivalent ARM-specific location:

结果显示,在等效的arm特定位置中没有定义函数:

/usr/arm-linux-gnueabi/include/linux/i2c-dev.h

When cross-compiling, this 2nd older header file is the one used. Had to re-declare locally a few of the inline i2c_smbus_... functions to get around the problem.

当交叉编译时,使用的是第2个旧的头文件。必须在本地重新声明一些内联i2c_smbus_…函数来解决这个问题。

#3


1  

From the i2c Linux kernel documentation:

来自i2c Linux内核文档:

Please note that there are two files named "i2c-dev.h" out there, one is distributed with the Linux kernel and is meant to be included from kernel driver code, the other one is distributed with i2c-tools and is meant to be included from user-space programs. You obviously want the second one here.

请注意,有两个文件名为“i2c-dev”。h“在那里,一个是与Linux内核一起发布的,它应该包含在内核驱动程序代码中,另一个是与i2c工具一起发布的,并且应该包含在用户空间程序中。显然你想要第二个。

So you need to include the i2c-dev.h from i2c-tools not from the Linux kernel.

所以你需要包含i2c-dev。h来自i2c-tools而不是Linux内核。