Page Menu
Home
FreeBSD
Search
Configure Global Search
Log In
Files
F131725114
D6634.id17077.diff
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Flag For Later
Award Token
Size
10 KB
Referenced Files
None
Subscribers
None
D6634.id17077.diff
View Options
Index: sys/arm/arm/nexus.c
===================================================================
--- sys/arm/arm/nexus.c
+++ sys/arm/arm/nexus.c
@@ -412,6 +412,10 @@
pcell_t *intr)
{
+#ifdef INTRNG
+ return (INTR_IRQ_INVALID);
+#else
return (intr_fdt_map_irq(iparent, intr, icells));
+#endif
}
#endif
Index: sys/dev/fdt/simplebus.c
===================================================================
--- sys/dev/fdt/simplebus.c
+++ sys/dev/fdt/simplebus.c
@@ -251,7 +251,9 @@
resource_list_init(&ndi->rl);
ofw_bus_reg_to_rl(dev, node, sc->acells, sc->scells, &ndi->rl);
+#ifndef INTRNG
ofw_bus_intr_to_rl(dev, node, &ndi->rl, NULL);
+#endif
return (ndi);
}
Index: sys/dev/gpio/ofw_gpiobus.c
===================================================================
--- sys/dev/gpio/ofw_gpiobus.c
+++ sys/dev/gpio/ofw_gpiobus.c
@@ -321,11 +321,13 @@
devi->pins[i] = pins[i].pin;
}
free(pins, M_DEVBUF);
+#ifndef INTRNG
/* Parse the interrupt resources. */
if (ofw_bus_intr_to_rl(bus, node, &dinfo->opd_dinfo.rl, NULL) != 0) {
ofw_gpiobus_destroy_devinfo(bus, dinfo);
return (NULL);
}
+#endif
device_set_ivars(child, dinfo);
return (dinfo);
Index: sys/dev/iicbus/ofw_iicbus.c
===================================================================
--- sys/dev/iicbus/ofw_iicbus.c
+++ sys/dev/iicbus/ofw_iicbus.c
@@ -187,8 +187,10 @@
childdev = device_add_child(dev, NULL, -1);
resource_list_init(&dinfo->opd_dinfo.rl);
+#ifndef INTRNG
ofw_bus_intr_to_rl(childdev, child,
&dinfo->opd_dinfo.rl, NULL);
+#endif
device_set_ivars(childdev, dinfo);
}
Index: sys/dev/ofw/ofw_bus_subr.h
===================================================================
--- sys/dev/ofw/ofw_bus_subr.h
+++ sys/dev/ofw/ofw_bus_subr.h
@@ -52,6 +52,13 @@
uintptr_t ocd_data;
};
+struct intr_map_data_fdt {
+ struct intr_map_data hdr;
+ phandle_t iparent;
+ u_int ncells;
+ pcell_t *cells;
+};
+
#define SIMPLEBUS_PNP_DESCR "Z:compat;P:private;"
#define SIMPLEBUS_PNP_INFO(t) \
MODULE_PNP_INFO(SIMPLEBUS_PNP_DESCR, simplebus, t, t, sizeof(t[0]), sizeof(t) / sizeof(t[0]));
@@ -82,7 +89,11 @@
/* Routines for parsing device-tree data into resource lists. */
int ofw_bus_reg_to_rl(device_t, phandle_t, pcell_t, pcell_t,
struct resource_list *);
+#ifndef INTRNG
int ofw_bus_intr_to_rl(device_t, phandle_t, struct resource_list *, int *);
+#endif
+int ofw_bus_intr_by_rid(device_t, phandle_t, int, phandle_t *, int *,
+ pcell_t **);
/* Helper to get device status property */
const char *ofw_bus_get_status(device_t dev);
Index: sys/dev/ofw/ofw_bus_subr.c
===================================================================
--- sys/dev/ofw/ofw_bus_subr.c
+++ sys/dev/ofw/ofw_bus_subr.c
@@ -516,6 +516,7 @@
return (iparent);
}
+#ifndef INTRNG
int
ofw_bus_intr_to_rl(device_t dev, phandle_t node,
struct resource_list *rl, int *rlen)
@@ -581,6 +582,78 @@
free(intr, M_OFWPROP);
return (err);
}
+#endif
+
+int
+ofw_bus_intr_by_rid(device_t dev, phandle_t node, int wanted_rid,
+ phandle_t *producer, int *ncells, pcell_t **cells)
+{
+ phandle_t iparent;
+ uint32_t icells, *intr;
+ int err, i, nintr, rid;
+ boolean_t extended;
+
+ nintr = OF_getencprop_alloc(node, "interrupts", sizeof(*intr),
+ (void **)&intr);
+ if (nintr > 0) {
+ iparent = ofw_bus_find_iparent(node);
+ if (iparent == 0) {
+ device_printf(dev, "No interrupt-parent found, "
+ "assuming direct parent\n");
+ iparent = OF_parent(node);
+ iparent = OF_xref_from_node(iparent);
+ }
+ if (OF_searchencprop(OF_node_from_xref(iparent),
+ "#interrupt-cells", &icells, sizeof(icells)) == -1) {
+ device_printf(dev, "Missing #interrupt-cells "
+ "property, assuming <1>\n");
+ icells = 1;
+ }
+ if (icells < 1 || icells > nintr) {
+ device_printf(dev, "Invalid #interrupt-cells property "
+ "value <%d>, assuming <1>\n", icells);
+ icells = 1;
+ }
+ extended = false;
+ } else {
+ nintr = OF_getencprop_alloc(node, "interrupts-extended",
+ sizeof(*intr), (void **)&intr);
+ if (nintr <= 0)
+ return (ESRCH);
+ extended = true;
+ }
+ err = ESRCH;
+ rid = 0;
+ for (i = 0; i < nintr; i += icells, rid++) {
+ if (extended) {
+ iparent = intr[i++];
+ if (OF_searchencprop(OF_node_from_xref(iparent),
+ "#interrupt-cells", &icells, sizeof(icells)) == -1) {
+ device_printf(dev, "Missing #interrupt-cells "
+ "property\n");
+ err = ENOENT;
+ break;
+ }
+ if (icells < 1 || (i + icells) > nintr) {
+ device_printf(dev, "Invalid #interrupt-cells "
+ "property value <%d>\n", icells);
+ err = ERANGE;
+ break;
+ }
+ }
+ if (rid == wanted_rid) {
+ *cells = malloc(icells * sizeof(**cells), M_OFWPROP,
+ M_WAITOK);
+ *producer = iparent;
+ *ncells= icells;
+ memcpy(*cells, intr + i, icells * sizeof(**cells));
+ err = 0;
+ break;
+ }
+ }
+ free(intr, M_OFWPROP);
+ return (err);
+}
phandle_t
ofw_bus_find_child(phandle_t start, const char *child_name)
Index: sys/dev/ofw/ofwbus.c
===================================================================
--- sys/dev/ofw/ofwbus.c
+++ sys/dev/ofw/ofwbus.c
@@ -43,6 +43,9 @@
#include <sys/module.h>
#include <sys/pcpu.h>
#include <sys/rman.h>
+#ifdef INTRNG
+#include <sys/intr.h>
+#endif
#include <vm/vm.h>
#include <vm/pmap.h>
@@ -77,6 +80,9 @@
static bus_alloc_resource_t ofwbus_alloc_resource;
static bus_adjust_resource_t ofwbus_adjust_resource;
static bus_release_resource_t ofwbus_release_resource;
+#ifdef INTRNG
+static bus_map_intr_t ofwbus_map_intr;
+#endif
static device_method_t ofwbus_methods[] = {
/* Device interface */
@@ -90,6 +96,9 @@
DEVMETHOD(bus_alloc_resource, ofwbus_alloc_resource),
DEVMETHOD(bus_adjust_resource, ofwbus_adjust_resource),
DEVMETHOD(bus_release_resource, ofwbus_release_resource),
+#ifdef INTRNG
+ DEVMETHOD(bus_map_intr, ofwbus_map_intr),
+#endif
DEVMETHOD_END
};
@@ -290,3 +299,53 @@
}
return (rman_release_resource(r));
}
+
+#ifdef INTRNG
+static void
+ofwbus_destruct_map_data(struct intr_map_data *map_data)
+{
+ struct intr_map_data_fdt *fdt_map_data;
+
+ KASSERT(map_data->type == INTR_MAP_DATA_FDT,
+ ("%s: bad map_data type %d", __func__, map_data->type));
+
+ fdt_map_data = (struct intr_map_data_fdt *)map_data;
+ OF_prop_free(fdt_map_data->cells);
+ free(fdt_map_data, M_OFWPROP);
+}
+
+static int
+ofwbus_map_intr(device_t bus, device_t child, int *rid, rman_res_t *start,
+ rman_res_t *end, rman_res_t *count, struct intr_map_data **imd)
+{
+ phandle_t iparent, node;
+ pcell_t *cells;
+ int ncells, rv;
+ u_int irq;
+ struct intr_map_data_fdt *fdt_data;
+
+ node = ofw_bus_get_node(child);
+ rv = ofw_bus_intr_by_rid(child, node, *rid, &iparent, &ncells, &cells);
+ if (rv != 0)
+ return (rv);
+
+ fdt_data = malloc(sizeof(*fdt_data), M_OFWPROP, M_WAITOK | M_ZERO);
+ fdt_data->hdr.type = INTR_MAP_DATA_FDT;
+ fdt_data->hdr.destruct = ofwbus_destruct_map_data;
+ fdt_data->iparent = iparent;
+ fdt_data->ncells = ncells;
+ fdt_data->cells = cells;
+ rv = intr_map_irq(NULL, iparent, (struct intr_map_data *)fdt_data,
+ &irq);
+ if (rv != 0) {
+ ofwbus_destruct_map_data((struct intr_map_data *)fdt_data);
+ return (rv);
+ }
+
+ *start = irq;
+ *end = irq;
+ *count = 1;
+ *imd = (struct intr_map_data *)fdt_data;
+ return (0);
+}
+#endif
Index: sys/kern/subr_intr.c
===================================================================
--- sys/kern/subr_intr.c
+++ sys/kern/subr_intr.c
@@ -64,12 +64,6 @@
#include <machine/smp.h>
#include <machine/stdarg.h>
-#ifdef FDT
-#include <dev/ofw/openfirm.h>
-#include <dev/ofw/ofw_bus.h>
-#include <dev/ofw/ofw_bus_subr.h>
-#endif
-
#ifdef DDB
#include <ddb/ddb.h>
#endif
@@ -591,33 +585,6 @@
return (ddata->idd_irq);
}
#endif
-#ifdef FDT
-/*
- * Map interrupt source according to FDT data into framework. If such mapping
- * does not exist, create it. Return unique interrupt number (resource handle)
- * associated with mapped interrupt source.
- */
-u_int
-intr_fdt_map_irq(phandle_t node, pcell_t *cells, u_int ncells)
-{
- size_t cellsize;
- struct intr_dev_data *ddata;
- struct intr_map_data_fdt *daf;
-
- cellsize = ncells * sizeof(*cells);
- ddata = intr_ddata_alloc(sizeof(struct intr_map_data_fdt) + cellsize);
- if (ddata == NULL)
- return (INTR_IRQ_INVALID); /* no space left */
-
- ddata->idd_xref = (intptr_t)node;
- ddata->idd_data->type = INTR_MAP_DATA_FDT;
-
- daf = (struct intr_map_data_fdt *)ddata->idd_data;
- daf->ncells = ncells;
- memcpy(daf->cells, cells, cellsize);
- return (ddata->idd_irq);
-}
-#endif
/*
* Store GPIO interrupt decription in framework and return unique interrupt
@@ -1034,7 +1001,11 @@
KASSERT(rman_get_start(res) == rman_get_end(res),
("%s: more interrupts in resource", __func__));
- isrc = intr_ddata_lookup(rman_get_start(res), &data);
+ data = rman_get_virtual(res);
+ if (data == NULL)
+ isrc = intr_ddata_lookup(rman_get_start(res), &data);
+ else
+ isrc = isrc_lookup(rman_get_start(res));
if (isrc == NULL)
return (EINVAL);
@@ -1050,7 +1021,11 @@
KASSERT(rman_get_start(res) == rman_get_end(res),
("%s: more interrupts in resource", __func__));
- isrc = intr_ddata_lookup(rman_get_start(res), &data);
+ data = rman_get_virtual(res);
+ if (data == NULL)
+ isrc = intr_ddata_lookup(rman_get_start(res), &data);
+ else
+ isrc = isrc_lookup(rman_get_start(res));
if (isrc == NULL)
return (EINVAL);
@@ -1069,7 +1044,11 @@
KASSERT(rman_get_start(res) == rman_get_end(res),
("%s: more interrupts in resource", __func__));
- isrc = intr_ddata_lookup(rman_get_start(res), &data);
+ data = rman_get_virtual(res);
+ if (data == NULL)
+ isrc = intr_ddata_lookup(rman_get_start(res), &data);
+ else
+ isrc = isrc_lookup(rman_get_start(res));
if (isrc == NULL)
return (EINVAL);
@@ -1129,7 +1108,11 @@
KASSERT(rman_get_start(res) == rman_get_end(res),
("%s: more interrupts in resource", __func__));
- isrc = intr_ddata_lookup(rman_get_start(res), &data);
+ data = rman_get_virtual(res);
+ if (data == NULL)
+ isrc = intr_ddata_lookup(rman_get_start(res), &data);
+ else
+ isrc = isrc_lookup(rman_get_start(res));
if (isrc == NULL || isrc->isrc_handlers == 0)
return (EINVAL);
Index: sys/sys/intr.h
===================================================================
--- sys/sys/intr.h
+++ sys/sys/intr.h
@@ -42,13 +42,6 @@
enum intr_trigger trig;
};
#endif
-#ifdef FDT
-struct intr_map_data_fdt {
- struct intr_map_data hdr;
- u_int ncells;
- pcell_t cells[0];
-};
-#endif
struct intr_map_data_gpio {
struct intr_map_data hdr;
@@ -129,9 +122,7 @@
u_int intr_acpi_map_irq(device_t, u_int, enum intr_polarity,
enum intr_trigger);
#endif
-#ifdef FDT
-u_int intr_fdt_map_irq(phandle_t, pcell_t *, u_int);
-#endif
+
u_int intr_gpio_map_irq(device_t dev, u_int pin_num, u_int pin_flags,
u_int intr_mode);
File Metadata
Details
Attached
Mime Type
text/plain
Expires
Sat, Oct 11, 4:18 PM (19 h, 50 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
23583748
Default Alt Text
D6634.id17077.diff (10 KB)
Attached To
Mode
D6634: INTRNG - rework FDT like interrupt mapping according to D6632
Attached
Detach File
Event Timeline
Log In to Comment