Skip to content

Commit 14ade5a

Browse files
committed
Merge tag 'scmi-updates-6.14' of https://git.kernel.org/pub/scm/linux/kernel/git/sudeep.holla/linux into soc/drivers
Arm SCMI updates for 6.14 This mainly has 2 updates: 1. Extension of the transport properties read from devicetree to support multiple SCMI platform/server instances 2. Addition of the capability to automatically load the proper SCMI vendor protocol module. The vendor protocol selection is already provided by the SCMI core while the automatic loading of vendor protocols was not. * tag 'scmi-updates-6.14' of https://git.kernel.org/pub/scm/linux/kernel/git/sudeep.holla/linux: firmware: arm_scmi: Add aliases to transport modules firmware: arm_scmi: Add module aliases to i.MX vendor protocols firmware: arm_scmi: Support vendor protocol modules autoloading firmware: arm_scmi: Allow transport properties for multiple instances Link: https://lore.kernel.org/r/20250102154024.2168165-1-sudeep.holla@arm.com Signed-off-by: Arnd Bergmann <arnd@arndb.de>
2 parents 8de2819 + 3f3f0e5 commit 14ade5a

8 files changed

Lines changed: 71 additions & 29 deletions

File tree

drivers/firmware/arm_scmi/common.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -442,7 +442,7 @@ struct scmi_transport_core_operations {
442442
*/
443443
struct scmi_transport {
444444
struct device *supplier;
445-
struct scmi_desc *desc;
445+
struct scmi_desc desc;
446446
struct scmi_transport_core_operations **core_ops;
447447
};
448448

@@ -468,7 +468,7 @@ static int __tag##_probe(struct platform_device *pdev) \
468468
device_set_of_node_from_dev(&spdev->dev, dev); \
469469
\
470470
strans.supplier = dev; \
471-
strans.desc = &(__desc); \
471+
memcpy(&strans.desc, &(__desc), sizeof(strans.desc)); \
472472
strans.core_ops = &(__core_ops); \
473473
\
474474
ret = platform_device_add_data(spdev, &strans, sizeof(strans)); \

drivers/firmware/arm_scmi/driver.c

Lines changed: 55 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@
2424
#include <linux/io.h>
2525
#include <linux/io-64-nonatomic-hi-lo.h>
2626
#include <linux/kernel.h>
27+
#include <linux/kmod.h>
2728
#include <linux/ktime.h>
2829
#include <linux/hashtable.h>
2930
#include <linux/list.h>
@@ -43,6 +44,8 @@
4344
#define CREATE_TRACE_POINTS
4445
#include <trace/events/scmi.h>
4546

47+
#define SCMI_VENDOR_MODULE_ALIAS_FMT "scmi-protocol-0x%02x-%s"
48+
4649
static DEFINE_IDA(scmi_id);
4750

4851
static DEFINE_XARRAY(scmi_protocols);
@@ -275,6 +278,44 @@ scmi_vendor_protocol_lookup(int protocol_id, char *vendor_id,
275278
return proto;
276279
}
277280

281+
static const struct scmi_protocol *
282+
scmi_vendor_protocol_get(int protocol_id, struct scmi_revision_info *version)
283+
{
284+
const struct scmi_protocol *proto;
285+
286+
proto = scmi_vendor_protocol_lookup(protocol_id, version->vendor_id,
287+
version->sub_vendor_id,
288+
version->impl_ver);
289+
if (!proto) {
290+
int ret;
291+
292+
pr_debug("Looking for '" SCMI_VENDOR_MODULE_ALIAS_FMT "'\n",
293+
protocol_id, version->vendor_id);
294+
295+
/* Note that vendor_id is mandatory for vendor protocols */
296+
ret = request_module(SCMI_VENDOR_MODULE_ALIAS_FMT,
297+
protocol_id, version->vendor_id);
298+
if (ret) {
299+
pr_warn("Problem loading module for protocol 0x%x\n",
300+
protocol_id);
301+
return NULL;
302+
}
303+
304+
/* Lookup again, once modules loaded */
305+
proto = scmi_vendor_protocol_lookup(protocol_id,
306+
version->vendor_id,
307+
version->sub_vendor_id,
308+
version->impl_ver);
309+
}
310+
311+
if (proto)
312+
pr_info("Loaded SCMI Vendor Protocol 0x%x - %s %s %X\n",
313+
protocol_id, proto->vendor_id ?: "",
314+
proto->sub_vendor_id ?: "", proto->impl_ver);
315+
316+
return proto;
317+
}
318+
278319
static const struct scmi_protocol *
279320
scmi_protocol_get(int protocol_id, struct scmi_revision_info *version)
280321
{
@@ -283,22 +324,15 @@ scmi_protocol_get(int protocol_id, struct scmi_revision_info *version)
283324
if (protocol_id < SCMI_PROTOCOL_VENDOR_BASE)
284325
proto = xa_load(&scmi_protocols, protocol_id);
285326
else
286-
proto = scmi_vendor_protocol_lookup(protocol_id,
287-
version->vendor_id,
288-
version->sub_vendor_id,
289-
version->impl_ver);
327+
proto = scmi_vendor_protocol_get(protocol_id, version);
328+
290329
if (!proto || !try_module_get(proto->owner)) {
291330
pr_warn("SCMI Protocol 0x%x not found!\n", protocol_id);
292331
return NULL;
293332
}
294333

295334
pr_debug("Found SCMI Protocol 0x%x\n", protocol_id);
296335

297-
if (protocol_id >= SCMI_PROTOCOL_VENDOR_BASE)
298-
pr_info("Loaded SCMI Vendor Protocol 0x%x - %s %s %X\n",
299-
protocol_id, proto->vendor_id ?: "",
300-
proto->sub_vendor_id ?: "", proto->impl_ver);
301-
302336
return proto;
303337
}
304338

@@ -366,7 +400,9 @@ int scmi_protocol_register(const struct scmi_protocol *proto)
366400
return ret;
367401
}
368402

