Subversion Repositories Kolibri OS

Rev

Rev 1633 | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed

  1.  
  2. #include <ddk.h>
  3. #include <linux/errno.h>
  4. #include <mutex.h>
  5. #include <linux/spinlock.h>
  6. #include <pci.h>
  7. #include <syscall.h>
  8.  
  9. #include "acpi.h"
  10. #include "acpi_bus.h"
  11.  
  12. #define PREFIX "ACPI: "
  13.  
  14. struct acpi_prt_entry
  15. {
  16.     struct list_head    list;
  17.     ACPI_PCI_ID         id;
  18.     u8                  pin;
  19.     ACPI_HANDLE         link;
  20.     u32                 index;      /* GSI, or link _CRS index */
  21. };
  22.  
  23. static LIST_HEAD(acpi_prt_list);
  24. static DEFINE_SPINLOCK(acpi_prt_lock);
  25.  
  26. static inline char pin_name(int pin)
  27. {
  28.     return 'A' + pin - 1;
  29. }
  30.  
  31.  
  32. /* --------------------------------------------------------------------------
  33.                          PCI IRQ Routing Table (PRT) Support
  34.    -------------------------------------------------------------------------- */
  35.  
  36. static struct acpi_prt_entry *acpi_pci_irq_find_prt_entry(struct pci_dev *dev,
  37.                               int pin)
  38. {
  39.     struct acpi_prt_entry *entry;
  40.     int segment = pci_domain_nr(dev->bus);
  41.     int bus = dev->bus->number;
  42.     int device = PCI_SLOT(dev->devfn);
  43.  
  44.     spin_lock(&acpi_prt_lock);
  45.     list_for_each_entry(entry, &acpi_prt_list, list) {
  46.         if ((segment == entry->id.Segment)
  47.             && (bus == entry->id.Bus)
  48.             && (device == entry->id.Device)
  49.             && (pin == entry->pin)) {
  50.             spin_unlock(&acpi_prt_lock);
  51.             return entry;
  52.         }
  53.     }
  54.     spin_unlock(&acpi_prt_lock);
  55.     return NULL;
  56. }
  57.  
  58. static int acpi_pci_irq_add_entry(ACPI_HANDLE handle, struct pci_bus *bus,
  59.                   struct acpi_pci_routing_table *prt)
  60. {
  61.     struct acpi_prt_entry *entry;
  62.  
  63.     entry = kzalloc(sizeof(struct acpi_prt_entry), GFP_KERNEL);
  64.     if (!entry)
  65.         return -ENOMEM;
  66.  
  67.     /*
  68.      * Note that the _PRT uses 0=INTA, 1=INTB, etc, while PCI uses
  69.      * 1=INTA, 2=INTB.  We use the PCI encoding throughout, so convert
  70.      * it here.
  71.      */
  72.     entry->id.Segment = pci_domain_nr(bus);
  73.     entry->id.Bus = bus->number;
  74.     entry->id.Device = (prt->Address >> 16) & 0xFFFF;
  75.     entry->pin = prt->Pin + 1;
  76.  
  77. //    do_prt_fixups(entry, prt);
  78.  
  79.     entry->index = prt->SourceIndex;
  80.  
  81.     /*
  82.      * Type 1: Dynamic
  83.      * ---------------
  84.      * The 'source' field specifies the PCI interrupt link device used to
  85.      * configure the IRQ assigned to this slot|dev|pin.  The 'source_index'
  86.      * indicates which resource descriptor in the resource template (of
  87.      * the link device) this interrupt is allocated from.
  88.      *
  89.      * NOTE: Don't query the Link Device for IRQ information at this time
  90.      *       because Link Device enumeration may not have occurred yet
  91.      *       (e.g. exists somewhere 'below' this _PRT entry in the ACPI
  92.      *       namespace).
  93.      */
  94.     if (prt->Source[0])
  95.         AcpiGetHandle(handle, prt->Source, &entry->link);
  96.  
  97.     /*
  98.      * Type 2: Static
  99.      * --------------
  100.      * The 'source' field is NULL, and the 'source_index' field specifies
  101.      * the IRQ value, which is hardwired to specific interrupt inputs on
  102.      * the interrupt controller.
  103.      */
  104.  
  105.     dbgprintf(PREFIX "      %04x:%02x:%02x[%c] -> %s[%d]\n",
  106.                   entry->id.Segment, entry->id.Bus,
  107.                   entry->id.Device, pin_name(entry->pin),
  108.                   prt->Source, entry->index);
  109.  
  110.     spin_lock(&acpi_prt_lock);
  111.     list_add_tail(&entry->list, &acpi_prt_list);
  112.     spin_unlock(&acpi_prt_lock);
  113.  
  114.     return 0;
  115. }
  116.  
  117.  
  118.  
  119. int acpi_pci_irq_add_prt(ACPI_HANDLE handle, struct pci_bus *bus)
  120. {
  121.     ACPI_STATUS status;
  122.     struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL };
  123.     struct acpi_pci_routing_table *entry;
  124.  
  125.     /* 'handle' is the _PRT's parent (root bridge or PCI-PCI bridge) */
  126.     status = AcpiGetName(handle, ACPI_FULL_PATHNAME, &buffer);
  127.     if (ACPI_FAILURE(status))
  128.         return -ENODEV;
  129.  
  130.     printk(KERN_DEBUG "ACPI: PCI Interrupt Routing Table [%s._PRT]\n",
  131.            (char *) buffer.Pointer);
  132.  
  133.     kfree(buffer.Pointer);
  134.  
  135.     buffer.Length = ACPI_ALLOCATE_BUFFER;
  136.     buffer.Pointer = NULL;
  137.  
  138.     status = AcpiGetIrqRoutingTable(handle, &buffer);
  139.     if (ACPI_FAILURE(status))
  140.     {
  141.         dbgprintf("AcpiGetIrqRoutingTable failed "
  142.                   "evaluating _PRT [%s]\n",AcpiFormatException(status));
  143.         kfree(buffer.Pointer);
  144.         return -ENODEV;
  145.     }
  146.  
  147.     entry = buffer.Pointer;
  148.     while (entry && (entry->Length > 0)) {
  149.         acpi_pci_irq_add_entry(handle, bus, entry);
  150.         entry = (struct acpi_pci_routing_table *)
  151.             ((unsigned long)entry + entry->Length);
  152.     }
  153.  
  154.     kfree(buffer.Pointer);
  155.     return 0;
  156. }
  157.  
  158. static struct acpi_prt_entry *acpi_pci_irq_lookup(struct pci_dev *dev, int pin)
  159. {
  160.     struct acpi_prt_entry *entry;
  161.     struct pci_dev *bridge;
  162.     u8 bridge_pin, orig_pin = pin;
  163.  
  164.     entry = acpi_pci_irq_find_prt_entry(dev, pin);
  165.     if (entry) {
  166.         ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Found %s[%c] _PRT entry\n",
  167.                   pci_name(dev), pin_name(pin)));
  168.         return entry;
  169.     }
  170.  
  171.     /*
  172.      * Attempt to derive an IRQ for this device from a parent bridge's
  173.      * PCI interrupt routing entry (eg. yenta bridge and add-in card bridge).
  174.      */
  175.     bridge = dev->bus->self;
  176.     while (bridge)
  177.     {
  178.         pin = pci_swizzle_interrupt_pin(dev, pin);
  179.  
  180.         if ((bridge->class >> 8) == PCI_CLASS_BRIDGE_CARDBUS) {
  181.             /* PC card has the same IRQ as its cardbridge */
  182.             bridge_pin = bridge->pin;
  183.             if (!bridge_pin) {
  184.                 ACPI_DEBUG_PRINT((ACPI_DB_INFO,
  185.                           "No interrupt pin configured for device %s\n",
  186.                           pci_name(bridge)));
  187.                 return NULL;
  188.             }
  189.             pin = bridge_pin;
  190.         }
  191.  
  192.         entry = acpi_pci_irq_find_prt_entry(bridge, pin);
  193.         if (entry) {
  194.             ACPI_DEBUG_PRINT((ACPI_DB_INFO,
  195.                      "Derived GSI for %s INT %c from %s\n",
  196.                      pci_name(dev), pin_name(orig_pin),
  197.                      pci_name(bridge)));
  198.             return entry;
  199.         }
  200.  
  201.         dev = bridge;
  202.         bridge = dev->bus->self;
  203.     }
  204.  
  205.     dbgprintf("can't derive routing for PCI INT %c\n",
  206.          pin_name(orig_pin));
  207.     return NULL;
  208. }
  209.  
  210.  
  211. int acpi_get_irq(struct pci_dev *dev)
  212. {
  213.     struct acpi_prt_entry *entry;
  214.     int gsi = -1;
  215.     u8 pin;
  216.  
  217.     int triggering = ACPI_LEVEL_SENSITIVE;
  218.     int polarity = ACPI_ACTIVE_LOW;
  219.  
  220.     char *link = NULL;
  221.     char link_desc[16];
  222.     int rc;
  223.  
  224.     pin = dev->pin;
  225.  
  226.     if ( !pin )
  227.     {
  228.         dbgprintf("No interrupt pin configured for device %s\n",
  229.                   pci_name(dev));
  230.         return 0;
  231.     }
  232.  
  233.     entry = acpi_pci_irq_lookup(dev, pin);
  234.     if (!entry) {
  235.         /*
  236.          * IDE legacy mode controller IRQs are magic. Why do compat
  237.          * extensions always make such a nasty mess.
  238.          */
  239.         if (dev->class >> 8 == PCI_CLASS_STORAGE_IDE &&
  240.                 (dev->class & 0x05) == 0)
  241.             return 0;
  242.     }
  243.  
  244.     if (entry)
  245.     {
  246.         if (entry->link)
  247.         {
  248.             gsi = acpi_pci_link_allocate_irq(entry->link,
  249.                              entry->index,
  250.                              &triggering, &polarity,
  251.                              &link);
  252. //            dbgprintf("link not implemen\n");
  253.         }
  254.         else
  255.             gsi = entry->index;
  256.     } else
  257.         gsi = -1;
  258.  
  259. #if 0
  260.  
  261.     /*
  262.      * No IRQ known to the ACPI subsystem - maybe the BIOS /
  263.      * driver reported one, then use it. Exit in any case.
  264.      */
  265.     if (gsi < 0) {
  266.         u32 dev_gsi;
  267.         dev_warn(&dev->dev, "PCI INT %c: no GSI", pin_name(pin));
  268.         /* Interrupt Line values above 0xF are forbidden */
  269.         if (dev->irq > 0 && (dev->irq <= 0xF) &&
  270.             (acpi_isa_irq_to_gsi(dev->irq, &dev_gsi) == 0)) {
  271.             printk(" - using ISA IRQ %d\n", dev->irq);
  272.             acpi_register_gsi(&dev->dev, dev_gsi,
  273.                       ACPI_LEVEL_SENSITIVE,
  274.                       ACPI_ACTIVE_LOW);
  275.             return 0;
  276.         } else {
  277.             printk("\n");
  278.             return 0;
  279.         }
  280.     }
  281.  
  282.     rc = acpi_register_gsi(&dev->dev, gsi, triggering, polarity);
  283.     if (rc < 0) {
  284.         dev_warn(&dev->dev, "PCI INT %c: failed to register GSI\n",
  285.              pin_name(pin));
  286.         return rc;
  287.     }
  288.     dev->irq = rc;
  289.  
  290.     if (link)
  291.         snprintf(link_desc, sizeof(link_desc), " -> Link[%s]", link);
  292.     else
  293.         link_desc[0] = '\0';
  294.  
  295.     dev_info(&dev->dev, "PCI INT %c%s -> GSI %u (%s, %s) -> IRQ %d\n",
  296.          pin_name(pin), link_desc, gsi,
  297.          (triggering == ACPI_LEVEL_SENSITIVE) ? "level" : "edge",
  298.          (polarity == ACPI_ACTIVE_LOW) ? "low" : "high", dev->irq);
  299. #endif
  300.     return gsi;
  301. }
  302.  
  303.  
  304. #define ACPI_PCI_LINK_MAX_POSSIBLE  16
  305.  
  306. /*
  307.  * If a link is initialized, we never change its active and initialized
  308.  * later even the link is disable. Instead, we just repick the active irq
  309.  */
  310. struct acpi_pci_link_irq {
  311.     u8 active;      /* Current IRQ */
  312.     u8 triggering;      /* All IRQs */
  313.     u8 polarity;        /* All IRQs */
  314.     u8 resource_type;
  315.     u8 possible_count;
  316.     u8 possible[ACPI_PCI_LINK_MAX_POSSIBLE];
  317.     u8 initialized:1;
  318.     u8 reserved:7;
  319. };
  320.  
  321. struct acpi_pci_link {
  322.     struct list_head        list;
  323.     struct acpi_device      *device;
  324.     struct acpi_pci_link_irq    irq;
  325.     int             refcnt;
  326. };
  327.  
  328. static LIST_HEAD(acpi_link_list);
  329. static DEFINE_MUTEX(acpi_link_lock);
  330.  
  331.  
  332. static int acpi_pci_link_set(struct acpi_pci_link *link, int irq)
  333. {
  334.     int result;
  335.     ACPI_STATUS status;
  336.     struct {
  337.         struct acpi_resource res;
  338.         struct acpi_resource end;
  339.     } *resource;
  340.  
  341.     ACPI_BUFFER buffer = { 0, NULL };
  342.  
  343.     if (!irq)
  344.         return -EINVAL;
  345.  
  346.     resource = kzalloc(sizeof(*resource) + 1, GFP_KERNEL);
  347.     if (!resource)
  348.         return -ENOMEM;
  349.  
  350.     buffer.Length = sizeof(*resource) + 1;
  351.     buffer.Pointer = resource;
  352.  
  353.     switch (link->irq.resource_type) {
  354.     case ACPI_RESOURCE_TYPE_IRQ:
  355.         resource->res.Type = ACPI_RESOURCE_TYPE_IRQ;
  356.         resource->res.Length = sizeof(struct acpi_resource);
  357.         resource->res.Data.Irq.Triggering = link->irq.triggering;
  358.         resource->res.Data.Irq.Polarity =
  359.             link->irq.polarity;
  360.         if (link->irq.triggering == ACPI_EDGE_SENSITIVE)
  361.             resource->res.Data.Irq.Sharable =
  362.                 ACPI_EXCLUSIVE;
  363.         else
  364.             resource->res.Data.Irq.Sharable = ACPI_SHARED;
  365.         resource->res.Data.Irq.InterruptCount = 1;
  366.         resource->res.Data.Irq.Interrupts[0] = irq;
  367.         break;
  368.  
  369.     case ACPI_RESOURCE_TYPE_EXTENDED_IRQ:
  370.         resource->res.Type = ACPI_RESOURCE_TYPE_EXTENDED_IRQ;
  371.         resource->res.Length = sizeof(struct acpi_resource);
  372.         resource->res.Data.ExtendedIrq.ProducerConsumer =
  373.             ACPI_CONSUMER;
  374.         resource->res.Data.ExtendedIrq.Triggering =
  375.             link->irq.triggering;
  376.         resource->res.Data.ExtendedIrq.Polarity =
  377.             link->irq.polarity;
  378.         if (link->irq.triggering == ACPI_EDGE_SENSITIVE)
  379.             resource->res.Data.Irq.Sharable =
  380.                 ACPI_EXCLUSIVE;
  381.         else
  382.             resource->res.Data.Irq.Sharable = ACPI_SHARED;
  383.         resource->res.Data.ExtendedIrq.InterruptCount = 1;
  384.         resource->res.Data.ExtendedIrq.Interrupts[0] = irq;
  385.         /* ignore resource_source, it's optional */
  386.         break;
  387.     default:
  388.         printk(KERN_ERR PREFIX "Invalid Resource_type %d\n", link->irq.resource_type);
  389.         result = -EINVAL;
  390.         goto end;
  391.  
  392.     }
  393.     resource->end.Type = ACPI_RESOURCE_TYPE_END_TAG;
  394.  
  395. #if 0
  396.     /* Attempt to set the resource */
  397.     status = acpi_set_current_resources(link->device->handle, &buffer);
  398.  
  399.     /* check for total failure */
  400.     if (ACPI_FAILURE(status)) {
  401.         dbgprintf("%s failure Evaluating _SRS", __FUNCTION__);
  402.         result = -ENODEV;
  403.         goto end;
  404.     }
  405.  
  406.     /* Query _STA, set device->status */
  407.     result = acpi_bus_get_status(link->device);
  408.     if (result) {
  409.         printk(KERN_ERR PREFIX "Unable to read status\n");
  410.         goto end;
  411.     }
  412.     if (!link->device->status.enabled) {
  413.         printk(KERN_WARNING PREFIX
  414.                   "%s [%s] disabled and referenced, BIOS bug\n",
  415.                   acpi_device_name(link->device),
  416.                   acpi_device_bid(link->device));
  417.     }
  418.  
  419.     /* Query _CRS, set link->irq.active */
  420.     result = acpi_pci_link_get_current(link);
  421.     if (result) {
  422.         goto end;
  423.     }
  424.  
  425.     /*
  426.      * Is current setting not what we set?
  427.      * set link->irq.active
  428.      */
  429.     if (link->irq.active != irq) {
  430.         /*
  431.          * policy: when _CRS doesn't return what we just _SRS
  432.          * assume _SRS worked and override _CRS value.
  433.          */
  434.         printk(KERN_WARNING PREFIX
  435.                   "%s [%s] BIOS reported IRQ %d, using IRQ %d\n",
  436.                   acpi_device_name(link->device),
  437.                   acpi_device_bid(link->device), link->irq.active, irq);
  438.         link->irq.active = irq;
  439.     }
  440. #endif
  441.  
  442.     ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Set IRQ %d\n", link->irq.active));
  443.  
  444. end:
  445.     kfree(resource);
  446.     return result;
  447. }
  448.  
  449.  
  450.  
  451. #define ACPI_MAX_IRQS       256
  452. #define ACPI_MAX_ISA_IRQ    16
  453.  
  454. #define PIRQ_PENALTY_PCI_AVAILABLE  (0)
  455. #define PIRQ_PENALTY_PCI_POSSIBLE   (16*16)
  456. #define PIRQ_PENALTY_PCI_USING      (16*16*16)
  457. #define PIRQ_PENALTY_ISA_TYPICAL    (16*16*16*16)
  458. #define PIRQ_PENALTY_ISA_USED       (16*16*16*16*16)
  459. #define PIRQ_PENALTY_ISA_ALWAYS     (16*16*16*16*16*16)
  460.  
  461. static int acpi_irq_penalty[ACPI_MAX_IRQS] = {
  462.     PIRQ_PENALTY_ISA_ALWAYS,    /* IRQ0 timer */
  463.     PIRQ_PENALTY_ISA_ALWAYS,    /* IRQ1 keyboard */
  464.     PIRQ_PENALTY_ISA_ALWAYS,    /* IRQ2 cascade */
  465.     PIRQ_PENALTY_ISA_TYPICAL,   /* IRQ3 serial */
  466.     PIRQ_PENALTY_ISA_TYPICAL,   /* IRQ4 serial */
  467.     PIRQ_PENALTY_ISA_TYPICAL,   /* IRQ5 sometimes SoundBlaster */
  468.     PIRQ_PENALTY_ISA_TYPICAL,   /* IRQ6 */
  469.     PIRQ_PENALTY_ISA_TYPICAL,   /* IRQ7 parallel, spurious */
  470.     PIRQ_PENALTY_ISA_TYPICAL,   /* IRQ8 rtc, sometimes */
  471.     PIRQ_PENALTY_PCI_AVAILABLE, /* IRQ9  PCI, often acpi */
  472.     PIRQ_PENALTY_PCI_AVAILABLE, /* IRQ10 PCI */
  473.     PIRQ_PENALTY_PCI_AVAILABLE, /* IRQ11 PCI */
  474.     PIRQ_PENALTY_ISA_USED,      /* IRQ12 mouse */
  475.     PIRQ_PENALTY_ISA_USED,      /* IRQ13 fpe, sometimes */
  476.     PIRQ_PENALTY_ISA_USED,      /* IRQ14 ide0 */
  477.     PIRQ_PENALTY_ISA_USED,      /* IRQ15 ide1 */
  478.     /* >IRQ15 */
  479. };
  480.  
  481.  
  482.  
  483.  
  484. static int acpi_irq_balance = 0;
  485.  
  486. static int acpi_pci_link_allocate(struct acpi_pci_link *link)
  487. {
  488.     int irq;
  489.     int i;
  490.  
  491.     if (link->irq.initialized) {
  492.         if (link->refcnt == 0)
  493.             /* This means the link is disabled but initialized */
  494.             acpi_pci_link_set(link, link->irq.active);
  495.         return 0;
  496.     }
  497.  
  498.     /*
  499.      * search for active IRQ in list of possible IRQs.
  500.      */
  501.     for (i = 0; i < link->irq.possible_count; ++i) {
  502.         if (link->irq.active == link->irq.possible[i])
  503.             break;
  504.     }
  505.     /*
  506.      * forget active IRQ that is not in possible list
  507.      */
  508.     if (i == link->irq.possible_count) {
  509.         dbgprintf(KERN_WARNING PREFIX "_CRS %d not found"
  510.                       " in _PRS\n", link->irq.active);
  511.         link->irq.active = 0;
  512.     }
  513.  
  514.     /*
  515.      * if active found, use it; else pick entry from end of possible list.
  516.      */
  517.     if (link->irq.active)
  518.         irq = link->irq.active;
  519.     else
  520.         irq = link->irq.possible[link->irq.possible_count - 1];
  521.  
  522.     if (acpi_irq_balance || !link->irq.active) {
  523.         /*
  524.          * Select the best IRQ.  This is done in reverse to promote
  525.          * the use of IRQs 9, 10, 11, and >15.
  526.          */
  527.         for (i = (link->irq.possible_count - 1); i >= 0; i--) {
  528.             if (acpi_irq_penalty[irq] >
  529.                 acpi_irq_penalty[link->irq.possible[i]])
  530.                 irq = link->irq.possible[i];
  531.         }
  532.     }
  533.  
  534.     /* Attempt to enable the link device at this IRQ. */
  535.     if (acpi_pci_link_set(link, irq)) {
  536.         printk(KERN_ERR PREFIX "Unable to set IRQ for %s [%s]. "
  537.                 "Try pci=noacpi or acpi=off\n",
  538.                 acpi_device_name(link->device),
  539.                 acpi_device_bid(link->device));
  540.         return -ENODEV;
  541.     } else {
  542.         acpi_irq_penalty[link->irq.active] += PIRQ_PENALTY_PCI_USING;
  543.         printk(KERN_WARNING PREFIX "%s [%s] enabled at IRQ %d\n",
  544.                acpi_device_name(link->device),
  545.                acpi_device_bid(link->device), link->irq.active);
  546.     }
  547.  
  548.     link->irq.initialized = 1;
  549.     return 0;
  550. }
  551.  
  552.  
  553. /*
  554.  * acpi_pci_link_allocate_irq
  555.  * success: return IRQ >= 0
  556.  * failure: return -1
  557.  */
  558. int acpi_pci_link_allocate_irq(ACPI_HANDLE handle, int index,
  559.                                int *triggering, int *polarity, char **name)
  560. {
  561.     int result;
  562.     struct acpi_device *device;
  563.     struct acpi_pci_link *link;
  564.  
  565.     result = acpi_bus_get_device(handle, &device);
  566.     if (result) {
  567.         printk(KERN_ERR PREFIX "Invalid link device\n");
  568.         return -1;
  569.     }
  570.  
  571.     link = acpi_driver_data(device);
  572.     if (!link) {
  573.         printk(KERN_ERR PREFIX "Invalid link context\n");
  574.         return -1;
  575.     }
  576.  
  577.     /* TBD: Support multiple index (IRQ) entries per Link Device */
  578.     if (index) {
  579.         printk(KERN_ERR PREFIX "Invalid index %d\n", index);
  580.         return -1;
  581.     }
  582.  
  583.     mutex_lock(&acpi_link_lock);
  584.     if (acpi_pci_link_allocate(link)) {
  585.         mutex_unlock(&acpi_link_lock);
  586.         return -1;
  587.     }
  588.  
  589.     if (!link->irq.active) {
  590.         mutex_unlock(&acpi_link_lock);
  591.         printk(KERN_ERR PREFIX "Link active IRQ is 0!\n");
  592.         return -1;
  593.     }
  594.     link->refcnt++;
  595.     mutex_unlock(&acpi_link_lock);
  596.  
  597.     if (triggering)
  598.         *triggering = link->irq.triggering;
  599.     if (polarity)
  600.         *polarity = link->irq.polarity;
  601.     if (name)
  602.         *name = acpi_device_bid(link->device);
  603.     ACPI_DEBUG_PRINT((ACPI_DB_INFO,
  604.               "Link %s is referenced\n",
  605.               acpi_device_bid(link->device)));
  606.     return (link->irq.active);
  607. }
  608.  
  609.  
  610.