ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
/*
|
|
|
|
* ACPI device specific properties support.
|
|
|
|
*
|
|
|
|
* Copyright (C) 2014, Intel Corporation
|
|
|
|
* All rights reserved.
|
|
|
|
*
|
|
|
|
* Authors: Mika Westerberg <mika.westerberg@linux.intel.com>
|
|
|
|
* Darren Hart <dvhart@linux.intel.com>
|
|
|
|
* Rafael J. Wysocki <rafael.j.wysocki@intel.com>
|
|
|
|
*
|
|
|
|
* This program is free software; you can redistribute it and/or modify
|
|
|
|
* it under the terms of the GNU General Public License version 2 as
|
|
|
|
* published by the Free Software Foundation.
|
|
|
|
*/
|
|
|
|
|
|
|
|
#include <linux/acpi.h>
|
|
|
|
#include <linux/device.h>
|
|
|
|
#include <linux/export.h>
|
|
|
|
|
|
|
|
#include "internal.h"
|
|
|
|
|
2017-07-21 19:39:34 +08:00
|
|
|
static int acpi_data_get_property_array(const struct acpi_device_data *data,
|
2015-08-27 10:40:05 +08:00
|
|
|
const char *name,
|
|
|
|
acpi_object_type type,
|
|
|
|
const union acpi_object **obj);
|
|
|
|
|
2017-07-20 02:28:57 +08:00
|
|
|
/* ACPI _DSD device properties GUID: daffd814-6eba-4d8c-8a91-bc9bbf4aa301 */
|
|
|
|
static const guid_t prp_guid =
|
|
|
|
GUID_INIT(0xdaffd814, 0x6eba, 0x4d8c,
|
|
|
|
0x8a, 0x91, 0xbc, 0x9b, 0xbf, 0x4a, 0xa3, 0x01);
|
|
|
|
/* ACPI _DSD data subnodes GUID: dbb8e3e6-5886-4ba6-8795-1319f52a966b */
|
|
|
|
static const guid_t ads_guid =
|
|
|
|
GUID_INIT(0xdbb8e3e6, 0x5886, 0x4ba6,
|
|
|
|
0x87, 0x95, 0x13, 0x19, 0xf5, 0x2a, 0x96, 0x6b);
|
2015-08-27 10:36:14 +08:00
|
|
|
|
|
|
|
static bool acpi_enumerate_nondev_subnodes(acpi_handle scope,
|
|
|
|
const union acpi_object *desc,
|
2017-03-28 15:52:16 +08:00
|
|
|
struct acpi_device_data *data,
|
|
|
|
struct fwnode_handle *parent);
|
2015-08-27 10:36:14 +08:00
|
|
|
static bool acpi_extract_properties(const union acpi_object *desc,
|
|
|
|
struct acpi_device_data *data);
|
|
|
|
|
2016-11-22 07:02:19 +08:00
|
|
|
static bool acpi_nondev_subnode_extract(const union acpi_object *desc,
|
|
|
|
acpi_handle handle,
|
|
|
|
const union acpi_object *link,
|
2017-03-28 15:52:16 +08:00
|
|
|
struct list_head *list,
|
|
|
|
struct fwnode_handle *parent)
|
2015-08-27 10:36:14 +08:00
|
|
|
{
|
|
|
|
struct acpi_data_node *dn;
|
2016-11-22 07:02:19 +08:00
|
|
|
bool result;
|
2015-08-27 10:36:14 +08:00
|
|
|
|
|
|
|
dn = kzalloc(sizeof(*dn), GFP_KERNEL);
|
|
|
|
if (!dn)
|
|
|
|
return false;
|
|
|
|
|
|
|
|
dn->name = link->package.elements[0].string.pointer;
|
2017-07-21 19:39:31 +08:00
|
|
|
dn->fwnode.ops = &acpi_data_fwnode_ops;
|
2017-03-28 15:52:16 +08:00
|
|
|
dn->parent = parent;
|
2015-08-27 10:36:14 +08:00
|
|
|
INIT_LIST_HEAD(&dn->data.subnodes);
|
|
|
|
|
2016-11-22 07:02:19 +08:00
|
|
|
result = acpi_extract_properties(desc, &dn->data);
|
2015-08-27 10:36:14 +08:00
|
|
|
|
2016-11-22 07:02:19 +08:00
|
|
|
if (handle) {
|
|
|
|
acpi_handle scope;
|
|
|
|
acpi_status status;
|
2015-08-27 10:36:14 +08:00
|
|
|
|
2016-11-22 07:02:19 +08:00
|
|
|
/*
|
|
|
|
* The scope for the subnode object lookup is the one of the
|
|
|
|
* namespace node (device) containing the object that has
|
|
|
|
* returned the package. That is, it's the scope of that
|
|
|
|
* object's parent.
|
|
|
|
*/
|
|
|
|
status = acpi_get_parent(handle, &scope);
|
|
|
|
if (ACPI_SUCCESS(status)
|
2017-03-28 15:52:16 +08:00
|
|
|
&& acpi_enumerate_nondev_subnodes(scope, desc, &dn->data,
|
|
|
|
&dn->fwnode))
|
2016-11-22 07:02:19 +08:00
|
|
|
result = true;
|
2017-03-28 15:52:16 +08:00
|
|
|
} else if (acpi_enumerate_nondev_subnodes(NULL, desc, &dn->data,
|
|
|
|
&dn->fwnode)) {
|
2016-11-22 07:02:19 +08:00
|
|
|
result = true;
|
|
|
|
}
|
2015-08-27 10:36:14 +08:00
|
|
|
|
2016-11-22 07:02:19 +08:00
|
|
|
if (result) {
|
2015-08-27 10:37:19 +08:00
|
|
|
dn->handle = handle;
|
2016-11-22 07:02:19 +08:00
|
|
|
dn->data.pointer = desc;
|
2015-08-27 10:36:14 +08:00
|
|
|
list_add_tail(&dn->sibling, list);
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
2016-11-22 07:02:19 +08:00
|
|
|
kfree(dn);
|
2015-08-27 10:36:14 +08:00
|
|
|
acpi_handle_debug(handle, "Invalid properties/subnodes data, skipping\n");
|
2016-11-22 07:02:19 +08:00
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
|
|
|
static bool acpi_nondev_subnode_data_ok(acpi_handle handle,
|
|
|
|
const union acpi_object *link,
|
2017-03-28 15:52:16 +08:00
|
|
|
struct list_head *list,
|
|
|
|
struct fwnode_handle *parent)
|
2016-11-22 07:02:19 +08:00
|
|
|
{
|
|
|
|
struct acpi_buffer buf = { ACPI_ALLOCATE_BUFFER };
|
|
|
|
acpi_status status;
|
|
|
|
|
|
|
|
status = acpi_evaluate_object_typed(handle, NULL, NULL, &buf,
|
|
|
|
ACPI_TYPE_PACKAGE);
|
|
|
|
if (ACPI_FAILURE(status))
|
|
|
|
return false;
|
|
|
|
|
2017-03-28 15:52:16 +08:00
|
|
|
if (acpi_nondev_subnode_extract(buf.pointer, handle, link, list,
|
|
|
|
parent))
|
2016-11-22 07:02:19 +08:00
|
|
|
return true;
|
2015-08-27 10:36:14 +08:00
|
|
|
|
|
|
|
ACPI_FREE(buf.pointer);
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2016-11-22 07:02:19 +08:00
|
|
|
static bool acpi_nondev_subnode_ok(acpi_handle scope,
|
|
|
|
const union acpi_object *link,
|
2017-03-28 15:52:16 +08:00
|
|
|
struct list_head *list,
|
|
|
|
struct fwnode_handle *parent)
|
2016-11-22 07:02:19 +08:00
|
|
|
{
|
|
|
|
acpi_handle handle;
|
|
|
|
acpi_status status;
|
|
|
|
|
|
|
|
if (!scope)
|
|
|
|
return false;
|
|
|
|
|
|
|
|
status = acpi_get_handle(scope, link->package.elements[1].string.pointer,
|
|
|
|
&handle);
|
|
|
|
if (ACPI_FAILURE(status))
|
|
|
|
return false;
|
|
|
|
|
2017-03-28 15:52:16 +08:00
|
|
|
return acpi_nondev_subnode_data_ok(handle, link, list, parent);
|
2016-11-22 07:02:19 +08:00
|
|
|
}
|
|
|
|
|
2015-08-27 10:36:14 +08:00
|
|
|
static int acpi_add_nondev_subnodes(acpi_handle scope,
|
|
|
|
const union acpi_object *links,
|
2017-03-28 15:52:16 +08:00
|
|
|
struct list_head *list,
|
|
|
|
struct fwnode_handle *parent)
|
2015-08-27 10:36:14 +08:00
|
|
|
{
|
|
|
|
bool ret = false;
|
|
|
|
int i;
|
|
|
|
|
|
|
|
for (i = 0; i < links->package.count; i++) {
|
2016-11-22 07:02:19 +08:00
|
|
|
const union acpi_object *link, *desc;
|
|
|
|
acpi_handle handle;
|
|
|
|
bool result;
|
2015-08-27 10:36:14 +08:00
|
|
|
|
|
|
|
link = &links->package.elements[i];
|
2016-11-22 07:02:19 +08:00
|
|
|
/* Only two elements allowed. */
|
|
|
|
if (link->package.count != 2)
|
|
|
|
continue;
|
|
|
|
|
|
|
|
/* The first one must be a string. */
|
|
|
|
if (link->package.elements[0].type != ACPI_TYPE_STRING)
|
|
|
|
continue;
|
|
|
|
|
|
|
|
/* The second one may be a string, a reference or a package. */
|
|
|
|
switch (link->package.elements[1].type) {
|
|
|
|
case ACPI_TYPE_STRING:
|
2017-03-28 15:52:16 +08:00
|
|
|
result = acpi_nondev_subnode_ok(scope, link, list,
|
|
|
|
parent);
|
2016-11-22 07:02:19 +08:00
|
|
|
break;
|
|
|
|
case ACPI_TYPE_LOCAL_REFERENCE:
|
|
|
|
handle = link->package.elements[1].reference.handle;
|
2017-03-28 15:52:16 +08:00
|
|
|
result = acpi_nondev_subnode_data_ok(handle, link, list,
|
|
|
|
parent);
|
2016-11-22 07:02:19 +08:00
|
|
|
break;
|
|
|
|
case ACPI_TYPE_PACKAGE:
|
|
|
|
desc = &link->package.elements[1];
|
2017-03-28 15:52:16 +08:00
|
|
|
result = acpi_nondev_subnode_extract(desc, NULL, link,
|
|
|
|
list, parent);
|
2016-11-22 07:02:19 +08:00
|
|
|
break;
|
|
|
|
default:
|
|
|
|
result = false;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
ret = ret || result;
|
2015-08-27 10:36:14 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
|
|
|
|
static bool acpi_enumerate_nondev_subnodes(acpi_handle scope,
|
|
|
|
const union acpi_object *desc,
|
2017-03-28 15:52:16 +08:00
|
|
|
struct acpi_device_data *data,
|
|
|
|
struct fwnode_handle *parent)
|
2015-08-27 10:36:14 +08:00
|
|
|
{
|
|
|
|
int i;
|
|
|
|
|
2017-07-20 02:28:57 +08:00
|
|
|
/* Look for the ACPI data subnodes GUID. */
|
2015-08-27 10:36:14 +08:00
|
|
|
for (i = 0; i < desc->package.count; i += 2) {
|
2017-07-20 02:28:57 +08:00
|
|
|
const union acpi_object *guid, *links;
|
2015-08-27 10:36:14 +08:00
|
|
|
|
2017-07-20 02:28:57 +08:00
|
|
|
guid = &desc->package.elements[i];
|
2015-08-27 10:36:14 +08:00
|
|
|
links = &desc->package.elements[i + 1];
|
|
|
|
|
|
|
|
/*
|
2017-07-20 02:28:57 +08:00
|
|
|
* The first element must be a GUID and the second one must be
|
2015-08-27 10:36:14 +08:00
|
|
|
* a package.
|
|
|
|
*/
|
2017-07-20 02:28:57 +08:00
|
|
|
if (guid->type != ACPI_TYPE_BUFFER ||
|
|
|
|
guid->buffer.length != 16 ||
|
|
|
|
links->type != ACPI_TYPE_PACKAGE)
|
2015-08-27 10:36:14 +08:00
|
|
|
break;
|
|
|
|
|
2017-07-20 02:28:57 +08:00
|
|
|
if (!guid_equal((guid_t *)guid->buffer.pointer, &ads_guid))
|
2015-08-27 10:36:14 +08:00
|
|
|
continue;
|
|
|
|
|
2017-03-28 15:52:16 +08:00
|
|
|
return acpi_add_nondev_subnodes(scope, links, &data->subnodes,
|
|
|
|
parent);
|
2015-08-27 10:36:14 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
return false;
|
|
|
|
}
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
|
|
|
|
static bool acpi_property_value_ok(const union acpi_object *value)
|
|
|
|
{
|
|
|
|
int j;
|
|
|
|
|
|
|
|
/*
|
|
|
|
* The value must be an integer, a string, a reference, or a package
|
|
|
|
* whose every element must be an integer, a string, or a reference.
|
|
|
|
*/
|
|
|
|
switch (value->type) {
|
|
|
|
case ACPI_TYPE_INTEGER:
|
|
|
|
case ACPI_TYPE_STRING:
|
|
|
|
case ACPI_TYPE_LOCAL_REFERENCE:
|
|
|
|
return true;
|
|
|
|
|
|
|
|
case ACPI_TYPE_PACKAGE:
|
|
|
|
for (j = 0; j < value->package.count; j++)
|
|
|
|
switch (value->package.elements[j].type) {
|
|
|
|
case ACPI_TYPE_INTEGER:
|
|
|
|
case ACPI_TYPE_STRING:
|
|
|
|
case ACPI_TYPE_LOCAL_REFERENCE:
|
|
|
|
continue;
|
|
|
|
|
|
|
|
default:
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
|
|
|
static bool acpi_properties_format_valid(const union acpi_object *properties)
|
|
|
|
{
|
|
|
|
int i;
|
|
|
|
|
|
|
|
for (i = 0; i < properties->package.count; i++) {
|
|
|
|
const union acpi_object *property;
|
|
|
|
|
|
|
|
property = &properties->package.elements[i];
|
|
|
|
/*
|
|
|
|
* Only two elements allowed, the first one must be a string and
|
|
|
|
* the second one has to satisfy certain conditions.
|
|
|
|
*/
|
|
|
|
if (property->package.count != 2
|
|
|
|
|| property->package.elements[0].type != ACPI_TYPE_STRING
|
|
|
|
|| !acpi_property_value_ok(&property->package.elements[1]))
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
2014-10-21 19:33:56 +08:00
|
|
|
static void acpi_init_of_compatible(struct acpi_device *adev)
|
|
|
|
{
|
|
|
|
const union acpi_object *of_compatible;
|
|
|
|
int ret;
|
|
|
|
|
2015-08-27 10:40:05 +08:00
|
|
|
ret = acpi_data_get_property_array(&adev->data, "compatible",
|
|
|
|
ACPI_TYPE_STRING, &of_compatible);
|
2014-10-21 19:33:56 +08:00
|
|
|
if (ret) {
|
|
|
|
ret = acpi_dev_get_property(adev, "compatible",
|
|
|
|
ACPI_TYPE_STRING, &of_compatible);
|
|
|
|
if (ret) {
|
2015-05-05 21:43:07 +08:00
|
|
|
if (adev->parent
|
|
|
|
&& adev->parent->flags.of_compatible_ok)
|
|
|
|
goto out;
|
|
|
|
|
2014-10-21 19:33:56 +08:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
adev->data.of_compatible = of_compatible;
|
2015-05-05 21:43:07 +08:00
|
|
|
|
|
|
|
out:
|
|
|
|
adev->flags.of_compatible_ok = 1;
|
2014-10-21 19:33:56 +08:00
|
|
|
}
|
|
|
|
|
2015-08-27 10:35:14 +08:00
|
|
|
static bool acpi_extract_properties(const union acpi_object *desc,
|
|
|
|
struct acpi_device_data *data)
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
{
|
|
|
|
int i;
|
|
|
|
|
|
|
|
if (desc->package.count % 2)
|
2015-08-27 10:35:14 +08:00
|
|
|
return false;
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
|
2017-07-20 02:28:57 +08:00
|
|
|
/* Look for the device properties GUID. */
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
for (i = 0; i < desc->package.count; i += 2) {
|
2017-07-20 02:28:57 +08:00
|
|
|
const union acpi_object *guid, *properties;
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
|
2017-07-20 02:28:57 +08:00
|
|
|
guid = &desc->package.elements[i];
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
properties = &desc->package.elements[i + 1];
|
|
|
|
|
|
|
|
/*
|
2017-07-20 02:28:57 +08:00
|
|
|
* The first element must be a GUID and the second one must be
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
* a package.
|
|
|
|
*/
|
2017-07-20 02:28:57 +08:00
|
|
|
if (guid->type != ACPI_TYPE_BUFFER ||
|
|
|
|
guid->buffer.length != 16 ||
|
|
|
|
properties->type != ACPI_TYPE_PACKAGE)
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
break;
|
|
|
|
|
2017-07-20 02:28:57 +08:00
|
|
|
if (!guid_equal((guid_t *)guid->buffer.pointer, &prp_guid))
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
continue;
|
|
|
|
|
|
|
|
/*
|
2017-07-20 02:28:57 +08:00
|
|
|
* We found the matching GUID. Now validate the format of the
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
* package immediately following it.
|
|
|
|
*/
|
|
|
|
if (!acpi_properties_format_valid(properties))
|
|
|
|
break;
|
|
|
|
|
2015-08-27 10:35:14 +08:00
|
|
|
data->properties = properties;
|
|
|
|
return true;
|
|
|
|
}
|
2014-10-21 19:33:56 +08:00
|
|
|
|
2015-08-27 10:35:14 +08:00
|
|
|
return false;
|
|
|
|
}
|
2015-05-05 21:43:07 +08:00
|
|
|
|
2015-08-27 10:35:14 +08:00
|
|
|
void acpi_init_properties(struct acpi_device *adev)
|
|
|
|
{
|
|
|
|
struct acpi_buffer buf = { ACPI_ALLOCATE_BUFFER };
|
|
|
|
struct acpi_hardware_id *hwid;
|
|
|
|
acpi_status status;
|
|
|
|
bool acpi_of = false;
|
|
|
|
|
2015-08-27 10:36:14 +08:00
|
|
|
INIT_LIST_HEAD(&adev->data.subnodes);
|
|
|
|
|
2017-08-01 20:10:41 +08:00
|
|
|
if (!adev->handle)
|
|
|
|
return;
|
|
|
|
|
2015-08-27 10:35:14 +08:00
|
|
|
/*
|
|
|
|
* Check if ACPI_DT_NAMESPACE_HID is present and inthat case we fill in
|
|
|
|
* Device Tree compatible properties for this device.
|
|
|
|
*/
|
|
|
|
list_for_each_entry(hwid, &adev->pnp.ids, list) {
|
|
|
|
if (!strcmp(hwid->id, ACPI_DT_NAMESPACE_HID)) {
|
|
|
|
acpi_of = true;
|
|
|
|
break;
|
|
|
|
}
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
}
|
|
|
|
|
2015-08-27 10:35:14 +08:00
|
|
|
status = acpi_evaluate_object_typed(adev->handle, "_DSD", NULL, &buf,
|
|
|
|
ACPI_TYPE_PACKAGE);
|
|
|
|
if (ACPI_FAILURE(status))
|
|
|
|
goto out;
|
|
|
|
|
|
|
|
if (acpi_extract_properties(buf.pointer, &adev->data)) {
|
|
|
|
adev->data.pointer = buf.pointer;
|
|
|
|
if (acpi_of)
|
|
|
|
acpi_init_of_compatible(adev);
|
2015-08-27 10:36:14 +08:00
|
|
|
}
|
2017-03-28 15:52:16 +08:00
|
|
|
if (acpi_enumerate_nondev_subnodes(adev->handle, buf.pointer,
|
|
|
|
&adev->data, acpi_fwnode_handle(adev)))
|
2015-08-27 10:36:14 +08:00
|
|
|
adev->data.pointer = buf.pointer;
|
|
|
|
|
|
|
|
if (!adev->data.pointer) {
|
2015-08-27 10:35:14 +08:00
|
|
|
acpi_handle_debug(adev->handle, "Invalid _DSD data, skipping\n");
|
|
|
|
ACPI_FREE(buf.pointer);
|
|
|
|
}
|
2015-05-05 21:43:07 +08:00
|
|
|
|
|
|
|
out:
|
|
|
|
if (acpi_of && !adev->flags.of_compatible_ok)
|
|
|
|
acpi_handle_info(adev->handle,
|
2015-05-22 10:24:34 +08:00
|
|
|
ACPI_DT_NAMESPACE_HID " requires 'compatible' property\n");
|
ACPI / property: Support Apple _DSM properties
While the rest of the world has standardized on _DSD as the way to store
device properties in AML (introduced with ACPI 5.1 in 2014), Apple has
been using a custom _DSM to achieve the same for much longer (ever since
they switched from DeviceTree-based PowerPC to Intel in 2005, verified
with MacOS X 10.4.11).
The theory of operation on macOS is as follows: AppleACPIPlatform.kext
invokes mergeEFIproperties() and mergeDSMproperties() for each device to
merge properties conveyed by EFI drivers as well as properties stored in
AML into the I/O Kit registry from which they can be retrieved by
drivers. We've been supporting EFI properties since commit 58c5475aba67
("x86/efi: Retrieve and assign Apple device properties"). The present
commit adds support for _DSM properties, thereby completing our support
for Apple device properties. The _DSM properties are made available
under the primary fwnode, the EFI properties under the secondary fwnode.
So for devices which possess both property types, they can all be
elegantly accessed with the uniform API in <linux/property.h>.
Until recently we had no need to support _DSM properties, they contained
only uninteresting garbage. The situation has changed with MacBooks and
MacBook Pros introduced since 2015: Their keyboard is attached with SPI
instead of USB and the _CRS data which is necessary to initialize the
spi driver only contains valid information if OSPM responds "false" to
_OSI("Darwin"). If OSPM responds "true", _CRS is empty and the spi
driver fails to initialize. The rationale is very simple, Apple only
cares about macOS and Windows: On Windows, _CRS contains valid data,
whereas on macOS it is empty. Instead, macOS gleans the necessary data
from the _DSM properties.
Since Linux deliberately defaults to responding "true" to _OSI("Darwin"),
we need to emulate macOS' behaviour by initializing the spi driver with
data returned by the _DSM.
An out-of-tree driver for the SPI keyboard exists which currently binds
to the ACPI device, invokes the _DSM, parses the returned package and
instantiates an SPI device with the data gleaned from the _DSM:
https://github.com/cb22/macbook12-spi-driver/commit/9a416d699ef4
https://github.com/cb22/macbook12-spi-driver/commit/0c34936ed9a1
By adding support for Apple's _DSM properties in generic ACPI code, the
out-of-tree driver will be able to register as a regular SPI driver,
significantly reducing its amount of code and improving its chances to
be mainlined.
The SPI keyboard will not be the only user of this commit: E.g. on the
MacBook8,1, the UART-attached Bluetooth device likewise returns empty
_CRS data if OSPM returns "true" to _OSI("Darwin").
The _DSM returns a Package whose format unfortunately deviates slightly
from the _DSD spec: The properties are marshalled up in a single Package
as alternating key/value elements, unlike _DSD which stores them as a
Package of 2-element Packages. The present commit therefore converts
the Package to _DSD format and the ACPI core can then treat the data as
if Apple would follow the standard.
Well, except for one small annoyance: The properties returned by the
_DSM only ever have one of two types, Integer or Buffer. The former is
retrievable as usual with device_property_read_u64(), but the latter is
not part of the _DSD spec and it is not possible to retrieve Buffer
properties with the device_property_read_*() functions due to the type
checking performed in drivers/acpi/property.c. It is however possible
to retrieve them with acpi_dev_get_property(). Apple is using the
Buffer type somewhat sloppily to store null-terminated strings but also
integers. The real data type is not distinguishable by the ACPI core
and the onus is on the caller to use the contents of the Buffer in an
appropriate way.
In case Apple moves to _DSD in the future, this commit first checks for
_DSD and falls back to _DSM only if _DSD is not found.
Tested-by: Ronald Tschalär <ronald@innovation.ch>
Acked-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Reviewed-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
Signed-off-by: Lukas Wunner <lukas@wunner.de>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2017-08-01 20:10:41 +08:00
|
|
|
|
|
|
|
if (!adev->data.pointer)
|
|
|
|
acpi_extract_apple_properties(adev);
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
}
|
|
|
|
|
2015-08-27 10:36:14 +08:00
|
|
|
static void acpi_destroy_nondev_subnodes(struct list_head *list)
|
|
|
|
{
|
|
|
|
struct acpi_data_node *dn, *next;
|
|
|
|
|
|
|
|
if (list_empty(list))
|
|
|
|
return;
|
|
|
|
|
|
|
|
list_for_each_entry_safe_reverse(dn, next, list, sibling) {
|
|
|
|
acpi_destroy_nondev_subnodes(&dn->data.subnodes);
|
2015-08-27 10:37:19 +08:00
|
|
|
wait_for_completion(&dn->kobj_done);
|
2015-08-27 10:36:14 +08:00
|
|
|
list_del(&dn->sibling);
|
|
|
|
ACPI_FREE((void *)dn->data.pointer);
|
|
|
|
kfree(dn);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
void acpi_free_properties(struct acpi_device *adev)
|
|
|
|
{
|
2015-08-27 10:36:14 +08:00
|
|
|
acpi_destroy_nondev_subnodes(&adev->data.subnodes);
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
ACPI_FREE((void *)adev->data.pointer);
|
2014-10-21 19:33:56 +08:00
|
|
|
adev->data.of_compatible = NULL;
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
adev->data.pointer = NULL;
|
|
|
|
adev->data.properties = NULL;
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
2015-08-27 10:40:05 +08:00
|
|
|
* acpi_data_get_property - return an ACPI property with given name
|
|
|
|
* @data: ACPI device deta object to get the property from
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
* @name: Name of the property
|
|
|
|
* @type: Expected property type
|
|
|
|
* @obj: Location to store the property value (if not %NULL)
|
|
|
|
*
|
|
|
|
* Look up a property with @name and store a pointer to the resulting ACPI
|
|
|
|
* object at the location pointed to by @obj if found.
|
|
|
|
*
|
|
|
|
* Callers must not attempt to free the returned objects. These objects will be
|
2015-08-27 10:40:05 +08:00
|
|
|
* freed by the ACPI core automatically during the removal of @data.
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
*
|
|
|
|
* Return: %0 if property with @name has been found (success),
|
|
|
|
* %-EINVAL if the arguments are invalid,
|
2015-11-30 23:11:35 +08:00
|
|
|
* %-EINVAL if the property doesn't exist,
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
* %-EPROTO if the property value type doesn't match @type.
|
|
|
|
*/
|
2017-07-21 19:39:34 +08:00
|
|
|
static int acpi_data_get_property(const struct acpi_device_data *data,
|
2015-08-27 10:40:05 +08:00
|
|
|
const char *name, acpi_object_type type,
|
|
|
|
const union acpi_object **obj)
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
{
|
|
|
|
const union acpi_object *properties;
|
|
|
|
int i;
|
|
|
|
|
2015-08-27 10:40:05 +08:00
|
|
|
if (!data || !name)
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
return -EINVAL;
|
|
|
|
|
2015-08-27 10:40:05 +08:00
|
|
|
if (!data->pointer || !data->properties)
|
2015-11-30 23:11:35 +08:00
|
|
|
return -EINVAL;
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
|
2015-08-27 10:40:05 +08:00
|
|
|
properties = data->properties;
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
for (i = 0; i < properties->package.count; i++) {
|
|
|
|
const union acpi_object *propname, *propvalue;
|
|
|
|
const union acpi_object *property;
|
|
|
|
|
|
|
|
property = &properties->package.elements[i];
|
|
|
|
|
|
|
|
propname = &property->package.elements[0];
|
|
|
|
propvalue = &property->package.elements[1];
|
|
|
|
|
|
|
|
if (!strcmp(name, propname->string.pointer)) {
|
|
|
|
if (type != ACPI_TYPE_ANY && propvalue->type != type)
|
|
|
|
return -EPROTO;
|
2015-11-30 23:11:35 +08:00
|
|
|
if (obj)
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
*obj = propvalue;
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
}
|
2015-11-30 23:11:35 +08:00
|
|
|
return -EINVAL;
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
}
|
2015-08-27 10:40:05 +08:00
|
|
|
|
|
|
|
/**
|
|
|
|
* acpi_dev_get_property - return an ACPI property with given name.
|
|
|
|
* @adev: ACPI device to get the property from.
|
|
|
|
* @name: Name of the property.
|
|
|
|
* @type: Expected property type.
|
|
|
|
* @obj: Location to store the property value (if not %NULL).
|
|
|
|
*/
|
2017-07-21 19:39:34 +08:00
|
|
|
int acpi_dev_get_property(const struct acpi_device *adev, const char *name,
|
2015-08-27 10:40:05 +08:00
|
|
|
acpi_object_type type, const union acpi_object **obj)
|
|
|
|
{
|
|
|
|
return adev ? acpi_data_get_property(&adev->data, name, type, obj) : -EINVAL;
|
|
|
|
}
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
EXPORT_SYMBOL_GPL(acpi_dev_get_property);
|
|
|
|
|
2017-07-21 19:39:34 +08:00
|
|
|
static const struct acpi_device_data *
|
|
|
|
acpi_device_data_of_node(const struct fwnode_handle *fwnode)
|
2015-08-27 10:40:05 +08:00
|
|
|
{
|
2017-07-21 19:39:31 +08:00
|
|
|
if (is_acpi_device_node(fwnode)) {
|
2017-07-21 19:39:34 +08:00
|
|
|
const struct acpi_device *adev = to_acpi_device_node(fwnode);
|
2015-08-27 10:40:05 +08:00
|
|
|
return &adev->data;
|
2017-07-21 19:39:31 +08:00
|
|
|
} else if (is_acpi_data_node(fwnode)) {
|
2017-07-21 19:39:34 +08:00
|
|
|
const struct acpi_data_node *dn = to_acpi_data_node(fwnode);
|
2015-08-27 10:40:05 +08:00
|
|
|
return &dn->data;
|
|
|
|
}
|
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
/**
|
2015-08-27 10:40:05 +08:00
|
|
|
* acpi_node_prop_get - return an ACPI property with given name.
|
|
|
|
* @fwnode: Firmware node to get the property from.
|
|
|
|
* @propname: Name of the property.
|
|
|
|
* @valptr: Location to store a pointer to the property value (if not %NULL).
|
|
|
|
*/
|
2017-07-21 19:39:34 +08:00
|
|
|
int acpi_node_prop_get(const struct fwnode_handle *fwnode,
|
|
|
|
const char *propname, void **valptr)
|
2015-08-27 10:40:05 +08:00
|
|
|
{
|
|
|
|
return acpi_data_get_property(acpi_device_data_of_node(fwnode),
|
|
|
|
propname, ACPI_TYPE_ANY,
|
|
|
|
(const union acpi_object **)valptr);
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* acpi_data_get_property_array - return an ACPI array property with given name
|
|
|
|
* @adev: ACPI data object to get the property from
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
* @name: Name of the property
|
|
|
|
* @type: Expected type of array elements
|
|
|
|
* @obj: Location to store a pointer to the property value (if not NULL)
|
|
|
|
*
|
|
|
|
* Look up an array property with @name and store a pointer to the resulting
|
|
|
|
* ACPI object at the location pointed to by @obj if found.
|
|
|
|
*
|
|
|
|
* Callers must not attempt to free the returned objects. Those objects will be
|
2015-08-27 10:40:05 +08:00
|
|
|
* freed by the ACPI core automatically during the removal of @data.
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
*
|
|
|
|
* Return: %0 if array property (package) with @name has been found (success),
|
|
|
|
* %-EINVAL if the arguments are invalid,
|
2015-11-30 23:11:35 +08:00
|
|
|
* %-EINVAL if the property doesn't exist,
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
* %-EPROTO if the property is not a package or the type of its elements
|
|
|
|
* doesn't match @type.
|
|
|
|
*/
|
2017-07-21 19:39:34 +08:00
|
|
|
static int acpi_data_get_property_array(const struct acpi_device_data *data,
|
2015-08-27 10:40:05 +08:00
|
|
|
const char *name,
|
|
|
|
acpi_object_type type,
|
|
|
|
const union acpi_object **obj)
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
{
|
|
|
|
const union acpi_object *prop;
|
|
|
|
int ret, i;
|
|
|
|
|
2015-08-27 10:40:05 +08:00
|
|
|
ret = acpi_data_get_property(data, name, ACPI_TYPE_PACKAGE, &prop);
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
if (ret)
|
|
|
|
return ret;
|
|
|
|
|
|
|
|
if (type != ACPI_TYPE_ANY) {
|
|
|
|
/* Check that all elements are of correct type. */
|
|
|
|
for (i = 0; i < prop->package.count; i++)
|
|
|
|
if (prop->package.elements[i].type != type)
|
|
|
|
return -EPROTO;
|
|
|
|
}
|
|
|
|
if (obj)
|
|
|
|
*obj = prop;
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
ACPI / property: Allow holes in reference properties
DT allows holes or empty phandles for references. This is used for example
in SPI subsystem where some chip selects are native and others are regular
GPIOs. In ACPI _DSD we currently do not support this but instead the
preceding reference consumes all following integer arguments.
For example we would like to support something like the below ASL fragment
for SPI:
Package () {
"cs-gpios",
Package () {
^GPIO, 19, 0, 0, // GPIO CS0
0, // Native CS
^GPIO, 20, 0, 0, // GPIO CS1
}
}
The zero in the middle means "no entry" or NULL reference. To support this
we change acpi_data_get_property_reference() to take firmware node and
num_args as argument and rename it to __acpi_node_get_property_reference().
The function returns -ENOENT if the given index resolves to "no entry"
reference and -ENODATA when there are no more entries in the property.
We then add static inline wrapper acpi_node_get_property_reference() that
passes MAX_ACPI_REFERENCE_ARGS as num_args to support the existing
behaviour which some drivers have been relying on.
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2016-09-29 21:39:41 +08:00
|
|
|
* __acpi_node_get_property_reference - returns handle to the referenced object
|
|
|
|
* @fwnode: Firmware node to get the property from
|
2015-08-27 10:42:33 +08:00
|
|
|
* @propname: Name of the property
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
* @index: Index of the reference to return
|
ACPI / property: Allow holes in reference properties
DT allows holes or empty phandles for references. This is used for example
in SPI subsystem where some chip selects are native and others are regular
GPIOs. In ACPI _DSD we currently do not support this but instead the
preceding reference consumes all following integer arguments.
For example we would like to support something like the below ASL fragment
for SPI:
Package () {
"cs-gpios",
Package () {
^GPIO, 19, 0, 0, // GPIO CS0
0, // Native CS
^GPIO, 20, 0, 0, // GPIO CS1
}
}
The zero in the middle means "no entry" or NULL reference. To support this
we change acpi_data_get_property_reference() to take firmware node and
num_args as argument and rename it to __acpi_node_get_property_reference().
The function returns -ENOENT if the given index resolves to "no entry"
reference and -ENODATA when there are no more entries in the property.
We then add static inline wrapper acpi_node_get_property_reference() that
passes MAX_ACPI_REFERENCE_ARGS as num_args to support the existing
behaviour which some drivers have been relying on.
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2016-09-29 21:39:41 +08:00
|
|
|
* @num_args: Maximum number of arguments after each reference
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
* @args: Location to store the returned reference with optional arguments
|
|
|
|
*
|
|
|
|
* Find property with @name, verifify that it is a package containing at least
|
|
|
|
* one object reference and if so, store the ACPI device object pointer to the
|
2014-11-05 07:29:07 +08:00
|
|
|
* target object in @args->adev. If the reference includes arguments, store
|
|
|
|
* them in the @args->args[] array.
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
*
|
2014-11-05 07:29:07 +08:00
|
|
|
* If there's more than one reference in the property value package, @index is
|
|
|
|
* used to select the one to return.
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
*
|
ACPI / property: Allow holes in reference properties
DT allows holes or empty phandles for references. This is used for example
in SPI subsystem where some chip selects are native and others are regular
GPIOs. In ACPI _DSD we currently do not support this but instead the
preceding reference consumes all following integer arguments.
For example we would like to support something like the below ASL fragment
for SPI:
Package () {
"cs-gpios",
Package () {
^GPIO, 19, 0, 0, // GPIO CS0
0, // Native CS
^GPIO, 20, 0, 0, // GPIO CS1
}
}
The zero in the middle means "no entry" or NULL reference. To support this
we change acpi_data_get_property_reference() to take firmware node and
num_args as argument and rename it to __acpi_node_get_property_reference().
The function returns -ENOENT if the given index resolves to "no entry"
reference and -ENODATA when there are no more entries in the property.
We then add static inline wrapper acpi_node_get_property_reference() that
passes MAX_ACPI_REFERENCE_ARGS as num_args to support the existing
behaviour which some drivers have been relying on.
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2016-09-29 21:39:41 +08:00
|
|
|
* It is possible to leave holes in the property value set like in the
|
|
|
|
* example below:
|
|
|
|
*
|
|
|
|
* Package () {
|
|
|
|
* "cs-gpios",
|
|
|
|
* Package () {
|
|
|
|
* ^GPIO, 19, 0, 0,
|
|
|
|
* ^GPIO, 20, 0, 0,
|
|
|
|
* 0,
|
|
|
|
* ^GPIO, 21, 0, 0,
|
|
|
|
* }
|
|
|
|
* }
|
|
|
|
*
|
|
|
|
* Calling this function with index %2 return %-ENOENT and with index %3
|
|
|
|
* returns the last entry. If the property does not contain any more values
|
|
|
|
* %-ENODATA is returned. The NULL entry must be single integer and
|
|
|
|
* preferably contain value %0.
|
|
|
|
*
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
* Return: %0 on success, negative error code on failure.
|
|
|
|
*/
|
2017-07-21 19:39:34 +08:00
|
|
|
int __acpi_node_get_property_reference(const struct fwnode_handle *fwnode,
|
ACPI / property: Allow holes in reference properties
DT allows holes or empty phandles for references. This is used for example
in SPI subsystem where some chip selects are native and others are regular
GPIOs. In ACPI _DSD we currently do not support this but instead the
preceding reference consumes all following integer arguments.
For example we would like to support something like the below ASL fragment
for SPI:
Package () {
"cs-gpios",
Package () {
^GPIO, 19, 0, 0, // GPIO CS0
0, // Native CS
^GPIO, 20, 0, 0, // GPIO CS1
}
}
The zero in the middle means "no entry" or NULL reference. To support this
we change acpi_data_get_property_reference() to take firmware node and
num_args as argument and rename it to __acpi_node_get_property_reference().
The function returns -ENOENT if the given index resolves to "no entry"
reference and -ENODATA when there are no more entries in the property.
We then add static inline wrapper acpi_node_get_property_reference() that
passes MAX_ACPI_REFERENCE_ARGS as num_args to support the existing
behaviour which some drivers have been relying on.
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2016-09-29 21:39:41 +08:00
|
|
|
const char *propname, size_t index, size_t num_args,
|
|
|
|
struct acpi_reference_args *args)
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
{
|
|
|
|
const union acpi_object *element, *end;
|
|
|
|
const union acpi_object *obj;
|
2017-07-21 19:39:34 +08:00
|
|
|
const struct acpi_device_data *data;
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
struct acpi_device *device;
|
|
|
|
int ret, idx = 0;
|
|
|
|
|
ACPI / property: Allow holes in reference properties
DT allows holes or empty phandles for references. This is used for example
in SPI subsystem where some chip selects are native and others are regular
GPIOs. In ACPI _DSD we currently do not support this but instead the
preceding reference consumes all following integer arguments.
For example we would like to support something like the below ASL fragment
for SPI:
Package () {
"cs-gpios",
Package () {
^GPIO, 19, 0, 0, // GPIO CS0
0, // Native CS
^GPIO, 20, 0, 0, // GPIO CS1
}
}
The zero in the middle means "no entry" or NULL reference. To support this
we change acpi_data_get_property_reference() to take firmware node and
num_args as argument and rename it to __acpi_node_get_property_reference().
The function returns -ENOENT if the given index resolves to "no entry"
reference and -ENODATA when there are no more entries in the property.
We then add static inline wrapper acpi_node_get_property_reference() that
passes MAX_ACPI_REFERENCE_ARGS as num_args to support the existing
behaviour which some drivers have been relying on.
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2016-09-29 21:39:41 +08:00
|
|
|
data = acpi_device_data_of_node(fwnode);
|
|
|
|
if (!data)
|
|
|
|
return -EINVAL;
|
|
|
|
|
2015-08-27 10:42:33 +08:00
|
|
|
ret = acpi_data_get_property(data, propname, ACPI_TYPE_ANY, &obj);
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
if (ret)
|
|
|
|
return ret;
|
|
|
|
|
|
|
|
/*
|
|
|
|
* The simplest case is when the value is a single reference. Just
|
|
|
|
* return that reference then.
|
|
|
|
*/
|
|
|
|
if (obj->type == ACPI_TYPE_LOCAL_REFERENCE) {
|
2014-11-05 07:29:07 +08:00
|
|
|
if (index)
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
return -EINVAL;
|
|
|
|
|
|
|
|
ret = acpi_bus_get_device(obj->reference.handle, &device);
|
|
|
|
if (ret)
|
|
|
|
return ret;
|
|
|
|
|
|
|
|
args->adev = device;
|
|
|
|
args->nargs = 0;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* If it is not a single reference, then it is a package of
|
|
|
|
* references followed by number of ints as follows:
|
|
|
|
*
|
|
|
|
* Package () { REF, INT, REF, INT, INT }
|
|
|
|
*
|
|
|
|
* The index argument is then used to determine which reference
|
|
|
|
* the caller wants (along with the arguments).
|
|
|
|
*/
|
|
|
|
if (obj->type != ACPI_TYPE_PACKAGE || index >= obj->package.count)
|
|
|
|
return -EPROTO;
|
|
|
|
|
|
|
|
element = obj->package.elements;
|
|
|
|
end = element + obj->package.count;
|
|
|
|
|
|
|
|
while (element < end) {
|
|
|
|
u32 nargs, i;
|
|
|
|
|
ACPI / property: Allow holes in reference properties
DT allows holes or empty phandles for references. This is used for example
in SPI subsystem where some chip selects are native and others are regular
GPIOs. In ACPI _DSD we currently do not support this but instead the
preceding reference consumes all following integer arguments.
For example we would like to support something like the below ASL fragment
for SPI:
Package () {
"cs-gpios",
Package () {
^GPIO, 19, 0, 0, // GPIO CS0
0, // Native CS
^GPIO, 20, 0, 0, // GPIO CS1
}
}
The zero in the middle means "no entry" or NULL reference. To support this
we change acpi_data_get_property_reference() to take firmware node and
num_args as argument and rename it to __acpi_node_get_property_reference().
The function returns -ENOENT if the given index resolves to "no entry"
reference and -ENODATA when there are no more entries in the property.
We then add static inline wrapper acpi_node_get_property_reference() that
passes MAX_ACPI_REFERENCE_ARGS as num_args to support the existing
behaviour which some drivers have been relying on.
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2016-09-29 21:39:41 +08:00
|
|
|
if (element->type == ACPI_TYPE_LOCAL_REFERENCE) {
|
|
|
|
ret = acpi_bus_get_device(element->reference.handle,
|
|
|
|
&device);
|
|
|
|
if (ret)
|
|
|
|
return -ENODEV;
|
|
|
|
|
|
|
|
nargs = 0;
|
|
|
|
element++;
|
|
|
|
|
|
|
|
/* assume following integer elements are all args */
|
|
|
|
for (i = 0; element + i < end && i < num_args; i++) {
|
|
|
|
int type = element[i].type;
|
|
|
|
|
|
|
|
if (type == ACPI_TYPE_INTEGER)
|
|
|
|
nargs++;
|
|
|
|
else if (type == ACPI_TYPE_LOCAL_REFERENCE)
|
|
|
|
break;
|
|
|
|
else
|
|
|
|
return -EPROTO;
|
|
|
|
}
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
|
ACPI / property: Allow holes in reference properties
DT allows holes or empty phandles for references. This is used for example
in SPI subsystem where some chip selects are native and others are regular
GPIOs. In ACPI _DSD we currently do not support this but instead the
preceding reference consumes all following integer arguments.
For example we would like to support something like the below ASL fragment
for SPI:
Package () {
"cs-gpios",
Package () {
^GPIO, 19, 0, 0, // GPIO CS0
0, // Native CS
^GPIO, 20, 0, 0, // GPIO CS1
}
}
The zero in the middle means "no entry" or NULL reference. To support this
we change acpi_data_get_property_reference() to take firmware node and
num_args as argument and rename it to __acpi_node_get_property_reference().
The function returns -ENOENT if the given index resolves to "no entry"
reference and -ENODATA when there are no more entries in the property.
We then add static inline wrapper acpi_node_get_property_reference() that
passes MAX_ACPI_REFERENCE_ARGS as num_args to support the existing
behaviour which some drivers have been relying on.
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2016-09-29 21:39:41 +08:00
|
|
|
if (nargs > MAX_ACPI_REFERENCE_ARGS)
|
2014-11-05 07:29:07 +08:00
|
|
|
return -EPROTO;
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
|
ACPI / property: Allow holes in reference properties
DT allows holes or empty phandles for references. This is used for example
in SPI subsystem where some chip selects are native and others are regular
GPIOs. In ACPI _DSD we currently do not support this but instead the
preceding reference consumes all following integer arguments.
For example we would like to support something like the below ASL fragment
for SPI:
Package () {
"cs-gpios",
Package () {
^GPIO, 19, 0, 0, // GPIO CS0
0, // Native CS
^GPIO, 20, 0, 0, // GPIO CS1
}
}
The zero in the middle means "no entry" or NULL reference. To support this
we change acpi_data_get_property_reference() to take firmware node and
num_args as argument and rename it to __acpi_node_get_property_reference().
The function returns -ENOENT if the given index resolves to "no entry"
reference and -ENODATA when there are no more entries in the property.
We then add static inline wrapper acpi_node_get_property_reference() that
passes MAX_ACPI_REFERENCE_ARGS as num_args to support the existing
behaviour which some drivers have been relying on.
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2016-09-29 21:39:41 +08:00
|
|
|
if (idx == index) {
|
|
|
|
args->adev = device;
|
|
|
|
args->nargs = nargs;
|
|
|
|
for (i = 0; i < nargs; i++)
|
|
|
|
args->args[i] = element[i].integer.value;
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
|
ACPI / property: Allow holes in reference properties
DT allows holes or empty phandles for references. This is used for example
in SPI subsystem where some chip selects are native and others are regular
GPIOs. In ACPI _DSD we currently do not support this but instead the
preceding reference consumes all following integer arguments.
For example we would like to support something like the below ASL fragment
for SPI:
Package () {
"cs-gpios",
Package () {
^GPIO, 19, 0, 0, // GPIO CS0
0, // Native CS
^GPIO, 20, 0, 0, // GPIO CS1
}
}
The zero in the middle means "no entry" or NULL reference. To support this
we change acpi_data_get_property_reference() to take firmware node and
num_args as argument and rename it to __acpi_node_get_property_reference().
The function returns -ENOENT if the given index resolves to "no entry"
reference and -ENODATA when there are no more entries in the property.
We then add static inline wrapper acpi_node_get_property_reference() that
passes MAX_ACPI_REFERENCE_ARGS as num_args to support the existing
behaviour which some drivers have been relying on.
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2016-09-29 21:39:41 +08:00
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
element += nargs;
|
|
|
|
} else if (element->type == ACPI_TYPE_INTEGER) {
|
|
|
|
if (idx == index)
|
|
|
|
return -ENOENT;
|
|
|
|
element++;
|
|
|
|
} else {
|
|
|
|
return -EPROTO;
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
}
|
|
|
|
|
ACPI / property: Allow holes in reference properties
DT allows holes or empty phandles for references. This is used for example
in SPI subsystem where some chip selects are native and others are regular
GPIOs. In ACPI _DSD we currently do not support this but instead the
preceding reference consumes all following integer arguments.
For example we would like to support something like the below ASL fragment
for SPI:
Package () {
"cs-gpios",
Package () {
^GPIO, 19, 0, 0, // GPIO CS0
0, // Native CS
^GPIO, 20, 0, 0, // GPIO CS1
}
}
The zero in the middle means "no entry" or NULL reference. To support this
we change acpi_data_get_property_reference() to take firmware node and
num_args as argument and rename it to __acpi_node_get_property_reference().
The function returns -ENOENT if the given index resolves to "no entry"
reference and -ENODATA when there are no more entries in the property.
We then add static inline wrapper acpi_node_get_property_reference() that
passes MAX_ACPI_REFERENCE_ARGS as num_args to support the existing
behaviour which some drivers have been relying on.
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2016-09-29 21:39:41 +08:00
|
|
|
idx++;
|
ACPI: Add support for device specific properties
Device Tree is used in many embedded systems to describe the system
configuration to the OS. It supports attaching properties or name-value
pairs to the devices it describe. With these properties one can pass
additional information to the drivers that would not be available
otherwise.
ACPI is another configuration mechanism (among other things) typically
seen, but not limited to, x86 machines. ACPI allows passing arbitrary
data from methods but there has not been mechanism equivalent to Device
Tree until the introduction of _DSD in the recent publication of the
ACPI 5.1 specification.
In order to facilitate ACPI usage in systems where Device Tree is
typically used, it would be beneficial to standardize a way to retrieve
Device Tree style properties from ACPI devices, which is what we do in
this patch.
If a given device described in ACPI namespace wants to export properties it
must implement _DSD method (Device Specific Data, introduced with ACPI 5.1)
that returns the properties in a package of packages. For example:
Name (_DSD, Package () {
ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"),
Package () {
Package () {"name1", <VALUE1>},
Package () {"name2", <VALUE2>},
...
}
})
The UUID reserved for properties is daffd814-6eba-4d8c-8a91-bc9bbf4aa301
and is documented in the ACPI 5.1 companion document called "_DSD
Implementation Guide" [1], [2].
We add several helper functions that can be used to extract these
properties and convert them to different Linux data types.
The ultimate goal is that we only have one device property API that
retrieves the requested properties from Device Tree or from ACPI
transparent to the caller.
[1] http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel.htm
[2] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org>
Reviewed-by: Josh Triplett <josh@joshtriplett.org>
Reviewed-by: Grant Likely <grant.likely@linaro.org>
Signed-off-by: Darren Hart <dvhart@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2014-10-21 19:33:55 +08:00
|
|
|
}
|
|
|
|
|
ACPI / property: Allow holes in reference properties
DT allows holes or empty phandles for references. This is used for example
in SPI subsystem where some chip selects are native and others are regular
GPIOs. In ACPI _DSD we currently do not support this but instead the
preceding reference consumes all following integer arguments.
For example we would like to support something like the below ASL fragment
for SPI:
Package () {
"cs-gpios",
Package () {
^GPIO, 19, 0, 0, // GPIO CS0
0, // Native CS
^GPIO, 20, 0, 0, // GPIO CS1
}
}
The zero in the middle means "no entry" or NULL reference. To support this
we change acpi_data_get_property_reference() to take firmware node and
num_args as argument and rename it to __acpi_node_get_property_reference().
The function returns -ENOENT if the given index resolves to "no entry"
reference and -ENODATA when there are no more entries in the property.
We then add static inline wrapper acpi_node_get_property_reference() that
passes MAX_ACPI_REFERENCE_ARGS as num_args to support the existing
behaviour which some drivers have been relying on.
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2016-09-29 21:39:41 +08:00
|
|
|
return -ENODATA;
|
2015-08-27 10:42:33 +08:00
|
|
|
}
|
ACPI / property: Allow holes in reference properties
DT allows holes or empty phandles for references. This is used for example
in SPI subsystem where some chip selects are native and others are regular
GPIOs. In ACPI _DSD we currently do not support this but instead the
preceding reference consumes all following integer arguments.
For example we would like to support something like the below ASL fragment
for SPI:
Package () {
"cs-gpios",
Package () {
^GPIO, 19, 0, 0, // GPIO CS0
0, // Native CS
^GPIO, 20, 0, 0, // GPIO CS1
}
}
The zero in the middle means "no entry" or NULL reference. To support this
we change acpi_data_get_property_reference() to take firmware node and
num_args as argument and rename it to __acpi_node_get_property_reference().
The function returns -ENOENT if the given index resolves to "no entry"
reference and -ENODATA when there are no more entries in the property.
We then add static inline wrapper acpi_node_get_property_reference() that
passes MAX_ACPI_REFERENCE_ARGS as num_args to support the existing
behaviour which some drivers have been relying on.
Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
2016-09-29 21:39:41 +08:00
|
|
|
EXPORT_SYMBOL_GPL(__acpi_node_get_property_reference);
|
2014-11-04 08:28:56 +08:00
|
|
|
|
2017-07-21 19:39:34 +08:00
|
|
|
static int acpi_data_prop_read_single(const struct acpi_device_data *data,
|
2015-08-27 10:40:05 +08:00
|
|
|
const char *propname,
|
|
|
|
enum dev_prop_type proptype, void *val)
|
2014-11-04 08:28:56 +08:00
|
|
|
{
|
|
|
|
const union acpi_object *obj;
|
|
|
|
int ret;
|
|
|
|
|
|
|
|
if (!val)
|
|
|
|
return -EINVAL;
|
|
|
|
|
|
|
|
if (proptype >= DEV_PROP_U8 && proptype <= DEV_PROP_U64) {
|
2015-08-27 10:40:05 +08:00
|
|
|
ret = acpi_data_get_property(data, propname, ACPI_TYPE_INTEGER, &obj);
|
2014-11-04 08:28:56 +08:00
|
|
|
if (ret)
|
|
|
|
return ret;
|
|
|
|
|
|
|
|
switch (proptype) {
|
|
|
|
case DEV_PROP_U8:
|
|
|
|
if (obj->integer.value > U8_MAX)
|
|
|
|
return -EOVERFLOW;
|
|
|
|
*(u8 *)val = obj->integer.value;
|
|
|
|
break;
|
|
|
|
case DEV_PROP_U16:
|
|
|
|
if (obj->integer.value > U16_MAX)
|
|
|
|
return -EOVERFLOW;
|
|
|
|
*(u16 *)val = obj->integer.value;
|
|
|
|
break;
|
|
|
|
case DEV_PROP_U32:
|
|
|
|
if (obj->integer.value > U32_MAX)
|
|
|
|
return -EOVERFLOW;
|
|
|
|
*(u32 *)val = obj->integer.value;
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
*(u64 *)val = obj->integer.value;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
} else if (proptype == DEV_PROP_STRING) {
|
2015-08-27 10:40:05 +08:00
|
|
|
ret = acpi_data_get_property(data, propname, ACPI_TYPE_STRING, &obj);
|
2014-11-04 08:28:56 +08:00
|
|
|
if (ret)
|
|
|
|
return ret;
|
|
|
|
|
|
|
|
*(char **)val = obj->string.pointer;
|
2017-03-28 20:22:19 +08:00
|
|
|
|
|
|
|
return 1;
|
2014-11-04 08:28:56 +08:00
|
|
|
} else {
|
|
|
|
ret = -EINVAL;
|
|
|
|
}
|
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
|
2015-08-27 10:40:05 +08:00
|
|
|
int acpi_dev_prop_read_single(struct acpi_device *adev, const char *propname,
|
|
|
|
enum dev_prop_type proptype, void *val)
|
|
|
|
{
|
2017-03-28 20:22:19 +08:00
|
|
|
int ret;
|
|
|
|
|
|
|
|
if (!adev)
|
|
|
|
return -EINVAL;
|
|
|
|
|
|
|
|
ret = acpi_data_prop_read_single(&adev->data, propname, proptype, val);
|
|
|
|
if (ret < 0 || proptype != ACPI_TYPE_STRING)
|
|
|
|
return ret;
|
|
|
|
return 0;
|
2015-08-27 10:40:05 +08:00
|
|
|
}
|
|
|
|
|
2014-11-04 08:28:56 +08:00
|
|
|
static int acpi_copy_property_array_u8(const union acpi_object *items, u8 *val,
|
|
|
|
size_t nval)
|
|
|
|
{
|
|
|
|
int i;
|
|
|
|
|
|
|
|
for (i = 0; i < nval; i++) {
|
|
|
|
if (items[i].type != ACPI_TYPE_INTEGER)
|
|
|
|
return -EPROTO;
|
|
|
|
if (items[i].integer.value > U8_MAX)
|
|
|
|
return -EOVERFLOW;
|
|
|
|
|
|
|
|
val[i] = items[i].integer.value;
|
|
|
|
}
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
static int acpi_copy_property_array_u16(const union acpi_object *items,
|
|
|
|
u16 *val, size_t nval)
|
|
|
|
{
|
|
|
|
int i;
|
|
|
|
|
|
|
|
for (i = 0; i < nval; i++) {
|
|
|
|
if (items[i].type != ACPI_TYPE_INTEGER)
|
|
|
|
return -EPROTO;
|
|
|
|
if (items[i].integer.value > U16_MAX)
|
|
|
|
return -EOVERFLOW;
|
|
|
|
|
|
|
|
val[i] = items[i].integer.value;
|
|
|
|
}
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
static int acpi_copy_property_array_u32(const union acpi_object *items,
|
|
|
|
u32 *val, size_t nval)
|
|
|
|
{
|
|
|
|
int i;
|
|
|
|
|
|
|
|
for (i = 0; i < nval; i++) {
|
|
|
|
if (items[i].type != ACPI_TYPE_INTEGER)
|
|
|
|
return -EPROTO;
|
|
|
|
if (items[i].integer.value > U32_MAX)
|
|
|
|
return -EOVERFLOW;
|
|
|
|
|
|
|
|
val[i] = items[i].integer.value;
|
|
|
|
}
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
static int acpi_copy_property_array_u64(const union acpi_object *items,
|
|
|
|
u64 *val, size_t nval)
|
|
|
|
{
|
|
|
|
int i;
|
|
|
|
|
|
|
|
for (i = 0; i < nval; i++) {
|
|
|
|
if (items[i].type != ACPI_TYPE_INTEGER)
|
|
|
|
return -EPROTO;
|
|
|
|
|
|
|
|
val[i] = items[i].integer.value;
|
|
|
|
}
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
static int acpi_copy_property_array_string(const union acpi_object *items,
|
|
|
|
char **val, size_t nval)
|
|
|
|
{
|
|
|
|
int i;
|
|
|
|
|
|
|
|
for (i = 0; i < nval; i++) {
|
|
|
|
if (items[i].type != ACPI_TYPE_STRING)
|
|
|
|
return -EPROTO;
|
|
|
|
|
|
|
|
val[i] = items[i].string.pointer;
|
|
|
|
}
|
2017-03-28 20:22:19 +08:00
|
|
|
return nval;
|
2014-11-04 08:28:56 +08:00
|
|
|
}
|
|
|
|
|
2017-07-21 19:39:34 +08:00
|
|
|
static int acpi_data_prop_read(const struct acpi_device_data *data,
|
2015-08-27 10:40:05 +08:00
|
|
|
const char *propname,
|
|
|
|
enum dev_prop_type proptype,
|
|
|
|
void *val, size_t nval)
|
2014-11-04 08:28:56 +08:00
|
|
|
{
|
|
|
|
const union acpi_object *obj;
|
|
|
|
const union acpi_object *items;
|
|
|
|
int ret;
|
|
|
|
|
|
|
|
if (val && nval == 1) {
|
2015-08-27 10:40:05 +08:00
|
|
|
ret = acpi_data_prop_read_single(data, propname, proptype, val);
|
2017-03-28 20:22:19 +08:00
|
|
|
if (ret >= 0)
|
2014-11-04 08:28:56 +08:00
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
|
2015-08-27 10:40:05 +08:00
|
|
|
ret = acpi_data_get_property_array(data, propname, ACPI_TYPE_ANY, &obj);
|
2014-11-04 08:28:56 +08:00
|
|
|
if (ret)
|
|
|
|
return ret;
|
|
|
|
|
|
|
|
if (!val)
|
|
|
|
return obj->package.count;
|
|
|
|
|
2017-03-28 20:22:19 +08:00
|
|
|
if (proptype != DEV_PROP_STRING && nval > obj->package.count)
|
2014-11-04 08:28:56 +08:00
|
|
|
return -EOVERFLOW;
|
2015-08-11 00:56:48 +08:00
|
|
|
else if (nval <= 0)
|
|
|
|
return -EINVAL;
|
2014-11-04 08:28:56 +08:00
|
|
|
|
|
|
|
items = obj->package.elements;
|
2015-08-11 00:56:48 +08:00
|
|
|
|
2014-11-04 08:28:56 +08:00
|
|
|
switch (proptype) {
|
|
|
|
case DEV_PROP_U8:
|
|
|
|
ret = acpi_copy_property_array_u8(items, (u8 *)val, nval);
|
|
|
|
break;
|
|
|
|
case DEV_PROP_U16:
|
|
|
|
ret = acpi_copy_property_array_u16(items, (u16 *)val, nval);
|
|
|
|
break;
|
|
|
|
case DEV_PROP_U32:
|
|
|
|
ret = acpi_copy_property_array_u32(items, (u32 *)val, nval);
|
|
|
|
break;
|
|
|
|
case DEV_PROP_U64:
|
|
|
|
ret = acpi_copy_property_array_u64(items, (u64 *)val, nval);
|
|
|
|
break;
|
|
|
|
case DEV_PROP_STRING:
|
2017-03-28 20:22:19 +08:00
|
|
|
ret = acpi_copy_property_array_string(
|
|
|
|
items, (char **)val,
|
|
|
|
min_t(u32, nval, obj->package.count));
|
2014-11-04 08:28:56 +08:00
|
|
|
break;
|
|
|
|
default:
|
|
|
|
ret = -EINVAL;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
return ret;
|
|
|
|
}
|
2015-08-27 10:40:05 +08:00
|
|
|
|
2017-07-21 19:39:34 +08:00
|
|
|
int acpi_dev_prop_read(const struct acpi_device *adev, const char *propname,
|
2015-08-27 10:40:05 +08:00
|
|
|
enum dev_prop_type proptype, void *val, size_t nval)
|
|
|
|
{
|
|
|
|
return adev ? acpi_data_prop_read(&adev->data, propname, proptype, val, nval) : -EINVAL;
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* acpi_node_prop_read - retrieve the value of an ACPI property with given name.
|
|
|
|
* @fwnode: Firmware node to get the property from.
|
|
|
|
* @propname: Name of the property.
|
|
|
|
* @proptype: Expected property type.
|
|
|
|
* @val: Location to store the property value (if not %NULL).
|
|
|
|
* @nval: Size of the array pointed to by @val.
|
|
|
|
*
|
|
|
|
* If @val is %NULL, return the number of array elements comprising the value
|
|
|
|
* of the property. Otherwise, read at most @nval values to the array at the
|
|
|
|
* location pointed to by @val.
|
|
|
|
*/
|
2017-07-21 19:39:34 +08:00
|
|
|
int acpi_node_prop_read(const struct fwnode_handle *fwnode,
|
|
|
|
const char *propname, enum dev_prop_type proptype,
|
|
|
|
void *val, size_t nval)
|
2015-08-27 10:40:05 +08:00
|
|
|
{
|
|
|
|
return acpi_data_prop_read(acpi_device_data_of_node(fwnode),
|
|
|
|
propname, proptype, val, nval);
|
|
|
|
}
|
2015-08-27 10:42:33 +08:00
|
|
|
|
|
|
|
/**
|
2017-03-28 15:52:18 +08:00
|
|
|
* acpi_get_next_subnode - Return the next child node handle for a fwnode
|
|
|
|
* @fwnode: Firmware node to find the next child node for.
|
2015-08-27 10:42:33 +08:00
|
|
|
* @child: Handle to one of the device's child nodes or a null handle.
|
|
|
|
*/
|
2017-07-21 19:39:36 +08:00
|
|
|
struct fwnode_handle *acpi_get_next_subnode(const struct fwnode_handle *fwnode,
|
2015-08-27 10:42:33 +08:00
|
|
|
struct fwnode_handle *child)
|
|
|
|
{
|
2017-07-21 19:39:32 +08:00
|
|
|
const struct acpi_device *adev = to_acpi_device_node(fwnode);
|
|
|
|
struct acpi_device *child_adev = NULL;
|
|
|
|
const struct list_head *head;
|
|
|
|
struct list_head *next;
|
2015-08-27 10:42:33 +08:00
|
|
|
|
2017-07-21 19:39:31 +08:00
|
|
|
if (!child || is_acpi_device_node(child)) {
|
2017-03-28 15:52:18 +08:00
|
|
|
if (adev)
|
|
|
|
head = &adev->children;
|
|
|
|
else
|
|
|
|
goto nondev;
|
|
|
|
|
2015-08-27 10:42:33 +08:00
|
|
|
if (list_empty(head))
|
|
|
|
goto nondev;
|
|
|
|
|
|
|
|
if (child) {
|
2017-07-21 19:39:32 +08:00
|
|
|
child_adev = to_acpi_device_node(child);
|
|
|
|
next = child_adev->node.next;
|
2015-08-27 10:42:33 +08:00
|
|
|
if (next == head) {
|
|
|
|
child = NULL;
|
|
|
|
goto nondev;
|
|
|
|
}
|
2017-07-21 19:39:32 +08:00
|
|
|
child_adev = list_entry(next, struct acpi_device, node);
|
2015-08-27 10:42:33 +08:00
|
|
|
} else {
|
2017-07-21 19:39:32 +08:00
|
|
|
child_adev = list_first_entry(head, struct acpi_device,
|
|
|
|
node);
|
2015-08-27 10:42:33 +08:00
|
|
|
}
|
2017-07-21 19:39:32 +08:00
|
|
|
return acpi_fwnode_handle(child_adev);
|
2015-08-27 10:42:33 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
nondev:
|
2017-07-21 19:39:31 +08:00
|
|
|
if (!child || is_acpi_data_node(child)) {
|
2017-07-21 19:39:32 +08:00
|
|
|
const struct acpi_data_node *data = to_acpi_data_node(fwnode);
|
2015-08-27 10:42:33 +08:00
|
|
|
struct acpi_data_node *dn;
|
|
|
|
|
2017-07-21 19:39:32 +08:00
|
|
|
if (child_adev)
|
|
|
|
head = &child_adev->data.subnodes;
|
2017-03-28 15:52:18 +08:00
|
|
|
else if (data)
|
|
|
|
head = &data->data.subnodes;
|
|
|
|
else
|
|
|
|
return NULL;
|
|
|
|
|
2015-08-27 10:42:33 +08:00
|
|
|
if (list_empty(head))
|
|
|
|
return NULL;
|
|
|
|
|
|
|
|
if (child) {
|
|
|
|
dn = to_acpi_data_node(child);
|
|
|
|
next = dn->sibling.next;
|
|
|
|
if (next == head)
|
|
|
|
return NULL;
|
|
|
|
|
|
|
|
dn = list_entry(next, struct acpi_data_node, sibling);
|
|
|
|
} else {
|
|
|
|
dn = list_first_entry(head, struct acpi_data_node, sibling);
|
|
|
|
}
|
|
|
|
return &dn->fwnode;
|
|
|
|
}
|
|
|
|
return NULL;
|
|
|
|
}
|
2017-03-28 15:52:16 +08:00
|
|
|
|
|
|
|
/**
|
|
|
|
* acpi_node_get_parent - Return parent fwnode of this fwnode
|
|
|
|
* @fwnode: Firmware node whose parent to get
|
|
|
|
*
|
|
|
|
* Returns parent node of an ACPI device or data firmware node or %NULL if
|
|
|
|
* not available.
|
|
|
|
*/
|
2017-07-21 19:39:36 +08:00
|
|
|
struct fwnode_handle *acpi_node_get_parent(const struct fwnode_handle *fwnode)
|
2017-03-28 15:52:16 +08:00
|
|
|
{
|
|
|
|
if (is_acpi_data_node(fwnode)) {
|
|
|
|
/* All data nodes have parent pointer so just return that */
|
|
|
|
return to_acpi_data_node(fwnode)->parent;
|
|
|
|
} else if (is_acpi_device_node(fwnode)) {
|
|
|
|
acpi_handle handle, parent_handle;
|
|
|
|
|
|
|
|
handle = to_acpi_device_node(fwnode)->handle;
|
|
|
|
if (ACPI_SUCCESS(acpi_get_parent(handle, &parent_handle))) {
|
|
|
|
struct acpi_device *adev;
|
|
|
|
|
|
|
|
if (!acpi_bus_get_device(parent_handle, &adev))
|
|
|
|
return acpi_fwnode_handle(adev);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return NULL;
|
|
|
|
}
|
2017-03-28 15:52:20 +08:00
|
|
|
|
|
|
|
/**
|
|
|
|
* acpi_graph_get_next_endpoint - Get next endpoint ACPI firmware node
|
|
|
|
* @fwnode: Pointer to the parent firmware node
|
|
|
|
* @prev: Previous endpoint node or %NULL to get the first
|
|
|
|
*
|
|
|
|
* Looks up next endpoint ACPI firmware node below a given @fwnode. Returns
|
|
|
|
* %NULL if there is no next endpoint, ERR_PTR() in case of error. In case
|
|
|
|
* of success the next endpoint is returned.
|
|
|
|
*/
|
2017-07-21 19:39:36 +08:00
|
|
|
struct fwnode_handle *acpi_graph_get_next_endpoint(
|
|
|
|
const struct fwnode_handle *fwnode, struct fwnode_handle *prev)
|
2017-03-28 15:52:20 +08:00
|
|
|
{
|
|
|
|
struct fwnode_handle *port = NULL;
|
|
|
|
struct fwnode_handle *endpoint;
|
|
|
|
|
|
|
|
if (!prev) {
|
|
|
|
do {
|
|
|
|
port = fwnode_get_next_child_node(fwnode, port);
|
|
|
|
/* Ports must have port property */
|
|
|
|
if (fwnode_property_present(port, "port"))
|
|
|
|
break;
|
|
|
|
} while (port);
|
|
|
|
} else {
|
|
|
|
port = fwnode_get_parent(prev);
|
|
|
|
}
|
|
|
|
|
|
|
|
if (!port)
|
|
|
|
return NULL;
|
|
|
|
|
|
|
|
endpoint = fwnode_get_next_child_node(port, prev);
|
|
|
|
while (!endpoint) {
|
|
|
|
port = fwnode_get_next_child_node(fwnode, port);
|
|
|
|
if (!port)
|
|
|
|
break;
|
|
|
|
if (fwnode_property_present(port, "port"))
|
|
|
|
endpoint = fwnode_get_next_child_node(port, NULL);
|
|
|
|
}
|
|
|
|
|
|
|
|
if (endpoint) {
|
|
|
|
/* Endpoints must have "endpoint" property */
|
|
|
|
if (!fwnode_property_present(endpoint, "endpoint"))
|
|
|
|
return ERR_PTR(-EPROTO);
|
|
|
|
}
|
|
|
|
|
|
|
|
return endpoint;
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* acpi_graph_get_child_prop_value - Return a child with a given property value
|
|
|
|
* @fwnode: device fwnode
|
|
|
|
* @prop_name: The name of the property to look for
|
|
|
|
* @val: the desired property value
|
|
|
|
*
|
|
|
|
* Return the port node corresponding to a given port number. Returns
|
|
|
|
* the child node on success, NULL otherwise.
|
|
|
|
*/
|
|
|
|
static struct fwnode_handle *acpi_graph_get_child_prop_value(
|
2017-07-21 19:39:36 +08:00
|
|
|
const struct fwnode_handle *fwnode, const char *prop_name,
|
|
|
|
unsigned int val)
|
2017-03-28 15:52:20 +08:00
|
|
|
{
|
|
|
|
struct fwnode_handle *child;
|
|
|
|
|
|
|
|
fwnode_for_each_child_node(fwnode, child) {
|
|
|
|
u32 nr;
|
|
|
|
|
2017-08-23 04:39:58 +08:00
|
|
|
if (fwnode_property_read_u32(child, prop_name, &nr))
|
2017-03-28 15:52:20 +08:00
|
|
|
continue;
|
|
|
|
|
|
|
|
if (val == nr)
|
|
|
|
return child;
|
|
|
|
}
|
|
|
|
|
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
* acpi_graph_get_remote_enpoint - Parses and returns remote end of an endpoint
|
|
|
|
* @fwnode: Endpoint firmware node pointing to a remote device
|
|
|
|
* @parent: Firmware node of remote port parent is filled here if not %NULL
|
|
|
|
* @port: Firmware node of remote port is filled here if not %NULL
|
|
|
|
* @endpoint: Firmware node of remote endpoint is filled here if not %NULL
|
|
|
|
*
|
|
|
|
* Function parses remote end of ACPI firmware remote endpoint and fills in
|
|
|
|
* fields requested by the caller. Returns %0 in case of success and
|
|
|
|
* negative errno otherwise.
|
|
|
|
*/
|
2017-07-21 19:39:36 +08:00
|
|
|
int acpi_graph_get_remote_endpoint(const struct fwnode_handle *__fwnode,
|
2017-03-28 15:52:20 +08:00
|
|
|
struct fwnode_handle **parent,
|
|
|
|
struct fwnode_handle **port,
|
|
|
|
struct fwnode_handle **endpoint)
|
|
|
|
{
|
2017-07-21 19:39:36 +08:00
|
|
|
struct fwnode_handle *fwnode;
|
2017-03-28 15:52:20 +08:00
|
|
|
unsigned int port_nr, endpoint_nr;
|
|
|
|
struct acpi_reference_args args;
|
|
|
|
int ret;
|
|
|
|
|
|
|
|
memset(&args, 0, sizeof(args));
|
2017-07-21 19:39:36 +08:00
|
|
|
ret = acpi_node_get_property_reference(__fwnode, "remote-endpoint", 0,
|
2017-03-28 15:52:20 +08:00
|
|
|
&args);
|
|
|
|
if (ret)
|
|
|
|
return ret;
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Always require two arguments with the reference: port and
|
|
|
|
* endpoint indices.
|
|
|
|
*/
|
|
|
|
if (args.nargs != 2)
|
|
|
|
return -EPROTO;
|
|
|
|
|
|
|
|
fwnode = acpi_fwnode_handle(args.adev);
|
|
|
|
port_nr = args.args[0];
|
|
|
|
endpoint_nr = args.args[1];
|
|
|
|
|
|
|
|
if (parent)
|
|
|
|
*parent = fwnode;
|
|
|
|
|
|
|
|
if (!port && !endpoint)
|
|
|
|
return 0;
|
|
|
|
|
|
|
|
fwnode = acpi_graph_get_child_prop_value(fwnode, "port", port_nr);
|
|
|
|
if (!fwnode)
|
|
|
|
return -EPROTO;
|
|
|
|
|
|
|
|
if (port)
|
|
|
|
*port = fwnode;
|
|
|
|
|
|
|
|
if (!endpoint)
|
|
|
|
return 0;
|
|
|
|
|
|
|
|
fwnode = acpi_graph_get_child_prop_value(fwnode, "endpoint",
|
|
|
|
endpoint_nr);
|
|
|
|
if (!fwnode)
|
|
|
|
return -EPROTO;
|
|
|
|
|
|
|
|
*endpoint = fwnode;
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
}
|
2017-06-06 17:37:37 +08:00
|
|
|
|
2017-07-21 19:39:36 +08:00
|
|
|
static bool acpi_fwnode_device_is_available(const struct fwnode_handle *fwnode)
|
2017-06-06 17:37:39 +08:00
|
|
|
{
|
|
|
|
if (!is_acpi_device_node(fwnode))
|
|
|
|
return false;
|
|
|
|
|
|
|
|
return acpi_device_is_present(to_acpi_device_node(fwnode));
|
|
|
|
}
|
|
|
|
|
2017-07-21 19:39:36 +08:00
|
|
|
static bool acpi_fwnode_property_present(const struct fwnode_handle *fwnode,
|
2017-06-06 17:37:37 +08:00
|
|
|
const char *propname)
|
|
|
|
{
|
|
|
|
return !acpi_node_prop_get(fwnode, propname, NULL);
|
|
|
|
}
|
|
|
|
|
2017-07-21 19:39:36 +08:00
|
|
|
static int
|
|
|
|
acpi_fwnode_property_read_int_array(const struct fwnode_handle *fwnode,
|
|
|
|
const char *propname,
|
|
|
|
unsigned int elem_size, void *val,
|
|
|
|
size_t nval)
|
2017-06-06 17:37:37 +08:00
|
|
|
{
|
|
|
|
enum dev_prop_type type;
|
|
|
|
|
|
|
|
switch (elem_size) {
|
|
|
|
case sizeof(u8):
|
|
|
|
type = DEV_PROP_U8;
|
|
|
|
break;
|
|
|
|
case sizeof(u16):
|
|
|
|
type = DEV_PROP_U16;
|
|
|
|
break;
|
|
|
|
case sizeof(u32):
|
|
|
|
type = DEV_PROP_U32;
|
|
|
|
break;
|
|
|
|
case sizeof(u64):
|
|
|
|
type = DEV_PROP_U64;
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
return -ENXIO;
|
|
|
|
}
|
|
|
|
|
|
|
|
return acpi_node_prop_read(fwnode, propname, type, val, nval);
|
|
|
|
}
|
|
|
|
|
2017-07-21 19:39:36 +08:00
|
|
|
static int
|
|
|
|
acpi_fwnode_property_read_string_array(const struct fwnode_handle *fwnode,
|
|
|
|
const char *propname, const char **val,
|
|
|
|
size_t nval)
|
2017-06-06 17:37:37 +08:00
|
|
|
{
|
|
|
|
return acpi_node_prop_read(fwnode, propname, DEV_PROP_STRING,
|
|
|
|
val, nval);
|
|
|
|
}
|
|
|
|
|
|
|
|
static struct fwnode_handle *
|
2017-07-21 19:39:36 +08:00
|
|
|
acpi_fwnode_get_named_child_node(const struct fwnode_handle *fwnode,
|
2017-06-06 17:37:37 +08:00
|
|
|
const char *childname)
|
|
|
|
{
|
|
|
|
struct fwnode_handle *child;
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Find first matching named child node of this fwnode.
|
|
|
|
* For ACPI this will be a data only sub-node.
|
|
|
|
*/
|
|
|
|
fwnode_for_each_child_node(fwnode, child)
|
|
|
|
if (acpi_data_node_match(child, childname))
|
|
|
|
return child;
|
|
|
|
|
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
|
2017-07-21 20:11:49 +08:00
|
|
|
static int
|
|
|
|
acpi_fwnode_get_reference_args(const struct fwnode_handle *fwnode,
|
|
|
|
const char *prop, const char *nargs_prop,
|
|
|
|
unsigned int args_count, unsigned int index,
|
|
|
|
struct fwnode_reference_args *args)
|
|
|
|
{
|
|
|
|
struct acpi_reference_args acpi_args;
|
|
|
|
unsigned int i;
|
|
|
|
int ret;
|
|
|
|
|
|
|
|
ret = __acpi_node_get_property_reference(fwnode, prop, index,
|
|
|
|
args_count, &acpi_args);
|
|
|
|
if (ret < 0)
|
|
|
|
return ret;
|
|
|
|
if (!args)
|
|
|
|
return 0;
|
|
|
|
|
|
|
|
args->nargs = acpi_args.nargs;
|
|
|
|
args->fwnode = acpi_fwnode_handle(acpi_args.adev);
|
|
|
|
|
|
|
|
for (i = 0; i < NR_FWNODE_REFERENCE_ARGS; i++)
|
|
|
|
args->args[i] = i < acpi_args.nargs ? acpi_args.args[i] : 0;
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2017-06-06 17:37:38 +08:00
|
|
|
static struct fwnode_handle *
|
2017-07-21 19:39:36 +08:00
|
|
|
acpi_fwnode_graph_get_next_endpoint(const struct fwnode_handle *fwnode,
|
2017-06-06 17:37:38 +08:00
|
|
|
struct fwnode_handle *prev)
|
|
|
|
{
|
|
|
|
struct fwnode_handle *endpoint;
|
|
|
|
|
|
|
|
endpoint = acpi_graph_get_next_endpoint(fwnode, prev);
|
|
|
|
if (IS_ERR(endpoint))
|
|
|
|
return NULL;
|
|
|
|
|
|
|
|
return endpoint;
|
|
|
|
}
|
|
|
|
|
|
|
|
static struct fwnode_handle *
|
2017-07-21 19:39:36 +08:00
|
|
|
acpi_fwnode_graph_get_remote_endpoint(const struct fwnode_handle *fwnode)
|
2017-06-06 17:37:38 +08:00
|
|
|
{
|
|
|
|
struct fwnode_handle *endpoint = NULL;
|
|
|
|
|
|
|
|
acpi_graph_get_remote_endpoint(fwnode, NULL, NULL, &endpoint);
|
|
|
|
|
|
|
|
return endpoint;
|
|
|
|
}
|
|
|
|
|
2017-07-21 19:39:36 +08:00
|
|
|
static struct fwnode_handle *
|
|
|
|
acpi_fwnode_get_parent(struct fwnode_handle *fwnode)
|
|
|
|
{
|
|
|
|
return acpi_node_get_parent(fwnode);
|
|
|
|
}
|
|
|
|
|
|
|
|
static int acpi_fwnode_graph_parse_endpoint(const struct fwnode_handle *fwnode,
|
2017-06-06 17:37:38 +08:00
|
|
|
struct fwnode_endpoint *endpoint)
|
|
|
|
{
|
|
|
|
struct fwnode_handle *port_fwnode = fwnode_get_parent(fwnode);
|
|
|
|
|
|
|
|
endpoint->local_fwnode = fwnode;
|
|
|
|
|
|
|
|
fwnode_property_read_u32(port_fwnode, "port", &endpoint->port);
|
|
|
|
fwnode_property_read_u32(fwnode, "endpoint", &endpoint->id);
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2017-07-21 19:39:31 +08:00
|
|
|
#define DECLARE_ACPI_FWNODE_OPS(ops) \
|
|
|
|
const struct fwnode_operations ops = { \
|
|
|
|
.device_is_available = acpi_fwnode_device_is_available, \
|
|
|
|
.property_present = acpi_fwnode_property_present, \
|
|
|
|
.property_read_int_array = \
|
|
|
|
acpi_fwnode_property_read_int_array, \
|
|
|
|
.property_read_string_array = \
|
|
|
|
acpi_fwnode_property_read_string_array, \
|
|
|
|
.get_parent = acpi_node_get_parent, \
|
|
|
|
.get_next_child_node = acpi_get_next_subnode, \
|
|
|
|
.get_named_child_node = acpi_fwnode_get_named_child_node, \
|
2017-07-21 20:11:49 +08:00
|
|
|
.get_reference_args = acpi_fwnode_get_reference_args, \
|
2017-07-21 19:39:31 +08:00
|
|
|
.graph_get_next_endpoint = \
|
|
|
|
acpi_fwnode_graph_get_next_endpoint, \
|
|
|
|
.graph_get_remote_endpoint = \
|
|
|
|
acpi_fwnode_graph_get_remote_endpoint, \
|
2017-07-21 19:39:36 +08:00
|
|
|
.graph_get_port_parent = acpi_fwnode_get_parent, \
|
2017-07-21 19:39:31 +08:00
|
|
|
.graph_parse_endpoint = acpi_fwnode_graph_parse_endpoint, \
|
|
|
|
}; \
|
|
|
|
EXPORT_SYMBOL_GPL(ops)
|
|
|
|
|
|
|
|
DECLARE_ACPI_FWNODE_OPS(acpi_device_fwnode_ops);
|
|
|
|
DECLARE_ACPI_FWNODE_OPS(acpi_data_fwnode_ops);
|
|
|
|
const struct fwnode_operations acpi_static_fwnode_ops;
|