Messages in this thread Patch in this message | | | From | Jiaying Liang <> | Date | Tue, 31 Jul 2018 16:43:19 -0700 | Subject | Fwd: [linux-sunxi] Re: [PATCH v2 2/3] mailbox: introduce ARM SMC based mailbox |
| |
<div dir="ltr"><br><div class="gmail_quote"><div>Added missing maintainers from the previous reply</div><div><br></div><div dir="ltr">On Sunday, 23 July 2017 16:26:55 UTC-7, Andre Przywara wrote:<blockquote class="gmail_quote" style="margin:0;margin-left:0.8ex;border-left:1px #ccc solid;padding-left:1ex">This mailbox driver implements a mailbox which signals transmitted data <br>via an ARM smc (secure monitor call) instruction. The mailbox receiver <br>is implemented in firmware and can synchronously return data when it <br>returns execution to the non-secure world again. <br>An asynchronous receive path is not implemented. <br>This allows the usage of a mailbox to trigger firmware actions on SoCs <br>which either don't have a separate management processor or on which such <br>a core is not available. A user of this mailbox could be the SCP <br>interface. <br> <br>Signed-off-by: Andre Przywara <<a rel="nofollow">andre.p...@arm.com</a>> <br>--- <br> drivers/mailbox/Kconfig | 8 ++ <br> drivers/mailbox/Makefile | 2 + <br> drivers/mailbox/arm-smc-mailb<wbr>ox.c | 155 ++++++++++++++++++++++++++++++<wbr>++++++++ <br> 3 files changed, 165 insertions(+) <br> create mode 100644 drivers/mailbox/arm-smc-mailbo<wbr>x.c <br> <br>diff --git a/drivers/mailbox/Kconfig b/drivers/mailbox/Kconfig <br>index c5731e5..5664b7f 100644 <br>--- a/drivers/mailbox/Kconfig <br>+++ b/drivers/mailbox/Kconfig <br>@@ -170,4 +170,12 @@ config BCM_FLEXRM_MBOX <br> Mailbox implementation of the Broadcom FlexRM ring manager, <br> which provides access to various offload engines on Broadcom <br> SoCs. Say Y here if you want to use the Broadcom FlexRM. <br>+ <br>+config ARM_SMC_MBOX <br>+ tristate "Generic ARM smc mailbox" <br>+ depends on OF && HAVE_ARM_SMCCC <br>+ help <br>+ Generic mailbox driver which uses ARM smc calls to call into <br>+ firmware for triggering mailboxes. <br>+ <br> endif <br>diff --git a/drivers/mailbox/Makefile b/drivers/mailbox/Makefile <br>index d54e412..8ec6869 100644 <br>--- a/drivers/mailbox/Makefile <br>+++ b/drivers/mailbox/Makefile <br>@@ -35,3 +35,5 @@ obj-$(CONFIG_BCM_FLEXRM_MBOX) <wbr> += bcm-flexrm-mailbox.o <br> obj-$(CONFIG_QCOM_APCS_IPC) <wbr> += qcom-apcs-ipc-mailbox.o <br> <br> obj-$(CONFIG_TEGRA_HSP_MBOX) <wbr> += tegra-hsp.o <br>+ <br>+obj-$(CONFIG_ARM_SMC_MBOX) <wbr> += arm-smc-mailbox.o <br>diff --git a/drivers/mailbox/arm-smc-mail<wbr>box.c b/drivers/mailbox/arm-smc-mail<wbr>box.c <br>new file mode 100644 <br>index 0000000..d7b61a7 <br>--- /dev/null <br>+++ b/drivers/mailbox/arm-smc-mail<wbr>box.c <br>@@ -0,0 +1,155 @@ <br>+/* <br>+ * Copyright (C) 2016,2017 ARM Ltd. <br>+ * <br>+ * This program is free software; you can redistribute it and/or modify <br>+ * it under the terms of the GNU General Public License version 2 as <br>+ * published by the Free Software Foundation. <br>+ * <br>+ * This device provides a mechanism for emulating a mailbox by using <br>+ * smc calls, allowing a "mailbox" consumer to sit in firmware running <br>+ * on the same core. <br>+ */ <br>+ <br>+#include <linux/device.h> <br>+#include <linux/kernel.h> <br>+#include <linux/mailbox_controller.h> <br>+#include <linux/module.h> <br>+#include <linux/platform_device.h> <br>+#include <linux/arm-smccc.h> <br>+ <br>+#define ARM_SMC_MBOX_USE_HVC BI<wbr>T(0) <br>+ <br>+struct arm_smc_chan_data { <br>+ u32 function_id; <br>+ u32 flags; <br>+}; <br>+ <br>+static int arm_smc_send_data(struct mbox_chan *link, void *data) <br>+{ <br>+ struct arm_smc_chan_data *chan_data = link->con_priv; <br>+ u32 function_id = chan_data->function_id; <br>+ struct arm_smccc_res res; <br>+ u32 msg = *(u32 *)data; <br>+ <br>+ if (chan_data->flags & ARM_SMC_MBOX_USE_HVC) <br>+ arm_smccc_hvc<wbr>(function_id, msg, 0, 0, 0, 0, 0, 0, &res); <br>+ else <br>+ arm_smccc_smc<wbr>(function_id, msg, 0, 0, 0, 0, 0, 0, &res); <br>+ <br>+ mbox_chan_received_da<wbr>ta(link, (void *)res.a0); <br>+ <br>+ return 0; <br>+} <br></blockquote><div><div>We have a use case that the message to post to the mailbox is larger</div><div>than 32bit. Can we change the SMC request to take the pointer as the</div><div>message argument instead of the the value?</div><div>But in this case, I am not clear on how the ATF to validate if the pointer</div><div>is valid. Any suggestions?</div><div><br></div><div>Furthermore, the received response can be larger that smc response</div><div>a0, any suggestion to solve this issue? reuse the input data pointer for</div><div>ATF to write copy the response data?<br></div><div><br></div><div>In case of asynchronous request, the request can be from remote first.</div><div>How to solve this issue to use a generic SMC mailbox driver?</div><div>Use mailbox mbox_send_message() for a separate rx request channel?<br></div><div><br></div><div>Thanks,</div><div>Wendy<br></div><br></div><blockquote class="gmail_quote" style="margin:0;margin-left:0.8ex;border-left:1px #ccc solid;padding-left:1ex">+ <br>+/* This mailbox is synchronous, so we are always done. */ <br>+static bool arm_smc_last_tx_done(struct mbox_chan *link) <br>+{ <br>+ return true; <br>+} <br>+ <br>+static const struct mbox_chan_ops arm_smc_mbox_chan_ops = { <br>+ .send_data = arm_smc_send_data, <br>+ .last_tx_done <wbr>= arm_smc_last_tx_done <br>+}; <br>+ <br>+static int arm_smc_mbox_probe(struct platform_device *pdev) <br>+{ <br>+ struct device *dev = &pdev->dev; <br>+ struct mbox_controller *mbox; <br>+ struct arm_smc_chan_data *chan_data; <br>+ const char *method; <br>+ bool use_hvc = false; <br>+ int ret, i; <br>+ <br>+ ret = of_property_count_elems_of_siz<wbr>e(dev->of_node, "arm,func-ids", <br>+ <wbr> sizeof(u32)); <br>+ if (ret < 0) <br>+ return ret; <br>+ <br>+ if (!of_property_read_string(dev-<wbr>>of_node, "method", &method)) { <br>+ if (!strcmp("hvc", method)) { <br>+ use_h<wbr>vc = true; <br>+ } else if (!strcmp("smc", method)) { <br>+ use_h<wbr>vc = false; <br>+ } else { <br>+ dev_w<wbr>arn(dev, "invalid \"method\" property: %s\n", <br>+ <wbr> method); <br>+ <br>+ retur<wbr>n -EINVAL; <br>+ } <br>+ } <br>+ <br>+ mbox = devm_kzalloc(dev, sizeof(*mbox), GFP_KERNEL); <br>+ if (!mbox) <br>+ return -ENOMEM; <br>+ <br>+ mbox->num_chans = ret; <br>+ mbox->chans = devm_kcalloc(dev, mbox->num_chans, sizeof(*mbox->chans), <br>+ <wbr> GFP_KERNEL); <br>+ if (!mbox->chans) <br>+ return -ENOMEM; <br>+ <br>+ chan_data = devm_kcalloc(dev, mbox->num_chans, sizeof(*chan_data), <br>+ <wbr> GFP_KERNEL); <br>+ if (!chan_data) <br>+ return -ENOMEM; <br>+ <br>+ for (i = 0; i < mbox->num_chans; i++) { <br>+ u32 function_id; <br>+ <br>+ ret = of_property_read_u32_index(dev<wbr>->of_node, <br>+ <wbr> "arm,func-ids", i, <br>+ <wbr> &function_id); <br>+ if (ret) <br>+ retur<wbr>n ret; <br>+ <br>+ chan_data[i].<wbr>function_id = function_id; <br>+ if (use_hvc) <br>+ chan_<wbr>data[i].flags |= ARM_SMC_MBOX_USE_HVC; <br>+ mbox->chans[i<wbr>].con_priv = &chan_data[i]; <br>+ } <br>+ <br>+ mbox->txdone_poll = true; <br>+ mbox->txdone_irq = false; <br>+ mbox->txpoll_period = 1; <br>+ mbox->ops = &arm_smc_mbox_chan_ops; <br>+ mbox->dev = dev; <br>+ <br>+ ret = mbox_controller_register(mbox)<wbr>; <br>+ if (ret) <br>+ return ret; <br>+ <br>+ platform_set_drvdata(<wbr>pdev, mbox); <br>+ dev_info(dev, "ARM SMC mailbox enabled with %d chan%s.\n", <br>+ mbox->num_chans, mbox->num_chans == 1 ? "" : "s"); <br>+ <br>+ return ret; <br>+} <br>+ <br>+static int arm_smc_mbox_remove(struct platform_device *pdev) <br>+{ <br>+ struct mbox_controller *mbox = platform_get_drvdata(pdev); <br>+ <br>+ mbox_controller_unreg<wbr>ister(mbox); <br>+ return 0; <br>+} <br>+ <br>+static const struct of_device_id arm_smc_mbox_of_match[] = { <br>+ { .compatible = "arm,smc-mbox", }, <br>+ {}, <br>+}; <br>+MODULE_DEVICE_TABLE(of, arm_smc_mbox_of_match); <br>+ <br>+static struct platform_driver arm_smc_mbox_driver = { <br>+ .driver = { <br>+ .name = "arm-smc-mbox", <br>+ .of_match_tab<wbr>le = arm_smc_mbox_of_match, <br>+ }, <br>+ .probe <wbr> = arm_smc_mbox_probe, <br>+ .remove <wbr> = arm_smc_mbox_remove, <br>+}; <br>+module_platform_driver(arm_sm<wbr>c_mbox_driver); <br>+ <br>+MODULE_AUTHOR("Andre Przywara <<a rel="nofollow">andre.p...@arm.com</a>>"); <br>+MODULE_DESCRIPTION("Generic ARM smc mailbox driver"); <br>+MODULE_LICENSE("GPL v2"); <br><span class="HOEnZb"><font color="#888888">-- <br>2.8.2 <br> <br></font></span></blockquote></div><span class="HOEnZb"><font color="#888888"> <p></p> -- <br> You received this message because you are subscribed to the Google Groups "linux-sunxi" group.<br> To unsubscribe from this group and stop receiving emails from it, send an email to <a href="mailto:linux-sunxi+unsubscribe@googlegroups.com" target="_blank">linux-sunxi+unsubscribe@<wbr>googlegroups.com</a>.<br> For more options, visit <a href="https://groups.google.com/d/optout" target="_blank">https://groups.google.com/d/<wbr>optout</a>.<br> </font></span></div><br></div> | |