Changeset cfc149b in rtems-libbsd


Ignore:
Timestamp:
Jan 10, 2018, 1:11:57 PM (17 months ago)
Author:
Sebastian Huber <sebastian.huber@…>
Branches:
a87e0f4f5c4795f77dc3956c7d1543f90f7d7710, 16fa6a4651faaa77ef72c7e03d285c143d6e54fa
Children:
2fba1e4
Parents:
e4923c8
git-author:
Sebastian Huber <sebastian.huber@…> (01/10/18 13:11:57)
git-committer:
Sebastian Huber <sebastian.huber@…> (01/23/18 13:55:02)
Message:

linux/of_irq.h: Generalize of_irq_to_resource()

Determine interrupt cells via device tree.

Update #3277.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • rtemsbsd/sys/powerpc/compat.c

    re4923c8 rcfc149b  
    363363}
    364364
     365static int
     366get_interrupt_cells(const void *fdt, int node)
     367{
     368        do {
     369                const fdt32_t *p;
     370                int len;
     371
     372                p = fdt_getprop(fdt, node, "interrupt-parent", &len);
     373                if (p != NULL) {
     374                        if (len != sizeof(*p))
     375                                return (-EINVAL);
     376
     377                        node = fdt_node_offset_by_phandle(fdt,
     378                            fdt32_to_cpu(*p));
     379                } else {
     380                        node = fdt_parent_offset(fdt, node);
     381                }
     382
     383                p = fdt_getprop(fdt, node, "#interrupt-cells", &len);
     384                if (p != NULL) {
     385                        if (len != sizeof(*p))
     386                                return (-EINVAL);
     387
     388                        return ((int)fdt32_to_cpu(*p));
     389                }
     390        } while (node >= 0);
     391
     392        return (-EINVAL);
     393}
     394
    365395int
    366396of_irq_to_resource(struct device_node *dn, int index,
     
    369399        const void *fdt = bsp_fdt_get();
    370400        int len;
    371         const fdt32_t *p;
     401        uint32_t spec_buf[8];
     402        const fdt32_t *spec;
     403        int node;
     404        int ic;
    372405        int i;
     406        int j;
     407        int item_len;
    373408        int irq;
    374409
     
    376411                memset(res, 0, sizeof(*res));
    377412
    378         p = fdt_getprop(fdt, dn->offset, "interrupts", &len);
    379         if (p == NULL)
    380                 return (-EINVAL);
    381 
    382         i = index * 16;
    383         if (i + 16 > len)
    384                 return (-EINVAL);
    385 
    386         irq = (int)fdt32_to_cpu(p[i / sizeof(*p)]);
    387 #ifdef __PPC__
    388         /* FIXME */
    389         irq -= 16;
    390 #endif
     413        node = dn->offset;
     414
     415        spec = fdt_getprop(fdt, node, "interrupts", &len);
     416        if (spec == NULL)
     417                return (-EINVAL);
     418
     419        ic = get_interrupt_cells(fdt, node);
     420        if (ic < 0 || ic >= RTEMS_ARRAY_SIZE(spec_buf))
     421                return (EINVAL);
     422
     423        item_len = ic * 4;
     424        i = index * item_len;
     425        if (i + item_len > len)
     426                return (-EINVAL);
     427
     428        for (j = 0; j < ic; ++j)
     429                spec_buf[j] = fdt32_to_cpu(spec[i / sizeof(*spec)]);
     430
     431        irq = bsp_fdt_map_intr(spec_buf, (size_t)ic);
    391432
    392433        if (res != NULL) {
Note: See TracChangeset for help on using the changeset viewer.