1 // SPDX-License-Identifier: GPL-2.0+
5 * Handling for platform devices in IPMI (ACPI, OF, and things
6 * coming from the platform.
9 #define pr_fmt(fmt) "ipmi_platform: " fmt
10 #define dev_fmt pr_fmt
12 #include <linux/types.h>
13 #include <linux/module.h>
14 #include <linux/of_device.h>
15 #include <linux/of_platform.h>
16 #include <linux/of_address.h>
17 #include <linux/of_irq.h>
18 #include <linux/acpi.h>
22 static bool platform_registered
;
23 static bool si_tryplatform
= true;
25 static bool si_tryacpi
= true;
28 static bool si_tryopenfirmware
= true;
31 static bool si_trydmi
= true;
33 static bool si_trydmi
= false;
36 module_param_named(tryplatform
, si_tryplatform
, bool, 0);
37 MODULE_PARM_DESC(tryplatform
, "Setting this to zero will disable the"
38 " default scan of the interfaces identified via platform"
39 " interfaces besides ACPI, OpenFirmware, and DMI");
41 module_param_named(tryacpi
, si_tryacpi
, bool, 0);
42 MODULE_PARM_DESC(tryacpi
, "Setting this to zero will disable the"
43 " default scan of the interfaces identified via ACPI");
46 module_param_named(tryopenfirmware
, si_tryopenfirmware
, bool, 0);
47 MODULE_PARM_DESC(tryopenfirmware
, "Setting this to zero will disable the"
48 " default scan of the interfaces identified via OpenFirmware");
51 module_param_named(trydmi
, si_trydmi
, bool, 0);
52 MODULE_PARM_DESC(trydmi
, "Setting this to zero will disable the"
53 " default scan of the interfaces identified via DMI");
57 /* For GPE-type interrupts. */
58 static u32
ipmi_acpi_gpe(acpi_handle gpe_device
,
59 u32 gpe_number
, void *context
)
61 struct si_sm_io
*io
= context
;
63 ipmi_si_irq_handler(io
->irq
, io
->irq_handler_data
);
64 return ACPI_INTERRUPT_HANDLED
;
67 static void acpi_gpe_irq_cleanup(struct si_sm_io
*io
)
72 ipmi_irq_start_cleanup(io
);
73 acpi_remove_gpe_handler(NULL
, io
->irq
, &ipmi_acpi_gpe
);
76 static int acpi_gpe_irq_setup(struct si_sm_io
*io
)
83 status
= acpi_install_gpe_handler(NULL
,
85 ACPI_GPE_LEVEL_TRIGGERED
,
88 if (status
!= AE_OK
) {
90 "Unable to claim ACPI GPE %d, running polled\n",
95 io
->irq_cleanup
= acpi_gpe_irq_cleanup
;
96 ipmi_irq_finish_setup(io
);
97 dev_info(io
->dev
, "Using ACPI GPE %d\n", io
->irq
);
103 static struct resource
*
104 ipmi_get_info_from_resources(struct platform_device
*pdev
,
107 struct resource
*res
, *res_second
;
109 res
= platform_get_resource(pdev
, IORESOURCE_IO
, 0);
111 io
->addr_space
= IPMI_IO_ADDR_SPACE
;
113 res
= platform_get_resource(pdev
, IORESOURCE_MEM
, 0);
115 io
->addr_space
= IPMI_MEM_ADDR_SPACE
;
118 dev_err(&pdev
->dev
, "no I/O or memory address\n");
121 io
->addr_data
= res
->start
;
123 io
->regspacing
= DEFAULT_REGSPACING
;
124 res_second
= platform_get_resource(pdev
,
125 (io
->addr_space
== IPMI_IO_ADDR_SPACE
) ?
126 IORESOURCE_IO
: IORESOURCE_MEM
,
129 if (res_second
->start
> io
->addr_data
)
130 io
->regspacing
= res_second
->start
- io
->addr_data
;
136 static int platform_ipmi_probe(struct platform_device
*pdev
)
139 u8 type
, slave_addr
, addr_source
, regsize
, regshift
;
142 rv
= device_property_read_u8(&pdev
->dev
, "addr-source", &addr_source
);
144 addr_source
= SI_PLATFORM
;
145 if (addr_source
>= SI_LAST
)
148 if (addr_source
== SI_SMBIOS
) {
151 } else if (addr_source
!= SI_HARDCODED
) {
156 rv
= device_property_read_u8(&pdev
->dev
, "ipmi-type", &type
);
160 memset(&io
, 0, sizeof(io
));
161 io
.addr_source
= addr_source
;
162 dev_info(&pdev
->dev
, "probing via %s\n",
163 ipmi_addr_src_to_str(addr_source
));
171 case SI_TYPE_INVALID
: /* User disabled this in hardcode. */
174 dev_err(&pdev
->dev
, "ipmi-type property is invalid\n");
178 io
.regsize
= DEFAULT_REGSIZE
;
179 rv
= device_property_read_u8(&pdev
->dev
, "reg-size", ®size
);
181 io
.regsize
= regsize
;
184 rv
= device_property_read_u8(&pdev
->dev
, "reg-shift", ®shift
);
186 io
.regshift
= regshift
;
188 if (!ipmi_get_info_from_resources(pdev
, &io
))
191 rv
= device_property_read_u8(&pdev
->dev
, "slave-addr", &slave_addr
);
193 io
.slave_addr
= 0x20;
195 io
.slave_addr
= slave_addr
;
197 io
.irq
= platform_get_irq_optional(pdev
, 0);
199 io
.irq_setup
= ipmi_std_irq_setup
;
205 pr_info("ipmi_si: %s: %s %#lx regsize %d spacing %d irq %d\n",
206 ipmi_addr_src_to_str(addr_source
),
207 (io
.addr_space
== IPMI_IO_ADDR_SPACE
) ? "io" : "mem",
208 io
.addr_data
, io
.regsize
, io
.regspacing
, io
.irq
);
210 ipmi_si_add_smi(&io
);
216 static const struct of_device_id of_ipmi_match
[] = {
217 { .type
= "ipmi", .compatible
= "ipmi-kcs",
218 .data
= (void *)(unsigned long) SI_KCS
},
219 { .type
= "ipmi", .compatible
= "ipmi-smic",
220 .data
= (void *)(unsigned long) SI_SMIC
},
221 { .type
= "ipmi", .compatible
= "ipmi-bt",
222 .data
= (void *)(unsigned long) SI_BT
},
225 MODULE_DEVICE_TABLE(of
, of_ipmi_match
);
227 static int of_ipmi_probe(struct platform_device
*pdev
)
229 const struct of_device_id
*match
;
231 struct resource resource
;
232 const __be32
*regsize
, *regspacing
, *regshift
;
233 struct device_node
*np
= pdev
->dev
.of_node
;
237 if (!si_tryopenfirmware
)
240 dev_info(&pdev
->dev
, "probing via device tree\n");
242 match
= of_match_device(of_ipmi_match
, &pdev
->dev
);
246 if (!of_device_is_available(np
))
249 ret
= of_address_to_resource(np
, 0, &resource
);
251 dev_warn(&pdev
->dev
, "invalid address from OF\n");
255 regsize
= of_get_property(np
, "reg-size", &proplen
);
256 if (regsize
&& proplen
!= 4) {
257 dev_warn(&pdev
->dev
, "invalid regsize from OF\n");
261 regspacing
= of_get_property(np
, "reg-spacing", &proplen
);
262 if (regspacing
&& proplen
!= 4) {
263 dev_warn(&pdev
->dev
, "invalid regspacing from OF\n");
267 regshift
= of_get_property(np
, "reg-shift", &proplen
);
268 if (regshift
&& proplen
!= 4) {
269 dev_warn(&pdev
->dev
, "invalid regshift from OF\n");
273 memset(&io
, 0, sizeof(io
));
274 io
.si_type
= (enum si_type
) match
->data
;
275 io
.addr_source
= SI_DEVICETREE
;
276 io
.irq_setup
= ipmi_std_irq_setup
;
278 if (resource
.flags
& IORESOURCE_IO
)
279 io
.addr_space
= IPMI_IO_ADDR_SPACE
;
281 io
.addr_space
= IPMI_MEM_ADDR_SPACE
;
283 io
.addr_data
= resource
.start
;
285 io
.regsize
= regsize
? be32_to_cpup(regsize
) : DEFAULT_REGSIZE
;
286 io
.regspacing
= regspacing
? be32_to_cpup(regspacing
) : DEFAULT_REGSPACING
;
287 io
.regshift
= regshift
? be32_to_cpup(regshift
) : 0;
289 io
.irq
= irq_of_parse_and_map(pdev
->dev
.of_node
, 0);
292 dev_dbg(&pdev
->dev
, "addr 0x%lx regsize %d spacing %d irq %d\n",
293 io
.addr_data
, io
.regsize
, io
.regspacing
, io
.irq
);
295 return ipmi_si_add_smi(&io
);
298 #define of_ipmi_match NULL
299 static int of_ipmi_probe(struct platform_device
*dev
)
306 static int find_slave_address(struct si_sm_io
*io
, int slave_addr
)
308 #ifdef CONFIG_IPMI_DMI_DECODE
310 slave_addr
= ipmi_dmi_get_slave_addr(io
->si_type
,
318 static int acpi_ipmi_probe(struct platform_device
*pdev
)
323 unsigned long long tmp
;
324 struct resource
*res
;
330 handle
= ACPI_HANDLE(&pdev
->dev
);
334 memset(&io
, 0, sizeof(io
));
335 io
.addr_source
= SI_ACPI
;
336 dev_info(&pdev
->dev
, "probing via ACPI\n");
338 io
.addr_info
.acpi_info
.acpi_handle
= handle
;
340 /* _IFT tells us the interface type: KCS, BT, etc */
341 status
= acpi_evaluate_integer(handle
, "_IFT", NULL
, &tmp
);
342 if (ACPI_FAILURE(status
)) {
344 "Could not find ACPI IPMI interface type\n");
353 io
.si_type
= SI_SMIC
;
358 case 4: /* SSIF, just ignore */
362 dev_info(&pdev
->dev
, "unknown IPMI type %lld\n", tmp
);
366 io
.regsize
= DEFAULT_REGSIZE
;
369 res
= ipmi_get_info_from_resources(pdev
, &io
);
375 /* If _GPE exists, use it; otherwise use standard interrupts */
376 status
= acpi_evaluate_integer(handle
, "_GPE", NULL
, &tmp
);
377 if (ACPI_SUCCESS(status
)) {
379 io
.irq_setup
= acpi_gpe_irq_setup
;
381 int irq
= platform_get_irq_optional(pdev
, 0);
385 io
.irq_setup
= ipmi_std_irq_setup
;
389 io
.slave_addr
= find_slave_address(&io
, io
.slave_addr
);
393 dev_info(io
.dev
, "%pR regsize %d spacing %d irq %d\n",
394 res
, io
.regsize
, io
.regspacing
, io
.irq
);
396 request_module("acpi_ipmi");
398 return ipmi_si_add_smi(&io
);
404 static const struct acpi_device_id acpi_ipmi_match
[] = {
408 MODULE_DEVICE_TABLE(acpi
, acpi_ipmi_match
);
410 static int acpi_ipmi_probe(struct platform_device
*dev
)
416 static int ipmi_probe(struct platform_device
*pdev
)
418 if (pdev
->dev
.of_node
&& of_ipmi_probe(pdev
) == 0)
421 if (acpi_ipmi_probe(pdev
) == 0)
424 return platform_ipmi_probe(pdev
);
427 static int ipmi_remove(struct platform_device
*pdev
)
429 return ipmi_si_remove_by_dev(&pdev
->dev
);
432 static int pdev_match_name(struct device
*dev
, const void *data
)
434 struct platform_device
*pdev
= to_platform_device(dev
);
435 const char *name
= data
;
437 return strcmp(pdev
->name
, name
) == 0;
440 void ipmi_remove_platform_device_by_name(char *name
)
444 while ((dev
= bus_find_device(&platform_bus_type
, NULL
, name
,
446 struct platform_device
*pdev
= to_platform_device(dev
);
448 platform_device_unregister(pdev
);
453 static const struct platform_device_id si_plat_ids
[] = {
454 { "dmi-ipmi-si", 0 },
455 { "hardcode-ipmi-si", 0 },
456 { "hotmod-ipmi-si", 0 },
460 struct platform_driver ipmi_platform_driver
= {
462 .name
= SI_DEVICE_NAME
,
463 .of_match_table
= of_ipmi_match
,
464 .acpi_match_table
= ACPI_PTR(acpi_ipmi_match
),
467 .remove
= ipmi_remove
,
468 .id_table
= si_plat_ids
471 void ipmi_si_platform_init(void)
473 int rv
= platform_driver_register(&ipmi_platform_driver
);
475 pr_err("Unable to register driver: %d\n", rv
);
477 platform_registered
= true;
480 void ipmi_si_platform_shutdown(void)
482 if (platform_registered
)
483 platform_driver_unregister(&ipmi_platform_driver
);