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 si_tryplatform
= true;
24 static bool si_tryacpi
= true;
27 static bool si_tryopenfirmware
= true;
30 static bool si_trydmi
= true;
32 static bool si_trydmi
= false;
35 module_param_named(tryplatform
, si_tryplatform
, bool, 0);
36 MODULE_PARM_DESC(tryplatform
, "Setting this to zero will disable the"
37 " default scan of the interfaces identified via platform"
38 " interfaces besides ACPI, OpenFirmware, and DMI");
40 module_param_named(tryacpi
, si_tryacpi
, bool, 0);
41 MODULE_PARM_DESC(tryacpi
, "Setting this to zero will disable the"
42 " default scan of the interfaces identified via ACPI");
45 module_param_named(tryopenfirmware
, si_tryopenfirmware
, bool, 0);
46 MODULE_PARM_DESC(tryopenfirmware
, "Setting this to zero will disable the"
47 " default scan of the interfaces identified via OpenFirmware");
50 module_param_named(trydmi
, si_trydmi
, bool, 0);
51 MODULE_PARM_DESC(trydmi
, "Setting this to zero will disable the"
52 " default scan of the interfaces identified via DMI");
56 /* For GPE-type interrupts. */
57 static u32
ipmi_acpi_gpe(acpi_handle gpe_device
,
58 u32 gpe_number
, void *context
)
60 struct si_sm_io
*io
= context
;
62 ipmi_si_irq_handler(io
->irq
, io
->irq_handler_data
);
63 return ACPI_INTERRUPT_HANDLED
;
66 static void acpi_gpe_irq_cleanup(struct si_sm_io
*io
)
71 ipmi_irq_start_cleanup(io
);
72 acpi_remove_gpe_handler(NULL
, io
->irq
, &ipmi_acpi_gpe
);
75 static int acpi_gpe_irq_setup(struct si_sm_io
*io
)
82 status
= acpi_install_gpe_handler(NULL
,
84 ACPI_GPE_LEVEL_TRIGGERED
,
87 if (status
!= AE_OK
) {
89 "Unable to claim ACPI GPE %d, running polled\n",
94 io
->irq_cleanup
= acpi_gpe_irq_cleanup
;
95 ipmi_irq_finish_setup(io
);
96 dev_info(io
->dev
, "Using ACPI GPE %d\n", io
->irq
);
102 static struct resource
*
103 ipmi_get_info_from_resources(struct platform_device
*pdev
,
106 struct resource
*res
, *res_second
;
108 res
= platform_get_resource(pdev
, IORESOURCE_IO
, 0);
110 io
->addr_space
= IPMI_IO_ADDR_SPACE
;
112 res
= platform_get_resource(pdev
, IORESOURCE_MEM
, 0);
114 io
->addr_space
= IPMI_MEM_ADDR_SPACE
;
117 dev_err(&pdev
->dev
, "no I/O or memory address\n");
120 io
->addr_data
= res
->start
;
122 io
->regspacing
= DEFAULT_REGSPACING
;
123 res_second
= platform_get_resource(pdev
,
124 (io
->addr_space
== IPMI_IO_ADDR_SPACE
) ?
125 IORESOURCE_IO
: IORESOURCE_MEM
,
128 if (res_second
->start
> io
->addr_data
)
129 io
->regspacing
= res_second
->start
- io
->addr_data
;
135 static int platform_ipmi_probe(struct platform_device
*pdev
)
138 u8 type
, slave_addr
, addr_source
, regsize
, regshift
;
141 rv
= device_property_read_u8(&pdev
->dev
, "addr-source", &addr_source
);
143 addr_source
= SI_PLATFORM
;
144 if (addr_source
>= SI_LAST
)
147 if (addr_source
== SI_SMBIOS
) {
150 } else if (addr_source
!= SI_HARDCODED
) {
155 rv
= device_property_read_u8(&pdev
->dev
, "ipmi-type", &type
);
159 memset(&io
, 0, sizeof(io
));
160 io
.addr_source
= addr_source
;
161 dev_info(&pdev
->dev
, "probing via %s\n",
162 ipmi_addr_src_to_str(addr_source
));
170 case SI_TYPE_INVALID
: /* User disabled this in hardcode. */
173 dev_err(&pdev
->dev
, "ipmi-type property is invalid\n");
177 io
.regsize
= DEFAULT_REGSIZE
;
178 rv
= device_property_read_u8(&pdev
->dev
, "reg-size", ®size
);
180 io
.regsize
= regsize
;
183 rv
= device_property_read_u8(&pdev
->dev
, "reg-shift", ®shift
);
185 io
.regshift
= regshift
;
187 if (!ipmi_get_info_from_resources(pdev
, &io
))
190 rv
= device_property_read_u8(&pdev
->dev
, "slave-addr", &slave_addr
);
192 dev_warn(&pdev
->dev
, "device has no slave-addr property\n");
193 io
.slave_addr
= 0x20;
195 io
.slave_addr
= slave_addr
;
198 io
.irq
= platform_get_irq(pdev
, 0);
200 io
.irq_setup
= ipmi_std_irq_setup
;
206 pr_info("ipmi_si: %s: %s %#lx regsize %d spacing %d irq %d\n",
207 ipmi_addr_src_to_str(addr_source
),
208 (io
.addr_space
== IPMI_IO_ADDR_SPACE
) ? "io" : "mem",
209 io
.addr_data
, io
.regsize
, io
.regspacing
, io
.irq
);
211 ipmi_si_add_smi(&io
);
217 static const struct of_device_id of_ipmi_match
[] = {
218 { .type
= "ipmi", .compatible
= "ipmi-kcs",
219 .data
= (void *)(unsigned long) SI_KCS
},
220 { .type
= "ipmi", .compatible
= "ipmi-smic",
221 .data
= (void *)(unsigned long) SI_SMIC
},
222 { .type
= "ipmi", .compatible
= "ipmi-bt",
223 .data
= (void *)(unsigned long) SI_BT
},
226 MODULE_DEVICE_TABLE(of
, of_ipmi_match
);
228 static int of_ipmi_probe(struct platform_device
*pdev
)
230 const struct of_device_id
*match
;
232 struct resource resource
;
233 const __be32
*regsize
, *regspacing
, *regshift
;
234 struct device_node
*np
= pdev
->dev
.of_node
;
238 if (!si_tryopenfirmware
)
241 dev_info(&pdev
->dev
, "probing via device tree\n");
243 match
= of_match_device(of_ipmi_match
, &pdev
->dev
);
247 if (!of_device_is_available(np
))
250 ret
= of_address_to_resource(np
, 0, &resource
);
252 dev_warn(&pdev
->dev
, "invalid address from OF\n");
256 regsize
= of_get_property(np
, "reg-size", &proplen
);
257 if (regsize
&& proplen
!= 4) {
258 dev_warn(&pdev
->dev
, "invalid regsize from OF\n");
262 regspacing
= of_get_property(np
, "reg-spacing", &proplen
);
263 if (regspacing
&& proplen
!= 4) {
264 dev_warn(&pdev
->dev
, "invalid regspacing from OF\n");
268 regshift
= of_get_property(np
, "reg-shift", &proplen
);
269 if (regshift
&& proplen
!= 4) {
270 dev_warn(&pdev
->dev
, "invalid regshift from OF\n");
274 memset(&io
, 0, sizeof(io
));
275 io
.si_type
= (enum si_type
) match
->data
;
276 io
.addr_source
= SI_DEVICETREE
;
277 io
.irq_setup
= ipmi_std_irq_setup
;
279 if (resource
.flags
& IORESOURCE_IO
)
280 io
.addr_space
= IPMI_IO_ADDR_SPACE
;
282 io
.addr_space
= IPMI_MEM_ADDR_SPACE
;
284 io
.addr_data
= resource
.start
;
286 io
.regsize
= regsize
? be32_to_cpup(regsize
) : DEFAULT_REGSIZE
;
287 io
.regspacing
= regspacing
? be32_to_cpup(regspacing
) : DEFAULT_REGSPACING
;
288 io
.regshift
= regshift
? be32_to_cpup(regshift
) : 0;
290 io
.irq
= irq_of_parse_and_map(pdev
->dev
.of_node
, 0);
293 dev_dbg(&pdev
->dev
, "addr 0x%lx regsize %d spacing %d irq %d\n",
294 io
.addr_data
, io
.regsize
, io
.regspacing
, io
.irq
);
296 return ipmi_si_add_smi(&io
);
299 #define of_ipmi_match NULL
300 static int of_ipmi_probe(struct platform_device
*dev
)
307 static int find_slave_address(struct si_sm_io
*io
, int slave_addr
)
309 #ifdef CONFIG_IPMI_DMI_DECODE
311 slave_addr
= ipmi_dmi_get_slave_addr(io
->si_type
,
319 static int acpi_ipmi_probe(struct platform_device
*pdev
)
324 unsigned long long tmp
;
325 struct resource
*res
;
331 handle
= ACPI_HANDLE(&pdev
->dev
);
335 memset(&io
, 0, sizeof(io
));
336 io
.addr_source
= SI_ACPI
;
337 dev_info(&pdev
->dev
, "probing via ACPI\n");
339 io
.addr_info
.acpi_info
.acpi_handle
= handle
;
341 /* _IFT tells us the interface type: KCS, BT, etc */
342 status
= acpi_evaluate_integer(handle
, "_IFT", NULL
, &tmp
);
343 if (ACPI_FAILURE(status
)) {
345 "Could not find ACPI IPMI interface type\n");
354 io
.si_type
= SI_SMIC
;
359 case 4: /* SSIF, just ignore */
363 dev_info(&pdev
->dev
, "unknown IPMI type %lld\n", tmp
);
367 io
.regsize
= DEFAULT_REGSIZE
;
370 res
= ipmi_get_info_from_resources(pdev
, &io
);
376 /* If _GPE exists, use it; otherwise use standard interrupts */
377 status
= acpi_evaluate_integer(handle
, "_GPE", NULL
, &tmp
);
378 if (ACPI_SUCCESS(status
)) {
380 io
.irq_setup
= acpi_gpe_irq_setup
;
382 int irq
= platform_get_irq(pdev
, 0);
386 io
.irq_setup
= ipmi_std_irq_setup
;
390 io
.slave_addr
= find_slave_address(&io
, io
.slave_addr
);
394 dev_info(io
.dev
, "%pR regsize %d spacing %d irq %d\n",
395 res
, io
.regsize
, io
.regspacing
, io
.irq
);
397 return ipmi_si_add_smi(&io
);
403 static const struct acpi_device_id acpi_ipmi_match
[] = {
407 MODULE_DEVICE_TABLE(acpi
, acpi_ipmi_match
);
409 static int acpi_ipmi_probe(struct platform_device
*dev
)
415 static int ipmi_probe(struct platform_device
*pdev
)
417 if (pdev
->dev
.of_node
&& of_ipmi_probe(pdev
) == 0)
420 if (acpi_ipmi_probe(pdev
) == 0)
423 return platform_ipmi_probe(pdev
);
426 static int ipmi_remove(struct platform_device
*pdev
)
428 return ipmi_si_remove_by_dev(&pdev
->dev
);
431 static const struct platform_device_id si_plat_ids
[] = {
432 { "dmi-ipmi-si", 0 },
433 { "hardcode-ipmi-si", 0 },
437 struct platform_driver ipmi_platform_driver
= {
440 .of_match_table
= of_ipmi_match
,
441 .acpi_match_table
= ACPI_PTR(acpi_ipmi_match
),
444 .remove
= ipmi_remove
,
445 .id_table
= si_plat_ids
448 void ipmi_si_platform_init(void)
450 int rv
= platform_driver_register(&ipmi_platform_driver
);
452 pr_err("Unable to register driver: %d\n", rv
);
455 void ipmi_si_platform_shutdown(void)
457 platform_driver_unregister(&ipmi_platform_driver
);