in masters/ds2482.c [445:526]
static int ds2482_probe(struct i2c_client *client,
const struct i2c_device_id *id)
{
struct ds2482_data *data;
int err = -ENODEV;
int temp1;
int idx;
if (!i2c_check_functionality(client->adapter,
I2C_FUNC_SMBUS_WRITE_BYTE_DATA |
I2C_FUNC_SMBUS_BYTE))
return -ENODEV;
if (!(data = kzalloc(sizeof(struct ds2482_data), GFP_KERNEL))) {
err = -ENOMEM;
goto exit;
}
data->client = client;
i2c_set_clientdata(client, data);
/* Reset the device (sets the read_ptr to status) */
if (ds2482_send_cmd(data, DS2482_CMD_RESET) < 0) {
dev_warn(&client->dev, "DS2482 reset failed.\n");
goto exit_free;
}
/* Sleep at least 525ns to allow the reset to complete */
ndelay(525);
/* Read the status byte - only reset bit and line should be set */
temp1 = i2c_smbus_read_byte(client);
if (temp1 != (DS2482_REG_STS_LL | DS2482_REG_STS_RST)) {
dev_warn(&client->dev, "DS2482 reset status "
"0x%02X - not a DS2482\n", temp1);
goto exit_free;
}
/* Detect the 8-port version */
data->w1_count = 1;
if (ds2482_set_channel(data, 7) == 0)
data->w1_count = 8;
/* Set all config items to 0 (off) */
ds2482_send_cmd_data(data, DS2482_CMD_WRITE_CONFIG,
ds2482_calculate_config(0x00));
mutex_init(&data->access_lock);
/* Register 1-wire interface(s) */
for (idx = 0; idx < data->w1_count; idx++) {
data->w1_ch[idx].pdev = data;
data->w1_ch[idx].channel = idx;
/* Populate all the w1 bus master stuff */
data->w1_ch[idx].w1_bm.data = &data->w1_ch[idx];
data->w1_ch[idx].w1_bm.read_byte = ds2482_w1_read_byte;
data->w1_ch[idx].w1_bm.write_byte = ds2482_w1_write_byte;
data->w1_ch[idx].w1_bm.touch_bit = ds2482_w1_touch_bit;
data->w1_ch[idx].w1_bm.triplet = ds2482_w1_triplet;
data->w1_ch[idx].w1_bm.reset_bus = ds2482_w1_reset_bus;
data->w1_ch[idx].w1_bm.set_pullup = ds2482_w1_set_pullup;
err = w1_add_master_device(&data->w1_ch[idx].w1_bm);
if (err) {
data->w1_ch[idx].pdev = NULL;
goto exit_w1_remove;
}
}
return 0;
exit_w1_remove:
for (idx = 0; idx < data->w1_count; idx++) {
if (data->w1_ch[idx].pdev != NULL)
w1_remove_master_device(&data->w1_ch[idx].w1_bm);
}
exit_free:
kfree(data);
exit:
return err;
}