summaryrefslogtreecommitdiff
path: root/drivers/firmware
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/firmware')
-rw-r--r--drivers/firmware/arm_ffa/driver.c27
-rw-r--r--drivers/firmware/arm_scmi/power.c6
-rw-r--r--drivers/firmware/arm_scmi/sensors.c2
-rw-r--r--drivers/firmware/samsung/exynos-acpm.c23
-rw-r--r--drivers/firmware/smccc/soc_id.c2
-rw-r--r--drivers/firmware/xilinx/zynqmp.c28
6 files changed, 74 insertions, 14 deletions
diff --git a/drivers/firmware/arm_ffa/driver.c b/drivers/firmware/arm_ffa/driver.c
index b9f17fda7243..cab32cfdac42 100644
--- a/drivers/firmware/arm_ffa/driver.c
+++ b/drivers/firmware/arm_ffa/driver.c
@@ -324,11 +324,9 @@ __ffa_partition_info_get(u32 uuid0, u32 uuid1, u32 uuid2, u32 uuid3,
#define PART_INFO_EXEC_CXT_MASK GENMASK(31, 16)
#define PART_INFO_PROPS_MASK GENMASK(63, 32)
#define FFA_PART_INFO_GET_REGS_FIRST_REG 3
-#define FFA_PART_INFO_GET_REGS_REGS_PER_DESC 3
-#define FFA_PART_INFO_GET_REGS_MAX_DESC \
- (((sizeof(ffa_value_t) / sizeof_field(ffa_value_t, a0)) - \
- FFA_PART_INFO_GET_REGS_FIRST_REG) / \
- FFA_PART_INFO_GET_REGS_REGS_PER_DESC)
+#define FFA_PART_INFO_GET_REGS_MIN_REGS_PER_DESC 3
+#define FFA_PART_INFO_GET_REGS_NUM_REGS \
+ (sizeof(ffa_value_t) / sizeof_field(ffa_value_t, a0))
#define PART_INFO_ID(x) ((u16)(FIELD_GET(PART_INFO_ID_MASK, (x))))
#define PART_INFO_EXEC_CXT(x) ((u16)(FIELD_GET(PART_INFO_EXEC_CXT_MASK, (x))))
#define PART_INFO_PROPERTIES(x) ((u32)(FIELD_GET(PART_INFO_PROPS_MASK, (x))))
@@ -342,7 +340,7 @@ __ffa_partition_info_get_regs(u32 uuid0, u32 uuid1, u32 uuid2, u32 uuid3,
do {
__le64 *regs;
- int idx, nr_desc, buf_idx;
+ int idx, nr_desc, buf_idx, regs_per_desc, max_desc;
invoke_ffa_fn((ffa_value_t){
.a0 = FFA_PARTITION_INFO_GET_REGS,
@@ -365,8 +363,18 @@ __ffa_partition_info_get_regs(u32 uuid0, u32 uuid1, u32 uuid2, u32 uuid3,
if (cur_idx < start_idx || cur_idx >= count)
return -EINVAL;
+ buf_sz = PARTITION_INFO_SZ(partition_info.a2);
+ if (buf_sz % sizeof(*regs))
+ return -EINVAL;
+
+ regs_per_desc = buf_sz / sizeof(*regs);
+ if (regs_per_desc < FFA_PART_INFO_GET_REGS_MIN_REGS_PER_DESC)
+ return -EINVAL;
+
nr_desc = cur_idx - start_idx + 1;
- if (nr_desc > FFA_PART_INFO_GET_REGS_MAX_DESC)
+ max_desc = (FFA_PART_INFO_GET_REGS_NUM_REGS -
+ FFA_PART_INFO_GET_REGS_FIRST_REG) / regs_per_desc;
+ if (nr_desc > max_desc)
return -EINVAL;
buf_idx = buf - buffer;
@@ -374,9 +382,6 @@ __ffa_partition_info_get_regs(u32 uuid0, u32 uuid1, u32 uuid2, u32 uuid3,
return -EINVAL;
tag = UUID_INFO_TAG(partition_info.a2);
- buf_sz = PARTITION_INFO_SZ(partition_info.a2);
- if (buf_sz > sizeof(*buffer))
- buf_sz = sizeof(*buffer);
regs = (void *)&partition_info.a3;
for (idx = 0; idx < nr_desc; idx++, buf++) {
@@ -395,7 +400,7 @@ __ffa_partition_info_get_regs(u32 uuid0, u32 uuid1, u32 uuid2, u32 uuid3,
buf->exec_ctxt = PART_INFO_EXEC_CXT(val);
buf->properties = PART_INFO_PROPERTIES(val);
uuid_copy(&buf->uuid, &uuid_regs.uuid);
- regs += 3;
+ regs += regs_per_desc;
}
start_idx = cur_idx + 1;
diff --git a/drivers/firmware/arm_scmi/power.c b/drivers/firmware/arm_scmi/power.c
index bb5062ab8280..28ef63a4ecc2 100644
--- a/drivers/firmware/arm_scmi/power.c
+++ b/drivers/firmware/arm_scmi/power.c
@@ -204,8 +204,12 @@ scmi_power_name_get(const struct scmi_protocol_handle *ph,
u32 domain)
{
struct scmi_power_info *pi = ph->get_priv(ph);
- struct power_dom_info *dom = pi->dom_info + domain;
+ struct power_dom_info *dom;
+
+ if (domain >= pi->num_domains)
+ return "unknown";
+ dom = pi->dom_info + domain;
return dom->name;
}
diff --git a/drivers/firmware/arm_scmi/sensors.c b/drivers/firmware/arm_scmi/sensors.c
index 882d55f987d2..836c294a9f42 100644
--- a/drivers/firmware/arm_scmi/sensors.c
+++ b/drivers/firmware/arm_scmi/sensors.c
@@ -793,7 +793,7 @@ static int scmi_sensor_config_get(const struct scmi_protocol_handle *ph,
if (!ret) {
struct scmi_sensor_info *s = si->sensors + sensor_id;
- *sensor_config = get_unaligned_le64(t->rx.buf);
+ *sensor_config = get_unaligned_le32(t->rx.buf);
s->sensor_config = *sensor_config;
}
diff --git a/drivers/firmware/samsung/exynos-acpm.c b/drivers/firmware/samsung/exynos-acpm.c
index 19db3674a28f..65949e7fd430 100644
--- a/drivers/firmware/samsung/exynos-acpm.c
+++ b/drivers/firmware/samsung/exynos-acpm.c
@@ -819,6 +819,29 @@ struct acpm_handle *devm_acpm_get_by_node(struct device *dev,
}
EXPORT_SYMBOL_GPL(devm_acpm_get_by_node);
+/**
+ * devm_acpm_get_by_phandle - Resource managed lookup of the standardized
+ * "samsung,acpm-ipc" handle.
+ * @dev: consumer device
+ *
+ * Return: pointer to handle on success, ERR_PTR(-errno) otherwise.
+ */
+struct acpm_handle *devm_acpm_get_by_phandle(struct device *dev)
+{
+ struct acpm_handle *handle;
+ struct device_node *np;
+
+ np = of_parse_phandle(dev->of_node, "samsung,acpm-ipc", 0);
+ if (!np)
+ return ERR_PTR(-ENODEV);
+
+ handle = devm_acpm_get_by_node(dev, np);
+ of_node_put(np);
+
+ return handle;
+}
+EXPORT_SYMBOL_GPL(devm_acpm_get_by_phandle);
+
static const struct acpm_match_data acpm_gs101 = {
.initdata_base = ACPM_GS101_INITDATA_BASE,
.acpm_clk_dev_name = "gs101-acpm-clk",
diff --git a/drivers/firmware/smccc/soc_id.c b/drivers/firmware/smccc/soc_id.c
index 2f7475e66b3c..a909d5e6dee5 100644
--- a/drivers/firmware/smccc/soc_id.c
+++ b/drivers/firmware/smccc/soc_id.c
@@ -60,7 +60,7 @@ static char __init *smccc_soc_name_init(void)
* to the ARM_SMCCC_ARCH_SOC_ID function. Fetch it if
* available.
*/
- args.a0 = ARM_SMCCC_ARCH_SOC_ID;
+ args.a0 = ARM_SMCCC_ARCH_SOC_ID64;
args.a1 = 2; /* SOC_ID name */
arm_smccc_1_2_invoke(&args, &res);
diff --git a/drivers/firmware/xilinx/zynqmp.c b/drivers/firmware/xilinx/zynqmp.c
index fbe8510f4927..af838b2dc327 100644
--- a/drivers/firmware/xilinx/zynqmp.c
+++ b/drivers/firmware/xilinx/zynqmp.c
@@ -1451,6 +1451,34 @@ int zynqmp_pm_get_node_status(const u32 node, u32 *const status,
EXPORT_SYMBOL_GPL(zynqmp_pm_get_node_status);
/**
+ * zynqmp_pm_get_rpu_node_status - PM call to request a RPU node's current power state
+ * @node: ID of the RPU component or sub-system in question
+ * @status: Current operating state of the requested RPU node.
+ * @requirements: Current requirements asserted on the RPU node.
+ * @usage: Usage information, used for RPU slave nodes only:
+ * PM_USAGE_NO_MASTER - No master is currently using
+ * the node
+ * PM_USAGE_CURRENT_MASTER - Only requesting master is
+ * currently using the node
+ * PM_USAGE_OTHER_MASTER - Only other masters are
+ * currently using the node
+ * PM_USAGE_BOTH_MASTERS - Both the current and at least
+ * one other master is currently
+ * using the node
+ *
+ * Return: Returns status, either success or error+reason
+ */
+int zynqmp_pm_get_rpu_node_status(const u32 node, u32 *const status,
+ u32 *const requirements, u32 *const usage)
+{
+ if (zynqmp_pm_feature(PM_GET_NODE_STATUS) < PM_API_VERSION_2)
+ return -EOPNOTSUPP;
+
+ return zynqmp_pm_get_node_status(node, status, requirements, usage);
+}
+EXPORT_SYMBOL_GPL(zynqmp_pm_get_rpu_node_status);
+
+/**
* zynqmp_pm_force_pwrdwn - PM call to request for another PU or subsystem to
* be powered down forcefully
* @node: Node ID of the targeted PU or subsystem