Skip to contentSkip to conversation

Hotplug for openfirmware/macio devices

PATCH In review Jeff Mahoney 1 participant 3 messages Sep 16, 2004

Subsystems (8)
Network drivers SCSI PowerPC Kbuild +4 more subsystems
lore
Share & tools
lore
#0 lore raw

PATCH 1/1 Hotplug for openfirmware/macio devices

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

Hey all -

Many devices on the macintosh hardware platform are hidden behind a macio asic that places devices beyond the PCI bus for hotplug. Loading the driver manually works fine, but we have this wonderful hotplug system now. Why should macio be a second class citizen?

At least for me, the most noticable one was my airport card, but there may be others. I only have an ibook and a powermac.

Attached are three patches, which do the following:
* kernel-of-hotplug.diff; against 2.6.9-rc2 (mainline)
~ - exports OF information to userspace
~ - removes struct of_device in favor of struct of_device_id, which

~    uses character arrays such that the structure can be more easily
~    used by module-init-tools [the renaming is required to use the
~    MODULE_DEVICE_TABLE macro]
~  - changes the semantics of OF_MATCH_ANY to be an empty string
~  - adds the name, type, and compat strings to the macio sysfs tree
~  - adds a hotplug filter to pass the name, type, and compat info

~ to hotplug
~ - adds the appropriate MODULE_DEVICE_TABLE entries so that
~ module-init-tools can know about macio devices
~ - (Yes, I know this information is available via /proc/device_tree,
~ but sysfs is a much more natural fit)
* hotplug-macio.diff
~ - macio.rc: handles coldplugging of devices by traversing
~ the macio sysfs tree
~ - macio.agent: handles macio hotplug events
* module-init-tools-3.0-pre10-openfirmware.diff
~ - adds support for a modules.ofmap table so that the hotplug scripts
~ can determine which modules to load based on the OF information.

Is there a limit for the length of the various OF strings? I've assumed 32 for the sake of testing, but it's completely arbitrary.

Take a look if you're interested. My familiarity with the PPC world is peripheral at best. I'd love feedback.

- -Jeff

- --
Jeff Mahoney
SuSE Labs
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.2.4 (GNU/Linux)
Comment: Using GnuPG with Thunderbird - http://enigmail.mozdev.org

iD8DBQFBSfKpLPWxlyuTD7IRAjogAJ0YN3ikH4Vdlc0HFL8VqmudfXdWPgCff6D6 8AwEoPW6w5nUGlzAiHmiq4I=
=pF7H
-----END PGP SIGNATURE-----

