1 // SPDX-License-Identifier: GPL-2.0-only
3 * Copyright (C) 2023, STMicroelectronics - All Rights Reserved
6 #include <linux/bitfield.h>
7 #include <linux/bits.h>
8 #include <linux/bus/stm32_firewall_device.h>
9 #include <linux/device.h>
10 #include <linux/err.h>
11 #include <linux/init.h>
13 #include <linux/kernel.h>
14 #include <linux/module.h>
16 #include <linux/of_platform.h>
17 #include <linux/platform_device.h>
18 #include <linux/types.h>
19 #include <linux/slab.h>
21 #include "stm32_firewall.h"
23 /* Corresponds to STM32_FIREWALL_MAX_EXTRA_ARGS + firewall ID */
24 #define STM32_FIREWALL_MAX_ARGS (STM32_FIREWALL_MAX_EXTRA_ARGS + 1)
26 static LIST_HEAD(firewall_controller_list
);
27 static DEFINE_MUTEX(firewall_controller_list_lock
);
29 /* Firewall device API */
31 int stm32_firewall_get_firewall(struct device_node
*np
, struct stm32_firewall
*firewall
,
32 unsigned int nb_firewall
)
34 struct stm32_firewall_controller
*ctrl
;
35 struct of_phandle_iterator it
;
36 unsigned int i
, j
= 0;
39 if (!firewall
|| !nb_firewall
)
42 /* Parse property with phandle parsed out */
43 of_for_each_phandle(&it
, err
, np
, "access-controllers", "#access-controller-cells", 0) {
44 struct of_phandle_args provider_args
;
45 struct device_node
*provider
= it
.node
;
50 pr_err("Unable to get access-controllers property for node %s\n, err: %d",
52 of_node_put(provider
);
56 if (j
>= nb_firewall
) {
57 pr_err("Too many firewall controllers");
58 of_node_put(provider
);
62 provider_args
.args_count
= of_phandle_iterator_args(&it
, provider_args
.args
,
63 STM32_FIREWALL_MAX_ARGS
);
65 /* Check if the parsed phandle corresponds to a registered firewall controller */
66 mutex_lock(&firewall_controller_list_lock
);
67 list_for_each_entry(ctrl
, &firewall_controller_list
, entry
) {
68 if (ctrl
->dev
->of_node
->phandle
== it
.phandle
) {
70 firewall
[j
].firewall_ctrl
= ctrl
;
74 mutex_unlock(&firewall_controller_list_lock
);
77 firewall
[j
].firewall_ctrl
= NULL
;
78 pr_err("No firewall controller registered for %s\n", np
->full_name
);
79 of_node_put(provider
);
83 err
= of_property_read_string_index(np
, "access-controller-names", j
, &fw_entry
);
85 firewall
[j
].entry
= fw_entry
;
87 /* Handle the case when there are no arguments given along with the phandle */
88 if (provider_args
.args_count
< 0 ||
89 provider_args
.args_count
> STM32_FIREWALL_MAX_ARGS
) {
90 of_node_put(provider
);
92 } else if (provider_args
.args_count
== 0) {
93 firewall
[j
].extra_args_size
= 0;
94 firewall
[j
].firewall_id
= U32_MAX
;
99 /* The firewall ID is always the first argument */
100 firewall
[j
].firewall_id
= provider_args
.args
[0];
102 /* Extra args start at the second argument */
103 for (i
= 0; i
< provider_args
.args_count
- 1; i
++)
104 firewall
[j
].extra_args
[i
] = provider_args
.args
[i
+ 1];
106 /* Remove the firewall ID arg that is not an extra argument */
107 firewall
[j
].extra_args_size
= provider_args
.args_count
- 1;
114 EXPORT_SYMBOL_GPL(stm32_firewall_get_firewall
);
116 int stm32_firewall_grant_access(struct stm32_firewall
*firewall
)
118 struct stm32_firewall_controller
*firewall_controller
;
120 if (!firewall
|| firewall
->firewall_id
== U32_MAX
)
123 firewall_controller
= firewall
->firewall_ctrl
;
125 if (!firewall_controller
)
128 return firewall_controller
->grant_access(firewall_controller
, firewall
->firewall_id
);
130 EXPORT_SYMBOL_GPL(stm32_firewall_grant_access
);
132 int stm32_firewall_grant_access_by_id(struct stm32_firewall
*firewall
, u32 subsystem_id
)
134 struct stm32_firewall_controller
*firewall_controller
;
136 if (!firewall
|| subsystem_id
== U32_MAX
|| firewall
->firewall_id
== U32_MAX
)
139 firewall_controller
= firewall
->firewall_ctrl
;
141 if (!firewall_controller
)
144 return firewall_controller
->grant_access(firewall_controller
, subsystem_id
);
146 EXPORT_SYMBOL_GPL(stm32_firewall_grant_access_by_id
);
148 void stm32_firewall_release_access(struct stm32_firewall
*firewall
)
150 struct stm32_firewall_controller
*firewall_controller
;
152 if (!firewall
|| firewall
->firewall_id
== U32_MAX
) {
153 pr_debug("Incorrect arguments when releasing a firewall access\n");
157 firewall_controller
= firewall
->firewall_ctrl
;
159 if (!firewall_controller
) {
160 pr_debug("No firewall controller to release\n");
164 firewall_controller
->release_access(firewall_controller
, firewall
->firewall_id
);
166 EXPORT_SYMBOL_GPL(stm32_firewall_release_access
);
168 void stm32_firewall_release_access_by_id(struct stm32_firewall
*firewall
, u32 subsystem_id
)
170 struct stm32_firewall_controller
*firewall_controller
;
172 if (!firewall
|| subsystem_id
== U32_MAX
|| firewall
->firewall_id
== U32_MAX
) {
173 pr_debug("Incorrect arguments when releasing a firewall access");
177 firewall_controller
= firewall
->firewall_ctrl
;
179 if (!firewall_controller
) {
180 pr_debug("No firewall controller to release");
184 firewall_controller
->release_access(firewall_controller
, subsystem_id
);
186 EXPORT_SYMBOL_GPL(stm32_firewall_release_access_by_id
);
188 /* Firewall controller API */
190 int stm32_firewall_controller_register(struct stm32_firewall_controller
*firewall_controller
)
192 struct stm32_firewall_controller
*ctrl
;
194 if (!firewall_controller
)
197 pr_info("Registering %s firewall controller\n", firewall_controller
->name
);
199 mutex_lock(&firewall_controller_list_lock
);
200 list_for_each_entry(ctrl
, &firewall_controller_list
, entry
) {
201 if (ctrl
== firewall_controller
) {
202 pr_debug("%s firewall controller already registered\n",
203 firewall_controller
->name
);
204 mutex_unlock(&firewall_controller_list_lock
);
208 list_add_tail(&firewall_controller
->entry
, &firewall_controller_list
);
209 mutex_unlock(&firewall_controller_list_lock
);
213 EXPORT_SYMBOL_GPL(stm32_firewall_controller_register
);
215 void stm32_firewall_controller_unregister(struct stm32_firewall_controller
*firewall_controller
)
217 struct stm32_firewall_controller
*ctrl
;
218 bool controller_removed
= false;
220 if (!firewall_controller
) {
221 pr_debug("Null reference while unregistering firewall controller\n");
225 mutex_lock(&firewall_controller_list_lock
);
226 list_for_each_entry(ctrl
, &firewall_controller_list
, entry
) {
227 if (ctrl
== firewall_controller
) {
228 controller_removed
= true;
229 list_del_init(&ctrl
->entry
);
233 mutex_unlock(&firewall_controller_list_lock
);
235 if (!controller_removed
)
236 pr_debug("There was no firewall controller named %s to unregister\n",
237 firewall_controller
->name
);
239 EXPORT_SYMBOL_GPL(stm32_firewall_controller_unregister
);
241 int stm32_firewall_populate_bus(struct stm32_firewall_controller
*firewall_controller
)
243 struct stm32_firewall
*firewalls
;
244 struct device_node
*child
;
245 struct device
*parent
;
250 parent
= firewall_controller
->dev
;
252 dev_dbg(parent
, "Populating %s system bus\n", dev_name(firewall_controller
->dev
));
254 for_each_available_child_of_node(dev_of_node(parent
), child
) {
255 /* The access-controllers property is mandatory for firewall bus devices */
256 len
= of_count_phandle_with_args(child
, "access-controllers",
257 "#access-controller-cells");
263 firewalls
= kcalloc(len
, sizeof(*firewalls
), GFP_KERNEL
);
269 err
= stm32_firewall_get_firewall(child
, firewalls
, (unsigned int)len
);
276 for (i
= 0; i
< len
; i
++) {
277 if (firewall_controller
->grant_access(firewall_controller
,
278 firewalls
[i
].firewall_id
)) {
280 * Peripheral access not allowed or not defined.
281 * Mark the node as populated so platform bus won't probe it
283 of_detach_node(child
);
284 dev_err(parent
, "%s: Device driver will not be probed\n",
294 EXPORT_SYMBOL_GPL(stm32_firewall_populate_bus
);