369-
pr_debug("Registered SCMI Protocol 0x%x\n", proto->id);
403+
pr_debug("Registered SCMI Protocol 0x%x - %s %s 0x%08X\n",
404+
proto->id, proto->vendor_id, proto->sub_vendor_id,
405+
proto->impl_ver);
370406

371407
return 0;
372408
}
@@ -3028,7 +3064,7 @@ static const struct scmi_desc *scmi_transport_setup(struct device *dev)
30283064
int ret;
30293065

30303066
trans = dev_get_platdata(dev);
3031-
if (!trans || !trans->desc || !trans->supplier || !trans->core_ops)
3067+
if (!trans || !trans->supplier || !trans->core_ops)
30323068
return NULL;
30333069

30343070
if (!device_link_add(dev, trans->supplier, DL_FLAG_AUTOREMOVE_CONSUMER)) {
@@ -3043,33 +3079,33 @@ static const struct scmi_desc *scmi_transport_setup(struct device *dev)
30433079
dev_info(dev, "Using %s\n", dev_driver_string(trans->supplier));
30443080

30453081
ret = of_property_read_u32(dev->of_node, "arm,max-rx-timeout-ms",
3046-
&trans->desc->max_rx_timeout_ms);
3082+
&trans->desc.max_rx_timeout_ms);
30473083
if (ret && ret != -EINVAL)
30483084
dev_err(dev, "Malformed arm,max-rx-timeout-ms DT property.\n");
30493085

30503086
ret = of_property_read_u32(dev->of_node, "arm,max-msg-size",
3051-
&trans->desc->max_msg_size);
3087+
&trans->desc.max_msg_size);
30523088
if (ret && ret != -EINVAL)
30533089
dev_err(dev, "Malformed arm,max-msg-size DT property.\n");
30543090

30553091
ret = of_property_read_u32(dev->of_node, "arm,max-msg",
3056-
&trans->desc->max_msg);
3092+
&trans->desc.max_msg);
30573093
if (ret && ret != -EINVAL)
30583094
dev_err(dev, "Malformed arm,max-msg DT property.\n");
30593095

30603096
dev_info(dev,
30613097
"SCMI max-rx-timeout: %dms / max-msg-size: %dbytes / max-msg: %d\n",
3062-
trans->desc->max_rx_timeout_ms, trans->desc->max_msg_size,
3063-
trans->desc->max_msg);
3098+
trans->desc.max_rx_timeout_ms, trans->desc.max_msg_size,
3099+
trans->desc.max_msg);
30643100

30653101
/* System wide atomic threshold for atomic ops .. if any */
30663102
if (!of_property_read_u32(dev->of_node, "atomic-threshold-us",
3067-
&trans->desc->atomic_threshold))
3103+
&trans->desc.atomic_threshold))
30683104
dev_info(dev,
30693105
"SCMI System wide atomic threshold set to %u us\n",
3070-
trans->desc->atomic_threshold);
3106+
trans->desc.atomic_threshold);
30713107

