You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Ubuntu下C++调用SMBus接口出现i2c_smbus_read_word_data未定义引用问题求助

问题解决:i2c_smbus_read_word_data 未定义引用错误

核心原因:链接库顺序错误

gcc链接器是按命令行顺序处理输入文件的,你把-li2c放在源文件前面时,链接器处理库的时候还没遇到需要解析的i2c_smbus_read_word_data符号,不会保留库中相关符号,后续处理源文件时自然找不到定义。

修正后的编译命令

gcc test_inc.cpp -li2c

将-li2c移到源文件名之后,让链接器先处理源文件的未定义符号,再从libi2c库中匹配对应的实现。

额外代码优化建议

  1. 移除ioctl失败分支里重复的return(1);,保留一个即可:
if (ioctl(file, I2C_SLAVE, addr) < 0) {
    return(1);
}
  1. 可以添加错误打印,方便调试定位问题:
#include <cstdio>
#include <errno.h>
#include <string.h>

extern "C" {
    #include <linux/i2c.h>
    #include <linux/i2c-dev.h>
    #include <i2c/smbus.h>
}
#include <fcntl.h> 
#include <sys/ioctl.h> 

int main(int argc, char ** argv)
{
    int file;
    int adapter_nr = 6;
    char filename[20];
    snprintf(filename, 19, "/dev/i2c-%d", adapter_nr);
    file = open(filename, O_RDWR);
    if (file < 0) {
        printf("Open adapter failed: %s\n", strerror(errno));
        return(1);
    }

    int addr = 0x0b;
    if (ioctl(file, I2C_SLAVE, addr) < 0) {
        printf("Set slave addr failed: %s\n", strerror(errno));
        return(1);
    }

    __u8 reg = 0x0d;
    __s32 res;

    res = i2c_smbus_read_word_data(file, reg);
    if (res < 0) {
        printf("SMBus read failed: %s\n", strerror(errno));
    } else {
        printf("Read result: 0x%04x\n", res);
    }

    close(file);
    return 0;
}

验证步骤(可选)

  1. 确认libi2c-dev安装状态:
dpkg -l libi2c-dev
  1. 确认库文件存在:
ls /usr/lib/x86_64-linux-gnu/libi2c.so

内容的提问来源于stack exchange,提问作者new_linux_explorer

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.11 22:40:29