ACPI/IORT: Look up IORT node through struct fwnode_handle pointer
Current IORT code provides a function (ie iort_get_fwnode()) which looks up a struct fwnode_handle pointer through a struct acpi_iort_node pointer for SMMU components but it lacks a function that implements the reverse look-up, namely struct fwnode_handle* -> struct acpi_iort_node*. Devices that are not IORT named components cannot be retrieved through their associated IORT named component scan interface because they just are not represented in the ACPI namespace; the reverse look-up is therefore required for all platform devices that represent IORT nodes (eg SMMUs) so that the struct acpi_iort_node* can be retrieved from the struct device->fwnode pointer. Signed-off-by: Hanjun Guo <hanjun.guo@linaro.org> [lorenzo.pieralisi@arm.com: re-indented/rewrote the commit log] Signed-off-by: Lorenzo Pieralisi <lorenzo.pieralisi@arm.com>
This commit is contained in:
parent
896dd2c324
commit
0a71d8b95f
|
@ -126,6 +126,31 @@ static inline void iort_delete_fwnode(struct acpi_iort_node *node)
|
||||||
spin_unlock(&iort_fwnode_lock);
|
spin_unlock(&iort_fwnode_lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* iort_get_iort_node() - Retrieve iort_node associated with an fwnode
|
||||||
|
*
|
||||||
|
* @fwnode: fwnode associated with device to be looked-up
|
||||||
|
*
|
||||||
|
* Returns: iort_node pointer on success, NULL on failure
|
||||||
|
*/
|
||||||
|
static inline struct acpi_iort_node *iort_get_iort_node(
|
||||||
|
struct fwnode_handle *fwnode)
|
||||||
|
{
|
||||||
|
struct iort_fwnode *curr;
|
||||||
|
struct acpi_iort_node *iort_node = NULL;
|
||||||
|
|
||||||
|
spin_lock(&iort_fwnode_lock);
|
||||||
|
list_for_each_entry(curr, &iort_fwnode_list, list) {
|
||||||
|
if (curr->fwnode == fwnode) {
|
||||||
|
iort_node = curr->iort_node;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
spin_unlock(&iort_fwnode_lock);
|
||||||
|
|
||||||
|
return iort_node;
|
||||||
|
}
|
||||||
|
|
||||||
typedef acpi_status (*iort_find_node_callback)
|
typedef acpi_status (*iort_find_node_callback)
|
||||||
(struct acpi_iort_node *node, void *context);
|
(struct acpi_iort_node *node, void *context);
|
||||||
|
|
||||||
|
@ -422,9 +447,25 @@ static struct acpi_iort_node *iort_find_dev_node(struct device *dev)
|
||||||
{
|
{
|
||||||
struct pci_bus *pbus;
|
struct pci_bus *pbus;
|
||||||
|
|
||||||
if (!dev_is_pci(dev))
|
if (!dev_is_pci(dev)) {
|
||||||
|
struct acpi_iort_node *node;
|
||||||
|
/*
|
||||||
|
* scan iort_fwnode_list to see if it's an iort platform
|
||||||
|
* device (such as SMMU, PMCG),its iort node already cached
|
||||||
|
* and associated with fwnode when iort platform devices
|
||||||
|
* were initialized.
|
||||||
|
*/
|
||||||
|
node = iort_get_iort_node(dev->fwnode);
|
||||||
|
if (node)
|
||||||
|
return node;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* if not, then it should be a platform device defined in
|
||||||
|
* DSDT/SSDT (with Named Component node in IORT)
|
||||||
|
*/
|
||||||
return iort_scan_node(ACPI_IORT_NODE_NAMED_COMPONENT,
|
return iort_scan_node(ACPI_IORT_NODE_NAMED_COMPONENT,
|
||||||
iort_match_node_callback, dev);
|
iort_match_node_callback, dev);
|
||||||
|
}
|
||||||
|
|
||||||
/* Find a PCI root bus */
|
/* Find a PCI root bus */
|
||||||
pbus = to_pci_dev(dev)->bus;
|
pbus = to_pci_dev(dev)->bus;
|
||||||
|
|
Loading…
Reference in New Issue