for (i = 0; i < CM36651_CS_CONF_REG_NUM; i++) {
ret = i2c_smbus_write_byte_data(client, cm36651_cs_reg[i],
cm36651->cs_ctrl_regs[i]); if (ret < 0) return ret;
}
for (i = 0; i < CM36651_PS_REG_NUM; i++) {
ret = i2c_smbus_write_byte_data(ps_client, cm36651_ps_reg[i],
cm36651->ps_ctrl_regs[i]); if (ret < 0) return ret;
}
/* Set shutdown mode */
ret = i2c_smbus_write_byte_data(client, CM36651_CS_CONF1,
CM36651_ALS_DISABLE); if (ret < 0) return ret;
ret = i2c_smbus_write_byte_data(cm36651->ps_client,
CM36651_PS_CONF1, CM36651_PS_DISABLE); if (ret < 0) return ret;
return 0;
}
staticint cm36651_read_output(struct cm36651_data *cm36651, struct iio_chan_spec const *chan, int *val)
{ struct i2c_client *client = cm36651->client; int ret = -EINVAL;
switch (chan->type) { case IIO_LIGHT:
*val = i2c_smbus_read_word_data(client, chan->address); if (*val < 0) return ret;
ret = i2c_smbus_write_byte_data(client, CM36651_CS_CONF1,
CM36651_ALS_DISABLE); if (ret < 0) return ret;
ret = IIO_VAL_INT; break; case IIO_PROXIMITY:
*val = i2c_smbus_read_byte(cm36651->ps_client); if (*val < 0) return ret;
if (!test_bit(CM36651_PROXIMITY_EV_EN, &cm36651->flags)) {
ret = i2c_smbus_write_byte_data(cm36651->ps_client,
CM36651_PS_CONF1, CM36651_PS_DISABLE); if (ret < 0) return ret;
}
/* * The PS INT pin is an active low signal that PS INT move logic low * when the object is detect. Once the MCU host received the PS INT * "LOW" signal, the Host needs to read the data at Alert Response * Address(ARA) to clear the PS INT signal. After clearing the PS * INT pin, the PS INT signal toggles from low to high.
*/
ret = i2c_smbus_read_byte(cm36651->ara_client); if (ret < 0) {
dev_err(&client->dev, "%s: Data read failed: %d\n", __func__, ret); return IRQ_HANDLED;
} switch (ret) { case CM36651_CLOSE_PROXIMITY:
ev_dir = IIO_EV_DIR_RISING; break; case CM36651_FAR_PROXIMITY:
ev_dir = IIO_EV_DIR_FALLING; break; default:
dev_err(&client->dev, "%s: Data read wrong: %d\n", __func__, ret); return IRQ_HANDLED;
}
staticint cm36651_set_operation_mode(struct cm36651_data *cm36651, int cmd)
{ struct i2c_client *client = cm36651->client; struct i2c_client *ps_client = cm36651->ps_client; int ret = -EINVAL;
switch (cmd) { case CM36651_CMD_READ_RAW_LIGHT:
ret = i2c_smbus_write_byte_data(client, CM36651_CS_CONF1,
cm36651->cs_ctrl_regs[CM36651_CS_CONF1]); break; case CM36651_CMD_READ_RAW_PROXIMITY: if (test_bit(CM36651_PROXIMITY_EV_EN, &cm36651->flags)) return CM36651_PROXIMITY_EV_EN;
ret = i2c_smbus_write_byte_data(ps_client, CM36651_PS_CONF1,
cm36651->ps_ctrl_regs[CM36651_PS_CONF1]); break; case CM36651_CMD_PROX_EV_EN: if (test_bit(CM36651_PROXIMITY_EV_EN, &cm36651->flags)) {
dev_err(&client->dev, "Already proximity event enable state\n"); return ret;
}
set_bit(CM36651_PROXIMITY_EV_EN, &cm36651->flags);
ret = i2c_smbus_write_byte_data(ps_client,
cm36651_ps_reg[CM36651_PS_CONF1],
CM36651_PS_INT_EN | CM36651_PS_PERS2 | CM36651_PS_IT2);
if (ret < 0) {
dev_err(&client->dev, "Proximity enable event failed\n"); return ret;
} break; case CM36651_CMD_PROX_EV_DIS: if (!test_bit(CM36651_PROXIMITY_EV_EN, &cm36651->flags)) {
dev_err(&client->dev, "Already proximity event disable state\n"); return ret;
}
clear_bit(CM36651_PROXIMITY_EV_EN, &cm36651->flags);
ret = i2c_smbus_write_byte_data(ps_client,
CM36651_PS_CONF1, CM36651_PS_DISABLE); break;
}
if (ret < 0)
dev_err(&client->dev, "Write register failed\n");
return ret;
}
staticint cm36651_read_channel(struct cm36651_data *cm36651, struct iio_chan_spec const *chan, int *val)
{ struct i2c_client *client = cm36651->client; int cmd, ret;
ret = i2c_smbus_write_byte_data(ps_client,
CM36651_PS_CONF1, int_time); if (ret < 0) {
dev_err(&client->dev, "PS integration time write failed\n"); return ret;
}
cm36651->ps_int_time = int_time; break; default: return -EINVAL;
}
return ret;
}
staticint cm36651_read_raw(struct iio_dev *indio_dev, struct iio_chan_spec const *chan, int *val, int *val2, long mask)
{ struct cm36651_data *cm36651 = iio_priv(indio_dev); int ret;
mutex_lock(&cm36651->lock);
switch (mask) { case IIO_CHAN_INFO_RAW:
ret = cm36651_read_channel(cm36651, chan, val); break; case IIO_CHAN_INFO_INT_TIME:
*val = 0;
ret = cm36651_read_int_time(cm36651, chan, val2); break; default:
ret = -EINVAL;
}
mutex_unlock(&cm36651->lock);
return ret;
}
staticint cm36651_write_raw(struct iio_dev *indio_dev, struct iio_chan_spec const *chan, int val, int val2, long mask)
{ struct cm36651_data *cm36651 = iio_priv(indio_dev); struct i2c_client *client = cm36651->client; int ret = -EINVAL;
if (mask == IIO_CHAN_INFO_INT_TIME) {
ret = cm36651_write_int_time(cm36651, chan, val2); if (ret < 0)
dev_err(&client->dev, "Integration time write failed\n");
}
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.