regmap_read val指针

时间:2017-01-11 14:49:45

标签: c linux-kernel linux-device-driver

我正在尝试使用regmap api访问I2C设备,并且完全不清楚val指针的预期类型是什么。

Cfr:int regmap_read(struct regmap * map,unsigned int reg,unsigned int * val)

我看到的两个选项(都是坏btw imho):

[1]它实际上是一个指向unsigned int类型的指针,你必须在读取它时使用一个中间变量。由于你不知道bitsize和unsigned int类型是什么,你永远不能确定它将保持32位。

[2]假设是一个指向类型的指针,该类型与你在regmap_config中的val_bits中传递的内容相对应(并且你必须错误地将该指针重新转换为API期望使其可编译的类型)。

文档根本没用(惊喜):

/**
...
* @val: Pointer to store read value
...
*/
https://patchwork.kernel.org/patch/9378201/这样的事情似乎表明它是[1], 但我看到其他司机,我假设工作[2]例如:

static inline int
ar1335_read_reg(struct ar1335_info *info, u16 addr, u16 *val)
{
    return regmap_read(info->regmap, addr, (unsigned int *) val);
}

https://github.com/Bogdacutu/STLinux-Kernel/blob/master/drivers/media/platform/tegra/ar1335.c

如果我尝试遵循这些功能(我认为,它是完整的抽象和更多的抽象)实际上分配给读取我认为我最终在

static int regmap_i2c_read(void *context,
                       const void *reg, size_t reg_size,
                       void *val, size_t val_size)
{
    struct device *dev = context;
    struct i2c_client *i2c = to_i2c_client(dev);
    struct i2c_msg xfer[2];
    int ret;

    xfer[0].addr = i2c->addr;
    xfer[0].flags = 0;
    xfer[0].len = reg_size;
    xfer[0].buf = (void *)reg;

    xfer[1].addr = i2c->addr;
    xfer[1].flags = I2C_M_RD;
    xfer[1].len = val_size;
    xfer[1].buf = val;

    ret = i2c_transfer(i2c->adapter, xfer, 2);
    if (ret == 2)
            return 0;
    else if (ret < 0)
            return ret;
    else
            return -EIO;
}

这表明它必须是指向真实数据类型的指针,例如,如果val_bits = 16,则为u16 *。

任何有见解的人? 如果是[2]为什么不使用void *指针来避免像i2c读取的丑陋的演员?历史一团糟?

谢谢,

布拉姆

0 个答案:

没有答案