[PATCH v6 03/14] firmware: scmi: support dummy channels for sandbox agent

AKASHI Takahiro takahiro.akashi at linaro.org
Wed Oct 11 12:06:56 CEST 2023


In sandbox scmi agent, channels are not used at all. But in this patch,
dummy channels are supported in order to test protocol-specific channels.

Signed-off-by: AKASHI Takahiro <takahiro.akashi at linaro.org>
Reviewed-by: Simon Glass <sjg at chromium.org>
Reviewed-by: Etienne Carriere <etienne.carriere at foss.st.com>
---
v5
* new commit
---
 arch/sandbox/include/asm/scmi_test.h       | 13 ++++
 drivers/firmware/scmi/sandbox-scmi_agent.c | 90 ++++++++++++++++++++++
 2 files changed, 103 insertions(+)

diff --git a/arch/sandbox/include/asm/scmi_test.h b/arch/sandbox/include/asm/scmi_test.h
index c72ec1e1cb25..75cb462a5584 100644
--- a/arch/sandbox/include/asm/scmi_test.h
+++ b/arch/sandbox/include/asm/scmi_test.h
@@ -88,6 +88,14 @@ struct sandbox_scmi_devices {
 };
 
 #ifdef CONFIG_SCMI_FIRMWARE
+/**
+ * sandbox_scmi_channel_id - Get the channel id
+ * @dev:	Reference to the SCMI protocol device
+ *
+ * Return:	Channel id
+ */
+unsigned int sandbox_scmi_channel_id(struct udevice *dev);
+
 /**
  * sandbox_scmi_service_ctx - Get the simulated SCMI services context
  * @return:	Reference to backend simulated resources state
@@ -101,6 +109,11 @@ struct sandbox_scmi_service *sandbox_scmi_service_ctx(void);
  */
 struct sandbox_scmi_devices *sandbox_scmi_devices_ctx(struct udevice *dev);
 #else
+inline unsigned int sandbox_scmi_channel_id(struct udevice *dev);
+{
+	return 0;
+}
+
 static inline struct sandbox_scmi_service *sandbox_scmi_service_ctx(void)
 {
 	return NULL;
diff --git a/drivers/firmware/scmi/sandbox-scmi_agent.c b/drivers/firmware/scmi/sandbox-scmi_agent.c
index 031882998dfa..394df043918f 100644
--- a/drivers/firmware/scmi/sandbox-scmi_agent.c
+++ b/drivers/firmware/scmi/sandbox-scmi_agent.c
@@ -33,6 +33,26 @@
  * various uclass devices, as clocks and reset controllers.
  */
 
+/**
+ * struct sandbox_channel - Description of sandbox transport
+ * @channel_id:		Channel identifier
+ *
+ * Dummy channel. This will be used to test if a protocol-specific
+ * channel is properly used.
+ * Id 0 means a channel for the sandbox agent.
+ */
+struct sandbox_channel {
+	unsigned int channel_id;
+};
+
+/**
+ * struct scmi_channel - Channel instance referenced in SCMI drivers
+ * @ref: Reference to local channel instance
+ **/
+struct scmi_channel {
+	struct sandbox_channel ref;
+};
+
 static struct sandbox_scmi_clk scmi_clk[] = {
 	{ .rate = 333 },
 	{ .rate = 200 },
@@ -470,6 +490,73 @@ static int sandbox_scmi_voltd_level_get(struct udevice *dev,
 	return 0;
 }
 
+/**
+ * sandbox_scmi_of_get_channel - assigne a channel
+ * @dev:	SCMI agent device
+ * @protocol:	SCMI protocol device
+ * @channel:	Pointer to channel info
+ *
+ * Assign a channel for the protocol, @protocol, in @channel,
+ * based on a device tree's property.
+ *
+ * Return: 0 on success, error code on failure
+ */
+static int sandbox_scmi_of_get_channel(struct udevice *dev,
+				       struct udevice *protocol,
+				       struct scmi_channel **channel)
+{
+	struct sandbox_channel *agent_chan = dev_get_plat(dev);
+	struct sandbox_channel *chan;
+	u32 channel_id;
+
+	if (dev_read_u32(protocol, "linaro,sandbox-channel-id", &channel_id)) {
+		/* Uses agent channel */
+		*channel = container_of(agent_chan, struct scmi_channel, ref);
+
+		return 0;
+	}
+
+	/* Setup a dedicated channel */
+	chan = calloc(1, sizeof(*chan));
+	if (!chan)
+		return -ENOMEM;
+
+	chan->channel_id = channel_id;
+
+	*channel = container_of(chan, struct scmi_channel, ref);
+
+	return 0;
+}
+
+/**
+ * sandbox_scmi_of_to_plat - assigne a channel to agent
+ * @dev:	SCMI agent device
+ *
+ * Assign a channel for the agent, @protocol.
+ *
+ * Return: always 0
+ */
+static int sandbox_scmi_of_to_plat(struct udevice *dev)
+{
+	struct sandbox_channel *chan = dev_get_plat(dev);
+
+	/* The channel for agent is always 0 */
+	chan->channel_id = 0;
+
+	return 0;
+}
+
+unsigned int sandbox_scmi_channel_id(struct udevice *dev)
+{
+	struct scmi_agent_proto_priv *priv;
+	struct sandbox_channel *chan;
+
+	priv = dev_get_parent_priv(dev);
+	chan = (struct sandbox_channel *)&priv->channel->ref;
+
+	return chan->channel_id;
+}
+
 static int sandbox_scmi_test_process_msg(struct udevice *dev,
 					 struct scmi_channel *channel,
 					 struct scmi_msg *msg)
@@ -584,6 +671,7 @@ static const struct udevice_id sandbox_scmi_test_ids[] = {
 };
 
 struct scmi_agent_ops sandbox_scmi_test_ops = {
+	.of_get_channel = sandbox_scmi_of_get_channel,
 	.process_msg = sandbox_scmi_test_process_msg,
 };
 
@@ -592,6 +680,8 @@ U_BOOT_DRIVER(sandbox_scmi_agent) = {
 	.id = UCLASS_SCMI_AGENT,
 	.of_match = sandbox_scmi_test_ids,
 	.priv_auto	= sizeof(struct sandbox_scmi_agent),
+	.plat_auto	= sizeof(struct sandbox_channel),
+	.of_to_plat	= sandbox_scmi_of_to_plat,
 	.probe = sandbox_scmi_test_probe,
 	.remove = sandbox_scmi_test_remove,
 	.ops = &sandbox_scmi_test_ops,
-- 
2.34.1



More information about the U-Boot mailing list