lkml.org 
[lkml]   [2010]   [Aug]   [16]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    Date
    From
    Subject[PATCH 4/4] [Patch-next] ACPI, APEI, HEST Fix the unsuitable usage of platform_data.
    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@np.css.fujitsu.com>
    ---
    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



    \
     
     \ /
      Last update: 2010-08-17 03:01    [W:0.028 / U:0.116 seconds]
    ©2003-2016 Jasper Spaans. hosted at Digital OceanAdvertise on this site