1 // SPDX-License-Identifier: GPL-2.0
3 * System Control and Management Interface (SCMI) Message Protocol bus layer
5 * Copyright (C) 2018 ARM Ltd.
8 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
10 #include <linux/types.h>
11 #include <linux/module.h>
12 #include <linux/kernel.h>
13 #include <linux/slab.h>
14 #include <linux/device.h>
18 static DEFINE_IDA(scmi_bus_id
);
19 static DEFINE_IDR(scmi_protocols
);
20 static DEFINE_SPINLOCK(protocol_lock
);
22 static const struct scmi_device_id
*
23 scmi_dev_match_id(struct scmi_device
*scmi_dev
, struct scmi_driver
*scmi_drv
)
25 const struct scmi_device_id
*id
= scmi_drv
->id_table
;
30 for (; id
->protocol_id
; id
++)
31 if (id
->protocol_id
== scmi_dev
->protocol_id
) {
34 else if (!strcmp(id
->name
, scmi_dev
->name
))
41 static int scmi_dev_match(struct device
*dev
, struct device_driver
*drv
)
43 struct scmi_driver
*scmi_drv
= to_scmi_driver(drv
);
44 struct scmi_device
*scmi_dev
= to_scmi_dev(dev
);
45 const struct scmi_device_id
*id
;
47 id
= scmi_dev_match_id(scmi_dev
, scmi_drv
);
54 static int scmi_protocol_init(int protocol_id
, struct scmi_handle
*handle
)
56 scmi_prot_init_fn_t fn
= idr_find(&scmi_protocols
, protocol_id
);
63 static int scmi_protocol_dummy_init(struct scmi_handle
*handle
)
68 static int scmi_dev_probe(struct device
*dev
)
70 struct scmi_driver
*scmi_drv
= to_scmi_driver(dev
->driver
);
71 struct scmi_device
*scmi_dev
= to_scmi_dev(dev
);
72 const struct scmi_device_id
*id
;
75 id
= scmi_dev_match_id(scmi_dev
, scmi_drv
);
79 if (!scmi_dev
->handle
)
82 ret
= scmi_protocol_init(scmi_dev
->protocol_id
, scmi_dev
->handle
);
86 /* Skip protocol initialisation for additional devices */
87 idr_replace(&scmi_protocols
, &scmi_protocol_dummy_init
,
88 scmi_dev
->protocol_id
);
90 return scmi_drv
->probe(scmi_dev
);
93 static int scmi_dev_remove(struct device
*dev
)
95 struct scmi_driver
*scmi_drv
= to_scmi_driver(dev
->driver
);
96 struct scmi_device
*scmi_dev
= to_scmi_dev(dev
);
99 scmi_drv
->remove(scmi_dev
);
104 static struct bus_type scmi_bus_type
= {
105 .name
= "scmi_protocol",
106 .match
= scmi_dev_match
,
107 .probe
= scmi_dev_probe
,
108 .remove
= scmi_dev_remove
,
111 int scmi_driver_register(struct scmi_driver
*driver
, struct module
*owner
,
112 const char *mod_name
)
116 driver
->driver
.bus
= &scmi_bus_type
;
117 driver
->driver
.name
= driver
->name
;
118 driver
->driver
.owner
= owner
;
119 driver
->driver
.mod_name
= mod_name
;
121 retval
= driver_register(&driver
->driver
);
123 pr_debug("registered new scmi driver %s\n", driver
->name
);
127 EXPORT_SYMBOL_GPL(scmi_driver_register
);
129 void scmi_driver_unregister(struct scmi_driver
*driver
)
131 driver_unregister(&driver
->driver
);
133 EXPORT_SYMBOL_GPL(scmi_driver_unregister
);
135 static void scmi_device_release(struct device
*dev
)
137 kfree(to_scmi_dev(dev
));
141 scmi_device_create(struct device_node
*np
, struct device
*parent
, int protocol
,
145 struct scmi_device
*scmi_dev
;
147 scmi_dev
= kzalloc(sizeof(*scmi_dev
), GFP_KERNEL
);
151 scmi_dev
->name
= kstrdup_const(name
?: "unknown", GFP_KERNEL
);
152 if (!scmi_dev
->name
) {
157 id
= ida_simple_get(&scmi_bus_id
, 1, 0, GFP_KERNEL
);
159 kfree_const(scmi_dev
->name
);
165 scmi_dev
->protocol_id
= protocol
;
166 scmi_dev
->dev
.parent
= parent
;
167 scmi_dev
->dev
.of_node
= np
;
168 scmi_dev
->dev
.bus
= &scmi_bus_type
;
169 scmi_dev
->dev
.release
= scmi_device_release
;
170 dev_set_name(&scmi_dev
->dev
, "scmi_dev.%d", id
);
172 retval
= device_register(&scmi_dev
->dev
);
178 kfree_const(scmi_dev
->name
);
179 put_device(&scmi_dev
->dev
);
180 ida_simple_remove(&scmi_bus_id
, id
);
184 void scmi_device_destroy(struct scmi_device
*scmi_dev
)
186 kfree_const(scmi_dev
->name
);
187 scmi_handle_put(scmi_dev
->handle
);
188 ida_simple_remove(&scmi_bus_id
, scmi_dev
->id
);
189 device_unregister(&scmi_dev
->dev
);
192 void scmi_set_handle(struct scmi_device
*scmi_dev
)
194 scmi_dev
->handle
= scmi_handle_get(&scmi_dev
->dev
);
197 int scmi_protocol_register(int protocol_id
, scmi_prot_init_fn_t fn
)
201 spin_lock(&protocol_lock
);
202 ret
= idr_alloc(&scmi_protocols
, fn
, protocol_id
, protocol_id
+ 1,
204 spin_unlock(&protocol_lock
);
205 if (ret
!= protocol_id
)
206 pr_err("unable to allocate SCMI idr slot, err %d\n", ret
);
210 EXPORT_SYMBOL_GPL(scmi_protocol_register
);
212 void scmi_protocol_unregister(int protocol_id
)
214 spin_lock(&protocol_lock
);
215 idr_remove(&scmi_protocols
, protocol_id
);
216 spin_unlock(&protocol_lock
);
218 EXPORT_SYMBOL_GPL(scmi_protocol_unregister
);
220 static int __scmi_devices_unregister(struct device
*dev
, void *data
)
222 struct scmi_device
*scmi_dev
= to_scmi_dev(dev
);
224 scmi_device_destroy(scmi_dev
);
228 static void scmi_devices_unregister(void)
230 bus_for_each_dev(&scmi_bus_type
, NULL
, NULL
, __scmi_devices_unregister
);
233 static int __init
scmi_bus_init(void)
237 retval
= bus_register(&scmi_bus_type
);
239 pr_err("scmi protocol bus register failed (%d)\n", retval
);
243 subsys_initcall(scmi_bus_init
);
245 static void __exit
scmi_bus_exit(void)
247 scmi_devices_unregister();
248 bus_unregister(&scmi_bus_type
);
249 ida_destroy(&scmi_bus_id
);
251 module_exit(scmi_bus_exit
);