PERFORCE change 42354 for review

John Baldwin jhb at FreeBSD.org
Fri Nov 14 13:21:02 PST 2003


On 14-Nov-2003 Peter Wemm wrote:
> http://perforce.freebsd.org/chv.cgi?CH=42354
> 
> Change 42354 by peter at peter_daintree on 2003/11/14 11:00:47
> 
>       commit jhb's acpi_extirq.patch - remerging it all the time is driving me nuts.  I have
>       two different machines that need it now. :-/

Does this really help?  Do they actualyl route interrupts correctly when
they didn't before?  If so, I can commit the patch to CVS, or at least
parts of it.
 
> Affected files ...
> 
> .. //depot/projects/hammer/sys/dev/acpica/acpi_pci_link.c#7 edit
> .. //depot/projects/hammer/sys/dev/acpica/acpi_pcib.c#9 edit
> 
> Differences ...
> 
> ==== //depot/projects/hammer/sys/dev/acpica/acpi_pci_link.c#7 (text+ko) ====
> 
> @@ -43,7 +43,7 @@
>  #define _COMPONENT   ACPI_BUS
>  ACPI_MODULE_NAME("PCI_LINK")
>  
> -#define MAX_POSSIBLE_INTERRUPTS      16
> +#define MAX_POSSIBLE_INTERRUPTS      240
>  #define MAX_ISA_INTERRUPTS   16
>  #define MAX_ACPI_INTERRUPTS  255
>  
> @@ -87,10 +87,68 @@
>   */
>  
>  static void
> +acpi_pci_link_dump_polarity(UINT32 ActiveHighLow)
> +{
> +
> +     switch (ActiveHighLow) {
> +     case ACPI_ACTIVE_HIGH:
> +             printf("high,");
> +             break;
> +
> +     case ACPI_ACTIVE_LOW:
> +             printf("low,");
> +             break;
> +
> +     default:
> +             printf("unknown,");
> +             break;
> +     }
> +}
> +
> +static void
> +acpi_pci_link_dump_trigger(UINT32 EdgeLevel)
> +{
> +
> +     switch (EdgeLevel) {
> +     case ACPI_EDGE_SENSITIVE:
> +             printf("edge,");
> +             break;
> +
> +     case ACPI_LEVEL_SENSITIVE:
> +             printf("level,");
> +             break;
> +
> +     default:
> +             printf("unknown,");
> +             break;
> +     }
> +}
> +
> +static void
> +acpi_pci_link_dump_sharemode(UINT32 SharedExclusive)
> +{
> +
> +     switch (SharedExclusive) {
> +     case ACPI_EXCLUSIVE:
> +             printf("exclusive");
> +             break;
> +
> +     case ACPI_SHARED:
> +             printf("sharable");
> +             break;
> +
> +     default:
> +             printf("unknown");
> +             break;
> +     }
> +}
> +
> +static void
>  acpi_pci_link_entry_dump(struct acpi_prt_entry *entry)
>  {
>       UINT8                   i;
>       ACPI_RESOURCE_IRQ       *Irq;
> +     ACPI_RESOURCE_EXT_IRQ   *ExtIrq;
>  
>       if (entry == NULL || entry->pci_link == NULL) {
>               return;
> @@ -105,57 +163,21 @@
>       }
>       printf("] ");
>  
> -     Irq = NULL;
>       switch (entry->pci_link->possible_resources.Id) {
>       case ACPI_RSTYPE_IRQ:
>               Irq = &entry->pci_link->possible_resources.Data.Irq;
>  
> -             switch (Irq->ActiveHighLow) {
> -             case ACPI_ACTIVE_HIGH:
> -                     printf("high,");
> -                     break;
> -
> -             case ACPI_ACTIVE_LOW:
> -                     printf("low,");
> -                     break;
> -
> -             default:
> -                     printf("unknown,");
> -                     break;
> -             }
> -             
> -             switch (Irq->EdgeLevel) {
> -             case ACPI_EDGE_SENSITIVE:
> -                     printf("edge,");
> -                     break;
> -
> -             case ACPI_LEVEL_SENSITIVE:
> -                     printf("level,");
> -                     break;
> -
> -             default:
> -                     printf("unknown,");
> -                     break;
> -             }
> -
> -             switch (Irq->SharedExclusive) {
> -             case ACPI_EXCLUSIVE:
> -                     printf("exclusive");
> -                     break;
> -
> -             case ACPI_SHARED:
> -                     printf("sharable");
> -                     break;
> -
> -             default:
> -                     printf("unknown");
> -                     break;
> -             }
> -
> +             acpi_pci_link_dump_polarity(Irq->ActiveHighLow);
> +             acpi_pci_link_dump_trigger(Irq->EdgeLevel);
> +             acpi_pci_link_dump_sharemode(Irq->SharedExclusive);
>               break;
>  
>       case ACPI_RSTYPE_EXT_IRQ:
> -             /* TBD */
> +             ExtIrq = &entry->pci_link->possible_resources.Data.ExtendedIrq;
> +
> +             acpi_pci_link_dump_polarity(ExtIrq->ActiveHighLow);
> +             acpi_pci_link_dump_trigger(ExtIrq->EdgeLevel);
> +             acpi_pci_link_dump_sharemode(ExtIrq->SharedExclusive);
>               break;
>       }
>  
> @@ -527,10 +549,12 @@
>               }
>       }
>  
> +#if 0
>       /* allow initial IRQ as valid one. */
>       if (link->initial_irq == irq) {
>               return (1);
>       }
> +#endif
>  
>       return (0);
>  }
> @@ -565,34 +589,35 @@
>  
>       bzero(&resbuf, sizeof(resbuf));
>       crsbuf.Pointer = NULL;
> -     resbuf.Id = ACPI_RSTYPE_IRQ;
> -     resbuf.Length = ACPI_SIZEOF_RESOURCE(ACPI_RESOURCE_IRQ);
>  
> -     if (link->possible_resources.Id != ACPI_RSTYPE_IRQ &&
> -         link->possible_resources.Id != ACPI_RSTYPE_EXT_IRQ) {
> +     switch (link->possible_resources.Id) {
> +     default:
>               ACPI_DEBUG_PRINT((ACPI_DB_ERROR,
>                   "Resource is not an IRQ entry %s - %d\n",
>                   acpi_name(link->handle), link->possible_resources.Id));
>               return_ACPI_STATUS (AE_TYPE);
> -     }
>  
> -     switch (link->possible_resources.Id) {
>       case ACPI_RSTYPE_IRQ:
> +             resbuf.Id = ACPI_RSTYPE_IRQ;
> +             resbuf.Length = ACPI_SIZEOF_RESOURCE(ACPI_RESOURCE_IRQ);
> +
>               /* structure copy other fields */
>               resbuf.Data.Irq = link->possible_resources.Data.Irq;
> +             resbuf.Data.Irq.NumberOfInterrupts = 1;
> +             resbuf.Data.Irq.Interrupts[0] = irq;
>               break;
>  
>       case ACPI_RSTYPE_EXT_IRQ:
> -             /* XXX */
> -             resbuf.Data.Irq.EdgeLevel = ACPI_LEVEL_SENSITIVE;
> -             resbuf.Data.Irq.ActiveHighLow = ACPI_ACTIVE_LOW;
> -             resbuf.Data.Irq.SharedExclusive = ACPI_SHARED;
> +             resbuf.Id = ACPI_RSTYPE_EXT_IRQ;
> +             resbuf.Length = ACPI_SIZEOF_RESOURCE(ACPI_RESOURCE_EXT_IRQ);
> +
> +             /* structure copy other fields */
> +             resbuf.Data.ExtendedIrq = link->possible_resources.Data.ExtendedIrq;
> +             resbuf.Data.ExtendedIrq.NumberOfInterrupts = 1;
> +             resbuf.Data.ExtendedIrq.Interrupts[0] = irq;
>               break;
>       }
>  
> -     resbuf.Data.Irq.NumberOfInterrupts = 1;
> -     resbuf.Data.Irq.Interrupts[0] = irq;
> -
>       error = acpi_AppendBufferResource(&crsbuf, &resbuf);
>       if (ACPI_FAILURE(error)) {
>               ACPI_DEBUG_PRINT((ACPI_DB_ERROR,
> 
> ==== //depot/projects/hammer/sys/dev/acpica/acpi_pcib.c#9 (text+ko) ====
> 
> @@ -118,6 +118,8 @@
>      ACPI_DEVICE_INFO         devinfo;
>      ACPI_BUFFER                      buf = {sizeof(devinfo), &devinfo};
>      ACPI_STATUS                      status;
> +    UINT32                   NumberOfInterrupts;
> +    UINT32                   *Interrupts;
>      u_int8_t                 *prtp;
>      int                              interrupt;
>      int                              i;
> @@ -234,16 +236,25 @@
>      }
>  
>      /* type-check the resource we've got */
> -    if (crsres->Id != ACPI_RSTYPE_IRQ) {    /* XXX ACPI_RSTYPE_EXT_IRQ */
> +    if (crsres->Id != ACPI_RSTYPE_IRQ && crsres->Id != ACPI_RSTYPE_EXT_IRQ) {
>       device_printf(pcib, "_CRS resource entry has unsupported type %d\n",
>           crsres->Id);
>       goto out;
>      }
>  
> +    /* set variables based on resource type */
> +    if (crsres->Id == ACPI_RSTYPE_IRQ) {
> +     NumberOfInterrupts = crsres->Data.Irq.NumberOfInterrupts;
> +     Interrupts = crsres->Data.Irq.Interrupts;
> +    } else {
> +     NumberOfInterrupts = crsres->Data.ExtendedIrq.NumberOfInterrupts;
> +     Interrupts = crsres->Data.ExtendedIrq.Interrupts;
> +    }
> +
>      /* if there's more than one interrupt, we are confused */
> -    if (crsres->Data.Irq.NumberOfInterrupts > 1) {
> +    if (NumberOfInterrupts > 1) {
>       device_printf(pcib, "device has too many interrupts (%d)\n",
> -         crsres->Data.Irq.NumberOfInterrupts);
> +         NumberOfInterrupts);
>       goto out;
>      }
>  
> @@ -255,10 +266,10 @@
>       *
>       * XXX check ASL examples to see if this is an acceptable set of tests
>       */
> -    if ((crsres->Data.Irq.NumberOfInterrupts == 1) && (crsres->Data.Irq.Interrupts[0] != 0)) {
> +    if ((NumberOfInterrupts == 1) && (Interrupts[0] != 0)) {
>       device_printf(pcib, "slot %d INT%c is routed to irq %d\n",
> -         pci_get_slot(dev), 'A' + pin, crsres->Data.Irq.Interrupts[0]);
> -     interrupt = crsres->Data.Irq.Interrupts[0];
> +         pci_get_slot(dev), 'A' + pin, Interrupts[0]);
> +     interrupt = Interrupts[0];
>       goto out;
>      }
>      
> @@ -276,14 +287,23 @@
>      }
>  
>      /* type-check the resource we've got */
> -    if (prsres->Id != ACPI_RSTYPE_IRQ) {    /* XXX ACPI_RSTYPE_EXT_IRQ */
> +    if (prsres->Id != ACPI_RSTYPE_IRQ || prsres->Id != ACPI_RSTYPE_EXT_IRQ) {
>       device_printf(pcib, "_PRS resource entry has unsupported type %d\n",
>           prsres->Id);
>       goto out;
>      }
>  
> +    /* set variables based on resource type */
> +    if (prsres->Id == ACPI_RSTYPE_IRQ) {
> +     NumberOfInterrupts = prsres->Data.Irq.NumberOfInterrupts;
> +     Interrupts = prsres->Data.Irq.Interrupts;
> +    } else {
> +     NumberOfInterrupts = prsres->Data.ExtendedIrq.NumberOfInterrupts;
> +     Interrupts = prsres->Data.ExtendedIrq.Interrupts;
> +    }
> +
>      /* there has to be at least one interrupt available */
> -    if (prsres->Data.Irq.NumberOfInterrupts < 1) {
> +    if (NumberOfInterrupts < 1) {
>       device_printf(pcib, "device has no interrupts\n");
>       goto out;
>      }
> @@ -300,34 +320,41 @@
>       * new interrupt.
>       */
>      device_printf(pcib, "possible interrupts:");
> -    for (i = 0; i < prsres->Data.Irq.NumberOfInterrupts; i++)
> -     printf("  %d", prsres->Data.Irq.Interrupts[i]);
> +    for (i = 0; i < NumberOfInterrupts; i++)
> +     printf("  %d", Interrupts[i]);
>      printf("\n");
>  
>      if (crsbuf.Pointer != NULL)                      /* should never happen */
>       AcpiOsFree(crsbuf.Pointer);
>      crsbuf.Pointer = NULL;
> -    resbuf.Id = ACPI_RSTYPE_IRQ;
> -    resbuf.Length = ACPI_SIZEOF_RESOURCE(ACPI_RESOURCE_IRQ);
> -    resbuf.Data.Irq = prsres->Data.Irq;              /* structure copy other fields */
> -    resbuf.Data.Irq.NumberOfInterrupts = 1;
> -    resbuf.Data.Irq.Interrupts[0] = prsres->Data.Irq.Interrupts[0];  /* just take first... */
> +    if (prsres->Id == ACPI_RSTYPE_IRQ) {
> +     resbuf.Id = ACPI_RSTYPE_IRQ;
> +     resbuf.Length = ACPI_SIZEOF_RESOURCE(ACPI_RESOURCE_IRQ);
> +     resbuf.Data.Irq = prsres->Data.Irq;             /* structure copy other fields */
> +     resbuf.Data.Irq.NumberOfInterrupts = 1;
> +     resbuf.Data.Irq.Interrupts[0] = Interrupts[0];  /* just take first... */
> +    } else {
> +     resbuf.Id = ACPI_RSTYPE_EXT_IRQ;
> +     resbuf.Length = ACPI_SIZEOF_RESOURCE(ACPI_RESOURCE_IRQ);
> +     resbuf.Data.ExtendedIrq = prsres->Data.ExtendedIrq;     /* structure copy other fields */
> +     resbuf.Data.ExtendedIrq.NumberOfInterrupts = 1;
> +     resbuf.Data.ExtendedIrq.Interrupts[0] = Interrupts[0];  /* just take first... */
> +    }
>      if (ACPI_FAILURE(status = acpi_AppendBufferResource(&crsbuf, &resbuf))) {
>       device_printf(pcib, "couldn't route interrupt %d via %s, interrupt resource build failed -
> %s\n",
> -                   prsres->Data.Irq.Interrupts[0], acpi_name(lnkdev),
AcpiFormatException(status));
> +                   Interrupts[0], acpi_name(lnkdev), AcpiFormatException(status));
>       goto out;
>      }
>      if (ACPI_FAILURE(status = AcpiSetCurrentResources(lnkdev, &crsbuf))) {
>       device_printf(pcib, "couldn't route interrupt %d via %s - %s\n",
> -                   prsres->Data.Irq.Interrupts[0], acpi_name(lnkdev),
AcpiFormatException(status));
> +                   Interrupts[0], acpi_name(lnkdev), AcpiFormatException(status));
>       goto out;
>      }
>      
>      /* successful, return the interrupt we just routed */
>      device_printf(pcib, "slot %d INT%c routed to irq %d via %s\n", 
> -     pci_get_slot(dev), 'A' + pin, prsres->Data.Irq.Interrupts[0],
> -     acpi_name(lnkdev));
> -    interrupt = prsres->Data.Irq.Interrupts[0];
> +     pci_get_slot(dev), 'A' + pin, Interrupts[0], acpi_name(lnkdev));
> +    interrupt = Interrupts[0];
>  
>   out:
>      if (crsbuf.Pointer != NULL)

-- 

John Baldwin <jhb at FreeBSD.org>  <><  http://www.FreeBSD.org/~jhb/
"Power Users Use the Power to Serve!"  -  http://www.FreeBSD.org/


More information about the p4-projects mailing list