Signed tag for the immutable platform-drivers-x86-int3472 branch
This branch contains 5.16-rc1 + the pending ACPI/i2c, tps68570 platform_data and INT3472 driver patches. -----BEGIN PGP SIGNATURE----- iQFIBAABCAAyFiEEuvA7XScYQRpenhd+kuxHeUQDJ9wFAmG6YLQUHGhkZWdvZWRl QHJlZGhhdC5jb20ACgkQkuxHeUQDJ9zwGwf8Csb4wXyc3duBlnX/9jO9REDVKTN9 HhmU2KQm29g10dN2nlFXEOG16xAy8zt3BE7QwniL/R5sUsKTCAEugY8Aqq/4+lFA vTU+YR9YqZFmEDGMfDngHeh9ZvSWIJS7IEXthxCkgGVhrd2Wl50jKTjVyq1RIDKv a7B4fOhguFv95xRlnXK+yoVUU7zZPWAgxyCqV0E0JEi8aWE8Y483IRCzcDEyJeDa HkgZLVwD9l3WQ4uZllVg1q5jfSprHwBa8dFxgcd6mOOYaKowiJ+GjnvnXOto5X72 zsODBJH15VzfVXF5cAqIvzN6nAFR8Mxieei+21iFyUD/Ps1vfWlodFHH2w== =Q1N9 -----END PGP SIGNATURE----- Merge tag 'platform-drivers-x86-int3472-1' of git://git.kernel.org/pub/scm/linux/kernel/git/pdx86/platform-drivers-x86 into media_tree Signed tag for the immutable platform-drivers-x86-int3472 branch This branch contains 5.16-rc1 + the pending ACPI/i2c, tps68570 platform_data and INT3472 driver patches. * tag 'platform-drivers-x86-int3472-1' of git://git.kernel.org/pub/scm/linux/kernel/git/pdx86/platform-drivers-x86: platform/x86: int3472: Deal with probe ordering issues platform/x86: int3472: Pass tps68470_regulator_platform_data to the tps68470-regulator MFD-cell platform/x86: int3472: Pass tps68470_clk_platform_data to the tps68470-regulator MFD-cell platform/x86: int3472: Add get_sensor_adev_and_name() helper platform/x86: int3472: Split into 2 drivers platform_data: Add linux/platform_data/tps68470.h file i2c: acpi: Add i2c_acpi_new_device_by_fwnode() function i2c: acpi: Use acpi_dev_ready_for_enumeration() helper ACPI: delay enumeration of devices with a _DEP pointing to an INT3472 device
This commit is contained in:
commit
3a956f0b12
|
@ -797,6 +797,12 @@ static const char * const acpi_ignore_dep_ids[] = {
|
||||||
NULL
|
NULL
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/* List of HIDs for which we honor deps of matching ACPI devs, when checking _DEP lists. */
|
||||||
|
static const char * const acpi_honor_dep_ids[] = {
|
||||||
|
"INT3472", /* Camera sensor PMIC / clk and regulator info */
|
||||||
|
NULL
|
||||||
|
};
|
||||||
|
|
||||||
static struct acpi_device *acpi_bus_get_parent(acpi_handle handle)
|
static struct acpi_device *acpi_bus_get_parent(acpi_handle handle)
|
||||||
{
|
{
|
||||||
struct acpi_device *device = NULL;
|
struct acpi_device *device = NULL;
|
||||||
|
@ -1762,9 +1768,13 @@ static void acpi_scan_dep_init(struct acpi_device *adev)
|
||||||
struct acpi_dep_data *dep;
|
struct acpi_dep_data *dep;
|
||||||
|
|
||||||
list_for_each_entry(dep, &acpi_dep_list, node) {
|
list_for_each_entry(dep, &acpi_dep_list, node) {
|
||||||
if (dep->consumer == adev->handle)
|
if (dep->consumer == adev->handle) {
|
||||||
|
if (dep->honor_dep)
|
||||||
|
adev->flags.honor_deps = 1;
|
||||||
|
|
||||||
adev->dep_unmet++;
|
adev->dep_unmet++;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void acpi_device_add_finalize(struct acpi_device *device)
|
void acpi_device_add_finalize(struct acpi_device *device)
|
||||||
|
@ -1967,7 +1977,7 @@ static u32 acpi_scan_check_dep(acpi_handle handle, bool check_dep)
|
||||||
for (count = 0, i = 0; i < dep_devices.count; i++) {
|
for (count = 0, i = 0; i < dep_devices.count; i++) {
|
||||||
struct acpi_device_info *info;
|
struct acpi_device_info *info;
|
||||||
struct acpi_dep_data *dep;
|
struct acpi_dep_data *dep;
|
||||||
bool skip;
|
bool skip, honor_dep;
|
||||||
|
|
||||||
status = acpi_get_object_info(dep_devices.handles[i], &info);
|
status = acpi_get_object_info(dep_devices.handles[i], &info);
|
||||||
if (ACPI_FAILURE(status)) {
|
if (ACPI_FAILURE(status)) {
|
||||||
|
@ -1976,6 +1986,7 @@ static u32 acpi_scan_check_dep(acpi_handle handle, bool check_dep)
|
||||||
}
|
}
|
||||||
|
|
||||||
skip = acpi_info_matches_ids(info, acpi_ignore_dep_ids);
|
skip = acpi_info_matches_ids(info, acpi_ignore_dep_ids);
|
||||||
|
honor_dep = acpi_info_matches_ids(info, acpi_honor_dep_ids);
|
||||||
kfree(info);
|
kfree(info);
|
||||||
|
|
||||||
if (skip)
|
if (skip)
|
||||||
|
@ -1989,6 +2000,7 @@ static u32 acpi_scan_check_dep(acpi_handle handle, bool check_dep)
|
||||||
|
|
||||||
dep->supplier = dep_devices.handles[i];
|
dep->supplier = dep_devices.handles[i];
|
||||||
dep->consumer = handle;
|
dep->consumer = handle;
|
||||||
|
dep->honor_dep = honor_dep;
|
||||||
|
|
||||||
mutex_lock(&acpi_dep_list_lock);
|
mutex_lock(&acpi_dep_list_lock);
|
||||||
list_add_tail(&dep->node , &acpi_dep_list);
|
list_add_tail(&dep->node , &acpi_dep_list);
|
||||||
|
@ -2155,8 +2167,8 @@ static void acpi_bus_attach(struct acpi_device *device, bool first_pass)
|
||||||
register_dock_dependent_device(device, ejd);
|
register_dock_dependent_device(device, ejd);
|
||||||
|
|
||||||
acpi_bus_get_status(device);
|
acpi_bus_get_status(device);
|
||||||
/* Skip devices that are not present. */
|
/* Skip devices that are not ready for enumeration (e.g. not present) */
|
||||||
if (!acpi_device_is_present(device)) {
|
if (!acpi_dev_ready_for_enumeration(device)) {
|
||||||
device->flags.initialized = false;
|
device->flags.initialized = false;
|
||||||
acpi_device_clear_enumerated(device);
|
acpi_device_clear_enumerated(device);
|
||||||
device->flags.power_manageable = 0;
|
device->flags.power_manageable = 0;
|
||||||
|
@ -2318,6 +2330,23 @@ void acpi_dev_clear_dependencies(struct acpi_device *supplier)
|
||||||
}
|
}
|
||||||
EXPORT_SYMBOL_GPL(acpi_dev_clear_dependencies);
|
EXPORT_SYMBOL_GPL(acpi_dev_clear_dependencies);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* acpi_dev_ready_for_enumeration - Check if the ACPI device is ready for enumeration
|
||||||
|
* @device: Pointer to the &struct acpi_device to check
|
||||||
|
*
|
||||||
|
* Check if the device is present and has no unmet dependencies.
|
||||||
|
*
|
||||||
|
* Return true if the device is ready for enumeratino. Otherwise, return false.
|
||||||
|
*/
|
||||||
|
bool acpi_dev_ready_for_enumeration(const struct acpi_device *device)
|
||||||
|
{
|
||||||
|
if (device->flags.honor_deps && device->dep_unmet)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
return acpi_device_is_present(device);
|
||||||
|
}
|
||||||
|
EXPORT_SYMBOL_GPL(acpi_dev_ready_for_enumeration);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* acpi_dev_get_first_consumer_dev - Return ACPI device dependent on @supplier
|
* acpi_dev_get_first_consumer_dev - Return ACPI device dependent on @supplier
|
||||||
* @supplier: Pointer to the dependee device
|
* @supplier: Pointer to the dependee device
|
||||||
|
|
|
@ -144,9 +144,12 @@ static int i2c_acpi_do_lookup(struct acpi_device *adev,
|
||||||
struct list_head resource_list;
|
struct list_head resource_list;
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
if (acpi_bus_get_status(adev) || !adev->status.present)
|
if (acpi_bus_get_status(adev))
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
|
|
||||||
|
if (!acpi_dev_ready_for_enumeration(adev))
|
||||||
|
return -ENODEV;
|
||||||
|
|
||||||
if (acpi_match_device_ids(adev, i2c_acpi_ignored_device_ids) == 0)
|
if (acpi_match_device_ids(adev, i2c_acpi_ignored_device_ids) == 0)
|
||||||
return -ENODEV;
|
return -ENODEV;
|
||||||
|
|
||||||
|
@ -473,8 +476,8 @@ struct notifier_block i2c_acpi_notifier = {
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* i2c_acpi_new_device - Create i2c-client for the Nth I2cSerialBus resource
|
* i2c_acpi_new_device_by_fwnode - Create i2c-client for the Nth I2cSerialBus resource
|
||||||
* @dev: Device owning the ACPI resources to get the client from
|
* @fwnode: fwnode with the ACPI resources to get the client from
|
||||||
* @index: Index of ACPI resource to get
|
* @index: Index of ACPI resource to get
|
||||||
* @info: describes the I2C device; note this is modified (addr gets set)
|
* @info: describes the I2C device; note this is modified (addr gets set)
|
||||||
* Context: can sleep
|
* Context: can sleep
|
||||||
|
@ -490,15 +493,20 @@ struct notifier_block i2c_acpi_notifier = {
|
||||||
* Returns a pointer to the new i2c-client, or error pointer in case of failure.
|
* Returns a pointer to the new i2c-client, or error pointer in case of failure.
|
||||||
* Specifically, -EPROBE_DEFER is returned if the adapter is not found.
|
* Specifically, -EPROBE_DEFER is returned if the adapter is not found.
|
||||||
*/
|
*/
|
||||||
struct i2c_client *i2c_acpi_new_device(struct device *dev, int index,
|
struct i2c_client *i2c_acpi_new_device_by_fwnode(struct fwnode_handle *fwnode,
|
||||||
|
int index,
|
||||||
struct i2c_board_info *info)
|
struct i2c_board_info *info)
|
||||||
{
|
{
|
||||||
struct acpi_device *adev = ACPI_COMPANION(dev);
|
|
||||||
struct i2c_acpi_lookup lookup;
|
struct i2c_acpi_lookup lookup;
|
||||||
struct i2c_adapter *adapter;
|
struct i2c_adapter *adapter;
|
||||||
|
struct acpi_device *adev;
|
||||||
LIST_HEAD(resource_list);
|
LIST_HEAD(resource_list);
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
|
adev = to_acpi_device_node(fwnode);
|
||||||
|
if (!adev)
|
||||||
|
return ERR_PTR(-ENODEV);
|
||||||
|
|
||||||
memset(&lookup, 0, sizeof(lookup));
|
memset(&lookup, 0, sizeof(lookup));
|
||||||
lookup.info = info;
|
lookup.info = info;
|
||||||
lookup.device_handle = acpi_device_handle(adev);
|
lookup.device_handle = acpi_device_handle(adev);
|
||||||
|
@ -520,7 +528,7 @@ struct i2c_client *i2c_acpi_new_device(struct device *dev, int index,
|
||||||
|
|
||||||
return i2c_new_client_device(adapter, info);
|
return i2c_new_client_device(adapter, info);
|
||||||
}
|
}
|
||||||
EXPORT_SYMBOL_GPL(i2c_acpi_new_device);
|
EXPORT_SYMBOL_GPL(i2c_acpi_new_device_by_fwnode);
|
||||||
|
|
||||||
bool i2c_acpi_waive_d0_probe(struct device *dev)
|
bool i2c_acpi_waive_d0_probe(struct device *dev)
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
obj-$(CONFIG_INTEL_SKL_INT3472) += intel_skl_int3472.o
|
obj-$(CONFIG_INTEL_SKL_INT3472) += intel_skl_int3472_discrete.o \
|
||||||
intel_skl_int3472-y := intel_skl_int3472_common.o \
|
intel_skl_int3472_tps68470.o
|
||||||
intel_skl_int3472_discrete.o \
|
intel_skl_int3472_discrete-y := discrete.o clk_and_regulator.o common.o
|
||||||
intel_skl_int3472_tps68470.o \
|
intel_skl_int3472_tps68470-y := tps68470.o tps68470_board_data.o common.o
|
||||||
intel_skl_int3472_clk_and_regulator.o
|
|
||||||
|
|
|
@ -9,7 +9,7 @@
|
||||||
#include <linux/regulator/driver.h>
|
#include <linux/regulator/driver.h>
|
||||||
#include <linux/slab.h>
|
#include <linux/slab.h>
|
||||||
|
|
||||||
#include "intel_skl_int3472_common.h"
|
#include "common.h"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* The regulators have to have .ops to be valid, but the only ops we actually
|
* The regulators have to have .ops to be valid, but the only ops we actually
|
|
@ -0,0 +1,82 @@
|
||||||
|
// SPDX-License-Identifier: GPL-2.0
|
||||||
|
/* Author: Dan Scally <djrscally@gmail.com> */
|
||||||
|
|
||||||
|
#include <linux/acpi.h>
|
||||||
|
#include <linux/slab.h>
|
||||||
|
|
||||||
|
#include "common.h"
|
||||||
|
|
||||||
|
union acpi_object *skl_int3472_get_acpi_buffer(struct acpi_device *adev, char *id)
|
||||||
|
{
|
||||||
|
struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL };
|
||||||
|
acpi_handle handle = adev->handle;
|
||||||
|
union acpi_object *obj;
|
||||||
|
acpi_status status;
|
||||||
|
|
||||||
|
status = acpi_evaluate_object(handle, id, NULL, &buffer);
|
||||||
|
if (ACPI_FAILURE(status))
|
||||||
|
return ERR_PTR(-ENODEV);
|
||||||
|
|
||||||
|
obj = buffer.pointer;
|
||||||
|
if (!obj)
|
||||||
|
return ERR_PTR(-ENODEV);
|
||||||
|
|
||||||
|
if (obj->type != ACPI_TYPE_BUFFER) {
|
||||||
|
acpi_handle_err(handle, "%s object is not an ACPI buffer\n", id);
|
||||||
|
kfree(obj);
|
||||||
|
return ERR_PTR(-EINVAL);
|
||||||
|
}
|
||||||
|
|
||||||
|
return obj;
|
||||||
|
}
|
||||||
|
|
||||||
|
int skl_int3472_fill_cldb(struct acpi_device *adev, struct int3472_cldb *cldb)
|
||||||
|
{
|
||||||
|
union acpi_object *obj;
|
||||||
|
int ret;
|
||||||
|
|
||||||
|
obj = skl_int3472_get_acpi_buffer(adev, "CLDB");
|
||||||
|
if (IS_ERR(obj))
|
||||||
|
return PTR_ERR(obj);
|
||||||
|
|
||||||
|
if (obj->buffer.length > sizeof(*cldb)) {
|
||||||
|
acpi_handle_err(adev->handle, "The CLDB buffer is too large\n");
|
||||||
|
ret = -EINVAL;
|
||||||
|
goto out_free_obj;
|
||||||
|
}
|
||||||
|
|
||||||
|
memcpy(cldb, obj->buffer.pointer, obj->buffer.length);
|
||||||
|
ret = 0;
|
||||||
|
|
||||||
|
out_free_obj:
|
||||||
|
kfree(obj);
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* sensor_adev_ret may be NULL, name_ret must not be NULL */
|
||||||
|
int skl_int3472_get_sensor_adev_and_name(struct device *dev,
|
||||||
|
struct acpi_device **sensor_adev_ret,
|
||||||
|
const char **name_ret)
|
||||||
|
{
|
||||||
|
struct acpi_device *adev = ACPI_COMPANION(dev);
|
||||||
|
struct acpi_device *sensor;
|
||||||
|
int ret = 0;
|
||||||
|
|
||||||
|
sensor = acpi_dev_get_first_consumer_dev(adev);
|
||||||
|
if (!sensor) {
|
||||||
|
dev_err(dev, "INT3472 seems to have no dependents.\n");
|
||||||
|
return -ENODEV;
|
||||||
|
}
|
||||||
|
|
||||||
|
*name_ret = devm_kasprintf(dev, GFP_KERNEL, I2C_DEV_NAME_FORMAT,
|
||||||
|
acpi_dev_name(sensor));
|
||||||
|
if (!*name_ret)
|
||||||
|
ret = -ENOMEM;
|
||||||
|
|
||||||
|
if (ret == 0 && sensor_adev_ret)
|
||||||
|
*sensor_adev_ret = sensor;
|
||||||
|
else
|
||||||
|
acpi_dev_put(sensor);
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
|
@ -105,12 +105,12 @@ struct int3472_discrete_device {
|
||||||
struct gpiod_lookup_table gpios;
|
struct gpiod_lookup_table gpios;
|
||||||
};
|
};
|
||||||
|
|
||||||
int skl_int3472_discrete_probe(struct platform_device *pdev);
|
|
||||||
int skl_int3472_discrete_remove(struct platform_device *pdev);
|
|
||||||
int skl_int3472_tps68470_probe(struct i2c_client *client);
|
|
||||||
union acpi_object *skl_int3472_get_acpi_buffer(struct acpi_device *adev,
|
union acpi_object *skl_int3472_get_acpi_buffer(struct acpi_device *adev,
|
||||||
char *id);
|
char *id);
|
||||||
int skl_int3472_fill_cldb(struct acpi_device *adev, struct int3472_cldb *cldb);
|
int skl_int3472_fill_cldb(struct acpi_device *adev, struct int3472_cldb *cldb);
|
||||||
|
int skl_int3472_get_sensor_adev_and_name(struct device *dev,
|
||||||
|
struct acpi_device **sensor_adev_ret,
|
||||||
|
const char **name_ret);
|
||||||
|
|
||||||
int skl_int3472_register_clock(struct int3472_discrete_device *int3472);
|
int skl_int3472_register_clock(struct int3472_discrete_device *int3472);
|
||||||
void skl_int3472_unregister_clock(struct int3472_discrete_device *int3472);
|
void skl_int3472_unregister_clock(struct int3472_discrete_device *int3472);
|
|
@ -14,7 +14,7 @@
|
||||||
#include <linux/platform_device.h>
|
#include <linux/platform_device.h>
|
||||||
#include <linux/uuid.h>
|
#include <linux/uuid.h>
|
||||||
|
|
||||||
#include "intel_skl_int3472_common.h"
|
#include "common.h"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* 79234640-9e10-4fea-a5c1-b5aa8b19756f
|
* 79234640-9e10-4fea-a5c1-b5aa8b19756f
|
||||||
|
@ -332,7 +332,9 @@ static int skl_int3472_parse_crs(struct int3472_discrete_device *int3472)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int skl_int3472_discrete_probe(struct platform_device *pdev)
|
static int skl_int3472_discrete_remove(struct platform_device *pdev);
|
||||||
|
|
||||||
|
static int skl_int3472_discrete_probe(struct platform_device *pdev)
|
||||||
{
|
{
|
||||||
struct acpi_device *adev = ACPI_COMPANION(&pdev->dev);
|
struct acpi_device *adev = ACPI_COMPANION(&pdev->dev);
|
||||||
struct int3472_discrete_device *int3472;
|
struct int3472_discrete_device *int3472;
|
||||||
|
@ -361,19 +363,10 @@ int skl_int3472_discrete_probe(struct platform_device *pdev)
|
||||||
int3472->dev = &pdev->dev;
|
int3472->dev = &pdev->dev;
|
||||||
platform_set_drvdata(pdev, int3472);
|
platform_set_drvdata(pdev, int3472);
|
||||||
|
|
||||||
int3472->sensor = acpi_dev_get_first_consumer_dev(adev);
|
ret = skl_int3472_get_sensor_adev_and_name(&pdev->dev, &int3472->sensor,
|
||||||
if (!int3472->sensor) {
|
&int3472->sensor_name);
|
||||||
dev_err(&pdev->dev, "INT3472 seems to have no dependents.\n");
|
if (ret)
|
||||||
return -ENODEV;
|
return ret;
|
||||||
}
|
|
||||||
|
|
||||||
int3472->sensor_name = devm_kasprintf(int3472->dev, GFP_KERNEL,
|
|
||||||
I2C_DEV_NAME_FORMAT,
|
|
||||||
acpi_dev_name(int3472->sensor));
|
|
||||||
if (!int3472->sensor_name) {
|
|
||||||
ret = -ENOMEM;
|
|
||||||
goto err_put_sensor;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Initialising this list means we can call gpiod_remove_lookup_table()
|
* Initialising this list means we can call gpiod_remove_lookup_table()
|
||||||
|
@ -387,15 +380,11 @@ int skl_int3472_discrete_probe(struct platform_device *pdev)
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
acpi_dev_clear_dependencies(adev);
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
err_put_sensor:
|
|
||||||
acpi_dev_put(int3472->sensor);
|
|
||||||
|
|
||||||
return ret;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int skl_int3472_discrete_remove(struct platform_device *pdev)
|
static int skl_int3472_discrete_remove(struct platform_device *pdev)
|
||||||
{
|
{
|
||||||
struct int3472_discrete_device *int3472 = platform_get_drvdata(pdev);
|
struct int3472_discrete_device *int3472 = platform_get_drvdata(pdev);
|
||||||
|
|
||||||
|
@ -411,3 +400,23 @@ int skl_int3472_discrete_remove(struct platform_device *pdev)
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static const struct acpi_device_id int3472_device_id[] = {
|
||||||
|
{ "INT3472", 0 },
|
||||||
|
{ }
|
||||||
|
};
|
||||||
|
MODULE_DEVICE_TABLE(acpi, int3472_device_id);
|
||||||
|
|
||||||
|
static struct platform_driver int3472_discrete = {
|
||||||
|
.driver = {
|
||||||
|
.name = "int3472-discrete",
|
||||||
|
.acpi_match_table = int3472_device_id,
|
||||||
|
},
|
||||||
|
.probe = skl_int3472_discrete_probe,
|
||||||
|
.remove = skl_int3472_discrete_remove,
|
||||||
|
};
|
||||||
|
module_platform_driver(int3472_discrete);
|
||||||
|
|
||||||
|
MODULE_DESCRIPTION("Intel SkyLake INT3472 ACPI Discrete Device Driver");
|
||||||
|
MODULE_AUTHOR("Daniel Scally <djrscally@gmail.com>");
|
||||||
|
MODULE_LICENSE("GPL v2");
|
|
@ -1,106 +0,0 @@
|
||||||
// SPDX-License-Identifier: GPL-2.0
|
|
||||||
/* Author: Dan Scally <djrscally@gmail.com> */
|
|
||||||
|
|
||||||
#include <linux/acpi.h>
|
|
||||||
#include <linux/i2c.h>
|
|
||||||
#include <linux/platform_device.h>
|
|
||||||
#include <linux/slab.h>
|
|
||||||
|
|
||||||
#include "intel_skl_int3472_common.h"
|
|
||||||
|
|
||||||
union acpi_object *skl_int3472_get_acpi_buffer(struct acpi_device *adev, char *id)
|
|
||||||
{
|
|
||||||
struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL };
|
|
||||||
acpi_handle handle = adev->handle;
|
|
||||||
union acpi_object *obj;
|
|
||||||
acpi_status status;
|
|
||||||
|
|
||||||
status = acpi_evaluate_object(handle, id, NULL, &buffer);
|
|
||||||
if (ACPI_FAILURE(status))
|
|
||||||
return ERR_PTR(-ENODEV);
|
|
||||||
|
|
||||||
obj = buffer.pointer;
|
|
||||||
if (!obj)
|
|
||||||
return ERR_PTR(-ENODEV);
|
|
||||||
|
|
||||||
if (obj->type != ACPI_TYPE_BUFFER) {
|
|
||||||
acpi_handle_err(handle, "%s object is not an ACPI buffer\n", id);
|
|
||||||
kfree(obj);
|
|
||||||
return ERR_PTR(-EINVAL);
|
|
||||||
}
|
|
||||||
|
|
||||||
return obj;
|
|
||||||
}
|
|
||||||
|
|
||||||
int skl_int3472_fill_cldb(struct acpi_device *adev, struct int3472_cldb *cldb)
|
|
||||||
{
|
|
||||||
union acpi_object *obj;
|
|
||||||
int ret;
|
|
||||||
|
|
||||||
obj = skl_int3472_get_acpi_buffer(adev, "CLDB");
|
|
||||||
if (IS_ERR(obj))
|
|
||||||
return PTR_ERR(obj);
|
|
||||||
|
|
||||||
if (obj->buffer.length > sizeof(*cldb)) {
|
|
||||||
acpi_handle_err(adev->handle, "The CLDB buffer is too large\n");
|
|
||||||
ret = -EINVAL;
|
|
||||||
goto out_free_obj;
|
|
||||||
}
|
|
||||||
|
|
||||||
memcpy(cldb, obj->buffer.pointer, obj->buffer.length);
|
|
||||||
ret = 0;
|
|
||||||
|
|
||||||
out_free_obj:
|
|
||||||
kfree(obj);
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
static const struct acpi_device_id int3472_device_id[] = {
|
|
||||||
{ "INT3472", 0 },
|
|
||||||
{ }
|
|
||||||
};
|
|
||||||
MODULE_DEVICE_TABLE(acpi, int3472_device_id);
|
|
||||||
|
|
||||||
static struct platform_driver int3472_discrete = {
|
|
||||||
.driver = {
|
|
||||||
.name = "int3472-discrete",
|
|
||||||
.acpi_match_table = int3472_device_id,
|
|
||||||
},
|
|
||||||
.probe = skl_int3472_discrete_probe,
|
|
||||||
.remove = skl_int3472_discrete_remove,
|
|
||||||
};
|
|
||||||
|
|
||||||
static struct i2c_driver int3472_tps68470 = {
|
|
||||||
.driver = {
|
|
||||||
.name = "int3472-tps68470",
|
|
||||||
.acpi_match_table = int3472_device_id,
|
|
||||||
},
|
|
||||||
.probe_new = skl_int3472_tps68470_probe,
|
|
||||||
};
|
|
||||||
|
|
||||||
static int skl_int3472_init(void)
|
|
||||||
{
|
|
||||||
int ret;
|
|
||||||
|
|
||||||
ret = platform_driver_register(&int3472_discrete);
|
|
||||||
if (ret)
|
|
||||||
return ret;
|
|
||||||
|
|
||||||
ret = i2c_register_driver(THIS_MODULE, &int3472_tps68470);
|
|
||||||
if (ret)
|
|
||||||
platform_driver_unregister(&int3472_discrete);
|
|
||||||
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
module_init(skl_int3472_init);
|
|
||||||
|
|
||||||
static void skl_int3472_exit(void)
|
|
||||||
{
|
|
||||||
platform_driver_unregister(&int3472_discrete);
|
|
||||||
i2c_del_driver(&int3472_tps68470);
|
|
||||||
}
|
|
||||||
module_exit(skl_int3472_exit);
|
|
||||||
|
|
||||||
MODULE_DESCRIPTION("Intel SkyLake INT3472 ACPI Device Driver");
|
|
||||||
MODULE_AUTHOR("Daniel Scally <djrscally@gmail.com>");
|
|
||||||
MODULE_LICENSE("GPL v2");
|
|
|
@ -2,27 +2,27 @@
|
||||||
/* Author: Dan Scally <djrscally@gmail.com> */
|
/* Author: Dan Scally <djrscally@gmail.com> */
|
||||||
|
|
||||||
#include <linux/i2c.h>
|
#include <linux/i2c.h>
|
||||||
|
#include <linux/kernel.h>
|
||||||
#include <linux/mfd/core.h>
|
#include <linux/mfd/core.h>
|
||||||
#include <linux/mfd/tps68470.h>
|
#include <linux/mfd/tps68470.h>
|
||||||
#include <linux/platform_device.h>
|
#include <linux/platform_device.h>
|
||||||
|
#include <linux/platform_data/tps68470.h>
|
||||||
#include <linux/regmap.h>
|
#include <linux/regmap.h>
|
||||||
|
#include <linux/string.h>
|
||||||
|
|
||||||
#include "intel_skl_int3472_common.h"
|
#include "common.h"
|
||||||
|
#include "tps68470.h"
|
||||||
|
|
||||||
#define DESIGNED_FOR_CHROMEOS 1
|
#define DESIGNED_FOR_CHROMEOS 1
|
||||||
#define DESIGNED_FOR_WINDOWS 2
|
#define DESIGNED_FOR_WINDOWS 2
|
||||||
|
|
||||||
|
#define TPS68470_WIN_MFD_CELL_COUNT 3
|
||||||
|
|
||||||
static const struct mfd_cell tps68470_cros[] = {
|
static const struct mfd_cell tps68470_cros[] = {
|
||||||
{ .name = "tps68470-gpio" },
|
{ .name = "tps68470-gpio" },
|
||||||
{ .name = "tps68470_pmic_opregion" },
|
{ .name = "tps68470_pmic_opregion" },
|
||||||
};
|
};
|
||||||
|
|
||||||
static const struct mfd_cell tps68470_win[] = {
|
|
||||||
{ .name = "tps68470-gpio" },
|
|
||||||
{ .name = "tps68470-clk" },
|
|
||||||
{ .name = "tps68470-regulator" },
|
|
||||||
};
|
|
||||||
|
|
||||||
static const struct regmap_config tps68470_regmap_config = {
|
static const struct regmap_config tps68470_regmap_config = {
|
||||||
.reg_bits = 8,
|
.reg_bits = 8,
|
||||||
.val_bits = 8,
|
.val_bits = 8,
|
||||||
|
@ -95,13 +95,21 @@ static int skl_int3472_tps68470_calc_type(struct acpi_device *adev)
|
||||||
return DESIGNED_FOR_WINDOWS;
|
return DESIGNED_FOR_WINDOWS;
|
||||||
}
|
}
|
||||||
|
|
||||||
int skl_int3472_tps68470_probe(struct i2c_client *client)
|
static int skl_int3472_tps68470_probe(struct i2c_client *client)
|
||||||
{
|
{
|
||||||
struct acpi_device *adev = ACPI_COMPANION(&client->dev);
|
struct acpi_device *adev = ACPI_COMPANION(&client->dev);
|
||||||
|
const struct int3472_tps68470_board_data *board_data;
|
||||||
|
struct tps68470_clk_platform_data clk_pdata = {};
|
||||||
|
struct mfd_cell *cells;
|
||||||
struct regmap *regmap;
|
struct regmap *regmap;
|
||||||
int device_type;
|
int device_type;
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
|
ret = skl_int3472_get_sensor_adev_and_name(&client->dev, NULL,
|
||||||
|
&clk_pdata.consumer_dev_name);
|
||||||
|
if (ret)
|
||||||
|
return ret;
|
||||||
|
|
||||||
regmap = devm_regmap_init_i2c(client, &tps68470_regmap_config);
|
regmap = devm_regmap_init_i2c(client, &tps68470_regmap_config);
|
||||||
if (IS_ERR(regmap)) {
|
if (IS_ERR(regmap)) {
|
||||||
dev_err(&client->dev, "Failed to create regmap: %ld\n", PTR_ERR(regmap));
|
dev_err(&client->dev, "Failed to create regmap: %ld\n", PTR_ERR(regmap));
|
||||||
|
@ -119,9 +127,38 @@ int skl_int3472_tps68470_probe(struct i2c_client *client)
|
||||||
device_type = skl_int3472_tps68470_calc_type(adev);
|
device_type = skl_int3472_tps68470_calc_type(adev);
|
||||||
switch (device_type) {
|
switch (device_type) {
|
||||||
case DESIGNED_FOR_WINDOWS:
|
case DESIGNED_FOR_WINDOWS:
|
||||||
|
board_data = int3472_tps68470_get_board_data(dev_name(&client->dev));
|
||||||
|
if (!board_data)
|
||||||
|
return dev_err_probe(&client->dev, -ENODEV, "No board-data found for this model\n");
|
||||||
|
|
||||||
|
cells = kcalloc(TPS68470_WIN_MFD_CELL_COUNT, sizeof(*cells), GFP_KERNEL);
|
||||||
|
if (!cells)
|
||||||
|
return -ENOMEM;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* The order of the cells matters here! The clk must be first
|
||||||
|
* because the regulator depends on it. The gpios must be last,
|
||||||
|
* acpi_gpiochip_add() calls acpi_dev_clear_dependencies() and
|
||||||
|
* the clk + regulators must be ready when this happens.
|
||||||
|
*/
|
||||||
|
cells[0].name = "tps68470-clk";
|
||||||
|
cells[0].platform_data = &clk_pdata;
|
||||||
|
cells[0].pdata_size = sizeof(clk_pdata);
|
||||||
|
cells[1].name = "tps68470-regulator";
|
||||||
|
cells[1].platform_data = (void *)board_data->tps68470_regulator_pdata;
|
||||||
|
cells[1].pdata_size = sizeof(struct tps68470_regulator_platform_data);
|
||||||
|
cells[2].name = "tps68470-gpio";
|
||||||
|
|
||||||
|
gpiod_add_lookup_table(board_data->tps68470_gpio_lookup_table);
|
||||||
|
|
||||||
ret = devm_mfd_add_devices(&client->dev, PLATFORM_DEVID_NONE,
|
ret = devm_mfd_add_devices(&client->dev, PLATFORM_DEVID_NONE,
|
||||||
tps68470_win, ARRAY_SIZE(tps68470_win),
|
cells, TPS68470_WIN_MFD_CELL_COUNT,
|
||||||
NULL, 0, NULL);
|
NULL, 0, NULL);
|
||||||
|
kfree(cells);
|
||||||
|
|
||||||
|
if (ret)
|
||||||
|
gpiod_remove_lookup_table(board_data->tps68470_gpio_lookup_table);
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case DESIGNED_FOR_CHROMEOS:
|
case DESIGNED_FOR_CHROMEOS:
|
||||||
ret = devm_mfd_add_devices(&client->dev, PLATFORM_DEVID_NONE,
|
ret = devm_mfd_add_devices(&client->dev, PLATFORM_DEVID_NONE,
|
||||||
|
@ -133,5 +170,42 @@ int skl_int3472_tps68470_probe(struct i2c_client *client)
|
||||||
return device_type;
|
return device_type;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* No acpi_dev_clear_dependencies() here, since the acpi_gpiochip_add()
|
||||||
|
* for the GPIO cell already does this.
|
||||||
|
*/
|
||||||
|
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int skl_int3472_tps68470_remove(struct i2c_client *client)
|
||||||
|
{
|
||||||
|
const struct int3472_tps68470_board_data *board_data;
|
||||||
|
|
||||||
|
board_data = int3472_tps68470_get_board_data(dev_name(&client->dev));
|
||||||
|
if (board_data)
|
||||||
|
gpiod_remove_lookup_table(board_data->tps68470_gpio_lookup_table);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static const struct acpi_device_id int3472_device_id[] = {
|
||||||
|
{ "INT3472", 0 },
|
||||||
|
{ }
|
||||||
|
};
|
||||||
|
MODULE_DEVICE_TABLE(acpi, int3472_device_id);
|
||||||
|
|
||||||
|
static struct i2c_driver int3472_tps68470 = {
|
||||||
|
.driver = {
|
||||||
|
.name = "int3472-tps68470",
|
||||||
|
.acpi_match_table = int3472_device_id,
|
||||||
|
},
|
||||||
|
.probe_new = skl_int3472_tps68470_probe,
|
||||||
|
.remove = skl_int3472_tps68470_remove,
|
||||||
|
};
|
||||||
|
module_i2c_driver(int3472_tps68470);
|
||||||
|
|
||||||
|
MODULE_DESCRIPTION("Intel SkyLake INT3472 ACPI TPS68470 Device Driver");
|
||||||
|
MODULE_AUTHOR("Daniel Scally <djrscally@gmail.com>");
|
||||||
|
MODULE_LICENSE("GPL v2");
|
||||||
|
MODULE_SOFTDEP("pre: clk-tps68470 tps68470-regulator");
|
|
@ -0,0 +1,25 @@
|
||||||
|
/* SPDX-License-Identifier: GPL-2.0 */
|
||||||
|
/*
|
||||||
|
* TI TPS68470 PMIC platform data definition.
|
||||||
|
*
|
||||||
|
* Copyright (c) 2021 Red Hat Inc.
|
||||||
|
*
|
||||||
|
* Red Hat authors:
|
||||||
|
* Hans de Goede <hdegoede@redhat.com>
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _INTEL_SKL_INT3472_TPS68470_H
|
||||||
|
#define _INTEL_SKL_INT3472_TPS68470_H
|
||||||
|
|
||||||
|
struct gpiod_lookup_table;
|
||||||
|
struct tps68470_regulator_platform_data;
|
||||||
|
|
||||||
|
struct int3472_tps68470_board_data {
|
||||||
|
const char *dev_name;
|
||||||
|
struct gpiod_lookup_table *tps68470_gpio_lookup_table;
|
||||||
|
const struct tps68470_regulator_platform_data *tps68470_regulator_pdata;
|
||||||
|
};
|
||||||
|
|
||||||
|
const struct int3472_tps68470_board_data *int3472_tps68470_get_board_data(const char *dev_name);
|
||||||
|
|
||||||
|
#endif
|
|
@ -0,0 +1,145 @@
|
||||||
|
// SPDX-License-Identifier: GPL-2.0
|
||||||
|
/*
|
||||||
|
* TI TPS68470 PMIC platform data definition.
|
||||||
|
*
|
||||||
|
* Copyright (c) 2021 Dan Scally <djrscally@gmail.com>
|
||||||
|
* Copyright (c) 2021 Red Hat Inc.
|
||||||
|
*
|
||||||
|
* Red Hat authors:
|
||||||
|
* Hans de Goede <hdegoede@redhat.com>
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <linux/dmi.h>
|
||||||
|
#include <linux/gpio/machine.h>
|
||||||
|
#include <linux/platform_data/tps68470.h>
|
||||||
|
#include <linux/regulator/machine.h>
|
||||||
|
#include "tps68470.h"
|
||||||
|
|
||||||
|
static struct regulator_consumer_supply int347a_core_consumer_supplies[] = {
|
||||||
|
REGULATOR_SUPPLY("dvdd", "i2c-INT347A:00"),
|
||||||
|
};
|
||||||
|
|
||||||
|
static struct regulator_consumer_supply int347a_ana_consumer_supplies[] = {
|
||||||
|
REGULATOR_SUPPLY("avdd", "i2c-INT347A:00"),
|
||||||
|
};
|
||||||
|
|
||||||
|
static struct regulator_consumer_supply int347a_vcm_consumer_supplies[] = {
|
||||||
|
REGULATOR_SUPPLY("vdd", "i2c-INT347A:00-VCM"),
|
||||||
|
};
|
||||||
|
|
||||||
|
static struct regulator_consumer_supply int347a_vsio_consumer_supplies[] = {
|
||||||
|
REGULATOR_SUPPLY("dovdd", "i2c-INT347A:00"),
|
||||||
|
REGULATOR_SUPPLY("vsio", "i2c-INT347A:00-VCM"),
|
||||||
|
};
|
||||||
|
|
||||||
|
static const struct regulator_init_data surface_go_tps68470_core_reg_init_data = {
|
||||||
|
.constraints = {
|
||||||
|
.min_uV = 1200000,
|
||||||
|
.max_uV = 1200000,
|
||||||
|
.apply_uV = true,
|
||||||
|
.valid_ops_mask = REGULATOR_CHANGE_STATUS,
|
||||||
|
},
|
||||||
|
.num_consumer_supplies = ARRAY_SIZE(int347a_core_consumer_supplies),
|
||||||
|
.consumer_supplies = int347a_core_consumer_supplies,
|
||||||
|
};
|
||||||
|
|
||||||
|
static const struct regulator_init_data surface_go_tps68470_ana_reg_init_data = {
|
||||||
|
.constraints = {
|
||||||
|
.min_uV = 2815200,
|
||||||
|
.max_uV = 2815200,
|
||||||
|
.apply_uV = true,
|
||||||
|
.valid_ops_mask = REGULATOR_CHANGE_STATUS,
|
||||||
|
},
|
||||||
|
.num_consumer_supplies = ARRAY_SIZE(int347a_ana_consumer_supplies),
|
||||||
|
.consumer_supplies = int347a_ana_consumer_supplies,
|
||||||
|
};
|
||||||
|
|
||||||
|
static const struct regulator_init_data surface_go_tps68470_vcm_reg_init_data = {
|
||||||
|
.constraints = {
|
||||||
|
.min_uV = 2815200,
|
||||||
|
.max_uV = 2815200,
|
||||||
|
.apply_uV = true,
|
||||||
|
.valid_ops_mask = REGULATOR_CHANGE_STATUS,
|
||||||
|
},
|
||||||
|
.num_consumer_supplies = ARRAY_SIZE(int347a_vcm_consumer_supplies),
|
||||||
|
.consumer_supplies = int347a_vcm_consumer_supplies,
|
||||||
|
};
|
||||||
|
|
||||||
|
/* Ensure the always-on VIO regulator has the same voltage as VSIO */
|
||||||
|
static const struct regulator_init_data surface_go_tps68470_vio_reg_init_data = {
|
||||||
|
.constraints = {
|
||||||
|
.min_uV = 1800600,
|
||||||
|
.max_uV = 1800600,
|
||||||
|
.apply_uV = true,
|
||||||
|
.always_on = true,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
static const struct regulator_init_data surface_go_tps68470_vsio_reg_init_data = {
|
||||||
|
.constraints = {
|
||||||
|
.min_uV = 1800600,
|
||||||
|
.max_uV = 1800600,
|
||||||
|
.apply_uV = true,
|
||||||
|
.valid_ops_mask = REGULATOR_CHANGE_STATUS,
|
||||||
|
},
|
||||||
|
.num_consumer_supplies = ARRAY_SIZE(int347a_vsio_consumer_supplies),
|
||||||
|
.consumer_supplies = int347a_vsio_consumer_supplies,
|
||||||
|
};
|
||||||
|
|
||||||
|
static const struct tps68470_regulator_platform_data surface_go_tps68470_pdata = {
|
||||||
|
.reg_init_data = {
|
||||||
|
[TPS68470_CORE] = &surface_go_tps68470_core_reg_init_data,
|
||||||
|
[TPS68470_ANA] = &surface_go_tps68470_ana_reg_init_data,
|
||||||
|
[TPS68470_VCM] = &surface_go_tps68470_vcm_reg_init_data,
|
||||||
|
[TPS68470_VIO] = &surface_go_tps68470_vio_reg_init_data,
|
||||||
|
[TPS68470_VSIO] = &surface_go_tps68470_vsio_reg_init_data,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
static struct gpiod_lookup_table surface_go_tps68470_gpios = {
|
||||||
|
.dev_id = "i2c-INT347A:00",
|
||||||
|
.table = {
|
||||||
|
GPIO_LOOKUP("tps68470-gpio", 9, "reset", GPIO_ACTIVE_LOW),
|
||||||
|
GPIO_LOOKUP("tps68470-gpio", 7, "powerdown", GPIO_ACTIVE_LOW)
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
static const struct int3472_tps68470_board_data surface_go_tps68470_board_data = {
|
||||||
|
.dev_name = "i2c-INT3472:05",
|
||||||
|
.tps68470_gpio_lookup_table = &surface_go_tps68470_gpios,
|
||||||
|
.tps68470_regulator_pdata = &surface_go_tps68470_pdata,
|
||||||
|
};
|
||||||
|
|
||||||
|
static const struct dmi_system_id int3472_tps68470_board_data_table[] = {
|
||||||
|
{
|
||||||
|
.matches = {
|
||||||
|
DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
|
||||||
|
DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Go"),
|
||||||
|
},
|
||||||
|
.driver_data = (void *)&surface_go_tps68470_board_data,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
.matches = {
|
||||||
|
DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
|
||||||
|
DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Go 2"),
|
||||||
|
},
|
||||||
|
.driver_data = (void *)&surface_go_tps68470_board_data,
|
||||||
|
},
|
||||||
|
{ }
|
||||||
|
};
|
||||||
|
|
||||||
|
const struct int3472_tps68470_board_data *int3472_tps68470_get_board_data(const char *dev_name)
|
||||||
|
{
|
||||||
|
const struct int3472_tps68470_board_data *board_data;
|
||||||
|
const struct dmi_system_id *match;
|
||||||
|
|
||||||
|
for (match = dmi_first_match(int3472_tps68470_board_data_table);
|
||||||
|
match;
|
||||||
|
match = dmi_first_match(match + 1)) {
|
||||||
|
board_data = match->driver_data;
|
||||||
|
if (strcmp(board_data->dev_name, dev_name) == 0)
|
||||||
|
return board_data;
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
|
@ -202,7 +202,8 @@ struct acpi_device_flags {
|
||||||
u32 coherent_dma:1;
|
u32 coherent_dma:1;
|
||||||
u32 cca_seen:1;
|
u32 cca_seen:1;
|
||||||
u32 enumeration_by_parent:1;
|
u32 enumeration_by_parent:1;
|
||||||
u32 reserved:19;
|
u32 honor_deps:1;
|
||||||
|
u32 reserved:18;
|
||||||
};
|
};
|
||||||
|
|
||||||
/* File System */
|
/* File System */
|
||||||
|
@ -285,6 +286,7 @@ struct acpi_dep_data {
|
||||||
struct list_head node;
|
struct list_head node;
|
||||||
acpi_handle supplier;
|
acpi_handle supplier;
|
||||||
acpi_handle consumer;
|
acpi_handle consumer;
|
||||||
|
bool honor_dep;
|
||||||
};
|
};
|
||||||
|
|
||||||
/* Performance Management */
|
/* Performance Management */
|
||||||
|
@ -693,6 +695,7 @@ static inline bool acpi_device_can_poweroff(struct acpi_device *adev)
|
||||||
bool acpi_dev_hid_uid_match(struct acpi_device *adev, const char *hid2, const char *uid2);
|
bool acpi_dev_hid_uid_match(struct acpi_device *adev, const char *hid2, const char *uid2);
|
||||||
|
|
||||||
void acpi_dev_clear_dependencies(struct acpi_device *supplier);
|
void acpi_dev_clear_dependencies(struct acpi_device *supplier);
|
||||||
|
bool acpi_dev_ready_for_enumeration(const struct acpi_device *device);
|
||||||
struct acpi_device *acpi_dev_get_first_consumer_dev(struct acpi_device *supplier);
|
struct acpi_device *acpi_dev_get_first_consumer_dev(struct acpi_device *supplier);
|
||||||
struct acpi_device *
|
struct acpi_device *
|
||||||
acpi_dev_get_next_match_dev(struct acpi_device *adev, const char *hid, const char *uid, s64 hrv);
|
acpi_dev_get_next_match_dev(struct acpi_device *adev, const char *hid, const char *uid, s64 hrv);
|
||||||
|
|
|
@ -1025,7 +1025,8 @@ bool i2c_acpi_get_i2c_resource(struct acpi_resource *ares,
|
||||||
struct acpi_resource_i2c_serialbus **i2c);
|
struct acpi_resource_i2c_serialbus **i2c);
|
||||||
int i2c_acpi_client_count(struct acpi_device *adev);
|
int i2c_acpi_client_count(struct acpi_device *adev);
|
||||||
u32 i2c_acpi_find_bus_speed(struct device *dev);
|
u32 i2c_acpi_find_bus_speed(struct device *dev);
|
||||||
struct i2c_client *i2c_acpi_new_device(struct device *dev, int index,
|
struct i2c_client *i2c_acpi_new_device_by_fwnode(struct fwnode_handle *fwnode,
|
||||||
|
int index,
|
||||||
struct i2c_board_info *info);
|
struct i2c_board_info *info);
|
||||||
struct i2c_adapter *i2c_acpi_find_adapter_by_handle(acpi_handle handle);
|
struct i2c_adapter *i2c_acpi_find_adapter_by_handle(acpi_handle handle);
|
||||||
bool i2c_acpi_waive_d0_probe(struct device *dev);
|
bool i2c_acpi_waive_d0_probe(struct device *dev);
|
||||||
|
@ -1043,8 +1044,9 @@ static inline u32 i2c_acpi_find_bus_speed(struct device *dev)
|
||||||
{
|
{
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
static inline struct i2c_client *i2c_acpi_new_device(struct device *dev,
|
static inline struct i2c_client *i2c_acpi_new_device_by_fwnode(
|
||||||
int index, struct i2c_board_info *info)
|
struct fwnode_handle *fwnode, int index,
|
||||||
|
struct i2c_board_info *info)
|
||||||
{
|
{
|
||||||
return ERR_PTR(-ENODEV);
|
return ERR_PTR(-ENODEV);
|
||||||
}
|
}
|
||||||
|
@ -1058,4 +1060,11 @@ static inline bool i2c_acpi_waive_d0_probe(struct device *dev)
|
||||||
}
|
}
|
||||||
#endif /* CONFIG_ACPI */
|
#endif /* CONFIG_ACPI */
|
||||||
|
|
||||||
|
static inline struct i2c_client *i2c_acpi_new_device(struct device *dev,
|
||||||
|
int index,
|
||||||
|
struct i2c_board_info *info)
|
||||||
|
{
|
||||||
|
return i2c_acpi_new_device_by_fwnode(dev_fwnode(dev), index, info);
|
||||||
|
}
|
||||||
|
|
||||||
#endif /* _LINUX_I2C_H */
|
#endif /* _LINUX_I2C_H */
|
||||||
|
|
|
@ -0,0 +1,35 @@
|
||||||
|
/* SPDX-License-Identifier: GPL-2.0-or-later */
|
||||||
|
/*
|
||||||
|
* TI TPS68470 PMIC platform data definition.
|
||||||
|
*
|
||||||
|
* Copyright (c) 2021 Red Hat Inc.
|
||||||
|
*
|
||||||
|
* Red Hat authors:
|
||||||
|
* Hans de Goede <hdegoede@redhat.com>
|
||||||
|
*/
|
||||||
|
#ifndef __PDATA_TPS68470_H
|
||||||
|
#define __PDATA_TPS68470_H
|
||||||
|
|
||||||
|
enum tps68470_regulators {
|
||||||
|
TPS68470_CORE,
|
||||||
|
TPS68470_ANA,
|
||||||
|
TPS68470_VCM,
|
||||||
|
TPS68470_VIO,
|
||||||
|
TPS68470_VSIO,
|
||||||
|
TPS68470_AUX1,
|
||||||
|
TPS68470_AUX2,
|
||||||
|
TPS68470_NUM_REGULATORS
|
||||||
|
};
|
||||||
|
|
||||||
|
struct regulator_init_data;
|
||||||
|
|
||||||
|
struct tps68470_regulator_platform_data {
|
||||||
|
const struct regulator_init_data *reg_init_data[TPS68470_NUM_REGULATORS];
|
||||||
|
};
|
||||||
|
|
||||||
|
struct tps68470_clk_platform_data {
|
||||||
|
const char *consumer_dev_name;
|
||||||
|
const char *consumer_con_id;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
Loading…
Reference in New Issue