3072-
return trans->desc;
3108+
return &trans->desc;
30733109
}
30743110

30753111
static int scmi_probe(struct platform_device *pdev)

drivers/firmware/arm_scmi/transports/mailbox.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -378,6 +378,7 @@ static const struct of_device_id scmi_of_match[] = {
378378
{ .compatible = "arm,scmi" },
379379
{ /* Sentinel */ },
380380
};
381+
MODULE_DEVICE_TABLE(of, scmi_of_match);
381382

382383
DEFINE_SCMI_TRANSPORT_DRIVER(scmi_mailbox, scmi_mailbox_driver,
383384
scmi_mailbox_desc, scmi_of_match, core);

drivers/firmware/arm_scmi/transports/smc.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -301,6 +301,7 @@ static const struct of_device_id scmi_of_match[] = {
301301
{ .compatible = "qcom,scmi-smc" },
302302
{ /* Sentinel */ },
303303
};
304+
MODULE_DEVICE_TABLE(of, scmi_of_match);
304305

305306
DEFINE_SCMI_TRANSPORT_DRIVER(scmi_smc, scmi_smc_driver, scmi_smc_desc,
306307
scmi_of_match, core);

drivers/firmware/arm_scmi/transports/virtio.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -921,6 +921,7 @@ static const struct virtio_device_id id_table[] = {
921921
{ VIRTIO_ID_SCMI, VIRTIO_DEV_ANY_ID },
922922
{ 0 }
923923
};
924+
MODULE_DEVICE_TABLE(virtio, id_table);
924925

925926
static struct virtio_driver virtio_scmi_driver = {
926927
.driver.name = "scmi-virtio",

drivers/firmware/arm_scmi/vendors/imx/imx-sm-bbm.c

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -374,10 +374,11 @@ static const struct scmi_protocol scmi_imx_bbm = {
374374
.ops = &scmi_imx_bbm_proto_ops,
375375
.events = &scmi_imx_bbm_protocol_events,
376376
.supported_version = SCMI_PROTOCOL_SUPPORTED_VERSION,
377-
.vendor_id = "NXP",
378-
.sub_vendor_id = "IMX",
377+
.vendor_id = SCMI_IMX_VENDOR,
378+
.sub_vendor_id = SCMI_IMX_SUBVENDOR,
379379
};
380380
module_scmi_protocol(scmi_imx_bbm);
381381

382+
MODULE_ALIAS("scmi-protocol-" __stringify(SCMI_PROTOCOL_IMX_BBM) "-" SCMI_IMX_VENDOR);
382383
MODULE_DESCRIPTION("i.MX SCMI BBM driver");
383384
MODULE_LICENSE("GPL");

drivers/firmware/arm_scmi/vendors/imx/imx-sm-misc.c

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -309,10 +309,11 @@ static const struct scmi_protocol scmi_imx_misc = {
309309
.ops = &scmi_imx_misc_proto_ops,
310310
.events = &scmi_imx_misc_protocol_events,
311311
.supported_version = SCMI_PROTOCOL_SUPPORTED_VERSION,
312-
.vendor_id = "NXP",
313-
.sub_vendor_id = "IMX",
312+
.vendor_id = SCMI_IMX_VENDOR,
313+
.sub_vendor_id = SCMI_IMX_SUBVENDOR,
314314
};
315315
module_scmi_protocol(scmi_imx_misc);
316316

317+
MODULE_ALIAS("scmi-protocol-" __stringify(SCMI_PROTOCOL_IMX_MISC) "-" SCMI_IMX_VENDOR);
317318
MODULE_DESCRIPTION("i.MX SCMI MISC driver");
318319
MODULE_LICENSE("GPL");

include/linux/scmi_imx_protocol.h

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,11 @@
1313
#include <linux/notifier.h>
1414
#include <linux/types.h>
1515

16-
enum scmi_nxp_protocol {
17-
SCMI_PROTOCOL_IMX_BBM = 0x81,
18-
SCMI_PROTOCOL_IMX_MISC = 0x84,
19-
};
16+
#define SCMI_PROTOCOL_IMX_BBM 0x81
17+
#define SCMI_PROTOCOL_IMX_MISC 0x84
18+
19+
#define SCMI_IMX_VENDOR "NXP"
20+
#define SCMI_IMX_SUBVENDOR "IMX"
2021

2122
struct scmi_imx_bbm_proto_ops {
2223
int (*rtc_time_set)(const struct scmi_protocol_handle *ph, u32 id,

0 commit comments

Comments
 (0)