lkml.org 
[lkml]   [2010]   [Mar]   [17]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    Subject[PATCH 1/3] hpet: convert to PNP driver
    From
    Date

    PNPACPI already parses _CRS, and does a more complete job than we did here,
    so let's just take advantage of that.

    Signed-off-by: Bjorn Helgaas <bjorn.helgaas@hp.com>
    ---

    drivers/char/hpet.c | 103 +++++++++++++--------------------------------------
    1 files changed, 27 insertions(+), 76 deletions(-)


    diff --git a/drivers/char/hpet.c b/drivers/char/hpet.c
    index e481c59..65a9aa8 100644
    --- a/drivers/char/hpet.c
    +++ b/drivers/char/hpet.c
    @@ -31,6 +31,7 @@
    #include <linux/seq_file.h>
    #include <linux/bitops.h>
    #include <linux/clocksource.h>
    +#include <linux/pnp.h>

    #include <asm/current.h>
    #include <asm/uaccess.h>
    @@ -40,7 +41,6 @@
    #include <asm/div64.h>

    #include <linux/acpi.h>
    -#include <acpi/acpi_bus.h>
    #include <linux/hpet.h>

    /*
    @@ -899,100 +899,53 @@ int hpet_alloc(struct hpet_data *hdp)
    return 0;
    }

    -static acpi_status hpet_resources(struct acpi_resource *res, void *data)
    +static int hpet_pnp_add(struct pnp_dev *dev, const struct pnp_device_id *dev_id)
    {
    - struct hpet_data *hdp;
    - acpi_status status;
    - struct acpi_resource_address64 addr;
    -
    - hdp = data;
    -
    - status = acpi_resource_to_address64(res, &addr);
    -
    - if (ACPI_SUCCESS(status)) {
    - hdp->hd_phys_address = addr.minimum;
    - hdp->hd_address = ioremap(addr.minimum, addr.address_length);
    -
    - if (hpet_is_known(hdp)) {
    - iounmap(hdp->hd_address);
    - return AE_ALREADY_EXISTS;
    - }
    - } else if (res->type == ACPI_RESOURCE_TYPE_FIXED_MEMORY32) {
    - struct acpi_resource_fixed_memory32 *fixmem32;
    -
    - fixmem32 = &res->data.fixed_memory32;
    - if (!fixmem32)
    - return AE_NO_MEMORY;
    + struct hpet_data data;
    + struct resource *mem, *irq;
    + int i;

    - hdp->hd_phys_address = fixmem32->address;
    - hdp->hd_address = ioremap(fixmem32->address,
    - HPET_RANGE_SIZE);
    + memset(&data, 0, sizeof(data));

    - if (hpet_is_known(hdp)) {
    - iounmap(hdp->hd_address);
    - return AE_ALREADY_EXISTS;
    - }
    - } else if (res->type == ACPI_RESOURCE_TYPE_EXTENDED_IRQ) {
    - struct acpi_resource_extended_irq *irqp;
    - int i, irq;
    + mem = pnp_get_resource(dev, IORESOURCE_MEM, 0);
    + if (!mem)
    + return -ENODEV;

    - irqp = &res->data.extended_irq;
    + data.hd_phys_address = mem->start;

    - for (i = 0; i < irqp->interrupt_count; i++) {
    - irq = acpi_register_gsi(NULL, irqp->interrupts[i],
    - irqp->triggering, irqp->polarity);
    - if (irq < 0)
    - return AE_ERROR;
    + if (hpet_is_known(&data))
    + return -EBUSY;

    - hdp->hd_irq[hdp->hd_nirqs] = irq;
    - hdp->hd_nirqs++;
    - }
    + i = 0;
    + while (data.hd_nirqs < ARRAY_SIZE(data.hd_irq)) {
    + irq = pnp_get_resource(dev, IORESOURCE_IRQ, i++);
    + if (pnp_resource_valid(irq) && pnp_resource_enabled(irq))
    + data.hd_irq[data.hd_nirqs++] = irq->start;
    }
    -
    - return AE_OK;
    -}
    -
    -static int hpet_acpi_add(struct acpi_device *device)
    -{
    - acpi_status result;
    - struct hpet_data data;
    -
    - memset(&data, 0, sizeof(data));
    -
    - result =
    - acpi_walk_resources(device->handle, METHOD_NAME__CRS,
    - hpet_resources, &data);
    -
    - if (ACPI_FAILURE(result))
    + if (!data.hd_nirqs)
    return -ENODEV;

    - if (!data.hd_address || !data.hd_nirqs) {
    - printk("%s: no address or irqs in _CRS\n", __func__);
    - return -ENODEV;
    - }
    + data.hd_address = ioremap(mem->start, resource_size(mem));

    return hpet_alloc(&data);
    }

    -static int hpet_acpi_remove(struct acpi_device *device, int type)
    +static void hpet_pnp_remove(struct pnp_dev *dev)
    {
    /* XXX need to unregister clocksource, dealloc mem, etc */
    - return -EINVAL;
    }

    -static const struct acpi_device_id hpet_device_ids[] = {
    +static const struct pnp_device_id hpet_device_ids[] = {
    {"PNP0103", 0},
    {"", 0},
    };
    MODULE_DEVICE_TABLE(acpi, hpet_device_ids);

    -static struct acpi_driver hpet_acpi_driver = {
    +static struct pnp_driver hpet_pnp_driver = {
    .name = "hpet",
    - .ids = hpet_device_ids,
    - .ops = {
    - .add = hpet_acpi_add,
    - .remove = hpet_acpi_remove,
    - },
    + .id_table = hpet_device_ids,
    + .probe = hpet_pnp_add,
    + .remove = hpet_pnp_remove,
    };

    static struct miscdevice hpet_misc = { HPET_MINOR, "hpet", &hpet_fops };
    @@ -1007,7 +960,7 @@ static int __init hpet_init(void)

    sysctl_header = register_sysctl_table(dev_root);

    - result = acpi_bus_register_driver(&hpet_acpi_driver);
    + result = pnp_register_driver(&hpet_pnp_driver);
    if (result < 0) {
    if (sysctl_header)
    unregister_sysctl_table(sysctl_header);
    @@ -1020,13 +973,11 @@ static int __init hpet_init(void)

    static void __exit hpet_exit(void)
    {
    - acpi_bus_unregister_driver(&hpet_acpi_driver);
    + pnp_unregister_driver(&hpet_pnp_driver);

    if (sysctl_header)
    unregister_sysctl_table(sysctl_header);
    misc_deregister(&hpet_misc);
    -
    - return;
    }

    module_init(hpet_init);


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