etc/hotplug/macio.rc new file +96 -0
@@ -0,0 +1,96 @@
+#!/bin/bash
+# $Id: ccw.rc,v 1.3 2004/05/13 11:59:50 hare Exp $
+# vim: syntax=sh
+#
+# macio.rc	configure macio devices.
+#
+
+SYSFS=needed
+cd /etc/hotplug
+. hotplug.functions
+
+if [ ! -d ${SYSFS}/bus/macio ]; then
+    echo "No macio bus support"
+    exit 0
+fi
+
+HWUP=/sbin/hwup
+macio_call_hotplug () {
+	# There may be /etc/hotplug.d/default/eventrecorder.hotplug
+	# that logs the environment of every hotplug events. Therefore
+	# we keep environment clean.
+#	echo " "\
+	eval \
+	$ENV \
+	${ACTION:+ ACTION=$ACTION} \
+	${DEVPATH:+ DEVPATH="$DEVPATH"} \
+	${OF_NAME:+ OF_NAME="$OF_NAME"} \
+	${OF_TYPE:+ OF_TYPE="$OF_TYPE"} \
+	${OF_COMPATIBLE:+ OF_COMPATIBLE="$OF_COMPATIBLE"} \
+	${HOTPLUG_TRACE:+ HOTPLUG_TRACE="$HOTPLUG_TRACE"} \
+	/sbin/hotplug macio \
+	< /dev/null > /dev/null 2>&1 & 
+}
+macio_boot_events_sysfs () {
+	cd /sys/bus/macio/devices
+	for i in *; do
+
+		if [ -d /sys/bus/macio/drivers/*/$i \
+			-a "$SKIP_DRIVEN_DEVICES" != no ]; then
+			echo -n . >&3
+		fi
+		OF_NAME=`cat $i/name`
+		OF_TYPE=`cat $i/type`
+                OF_COMPATIBLE=`cat $i/compatible`
+		DEVPATH=`cd $i/ ; /bin/pwd`
+		echo -n "*" >&3
+		macio_call_hotplug
+	done
+}
+
+macio_boot_events () {
+	macio_boot_events_sysfs
+}
+
+# See how we were called.
+case "$1" in
+  start)
+	ACTION=add
+	macio_boot_events;
+
+        # Configure all macio devices for which a hwcfg file is found
+	cd /etc/sysconfig/hardware
+        for cfg in hwcfg-bus-macio*; do
+            # Skip all symbolic links, only use the actual configuration
+            if [ -f "$cfg" -a ! -L "$cfg" ] ; then
+                cfgname=`echo $cfg | sed -n 's,hwcfg-.*-bus,bus,p;s,hwcfg-.*-id,id,p;s,hwcfg-bus,bus,p'`
+		if [ "$cfgname" ]; then
+		    debug_mesg "Calling ${HWUP} ${cfgname}"
+		    ${HWUP} ${cfgname}
+		    echo -n "*" >&3
+		else
+		    echo -n "." >&3
+		fi
+            fi
+        done
+
+	
+        ;;
+  stop)
+	# echo "$0 stop -- ignored"
+        ;;
+  status)
+	# echo "$0 status -- ignored"
+  	;;
+  status-verbose)
+	# echo "$0 status-verbose -- ignored"
+	;;
+  restart)
+	# always invoke by absolute path, else PATH=$PATH:
+	$0 stop && $0 start
+	;;
+  *)
+        echo $"Usage: $0 {start|stop|status[-verbose]|restart}"
+        exit 1
+	;;
+esac
etc/hotplug/macio.agent new file +84 -0

84 lines not on this page · raw message

module-init-tools-3.0-pre10/depmod.c +1 -0
diff -rup -x '.*.[^ch]' modutils-2.4.26/module-init-tools-3.0-pre10/depmod.c modutils-2.4.26.devel/module-init-tools-3.0-pre10/depmod.c
@@ -648,6 +648,7 @@ static struct depfile depfiles[] = {
 	{ "modules.ieee1394map", output_ieee1394_table },
 	{ "modules.isapnpmap", output_isapnp_table },
 	{ "modules.inputmap", output_input_table },
+	{ "modules.ofmap", output_of_table },
 	{ "modules.alias", output_aliases },
 	{ "modules.symbols", output_symbols },
 };
module-init-tools-3.0-pre10/depmod.h +2 -0
diff -rup -x '.*.[^ch]' modutils-2.4.26/module-init-tools-3.0-pre10/depmod.h modutils-2.4.26.devel/module-init-tools-3.0-pre10/depmod.h
@@ -47,6 +47,8 @@ struct module
 	void *pnp_card_table;
 	unsigned int input_size;
 	void *input_table;
+	unsigned int of_size;
+	void *of_table;
 
 	/* File contents and length. */
 	void *data;
module-init-tools-3.0-pre10/moduleops_core.c +5 -0
diff -rup -x '.*.[^ch]' modutils-2.4.26/module-init-tools-3.0-pre10/moduleops_core.c modutils-2.4.26.devel/module-init-tools-3.0-pre10/moduleops_core.c
@@ -192,6 +192,11 @@ static void PERBIT(fetch_tables)(struct 
 	module->input_size = PERBIT(INPUT_DEVICE_SIZE);
 	module->input_table = PERBIT(deref_sym)(module->data,
 					"__mod_input_device_table");
+
+	module->of_size = PERBIT(OF_DEVICE_SIZE);
+	module->of_table = PERBIT(deref_sym)(module->data,
+					"__mod_of_device_table");
+
 }
 
 struct module_ops PERBIT(mod_ops) = {
module-init-tools-3.0-pre10/tables.c +30 -0
diff -rup -x '.*.[^ch]' modutils-2.4.26/module-init-tools-3.0-pre10/tables.c modutils-2.4.26.devel/module-init-tools-3.0-pre10/tables.c
@@ -340,3 +340,33 @@ void output_input_table(struct module *m
 		}
 	}
 }
+
+/* We set driver_data to zero */
+static void output_of_entry(struct of_device_id *dev, char *name, FILE *out)
+{
+
+        fprintf (out, "%-20s %-20s %-20s %s\n",
+                name,
+                dev->name[0] ? dev->name : "*",
+                dev->type[0] ? dev->type : "*",
+                dev->compatible[0] ? dev->compatible : "*");
+}
+
+void output_of_table(struct module *modules, FILE *out)
+{
+	struct module *i;
+
+        fprintf (out, "# of module          name                 type                 compatible\n");                                 
+	for (i = modules; i; i = i->next) {
+		struct of_device_id *e;
+		char shortname[strlen(i->pathname) + 1];
+
+		if (!i->of_table)
+			continue;
+
+		make_shortname(shortname, i->pathname);
+		for (e = i->of_table; e->name[0]|e->type[0]|e->compatible[0];
+                     e = (void *)e + i->of_size)
+			output_of_entry(e, shortname, out);
+	}
+}
module-init-tools-3.0-pre10/tables.h +11 -0
diff -rup -x '.*.[^ch]' modutils-2.4.26/module-init-tools-3.0-pre10/tables.h modutils-2.4.26.devel/module-init-tools-3.0-pre10/tables.h
@@ -116,6 +116,16 @@ struct input_device_id_32 {
 #define INPUT_DEVICE_SIZE32 (4 + 4 * 2 + 4 + 16 * 4 + 4 + 2 * 4 + 4 + 4 + 4 + 4 * 4 + 4)
 #define INPUT_DEVICE_SIZE64 (8 + 4 * 2 + 8 + 8 * 8 + 8 + 8 + 8 + 8 + 8 + 2 * 8 + 8)
 
+#define MAX_OF_NAMELEN (32)
+struct of_device_id {
+	char name[MAX_OF_NAMELEN];
+	char type[MAX_OF_NAMELEN];
+	char compatible[MAX_OF_NAMELEN];
+};
+
+#define OF_DEVICE_SIZE32 (MAX_OF_NAMELEN * 3 + 4)
+#define OF_DEVICE_SIZE64 (MAX_OF_NAMELEN * 3 + 8)
+
 /* Functions provided by tables.c */
 struct module;
 void output_usb_table(struct module *modules, FILE *out);
@@ -124,5 +134,6 @@ void output_pci_table(struct module *mod
 void output_ccw_table(struct module *modules, FILE *out);
 void output_isapnp_table(struct module *modules, FILE *out);
 void output_input_table(struct module *modules, FILE *out);
+void output_of_table(struct module *modules, FILE *out);
 
 #endif /* MODINITTOOLS_TABLES_H */
arch/ppc/syslib/of_device.c +8 -7
diff -ruNpX dontdiff linux-2.6.8/arch/ppc/syslib/of_device.c linux-2.6.8.devel/arch/ppc/syslib/of_device.c
@@ -3,6 +3,7 @@
 #include <linux/kernel.h>
 #include <linux/init.h>
 #include <linux/module.h>
+#include <linux/mod_devicetable.h>
 #include <asm/errno.h>
 #include <asm/of_device.h>
 
@@ -15,20 +16,20 @@
  * Used by a driver to check whether an of_device present in the
  * system is in its list of supported devices.
  */
-const struct of_match * of_match_device(const struct of_match *matches,
+const struct of_device_id * of_match_device(const struct of_device_id *matches,
 					const struct of_device *dev)
 {
 	if (!dev->node)
 		return NULL;
-	while (matches->name || matches->type || matches->compatible) {
+	while (matches->name[0] || matches->type[0] || matches->compatible[0]) {
 		int match = 1;
-		if (matches->name && matches->name != OF_ANY_MATCH)
+		if (matches->name[0])
 			match &= dev->node->name
 				&& !strcmp(matches->name, dev->node->name);
-		if (matches->type && matches->type != OF_ANY_MATCH)
+		if (matches->type[0])
 			match &= dev->node->type
 				&& !strcmp(matches->type, dev->node->type);
-		if (matches->compatible && matches->compatible != OF_ANY_MATCH)
+		if (matches->compatible[0])
 			match &= device_is_compatible(dev->node,
 				matches->compatible);
 		if (match)
@@ -42,7 +43,7 @@ static int of_platform_bus_match(struct 
 {
 	struct of_device * of_dev = to_of_device(dev);
 	struct of_platform_driver * of_drv = to_of_platform_driver(drv);
-	const struct of_match * matches = of_drv->match_table;
+	const struct of_device_id * matches = of_drv->match_table;
 
 	if (!matches)
 		return 0;
@@ -75,7 +76,7 @@ static int of_device_probe(struct device
 	int error = -ENODEV;
 	struct of_platform_driver *drv;
 	struct of_device *of_dev;
-	const struct of_match *match;
+	const struct of_device_id *match;
 
 	drv = to_of_platform_driver(dev->driver);
 	of_dev = to_of_device(dev);
drivers/i2c/busses/i2c-keywest.c +3 -4
diff -ruNpX dontdiff linux-2.6.8/drivers/i2c/busses/i2c-keywest.c linux-2.6.8.devel/drivers/i2c/busses/i2c-keywest.c
@@ -694,7 +694,7 @@ dispose_iface(struct device *dev)
 }
 
 static int
-create_iface_macio(struct macio_dev* dev, const struct of_match *match)
+create_iface_macio(struct macio_dev* dev, const struct of_device_id *match)
 {
 	return create_iface(dev->ofdev.node, &dev->ofdev.dev);
 }
@@ -706,7 +706,7 @@ dispose_iface_macio(struct macio_dev* de
 }
 
 static int
-create_iface_of_platform(struct of_device* dev, const struct of_match *match)
+create_iface_of_platform(struct of_device* dev, const struct of_device_id *match)
 {
 	return create_iface(dev->node, &dev->dev);
 }
@@ -717,10 +717,9 @@ dispose_iface_of_platform(struct of_devi
 	return dispose_iface(&dev->dev);
 }
 
-static struct of_match i2c_keywest_match[] = 
+static struct of_device_id i2c_keywest_match[] = 
 {
 	{
-	.name 		= OF_ANY_MATCH,
 	.type		= "i2c",
 	.compatible	= "keywest"
 	},
drivers/ide/ppc/pmac.c +2 -10
diff -ruNpX dontdiff linux-2.6.8/drivers/ide/ppc/pmac.c linux-2.6.8.devel/drivers/ide/ppc/pmac.c
@@ -1279,7 +1279,7 @@ pmac_ide_setup_device(pmac_ide_hwif_t *p
  * Attach to a macio probed interface
  */
 static int __devinit
-pmac_ide_macio_attach(struct macio_dev *mdev, const struct of_match *match)
+pmac_ide_macio_attach(struct macio_dev *mdev, const struct of_device_id *match)
 {
 	unsigned long base, regbase;
 	int irq;
@@ -1500,27 +1500,19 @@ pmac_ide_pci_resume(struct pci_dev *pdev
 	return rc;
 }
 
-static struct of_match pmac_ide_macio_match[] = 
+static struct of_device_id pmac_ide_macio_match[] = 
 {
 	{
 	.name 		= "IDE",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH
 	},
 	{
 	.name 		= "ATA",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH
 	},
 	{
-	.name 		= OF_ANY_MATCH,
 	.type		= "ide",
-	.compatible	= OF_ANY_MATCH
 	},
 	{
-	.name 		= OF_ANY_MATCH,
 	.type		= "ata",
-	.compatible	= OF_ANY_MATCH
 	},
 	{},
 };
drivers/macintosh/macio_asic.c +71 -2

96 lines not on this page · raw message

drivers/macintosh/macio_sysfs.c +49 -0

49 lines not on this page · raw message

drivers/macintosh/Makefile +1 -1
diff -ruNpX dontdiff linux-2.6.8/drivers/macintosh/Makefile linux-2.6.8.devel/drivers/macintosh/Makefile
@@ -4,7 +4,7 @@
 
 # Each configuration option enables a list of files.
 
-obj-$(CONFIG_PPC_PMAC)		+= macio_asic.o
+obj-$(CONFIG_PPC_PMAC)		+= macio_asic.o macio_sysfs.o
 
 obj-$(CONFIG_PMAC_PBOOK)	+= mediabay.o
 obj-$(CONFIG_MAC_SERIAL)	+= macserial.o
drivers/macintosh/mediabay.c +2 -5
diff -ruNpX dontdiff linux-2.6.8/drivers/macintosh/mediabay.c linux-2.6.8.devel/drivers/macintosh/mediabay.c
@@ -648,7 +648,7 @@ static int __pmac media_bay_task(void *x
 	}
 }
 
-static int __devinit media_bay_attach(struct macio_dev *mdev, const struct of_match *match)
+static int __devinit media_bay_attach(struct macio_dev *mdev, const struct of_device_id *match)
 {
 	struct media_bay_info* bay;
 	volatile u32 *regbase;
@@ -802,23 +802,20 @@ static struct mb_ops keylargo_mb_ops __p
  * Therefore we do it all by polling the media bay once each tick.
  */
 
-static struct of_match media_bay_match[] =
+static struct of_device_id media_bay_match[] =
 {
 	{
 	.name		= "media-bay",
-	.type		= OF_ANY_MATCH,
 	.compatible	= "keylargo-media-bay",
 	.data		= &keylargo_mb_ops,
 	},
 	{
 	.name		= "media-bay",
-	.type		= OF_ANY_MATCH,
 	.compatible	= "heathrow-media-bay",
 	.data		= &heathrow_mb_ops,
 	},
 	{
 	.name		= "media-bay",
-	.type		= OF_ANY_MATCH,
 	.compatible	= "ohare-media-bay",
 	.data		= &ohare_mb_ops,
 	},
drivers/macintosh/therm_windtunnel.c +3 -3
diff -ruNpX dontdiff linux-2.6.8/drivers/macintosh/therm_windtunnel.c linux-2.6.8.devel/drivers/macintosh/therm_windtunnel.c
@@ -43,6 +43,7 @@
 #include <asm/system.h>
 #include <asm/sections.h>
 #include <asm/of_device.h>
+#include <asm/macio.h>
 
 #define LOG_TEMP		0			/* continously log temperature */
 
@@ -453,7 +454,7 @@ do_probe( struct i2c_adapter *adapter, i
 /************************************************************************/
 
 static int
-therm_of_probe( struct of_device *dev, const struct of_match *match )
+therm_of_probe( struct of_device *dev, const struct of_device_id *match )
 {
 	return i2c_add_driver( &g4fan_driver );
 }
@@ -464,9 +465,8 @@ therm_of_remove( struct of_device *dev )
 	return i2c_del_driver( &g4fan_driver );
 }
 
-static struct of_match therm_of_match[] = {{
+static struct of_device_id therm_of_match[] = {{
 	.name		= "fan",
-	.type		= OF_ANY_MATCH,
 	.compatible	= "adm1030"
     }, {}
 };
drivers/net/wireless/airport.c +4 -4
diff -ruNpX dontdiff linux-2.6.8/drivers/net/wireless/airport.c linux-2.6.8.devel/drivers/net/wireless/airport.c
@@ -188,7 +188,7 @@ static int airport_hard_reset(struct ori
 }
 
 static int
-airport_attach(struct macio_dev *mdev, const struct of_match *match)
+airport_attach(struct macio_dev *mdev, const struct of_device_id *match)
 {
 	struct orinoco_private *priv;
 	struct net_device *dev;
@@ -272,16 +272,16 @@ MODULE_AUTHOR("Benjamin Herrenschmidt <b
 MODULE_DESCRIPTION("Driver for the Apple Airport wireless card.");
 MODULE_LICENSE("Dual MPL/GPL");
 
-static struct of_match airport_match[] = 
+static struct of_device_id airport_match[] = 
 {
 	{
 	.name 		= "radio",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH
 	},
 	{},
 };
 
+MODULE_DEVICE_TABLE (of, airport_match);
+
 static struct macio_driver airport_driver = 
 {
 	.name 		= DRIVER_NAME,

Files linux-2.6.8/drivers/pci/gen-devlist and linux-2.6.8.devel/drivers/pci/gen-devlist differ

drivers/scsi/mac53c94.c +3 -4
diff -ruNpX dontdiff linux-2.6.8/drivers/scsi/mac53c94.c linux-2.6.8.devel/drivers/scsi/mac53c94.c
@@ -425,7 +425,7 @@ static struct scsi_host_template mac53c9
 	.use_clustering	= DISABLE_CLUSTERING,
 };
 
-static int mac53c94_probe(struct macio_dev *mdev, const struct of_match *match)
+static int mac53c94_probe(struct macio_dev *mdev, const struct of_device_id *match)
 {
 	struct device_node *node = macio_get_of_node(mdev);
 	struct pci_dev *pdev = macio_get_pci_dev(mdev);
@@ -545,15 +545,14 @@ static int mac53c94_remove(struct macio_
 }
 
 
-static struct of_match mac53c94_match[] = 
+static struct of_device_id mac53c94_match[] = 
 {
 	{
 	.name 		= "53c94",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH
 	},
 	{},
 };
+MODULE_DEVICE_TABLE (of, mac53c94_match);
 
 static struct macio_driver mac53c94_driver = 
 {
drivers/scsi/mesh.c +3 -5
diff -ruNpX dontdiff linux-2.6.8/drivers/scsi/mesh.c linux-2.6.8.devel/drivers/scsi/mesh.c
@@ -1847,7 +1847,7 @@ static struct scsi_host_template mesh_te
 	.use_clustering			= DISABLE_CLUSTERING,
 };
 
-static int mesh_probe(struct macio_dev *mdev, const struct of_match *match)
+static int mesh_probe(struct macio_dev *mdev, const struct of_device_id *match)
 {
 	struct device_node *mesh = macio_get_of_node(mdev);
 	struct pci_dev* pdev = macio_get_pci_dev(mdev);
@@ -2014,20 +2014,18 @@ static int mesh_remove(struct macio_dev 
 }
 
 
-static struct of_match mesh_match[] = 
+static struct of_device_id mesh_match[] = 
 {
 	{
 	.name 		= "mesh",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH
 	},
 	{
-	.name 		= OF_ANY_MATCH,
 	.type		= "scsi",
 	.compatible	= "chrp,mesh0"
 	},
 	{},
 };
+MODULE_DEVICE_TABLE (of, mesh_match);
 
 static struct macio_driver mesh_driver = 
 {
drivers/serial/pmac_zilog.c +3 -6
diff -ruNpX dontdiff linux-2.6.8/drivers/serial/pmac_zilog.c linux-2.6.8.devel/drivers/serial/pmac_zilog.c
@@ -1520,7 +1520,7 @@ static void pmz_dispose_port(struct uart
 /*
  * Called upon match with an escc node in the devive-tree.
  */
-static int pmz_attach(struct macio_dev *mdev, const struct of_match *match)
+static int pmz_attach(struct macio_dev *mdev, const struct of_device_id *match)
 {
 	int i;
 	
@@ -1826,20 +1826,17 @@ err_out:
 	return rc;
 }
 
-static struct of_match pmz_match[] = 
+static struct of_device_id pmz_match[] = 
 {
 	{
 	.name 		= "ch-a",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH
 	},
 	{
 	.name 		= "ch-b",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH
 	},
 	{},
 };
+MODULE_DEVICE_TABLE (of, pmz_match);
 
 static struct macio_driver pmz_driver = 
 {
include/asm-ppc/macio.h +3 -2
diff -ruNpX dontdiff linux-2.6.8/include/asm-ppc/macio.h linux-2.6.8.devel/include/asm-ppc/macio.h
@@ -1,6 +1,7 @@
 #ifndef __MACIO_ASIC_H__
 #define __MACIO_ASIC_H__
 
+#include <linux/mod_devicetable.h>
 #include <asm/of_device.h>
 
 extern struct bus_type macio_bus_type;
@@ -120,10 +121,10 @@ static inline struct pci_dev *macio_get_
 struct macio_driver
 {
 	char			*name;
-	struct of_match		*match_table;
+	struct of_device_id	*match_table;
 	struct module		*owner;
 
-	int	(*probe)(struct macio_dev* dev, const struct of_match *match);
+	int	(*probe)(struct macio_dev* dev, const struct of_device_id *match);
 	int	(*remove)(struct macio_dev* dev);
 
 	int	(*suspend)(struct macio_dev* dev, u32 state);
include/asm-ppc/of_device.h +4 -16
diff -ruNpX dontdiff linux-2.6.8/include/asm-ppc/of_device.h linux-2.6.8.devel/include/asm-ppc/of_device.h
@@ -24,20 +24,8 @@ struct of_device
 };
 #define	to_of_device(d) container_of(d, struct of_device, dev)
 
-/*
- * Struct used for matching a device
- */
-struct of_match
-{
-	char	*name;
-	char	*type;
-	char	*compatible;
-	void	*data;
-};
-#define OF_ANY_MATCH		((char *)-1L)
-
-extern const struct of_match *of_match_device(
-	const struct of_match *matches, const struct of_device *dev);
+extern const struct of_device_id *of_match_device(
+	const struct of_device_id *matches, const struct of_device *dev);
 
 extern struct of_device *of_dev_get(struct of_device *dev);
 extern void of_dev_put(struct of_device *dev);
@@ -49,10 +37,10 @@ extern void of_dev_put(struct of_device 
 struct of_platform_driver
 {
 	char			*name;
-	struct of_match		*match_table;
+	struct of_device_id	*match_table;
 	struct module		*owner;
 
-	int	(*probe)(struct of_device* dev, const struct of_match *match);
+	int	(*probe)(struct of_device* dev, const struct of_device_id *match);
 	int	(*remove)(struct of_device* dev);
 
 	int	(*suspend)(struct of_device* dev, u32 state);
include/linux/mod_devicetable.h +11 -0
diff -ruNpX dontdiff linux-2.6.8/include/linux/mod_devicetable.h linux-2.6.8.devel/include/linux/mod_devicetable.h
@@ -164,5 +164,16 @@ struct pnp_card_device_id {
 	} devs[PNP_MAX_DEVICES];
 };
 
+/*
+ * Struct used for matching a device
+ */
+struct of_device_id
+{
+	char	name[32];
+	char	type[32];
+	char	compatible[32];
+	void	*data;
+};
+
 
 #endif /* LINUX_MOD_DEVICETABLE_H */
scripts/mod/file2alias.c +13 -0
diff -ruNpX dontdiff linux-2.6.8/scripts/mod/file2alias.c linux-2.6.8.devel/scripts/mod/file2alias.c
@@ -199,6 +199,15 @@ static int do_pnp_card_entry(const char 
 	return 1;
 }
 
+static int do_macio_entry (const char *filename, struct of_device_id *of, char *alias)
+{
+    sprintf (alias, "macio:N%sT%sC%s",
+                    of->name[0] ? of->name : "*",
+                    of->type[0] ? of->type : "*",
+                    of->compatible[0] ? of->compatible : "*");
+    return 1;
+}
+
 /* Ignore any prefix, eg. v850 prepends _ */
 static inline int sym_is(const char *symbol, const char *name)
 {
@@ -271,6 +280,10 @@ void handle_moddevtable(struct module *m
 	else if (sym_is(symname, "__mod_pnp_card_device_table"))
 		do_table(symval, sym->st_size, sizeof(struct pnp_card_device_id),
 			 do_pnp_card_entry, mod);
+        else if (sym_is(symname, "__mod_macio_device_table"))
+		do_table(symval, sym->st_size, sizeof(struct of_device_id),
+			 do_macio_entry, mod);
+
 }
 
 /* Now add out buffered information to the generated C source */
#1 lore raw

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

Jeff Mahoney wrote:

|
| Hey all -
|
| Many devices on the macintosh hardware platform are hidden behind a
| macio asic that places devices beyond the PCI bus for hotplug. Loading
| the driver manually works fine, but we have this wonderful hotplug
| system now. Why should macio be a second class citizen?
|
| At least for me, the most noticable one was my airport card, but there
| may be others. I only have an ibook and a powermac.
|
| Attached are three patches, which do the following:
| * kernel-of-hotplug.diff; against 2.6.9-rc2 (mainline)

| Take a look if you're interested. My familiarity with the PPC world is | peripheral at best. I'd love feedback.

As a quick note, it's been pointed out to me that some of the drivers won't compile as is.

I only compile tested with the drivers I use, so stuff slipped by. I'll have an updated kernel patch in a little bit.

- -Jeff

- --
Jeff Mahoney
SuSE Labs
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.2.4 (GNU/Linux)
Comment: Using GnuPG with Thunderbird - http://enigmail.mozdev.org

iD8DBQFBSgEeLPWxlyuTD7IRArijAJwOG/8WGId3foGajgKTu3/s4gRJMQCePHMq CggbvmovKdA0YBkED6aLkJs=
=6pUe
-----END PGP SIGNATURE-----

#2 lore raw
In reply to Jeff Mahoney

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

Jeff Mahoney wrote:

|
| Hey all -
|
| Many devices on the macintosh hardware platform are hidden behind a
| macio asic that places devices beyond the PCI bus for hotplug. Loading
| the driver manually works fine, but we have this wonderful hotplug
| system now. Why should macio be a second class citizen?
|
| At least for me, the most noticable one was my airport card, but there
| may be others. I only have an ibook and a powermac.
|
| Attached are three patches, which do the following:
| * kernel-of-hotplug.diff; against 2.6.9-rc2 (mainline)
| ~  - exports OF information to userspace
| ~  - removes struct of_device in favor of struct of_device_id, which
| ~    uses character arrays such that the structure can be more easily
| ~    used by module-init-tools [the renaming is required to use the
| ~    MODULE_DEVICE_TABLE macro]
| ~  - changes the semantics of OF_MATCH_ANY to be an empty string
| ~  - adds the name, type, and compat strings to the macio sysfs tree
| ~  - adds a hotplug filter to pass the name, type, and compat info
| ~    to hotplug
| ~  - adds the appropriate MODULE_DEVICE_TABLE entries so that
| ~    module-init-tools can know about macio devices
| ~  - (Yes, I know this information is available via /proc/device_tree,
| ~     but sysfs is a much more natural fit)
| * hotplug-macio.diff
| ~  - macio.rc: handles coldplugging of devices by traversing
| ~    the macio sysfs tree
| ~  - macio.agent: handles macio hotplug events
| * module-init-tools-3.0-pre10-openfirmware.diff
| ~  - adds support for a modules.ofmap table so that the hotplug scripts
| ~    can determine which modules to load based on the OF information.
|
| Is there a limit for the length of the various OF strings? I've assumed
| 32 for the sake of testing, but it's completely arbitrary.
|
| Take a look if you're interested. My familiarity with the PPC world is
| peripheral at best. I'd love feedback.

As promised, updated kernel patch.

- -Jeff

- --
Jeff Mahoney
SuSE Labs
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.2.4 (GNU/Linux)
Comment: Using GnuPG with Thunderbird - http://enigmail.mozdev.org

iD8DBQFBShNkLPWxlyuTD7IRAioJAJsFWzAyp3AbXLd8Q7c2VQVYOMt4EwCeLGF2 /fUIjnQUXqJHPK4H9CeUI4k=
=HFZy
-----END PGP SIGNATURE-----

arch/ppc/syslib/of_device.c +8 -7
diff -rupN -X dontdiff linux-2.6.8/arch/ppc/syslib/of_device.c linux-2.6.8.devel/arch/ppc/syslib/of_device.c
@@ -3,6 +3,7 @@
 #include <linux/kernel.h>
 #include <linux/init.h>
 #include <linux/module.h>
+#include <linux/mod_devicetable.h>
 #include <asm/errno.h>
 #include <asm/of_device.h>
 
@@ -15,20 +16,20 @@
  * Used by a driver to check whether an of_device present in the
  * system is in its list of supported devices.
  */
-const struct of_match * of_match_device(const struct of_match *matches,
+const struct of_device_id * of_match_device(const struct of_device_id *matches,
 					const struct of_device *dev)
 {
 	if (!dev->node)
 		return NULL;
-	while (matches->name || matches->type || matches->compatible) {
+	while (matches->name[0] || matches->type[0] || matches->compatible[0]) {
 		int match = 1;
-		if (matches->name && matches->name != OF_ANY_MATCH)
+		if (matches->name[0])
 			match &= dev->node->name
 				&& !strcmp(matches->name, dev->node->name);
-		if (matches->type && matches->type != OF_ANY_MATCH)
+		if (matches->type[0])
 			match &= dev->node->type
 				&& !strcmp(matches->type, dev->node->type);
-		if (matches->compatible && matches->compatible != OF_ANY_MATCH)
+		if (matches->compatible[0])
 			match &= device_is_compatible(dev->node,
 				matches->compatible);
 		if (match)
@@ -42,7 +43,7 @@ static int of_platform_bus_match(struct 
 {
 	struct of_device * of_dev = to_of_device(dev);
 	struct of_platform_driver * of_drv = to_of_platform_driver(drv);
-	const struct of_match * matches = of_drv->match_table;
+	const struct of_device_id * matches = of_drv->match_table;
 
 	if (!matches)
 		return 0;
@@ -75,7 +76,7 @@ static int of_device_probe(struct device
 	int error = -ENODEV;
 	struct of_platform_driver *drv;
 	struct of_device *of_dev;
-	const struct of_match *match;
+	const struct of_device_id *match;
 
 	drv = to_of_platform_driver(dev->driver);
 	of_dev = to_of_device(dev);
drivers/i2c/busses/i2c-keywest.c +3 -4
diff -rupN -X dontdiff linux-2.6.8/drivers/i2c/busses/i2c-keywest.c linux-2.6.8.devel/drivers/i2c/busses/i2c-keywest.c
@@ -694,7 +694,7 @@ dispose_iface(struct device *dev)
 }
 
 static int
-create_iface_macio(struct macio_dev* dev, const struct of_match *match)
+create_iface_macio(struct macio_dev* dev, const struct of_device_id *match)
 {
 	return create_iface(dev->ofdev.node, &dev->ofdev.dev);
 }
@@ -706,7 +706,7 @@ dispose_iface_macio(struct macio_dev* de
 }
 
 static int
-create_iface_of_platform(struct of_device* dev, const struct of_match *match)
+create_iface_of_platform(struct of_device* dev, const struct of_device_id *match)
 {
 	return create_iface(dev->node, &dev->dev);
 }
@@ -717,10 +717,9 @@ dispose_iface_of_platform(struct of_devi
 	return dispose_iface(&dev->dev);
 }
 
-static struct of_match i2c_keywest_match[] = 
+static struct of_device_id i2c_keywest_match[] = 
 {
 	{
-	.name 		= OF_ANY_MATCH,
 	.type		= "i2c",
 	.compatible	= "keywest"
 	},
drivers/ide/ppc/pmac.c +2 -10
diff -rupN -X dontdiff linux-2.6.8/drivers/ide/ppc/pmac.c linux-2.6.8.devel/drivers/ide/ppc/pmac.c
@@ -1279,7 +1279,7 @@ pmac_ide_setup_device(pmac_ide_hwif_t *p
  * Attach to a macio probed interface
  */
 static int __devinit
-pmac_ide_macio_attach(struct macio_dev *mdev, const struct of_match *match)
+pmac_ide_macio_attach(struct macio_dev *mdev, const struct of_device_id *match)
 {
 	unsigned long base, regbase;
 	int irq;
@@ -1500,27 +1500,19 @@ pmac_ide_pci_resume(struct pci_dev *pdev
 	return rc;
 }
 
-static struct of_match pmac_ide_macio_match[] = 
+static struct of_device_id pmac_ide_macio_match[] = 
 {
 	{
 	.name 		= "IDE",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH
 	},
 	{
 	.name 		= "ATA",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH
 	},
 	{
-	.name 		= OF_ANY_MATCH,
 	.type		= "ide",
-	.compatible	= OF_ANY_MATCH
 	},
 	{
-	.name 		= OF_ANY_MATCH,
 	.type		= "ata",
-	.compatible	= OF_ANY_MATCH
 	},
 	{},
 };
drivers/macintosh/macio_asic.c +71 -2

96 lines not on this page · raw message

drivers/macintosh/macio_sysfs.c +49 -0

49 lines not on this page · raw message

drivers/macintosh/Makefile +1 -1
diff -rupN -X dontdiff linux-2.6.8/drivers/macintosh/Makefile linux-2.6.8.devel/drivers/macintosh/Makefile
@@ -4,7 +4,7 @@
 
 # Each configuration option enables a list of files.
 
-obj-$(CONFIG_PPC_PMAC)		+= macio_asic.o
+obj-$(CONFIG_PPC_PMAC)		+= macio_asic.o macio_sysfs.o
 
 obj-$(CONFIG_PMAC_PBOOK)	+= mediabay.o
 obj-$(CONFIG_MAC_SERIAL)	+= macserial.o
drivers/macintosh/mediabay.c +2 -5
diff -rupN -X dontdiff linux-2.6.8/drivers/macintosh/mediabay.c linux-2.6.8.devel/drivers/macintosh/mediabay.c
@@ -648,7 +648,7 @@ static int __pmac media_bay_task(void *x
 	}
 }
 
-static int __devinit media_bay_attach(struct macio_dev *mdev, const struct of_match *match)
+static int __devinit media_bay_attach(struct macio_dev *mdev, const struct of_device_id *match)
 {
 	struct media_bay_info* bay;
 	volatile u32 *regbase;
@@ -802,23 +802,20 @@ static struct mb_ops keylargo_mb_ops __p
  * Therefore we do it all by polling the media bay once each tick.
  */
 
-static struct of_match media_bay_match[] =
+static struct of_device_id media_bay_match[] =
 {
 	{
 	.name		= "media-bay",
-	.type		= OF_ANY_MATCH,
 	.compatible	= "keylargo-media-bay",
 	.data		= &keylargo_mb_ops,
 	},
 	{
 	.name		= "media-bay",
-	.type		= OF_ANY_MATCH,
 	.compatible	= "heathrow-media-bay",
 	.data		= &heathrow_mb_ops,
 	},
 	{
 	.name		= "media-bay",
-	.type		= OF_ANY_MATCH,
 	.compatible	= "ohare-media-bay",
 	.data		= &ohare_mb_ops,
 	},
drivers/macintosh/therm_windtunnel.c +3 -3
diff -rupN -X dontdiff linux-2.6.8/drivers/macintosh/therm_windtunnel.c linux-2.6.8.devel/drivers/macintosh/therm_windtunnel.c
@@ -43,6 +43,7 @@
 #include <asm/system.h>
 #include <asm/sections.h>
 #include <asm/of_device.h>
+#include <asm/macio.h>
 
 #define LOG_TEMP		0			/* continously log temperature */
 
@@ -453,7 +454,7 @@ do_probe( struct i2c_adapter *adapter, i
 /************************************************************************/
 
 static int
-therm_of_probe( struct of_device *dev, const struct of_match *match )
+therm_of_probe( struct of_device *dev, const struct of_device_id *match )
 {
 	return i2c_add_driver( &g4fan_driver );
 }
@@ -464,9 +465,8 @@ therm_of_remove( struct of_device *dev )
 	return i2c_del_driver( &g4fan_driver );
 }
 
-static struct of_match therm_of_match[] = {{
+static struct of_device_id therm_of_match[] = {{
 	.name		= "fan",
-	.type		= OF_ANY_MATCH,
 	.compatible	= "adm1030"
     }, {}
 };
drivers/net/bmac.c +2 -5
diff -rupN -X dontdiff linux-2.6.8/drivers/net/bmac.c linux-2.6.8.devel/drivers/net/bmac.c
@@ -1261,7 +1261,7 @@ static void bmac_reset_and_enable(struct
 	spin_unlock_irqrestore(&bp->lock, flags);
 }
 
-static int __devinit bmac_probe(struct macio_dev *mdev, const struct of_match *match)
+static int __devinit bmac_probe(struct macio_dev *mdev, const struct of_device_id *match)
 {
 	int j, rev, ret;
 	struct bmac_data *bp;
@@ -1649,16 +1649,13 @@ static int __devexit bmac_remove(struct 
 	return 0;
 }
 
-static struct of_match bmac_match[] = 
+static struct of_device_id bmac_match[] = 
 {
 	{
 	.name 		= "bmac",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH,
 	.data		= (void *)0,
 	},
 	{
-	.name 		= OF_ANY_MATCH,
 	.type		= "network",
 	.compatible	= "bmac+",
 	.data		= (void *)1,
drivers/net/mace.c +2 -4
diff -rupN -X dontdiff linux-2.6.8/drivers/net/mace.c linux-2.6.8.devel/drivers/net/mace.c
@@ -109,7 +109,7 @@ bitrev(int b)
 }
 
 
-static int __devinit mace_probe(struct macio_dev *mdev, const struct of_match *match)
+static int __devinit mace_probe(struct macio_dev *mdev, const struct of_device_id *match)
 {
 	struct device_node *mace = macio_get_of_node(mdev);
 	struct net_device *dev;
@@ -1011,12 +1011,10 @@ static irqreturn_t mace_rxdma_intr(int i
     return IRQ_HANDLED;
 }
 
-static struct of_match mace_match[] = 
+static struct of_device_id mace_match[] = 
 {
 	{
 	.name 		= "mace",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH
 	},
 	{},
 };
drivers/net/wireless/airport.c +4 -4
diff -rupN -X dontdiff linux-2.6.8/drivers/net/wireless/airport.c linux-2.6.8.devel/drivers/net/wireless/airport.c
@@ -188,7 +188,7 @@ static int airport_hard_reset(struct ori
 }
 
 static int
-airport_attach(struct macio_dev *mdev, const struct of_match *match)
+airport_attach(struct macio_dev *mdev, const struct of_device_id *match)
 {
 	struct orinoco_private *priv;
 	struct net_device *dev;
@@ -272,16 +272,16 @@ MODULE_AUTHOR("Benjamin Herrenschmidt <b
 MODULE_DESCRIPTION("Driver for the Apple Airport wireless card.");
 MODULE_LICENSE("Dual MPL/GPL");
 
-static struct of_match airport_match[] = 
+static struct of_device_id airport_match[] = 
 {
 	{
 	.name 		= "radio",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH
 	},
 	{},
 };
 
+MODULE_DEVICE_TABLE (of, airport_match);
+
 static struct macio_driver airport_driver = 
 {
 	.name 		= DRIVER_NAME,
drivers/scsi/mac53c94.c +3 -4
diff -rupN -X dontdiff linux-2.6.8/drivers/scsi/mac53c94.c linux-2.6.8.devel/drivers/scsi/mac53c94.c
@@ -425,7 +425,7 @@ static struct scsi_host_template mac53c9
 	.use_clustering	= DISABLE_CLUSTERING,
 };
 
-static int mac53c94_probe(struct macio_dev *mdev, const struct of_match *match)
+static int mac53c94_probe(struct macio_dev *mdev, const struct of_device_id *match)
 {
 	struct device_node *node = macio_get_of_node(mdev);
 	struct pci_dev *pdev = macio_get_pci_dev(mdev);
@@ -545,15 +545,14 @@ static int mac53c94_remove(struct macio_
 }
 
 
-static struct of_match mac53c94_match[] = 
+static struct of_device_id mac53c94_match[] = 
 {
 	{
 	.name 		= "53c94",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH
 	},
 	{},
 };
+MODULE_DEVICE_TABLE (of, mac53c94_match);
 
 static struct macio_driver mac53c94_driver = 
 {
drivers/scsi/mesh.c +3 -5
diff -rupN -X dontdiff linux-2.6.8/drivers/scsi/mesh.c linux-2.6.8.devel/drivers/scsi/mesh.c
@@ -1847,7 +1847,7 @@ static struct scsi_host_template mesh_te
 	.use_clustering			= DISABLE_CLUSTERING,
 };
 
-static int mesh_probe(struct macio_dev *mdev, const struct of_match *match)
+static int mesh_probe(struct macio_dev *mdev, const struct of_device_id *match)
 {
 	struct device_node *mesh = macio_get_of_node(mdev);
 	struct pci_dev* pdev = macio_get_pci_dev(mdev);
@@ -2014,20 +2014,18 @@ static int mesh_remove(struct macio_dev 
 }
 
 
-static struct of_match mesh_match[] = 
+static struct of_device_id mesh_match[] = 
 {
 	{
 	.name 		= "mesh",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH
 	},
 	{
-	.name 		= OF_ANY_MATCH,
 	.type		= "scsi",
 	.compatible	= "chrp,mesh0"
 	},
 	{},
 };
+MODULE_DEVICE_TABLE (of, mesh_match);
 
 static struct macio_driver mesh_driver = 
 {
drivers/serial/pmac_zilog.c +3 -6
diff -rupN -X dontdiff linux-2.6.8/drivers/serial/pmac_zilog.c linux-2.6.8.devel/drivers/serial/pmac_zilog.c
@@ -1520,7 +1520,7 @@ static void pmz_dispose_port(struct uart
 /*
  * Called upon match with an escc node in the devive-tree.
  */
-static int pmz_attach(struct macio_dev *mdev, const struct of_match *match)
+static int pmz_attach(struct macio_dev *mdev, const struct of_device_id *match)
 {
 	int i;
 	
@@ -1826,20 +1826,17 @@ err_out:
 	return rc;
 }
 
-static struct of_match pmz_match[] = 
+static struct of_device_id pmz_match[] = 
 {
 	{
 	.name 		= "ch-a",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH
 	},
 	{
 	.name 		= "ch-b",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH
 	},
 	{},
 };
+MODULE_DEVICE_TABLE (of, pmz_match);
 
 static struct macio_driver pmz_driver = 
 {
drivers/video/platinumfb.c +2 -4
diff -rupN -X dontdiff linux-2.6.8/drivers/video/platinumfb.c linux-2.6.8.devel/drivers/video/platinumfb.c
@@ -523,7 +523,7 @@ int __init platinumfb_setup(char *option
 #define invalidate_cache(addr)
 #endif
 
-static int __devinit platinumfb_probe(struct of_device* odev, const struct of_match *match)
+static int __devinit platinumfb_probe(struct of_device* odev, const struct of_device_id *match)
 {
 	struct device_node	*dp = odev->node;
 	struct fb_info		*info;
@@ -647,12 +647,10 @@ static int __devexit platinumfb_remove(s
 	return 0;
 }
 
-static struct of_match platinumfb_match[] = 
+static struct of_device_id platinumfb_match[] = 
 {
 	{
 	.name 		= "platinum",
-	.type		= OF_ANY_MATCH,
-	.compatible	= OF_ANY_MATCH,
 	},
 	{},
 };
include/asm-ppc/macio.h +3 -2
diff -rupN -X dontdiff linux-2.6.8/include/asm-ppc/macio.h linux-2.6.8.devel/include/asm-ppc/macio.h
@@ -1,6 +1,7 @@
 #ifndef __MACIO_ASIC_H__
 #define __MACIO_ASIC_H__
 
+#include <linux/mod_devicetable.h>
 #include <asm/of_device.h>
 
 extern struct bus_type macio_bus_type;
@@ -120,10 +121,10 @@ static inline struct pci_dev *macio_get_
 struct macio_driver
 {
 	char			*name;
-	struct of_match		*match_table;
+	struct of_device_id	*match_table;
 	struct module		*owner;
 
-	int	(*probe)(struct macio_dev* dev, const struct of_match *match);
+	int	(*probe)(struct macio_dev* dev, const struct of_device_id *match);
 	int	(*remove)(struct macio_dev* dev);
 
 	int	(*suspend)(struct macio_dev* dev, u32 state);
include/asm-ppc/of_device.h +4 -16
diff -rupN -X dontdiff linux-2.6.8/include/asm-ppc/of_device.h linux-2.6.8.devel/include/asm-ppc/of_device.h
@@ -24,20 +24,8 @@ struct of_device
 };
 #define	to_of_device(d) container_of(d, struct of_device, dev)
 
-/*
- * Struct used for matching a device
- */
-struct of_match
-{
-	char	*name;
-	char	*type;
-	char	*compatible;
-	void	*data;
-};
-#define OF_ANY_MATCH		((char *)-1L)
-
-extern const struct of_match *of_match_device(
-	const struct of_match *matches, const struct of_device *dev);
+extern const struct of_device_id *of_match_device(
+	const struct of_device_id *matches, const struct of_device *dev);
 
 extern struct of_device *of_dev_get(struct of_device *dev);
 extern void of_dev_put(struct of_device *dev);
@@ -49,10 +37,10 @@ extern void of_dev_put(struct of_device 
 struct of_platform_driver
 {
 	char			*name;
-	struct of_match		*match_table;
+	struct of_device_id	*match_table;
 	struct module		*owner;
 
-	int	(*probe)(struct of_device* dev, const struct of_match *match);
+	int	(*probe)(struct of_device* dev, const struct of_device_id *match);
 	int	(*remove)(struct of_device* dev);
 
 	int	(*suspend)(struct of_device* dev, u32 state);
include/linux/mod_devicetable.h +11 -0
diff -rupN -X dontdiff linux-2.6.8/include/linux/mod_devicetable.h linux-2.6.8.devel/include/linux/mod_devicetable.h
@@ -164,5 +164,16 @@ struct pnp_card_device_id {
 	} devs[PNP_MAX_DEVICES];
 };
 
+/*
+ * Struct used for matching a device
+ */
+struct of_device_id
+{
+	char	name[32];
+	char	type[32];
+	char	compatible[32];
+	void	*data;
+};
+
 
 #endif /* LINUX_MOD_DEVICETABLE_H */
scripts/mod/file2alias.c +13 -0
diff -rupN -X dontdiff linux-2.6.8/scripts/mod/file2alias.c linux-2.6.8.devel/scripts/mod/file2alias.c
@@ -199,6 +199,15 @@ static int do_pnp_card_entry(const char 
 	return 1;
 }
 
+static int do_macio_entry (const char *filename, struct of_device_id *of, char *alias)
+{
+    sprintf (alias, "macio:N%sT%sC%s",
+                    of->name[0] ? of->name : "*",
+                    of->type[0] ? of->type : "*",
+                    of->compatible[0] ? of->compatible : "*");
+    return 1;
+}
+
 /* Ignore any prefix, eg. v850 prepends _ */
 static inline int sym_is(const char *symbol, const char *name)
 {
@@ -271,6 +280,10 @@ void handle_moddevtable(struct module *m
 	else if (sym_is(symname, "__mod_pnp_card_device_table"))
 		do_table(symval, sym->st_size, sizeof(struct pnp_card_device_id),
 			 do_pnp_card_entry, mod);
+        else if (sym_is(symname, "__mod_macio_device_table"))
+		do_table(symval, sym->st_size, sizeof(struct of_device_id),
+			 do_macio_entry, mod);
+
 }
 
 /* Now add out buffered information to the generated C source */