Commit 42d1c1dc authored by Hans de Goede's avatar Hans de Goede Committed by Jonathan Cameron

iio: accel: bmc150: Move check for second ACPI device into a separate function

Move the check for a second ACPI device for BOSC0200 ACPI fwnodes into
a new bmc150_acpi_dual_accel_probe() helper function.

This is a preparation patch for adding support for a new "DUAL250E" ACPI
Hardware-ID (HID) used on some devices.
Signed-off-by: default avatarHans de Goede <hdegoede@redhat.com>
Reviewed-by: default avatarAndy Shevchenko <andy.shevchenko@gmail.com>
Link: https://lore.kernel.org/r/20210523170103.176958-4-hdegoede@redhat.comSigned-off-by: default avatarJonathan Cameron <Jonathan.Cameron@huawei.com>
parent f407e2dc
...@@ -21,6 +21,52 @@ ...@@ -21,6 +21,52 @@
#include "bmc150-accel.h" #include "bmc150-accel.h"
#ifdef CONFIG_ACPI
static const struct acpi_device_id bmc150_acpi_dual_accel_ids[] = {
{"BOSC0200"},
{ }
};
/*
* Some acpi_devices describe 2 accelerometers in a single ACPI device,
* try instantiating a second i2c_client for an I2cSerialBusV2 ACPI resource
* with index 1.
*/
static void bmc150_acpi_dual_accel_probe(struct i2c_client *client)
{
struct acpi_device *adev = ACPI_COMPANION(&client->dev);
struct i2c_client *second_dev;
struct i2c_board_info board_info = {
.type = "bmc150_accel",
/*
* The 2nd accel sits in the base of 2-in-1s. Note this name is
* static, as there should never be more then 1 BOSC0200 ACPI
* node with 2 accelerometers in it.
*/
.dev_name = "BOSC0200:base",
.fwnode = client->dev.fwnode,
.irq = -ENOENT,
};
if (acpi_match_device_ids(adev, bmc150_acpi_dual_accel_ids))
return;
second_dev = i2c_acpi_new_device(&client->dev, 1, &board_info);
if (!IS_ERR(second_dev))
bmc150_set_second_device(client, second_dev);
}
static void bmc150_acpi_dual_accel_remove(struct i2c_client *client)
{
struct i2c_client *second_dev = bmc150_get_second_device(client);
i2c_unregister_device(second_dev);
}
#else
static void bmc150_acpi_dual_accel_probe(struct i2c_client *client) {}
static void bmc150_acpi_dual_accel_remove(struct i2c_client *client) {}
#endif
static int bmc150_accel_probe(struct i2c_client *client, static int bmc150_accel_probe(struct i2c_client *client,
const struct i2c_device_id *id) const struct i2c_device_id *id)
{ {
...@@ -30,7 +76,6 @@ static int bmc150_accel_probe(struct i2c_client *client, ...@@ -30,7 +76,6 @@ static int bmc150_accel_probe(struct i2c_client *client,
i2c_check_functionality(client->adapter, I2C_FUNC_I2C) || i2c_check_functionality(client->adapter, I2C_FUNC_I2C) ||
i2c_check_functionality(client->adapter, i2c_check_functionality(client->adapter,
I2C_FUNC_SMBUS_READ_I2C_BLOCK); I2C_FUNC_SMBUS_READ_I2C_BLOCK);
struct acpi_device __maybe_unused *adev;
int ret; int ret;
regmap = devm_regmap_init_i2c(client, &bmc150_regmap_conf); regmap = devm_regmap_init_i2c(client, &bmc150_regmap_conf);
...@@ -47,41 +92,18 @@ static int bmc150_accel_probe(struct i2c_client *client, ...@@ -47,41 +92,18 @@ static int bmc150_accel_probe(struct i2c_client *client,
return ret; return ret;
/* /*
* Some BOSC0200 acpi_devices describe 2 accelerometers in a single ACPI * The !id check avoids recursion when probe() gets called
* device, try instantiating a second i2c_client for an I2cSerialBusV2 * for the second client.
* ACPI resource with index 1. The !id check avoids recursion when
* bmc150_accel_probe() gets called for the second client.
*/ */
#ifdef CONFIG_ACPI if (!id && has_acpi_companion(&client->dev))
adev = ACPI_COMPANION(&client->dev); bmc150_acpi_dual_accel_probe(client);
if (!id && adev && strcmp(acpi_device_hid(adev), "BOSC0200") == 0) {
struct i2c_board_info board_info = {
.type = "bmc150_accel",
/*
* The 2nd accel sits in the base of 2-in-1s. Note this
* name is static, as there should never be more then 1
* BOSC0200 ACPI node with 2 accelerometers in it.
*/
.dev_name = "BOSC0200:base",
.fwnode = client->dev.fwnode,
.irq = -ENOENT,
};
struct i2c_client *second_dev;
second_dev = i2c_acpi_new_device(&client->dev, 1, &board_info);
if (!IS_ERR(second_dev))
bmc150_set_second_device(client, second_dev);
}
#endif
return 0; return 0;
} }
static int bmc150_accel_remove(struct i2c_client *client) static int bmc150_accel_remove(struct i2c_client *client)
{ {
struct i2c_client *second_dev = bmc150_get_second_device(client); bmc150_acpi_dual_accel_remove(client);
i2c_unregister_device(second_dev);
return bmc150_accel_core_remove(&client->dev); return bmc150_accel_core_remove(&client->dev);
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment