platform_data in hest_parse_ghes() is used for saving the address of entry information of erst_tab. When the device is failed to be added, platform_data will be freed by platform_device_put(). But the value saved in platform_data should not be freed here. If it is done, it will make system panic. So I think platform_data should save the address of allocated memory which saves entry information of erst_tab. This patch fixed it and I confirmed it on x86_64 next-tree. Signed-off-by: Jin Dongming <jin.dongming@xxxxxxxxxxxxxxxxxx> --- drivers/acpi/apei/ghes.c | 2 +- drivers/acpi/apei/hest.c | 19 ++++++++++++++----- 2 files changed, 15 insertions(+), 6 deletions(-) diff --git a/drivers/acpi/apei/ghes.c b/drivers/acpi/apei/ghes.c index 385a605..b35c622 100644 --- a/drivers/acpi/apei/ghes.c +++ b/drivers/acpi/apei/ghes.c @@ -302,7 +302,7 @@ static int __devinit ghes_probe(struct platform_device *ghes_dev) struct ghes *ghes = NULL; int rc = -EINVAL; - generic = ghes_dev->dev.platform_data; + generic = *(struct acpi_hest_generic **)(ghes_dev->dev.platform_data); if (!generic->enabled) return -ENODEV; diff --git a/drivers/acpi/apei/hest.c b/drivers/acpi/apei/hest.c index 343168d..5a65e2a 100644 --- a/drivers/acpi/apei/hest.c +++ b/drivers/acpi/apei/hest.c @@ -137,20 +137,29 @@ static int hest_parse_ghes_count(struct acpi_hest_header *hest_hdr, void *data) static int hest_parse_ghes(struct acpi_hest_header *hest_hdr, void *data) { - struct acpi_hest_generic *generic; + void **platform_data; struct platform_device *ghes_dev; struct ghes_arr *ghes_arr = data; int rc; if (hest_hdr->type != ACPI_HEST_TYPE_GENERIC_ERROR) return 0; - generic = (struct acpi_hest_generic *)hest_hdr; - if (!generic->enabled) + + platform_data = kmalloc(sizeof(void *), GFP_KERNEL); + if (!platform_data) + return -ENOMEM; + + *platform_data = hest_hdr; + if (!((struct acpi_hest_generic *)*platform_data)->enabled) return 0; + ghes_dev = platform_device_alloc("GHES", hest_hdr->source_id); - if (!ghes_dev) + if (!ghes_dev) { + kfree(platform_data); return -ENOMEM; - ghes_dev->dev.platform_data = generic; + } + + ghes_dev->dev.platform_data = platform_data; rc = platform_device_add(ghes_dev); if (rc) goto err; -- 1.7.1.1 -- To unsubscribe from this list: send the line "unsubscribe linux-acpi" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html