diff --git a/drivers/macintosh/adb.c b/drivers/macintosh/adb.c
new file mode 100644
index 0000000..7297c77
--- /dev/null
+++ b/drivers/macintosh/adb.c
@@ -0,0 +1,910 @@
+/*
+ * Device driver for the Apple Desktop Bus
+ * and the /dev/adb device on macintoshes.
+ *
+ * Copyright (C) 1996 Paul Mackerras.
+ *
+ * Modified to declare controllers as structures, added
+ * client notification of bus reset and handles PowerBook
+ * sleep, by Benjamin Herrenschmidt.
+ *
+ * To do:
+ *
+ * - /sys/bus/adb to list the devices and infos
+ * - more /dev/adb to allow userland to receive the
+ *   flow of auto-polling datas from a given device.
+ * - move bus probe to a kernel thread
+ */
+
+#include <linux/config.h>
+#include <linux/types.h>
+#include <linux/errno.h>
+#include <linux/kernel.h>
+#include <linux/slab.h>
+#include <linux/module.h>
+#include <linux/fs.h>
+#include <linux/mm.h>
+#include <linux/sched.h>
+#include <linux/smp_lock.h>
+#include <linux/adb.h>
+#include <linux/cuda.h>
+#include <linux/pmu.h>
+#include <linux/notifier.h>
+#include <linux/wait.h>
+#include <linux/init.h>
+#include <linux/delay.h>
+#include <linux/spinlock.h>
+#include <linux/completion.h>
+#include <linux/device.h>
+#include <linux/devfs_fs_kernel.h>
+
+#include <asm/uaccess.h>
+#include <asm/semaphore.h>
+#ifdef CONFIG_PPC
+#include <asm/prom.h>
+#endif
+
+
+EXPORT_SYMBOL(adb_controller);
+EXPORT_SYMBOL(adb_client_list);
+
+extern struct adb_driver via_macii_driver;
+extern struct adb_driver via_maciisi_driver;
+extern struct adb_driver via_cuda_driver;
+extern struct adb_driver adb_iop_driver;
+extern struct adb_driver via_pmu_driver;
+extern struct adb_driver macio_adb_driver;
+
+static struct adb_driver *adb_driver_list[] = {
+#ifdef CONFIG_ADB_MACII
+	&via_macii_driver,
+#endif
+#ifdef CONFIG_ADB_MACIISI
+	&via_maciisi_driver,
+#endif
+#ifdef CONFIG_ADB_CUDA
+	&via_cuda_driver,
+#endif
+#ifdef CONFIG_ADB_IOP
+	&adb_iop_driver,
+#endif
+#if defined(CONFIG_ADB_PMU) || defined(CONFIG_ADB_PMU68K)
+	&via_pmu_driver,
+#endif
+#ifdef CONFIG_ADB_MACIO
+	&macio_adb_driver,
+#endif
+	NULL
+};
+
+static struct class_simple *adb_dev_class;
+
+struct adb_driver *adb_controller;
+struct notifier_block *adb_client_list = NULL;
+static int adb_got_sleep;
+static int adb_inited;
+static pid_t adb_probe_task_pid;
+static DECLARE_MUTEX(adb_probe_mutex);
+static struct completion adb_probe_task_comp;
+static int sleepy_trackpad;
+static int autopoll_devs;
+int __adb_probe_sync;
+
+#ifdef CONFIG_PMAC_PBOOK
+static int adb_notify_sleep(struct pmu_sleep_notifier *self, int when);
+static struct pmu_sleep_notifier adb_sleep_notifier = {
+	adb_notify_sleep,
+	SLEEP_LEVEL_ADB,
+};
+#endif
+
+static int adb_scan_bus(void);
+static int do_adb_reset_bus(void);
+static void adbdev_init(void);
+static int try_handler_change(int, int);
+
+static struct adb_handler {
+	void (*handler)(unsigned char *, int, struct pt_regs *, int);
+	int original_address;
+	int handler_id;
+	int busy;
+} adb_handler[16];
+
+/*
+ * The adb_handler_sem mutex protects all accesses to the original_address
+ * and handler_id fields of adb_handler[i] for all i, and changes to the
+ * handler field.
+ * Accesses to the handler field are protected by the adb_handler_lock
+ * rwlock.  It is held across all calls to any handler, so that by the
+ * time adb_unregister returns, we know that the old handler isn't being
+ * called.
+ */
+static DECLARE_MUTEX(adb_handler_sem);
+static DEFINE_RWLOCK(adb_handler_lock);
+
+#if 0
+static void printADBreply(struct adb_request *req)
+{
+        int i;
+
+        printk("adb reply (%d)", req->reply_len);
+        for(i = 0; i < req->reply_len; i++)
+                printk(" %x", req->reply[i]);
+        printk("\n");
+
+}
+#endif
+
+
+static __inline__ void adb_wait_ms(unsigned int ms)
+{
+	if (current->pid && adb_probe_task_pid &&
+	  adb_probe_task_pid == current->pid)
+		msleep(ms);
+	else
+		mdelay(ms);
+}
+
+static int adb_scan_bus(void)
+{
+	int i, highFree=0, noMovement;
+	int devmask = 0;
+	struct adb_request req;
+	
+	/* assumes adb_handler[] is all zeroes at this point */
+	for (i = 1; i < 16; i++) {
+		/* see if there is anything at address i */
+		adb_request(&req, NULL, ADBREQ_SYNC | ADBREQ_REPLY, 1,
+                            (i << 4) | 0xf);
+		if (req.reply_len > 1)
+			/* one or more devices at this address */
+			adb_handler[i].original_address = i;
+		else if (i > highFree)
+			highFree = i;
+	}
+
+	/* Note we reset noMovement to 0 each time we move a device */
+	for (noMovement = 1; noMovement < 2 && highFree > 0; noMovement++) {
+		for (i = 1; i < 16; i++) {
+			if (adb_handler[i].original_address == 0)
+				continue;
+			/*
+			 * Send a "talk register 3" command to address i
+			 * to provoke a collision if there is more than
+			 * one device at this address.
+			 */
+			adb_request(&req, NULL, ADBREQ_SYNC | ADBREQ_REPLY, 1,
+				    (i << 4) | 0xf);
+			/*
+			 * Move the device(s) which didn't detect a
+			 * collision to address `highFree'.  Hopefully
+			 * this only moves one device.
+			 */
+			adb_request(&req, NULL, ADBREQ_SYNC, 3,
+				    (i<< 4) | 0xb, (highFree | 0x60), 0xfe);
+			/*
+			 * See if anybody actually moved. This is suggested
+			 * by HW TechNote 01:
+			 *
+			 * http://developer.apple.com/technotes/hw/hw_01.html
+			 */
+			adb_request(&req, NULL, ADBREQ_SYNC | ADBREQ_REPLY, 1,
+				    (highFree << 4) | 0xf);
+			if (req.reply_len <= 1) continue;
+			/*
+			 * Test whether there are any device(s) left
+			 * at address i.
+			 */
+			adb_request(&req, NULL, ADBREQ_SYNC | ADBREQ_REPLY, 1,
+				    (i << 4) | 0xf);
+			if (req.reply_len > 1) {
+				/*
+				 * There are still one or more devices
+				 * left at address i.  Register the one(s)
+				 * we moved to `highFree', and find a new
+				 * value for highFree.
+				 */
+				adb_handler[highFree].original_address =
+					adb_handler[i].original_address;
+				while (highFree > 0 &&
+				       adb_handler[highFree].original_address)
+					highFree--;
+				if (highFree <= 0)
+					break;
+
+				noMovement = 0;
+			}
+			else {
+				/*
+				 * No devices left at address i; move the
+				 * one(s) we moved to `highFree' back to i.
+				 */
+				adb_request(&req, NULL, ADBREQ_SYNC, 3,
+					    (highFree << 4) | 0xb,
+					    (i | 0x60), 0xfe);
+			}
+		}	
+	}
+
+	/* Now fill in the handler_id field of the adb_handler entries. */
+	printk(KERN_DEBUG "adb devices:");
+	for (i = 1; i < 16; i++) {
+		if (adb_handler[i].original_address == 0)
+			continue;
+		adb_request(&req, NULL, ADBREQ_SYNC | ADBREQ_REPLY, 1,
+			    (i << 4) | 0xf);
+		adb_handler[i].handler_id = req.reply[2];
+		printk(" [%d]: %d %x", i, adb_handler[i].original_address,
+		       adb_handler[i].handler_id);
+		devmask |= 1 << i;
+	}
+	printk("\n");
+	return devmask;
+}
+
+/*
+ * This kernel task handles ADB probing. It dies once probing is
+ * completed.
+ */
+static int
+adb_probe_task(void *x)
+{
+	sigset_t blocked;
+
+	strcpy(current->comm, "kadbprobe");
+
+	sigfillset(&blocked);
+	sigprocmask(SIG_BLOCK, &blocked, NULL);
+	flush_signals(current);
+
+	printk(KERN_INFO "adb: starting probe task...\n");
+	do_adb_reset_bus();
+	printk(KERN_INFO "adb: finished probe task...\n");
+	
+	adb_probe_task_pid = 0;
+	up(&adb_probe_mutex);
+	
+	return 0;
+}
+
+static void
+__adb_probe_task(void *data)
+{
+	adb_probe_task_pid = kernel_thread(adb_probe_task, NULL, SIGCHLD | CLONE_KERNEL);
+}
+
+static DECLARE_WORK(adb_reset_work, __adb_probe_task, NULL);
+
+int
+adb_reset_bus(void)
+{
+	if (__adb_probe_sync) {
+		do_adb_reset_bus();
+		return 0;
+	}
+
+	down(&adb_probe_mutex);
+	schedule_work(&adb_reset_work);
+	return 0;
+}
+
+int __init adb_init(void)
+{
+	struct adb_driver *driver;
+	int i;
+
+#ifdef CONFIG_PPC32
+	if ( (_machine != _MACH_chrp) && (_machine != _MACH_Pmac) )
+		return 0;
+#endif
+#ifdef CONFIG_MAC
+	if (!MACH_IS_MAC)
+		return 0;
+#endif
+
+	/* xmon may do early-init */
+	if (adb_inited)
+		return 0;
+	adb_inited = 1;
+		
+	adb_controller = NULL;
+
+	i = 0;
+	while ((driver = adb_driver_list[i++]) != NULL) {
+		if (!driver->probe()) {
+			adb_controller = driver;
+			break;
+		}
+	}
+	if ((adb_controller == NULL) || adb_controller->init()) {
+		printk(KERN_WARNING "Warning: no ADB interface detected\n");
+		adb_controller = NULL;
+	} else {
+#ifdef CONFIG_PMAC_PBOOK
+		pmu_register_sleep_notifier(&adb_sleep_notifier);
+#endif /* CONFIG_PMAC_PBOOK */
+#ifdef CONFIG_PPC
+		if (machine_is_compatible("AAPL,PowerBook1998") ||
+			machine_is_compatible("PowerBook1,1"))
+			sleepy_trackpad = 1;
+#endif /* CONFIG_PPC */
+		init_completion(&adb_probe_task_comp);
+		adbdev_init();
+		adb_reset_bus();
+	}
+	return 0;
+}
+
+__initcall(adb_init);
+
+#ifdef CONFIG_PMAC_PBOOK
+/*
+ * notify clients before sleep and reset bus afterwards
+ */
+int
+adb_notify_sleep(struct pmu_sleep_notifier *self, int when)
+{
+	int ret;
+	
+	switch (when) {
+	case PBOOK_SLEEP_REQUEST:
+		adb_got_sleep = 1;
+		/* We need to get a lock on the probe thread */
+		down(&adb_probe_mutex);
+		/* Stop autopoll */
+		if (adb_controller->autopoll)
+			adb_controller->autopoll(0);
+		ret = notifier_call_chain(&adb_client_list, ADB_MSG_POWERDOWN, NULL);
+		if (ret & NOTIFY_STOP_MASK) {
+			up(&adb_probe_mutex);
+			return PBOOK_SLEEP_REFUSE;
+		}
+		break;
+	case PBOOK_SLEEP_REJECT:
+		if (adb_got_sleep) {
+			adb_got_sleep = 0;
+			up(&adb_probe_mutex);
+			adb_reset_bus();
+		}
+		break;
+		
+	case PBOOK_SLEEP_NOW:
+		break;
+	case PBOOK_WAKE:
+		adb_got_sleep = 0;
+		up(&adb_probe_mutex);
+		adb_reset_bus();
+		break;
+	}
+	return PBOOK_SLEEP_OK;
+}
+#endif /* CONFIG_PMAC_PBOOK */
+
+static int
+do_adb_reset_bus(void)
+{
+	int ret, nret;
+	
+	if (adb_controller == NULL)
+		return -ENXIO;
+		
+	if (adb_controller->autopoll)
+		adb_controller->autopoll(0);
+
+	nret = notifier_call_chain(&adb_client_list, ADB_MSG_PRE_RESET, NULL);
+	if (nret & NOTIFY_STOP_MASK) {
+		if (adb_controller->autopoll)
+			adb_controller->autopoll(autopoll_devs);
+		return -EBUSY;
+	}
+
+	if (sleepy_trackpad) {
+		/* Let the trackpad settle down */
+		adb_wait_ms(500);
+	}
+
+	down(&adb_handler_sem);
+	write_lock_irq(&adb_handler_lock);
+	memset(adb_handler, 0, sizeof(adb_handler));
+	write_unlock_irq(&adb_handler_lock);
+
+	/* That one is still a bit synchronous, oh well... */
+	if (adb_controller->reset_bus)
+		ret = adb_controller->reset_bus();
+	else
+		ret = 0;
+
+	if (sleepy_trackpad) {
+		/* Let the trackpad settle down */
+		adb_wait_ms(1500);
+	}
+
+	if (!ret) {
+		autopoll_devs = adb_scan_bus();
+		if (adb_controller->autopoll)
+			adb_controller->autopoll(autopoll_devs);
+	}
+	up(&adb_handler_sem);
+
+	nret = notifier_call_chain(&adb_client_list, ADB_MSG_POST_RESET, NULL);
+	if (nret & NOTIFY_STOP_MASK)
+		return -EBUSY;
+	
+	return ret;
+}
+
+void
+adb_poll(void)
+{
+	if ((adb_controller == NULL)||(adb_controller->poll == NULL))
+		return;
+	adb_controller->poll();
+}
+
+static void
+adb_probe_wakeup(struct adb_request *req)
+{
+	complete(&adb_probe_task_comp);
+}
+
+/* Static request used during probe */
+static struct adb_request adb_sreq;
+static unsigned long adb_sreq_lock; // Use semaphore ! */ 
+
+int
+adb_request(struct adb_request *req, void (*done)(struct adb_request *),
+	    int flags, int nbytes, ...)
+{
+	va_list list;
+	int i, use_sreq;
+	int rc;
+
+	if ((adb_controller == NULL) || (adb_controller->send_request == NULL))
+		return -ENXIO;
+	if (nbytes < 1)
+		return -EINVAL;
+	if (req == NULL && (flags & ADBREQ_NOSEND))
+		return -EINVAL;
+	
+	if (req == NULL) {
+		if (test_and_set_bit(0,&adb_sreq_lock)) {
+			printk("adb.c: Warning: contention on static request !\n");
+			return -EPERM;
+		}
+		req = &adb_sreq;
+		flags |= ADBREQ_SYNC;
+		use_sreq = 1;
+	} else
+		use_sreq = 0;
+	req->nbytes = nbytes+1;
+	req->done = done;
+	req->reply_expected = flags & ADBREQ_REPLY;
+	req->data[0] = ADB_PACKET;
+	va_start(list, nbytes);
+	for (i = 0; i < nbytes; ++i)
+		req->data[i+1] = va_arg(list, int);
+	va_end(list);
+
+	if (flags & ADBREQ_NOSEND)
+		return 0;
+
+	/* Synchronous requests send from the probe thread cause it to
+	 * block. Beware that the "done" callback will be overriden !
+	 */
+	if ((flags & ADBREQ_SYNC) &&
+	    (current->pid && adb_probe_task_pid &&
+	    adb_probe_task_pid == current->pid)) {
+		req->done = adb_probe_wakeup;
+		rc = adb_controller->send_request(req, 0);
+		if (rc || req->complete)
+			goto bail;
+		wait_for_completion(&adb_probe_task_comp);
+		rc = 0;
+		goto bail;
+	}
+
+	rc = adb_controller->send_request(req, flags & ADBREQ_SYNC);
+bail:
+	if (use_sreq)
+		clear_bit(0, &adb_sreq_lock);
+
+	return rc;
+}
+
+ /* Ultimately this should return the number of devices with
+    the given default id.
+    And it does it now ! Note: changed behaviour: This function
+    will now register if default_id _and_ handler_id both match
+    but handler_id can be left to 0 to match with default_id only.
+    When handler_id is set, this function will try to adjust
+    the handler_id id it doesn't match. */
+int
+adb_register(int default_id, int handler_id, struct adb_ids *ids,
+	     void (*handler)(unsigned char *, int, struct pt_regs *, int))
+{
+	int i;
+
+	down(&adb_handler_sem);
+	ids->nids = 0;
+	for (i = 1; i < 16; i++) {
+		if ((adb_handler[i].original_address == default_id) &&
+		    (!handler_id || (handler_id == adb_handler[i].handler_id) || 
+		    try_handler_change(i, handler_id))) {
+			if (adb_handler[i].handler != 0) {
+				printk(KERN_ERR
+				       "Two handlers for ADB device %d\n",
+				       default_id);
+				continue;
+			}
+			write_lock_irq(&adb_handler_lock);
+			adb_handler[i].handler = handler;
+			write_unlock_irq(&adb_handler_lock);
+			ids->id[ids->nids++] = i;
+		}
+	}
+	up(&adb_handler_sem);
+	return ids->nids;
+}
+
+int
+adb_unregister(int index)
+{
+	int ret = -ENODEV;
+
+	down(&adb_handler_sem);
+	write_lock_irq(&adb_handler_lock);
+	if (adb_handler[index].handler) {
+		while(adb_handler[index].busy) {
+			write_unlock_irq(&adb_handler_lock);
+			yield();
+			write_lock_irq(&adb_handler_lock);
+		}
+		ret = 0;
+		adb_handler[index].handler = NULL;
+	}
+	write_unlock_irq(&adb_handler_lock);
+	up(&adb_handler_sem);
+	return ret;
+}
+
+void
+adb_input(unsigned char *buf, int nb, struct pt_regs *regs, int autopoll)
+{
+	int i, id;
+	static int dump_adb_input = 0;
+	unsigned long flags;
+	
+	void (*handler)(unsigned char *, int, struct pt_regs *, int);
+
+	/* We skip keystrokes and mouse moves when the sleep process
+	 * has been started. We stop autopoll, but this is another security
+	 */
+	if (adb_got_sleep)
+		return;
+		
+	id = buf[0] >> 4;
+	if (dump_adb_input) {
+		printk(KERN_INFO "adb packet: ");
+		for (i = 0; i < nb; ++i)
+			printk(" %x", buf[i]);
+		printk(", id = %d\n", id);
+	}
+	write_lock_irqsave(&adb_handler_lock, flags);
+	handler = adb_handler[id].handler;
+	if (handler != NULL)
+		adb_handler[id].busy = 1;
+	write_unlock_irqrestore(&adb_handler_lock, flags);
+	if (handler != NULL) {
+		(*handler)(buf, nb, regs, autopoll);
+		wmb();
+		adb_handler[id].busy = 0;
+	}
+		
+}
+
+/* Try to change handler to new_id. Will return 1 if successful. */
+static int try_handler_change(int address, int new_id)
+{
+	struct adb_request req;
+
+	if (adb_handler[address].handler_id == new_id)
+	    return 1;
+	adb_request(&req, NULL, ADBREQ_SYNC, 3,
+	    ADB_WRITEREG(address, 3), address | 0x20, new_id);
+	adb_request(&req, NULL, ADBREQ_SYNC | ADBREQ_REPLY, 1,
+	    ADB_READREG(address, 3));
+	if (req.reply_len < 2)
+	    return 0;
+	if (req.reply[2] != new_id)
+	    return 0;
+	adb_handler[address].handler_id = req.reply[2];
+
+	return 1;
+}
+
+int
+adb_try_handler_change(int address, int new_id)
+{
+	int ret;
+
+	down(&adb_handler_sem);
+	ret = try_handler_change(address, new_id);
+	up(&adb_handler_sem);
+	return ret;
+}
+
+int
+adb_get_infos(int address, int *original_address, int *handler_id)
+{
+	down(&adb_handler_sem);
+	*original_address = adb_handler[address].original_address;
+	*handler_id = adb_handler[address].handler_id;
+	up(&adb_handler_sem);
+
+	return (*original_address != 0);
+}
+
+
+/*
+ * /dev/adb device driver.
+ */
+
+#define ADB_MAJOR	56	/* major number for /dev/adb */
+
+struct adbdev_state {
+	spinlock_t	lock;
+	atomic_t	n_pending;
+	struct adb_request *completed;
+  	wait_queue_head_t wait_queue;
+	int		inuse;
+};
+
+static void adb_write_done(struct adb_request *req)
+{
+	struct adbdev_state *state = (struct adbdev_state *) req->arg;
+	unsigned long flags;
+
+	if (!req->complete) {
+		req->reply_len = 0;
+		req->complete = 1;
+	}
+	spin_lock_irqsave(&state->lock, flags);
+	atomic_dec(&state->n_pending);
+	if (!state->inuse) {
+		kfree(req);
+		if (atomic_read(&state->n_pending) == 0) {
+			spin_unlock_irqrestore(&state->lock, flags);
+			kfree(state);
+			return;
+		}
+	} else {
+		struct adb_request **ap = &state->completed;
+		while (*ap != NULL)
+			ap = &(*ap)->next;
+		req->next = NULL;
+		*ap = req;
+		wake_up_interruptible(&state->wait_queue);
+	}
+	spin_unlock_irqrestore(&state->lock, flags);
+}
+
+static int
+do_adb_query(struct adb_request *req)
+{
+	int	ret = -EINVAL;
+
+	switch(req->data[1])
+	{
+	case ADB_QUERY_GETDEVINFO:
+		if (req->nbytes < 3)
+			break;
+		down(&adb_handler_sem);
+		req->reply[0] = adb_handler[req->data[2]].original_address;
+		req->reply[1] = adb_handler[req->data[2]].handler_id;
+		up(&adb_handler_sem);
+		req->complete = 1;
+		req->reply_len = 2;
+		adb_write_done(req);
+		ret = 0;
+		break;
+	}
+	return ret;
+}
+
+static int adb_open(struct inode *inode, struct file *file)
+{
+	struct adbdev_state *state;
+
+	if (iminor(inode) > 0 || adb_controller == NULL)
+		return -ENXIO;
+	state = kmalloc(sizeof(struct adbdev_state), GFP_KERNEL);
+	if (state == 0)
+		return -ENOMEM;
+	file->private_data = state;
+	spin_lock_init(&state->lock);
+	atomic_set(&state->n_pending, 0);
+	state->completed = NULL;
+	init_waitqueue_head(&state->wait_queue);
+	state->inuse = 1;
+
+	return 0;
+}
+
+static int adb_release(struct inode *inode, struct file *file)
+{
+	struct adbdev_state *state = file->private_data;
+	unsigned long flags;
+
+	lock_kernel();
+	if (state) {
+		file->private_data = NULL;
+		spin_lock_irqsave(&state->lock, flags);
+		if (atomic_read(&state->n_pending) == 0
+		    && state->completed == NULL) {
+			spin_unlock_irqrestore(&state->lock, flags);
+			kfree(state);
+		} else {
+			state->inuse = 0;
+			spin_unlock_irqrestore(&state->lock, flags);
+		}
+	}
+	unlock_kernel();
+	return 0;
+}
+
+static ssize_t adb_read(struct file *file, char __user *buf,
+			size_t count, loff_t *ppos)
+{
+	int ret = 0;
+	struct adbdev_state *state = file->private_data;
+	struct adb_request *req;
+	wait_queue_t wait = __WAITQUEUE_INITIALIZER(wait,current);
+	unsigned long flags;
+
+	if (count < 2)
+		return -EINVAL;
+	if (count > sizeof(req->reply))
+		count = sizeof(req->reply);
+	if (!access_ok(VERIFY_WRITE, buf, count))
+		return -EFAULT;
+
+	req = NULL;
+	spin_lock_irqsave(&state->lock, flags);
+	add_wait_queue(&state->wait_queue, &wait);
+	current->state = TASK_INTERRUPTIBLE;
+
+	for (;;) {
+		req = state->completed;
+		if (req != NULL)
+			state->completed = req->next;
+		else if (atomic_read(&state->n_pending) == 0)
+			ret = -EIO;
+		if (req != NULL || ret != 0)
+			break;
+		
+		if (file->f_flags & O_NONBLOCK) {
+			ret = -EAGAIN;
+			break;
+		}
+		if (signal_pending(current)) {
+			ret = -ERESTARTSYS;
+			break;
+		}
+		spin_unlock_irqrestore(&state->lock, flags);
+		schedule();
+		spin_lock_irqsave(&state->lock, flags);
+	}
+
+	current->state = TASK_RUNNING;
+	remove_wait_queue(&state->wait_queue, &wait);
+	spin_unlock_irqrestore(&state->lock, flags);
+	
+	if (ret)
+		return ret;
+
+	ret = req->reply_len;
+	if (ret > count)
+		ret = count;
+	if (ret > 0 && copy_to_user(buf, req->reply, ret))
+		ret = -EFAULT;
+
+	kfree(req);
+	return ret;
+}
+
+static ssize_t adb_write(struct file *file, const char __user *buf,
+			 size_t count, loff_t *ppos)
+{
+	int ret/*, i*/;
+	struct adbdev_state *state = file->private_data;
+	struct adb_request *req;
+
+	if (count < 2 || count > sizeof(req->data))
+		return -EINVAL;
+	if (adb_controller == NULL)
+		return -ENXIO;
+	if (!access_ok(VERIFY_READ, buf, count))
+		return -EFAULT;
+
+	req = (struct adb_request *) kmalloc(sizeof(struct adb_request),
+					     GFP_KERNEL);
+	if (req == NULL)
+		return -ENOMEM;
+
+	req->nbytes = count;
+	req->done = adb_write_done;
+	req->arg = (void *) state;
+	req->complete = 0;
+	
+	ret = -EFAULT;
+	if (copy_from_user(req->data, buf, count))
+		goto out;
+
+	atomic_inc(&state->n_pending);
+
+	/* If a probe is in progress or we are sleeping, wait for it to complete */
+	down(&adb_probe_mutex);
+
+	/* Queries are special requests sent to the ADB driver itself */
+	if (req->data[0] == ADB_QUERY) {
+		if (count > 1)
+			ret = do_adb_query(req);
+		else
+			ret = -EINVAL;
+		up(&adb_probe_mutex);
+	}
+	/* Special case for ADB_BUSRESET request, all others are sent to
+	   the controller */
+	else if ((req->data[0] == ADB_PACKET)&&(count > 1)
+		&&(req->data[1] == ADB_BUSRESET)) {
+		ret = do_adb_reset_bus();
+		up(&adb_probe_mutex);
+		atomic_dec(&state->n_pending);
+		if (ret == 0)
+			ret = count;
+		goto out;
+	} else {	
+		req->reply_expected = ((req->data[1] & 0xc) == 0xc);
+		if (adb_controller && adb_controller->send_request)
+			ret = adb_controller->send_request(req, 0);
+		else
+			ret = -ENXIO;
+		up(&adb_probe_mutex);
+	}
+
+	if (ret != 0) {
+		atomic_dec(&state->n_pending);
+		goto out;
+	}
+	return count;
+
+out:
+	kfree(req);
+	return ret;
+}
+
+static struct file_operations adb_fops = {
+	.owner		= THIS_MODULE,
+	.llseek		= no_llseek,
+	.read		= adb_read,
+	.write		= adb_write,
+	.open		= adb_open,
+	.release	= adb_release,
+};
+
+static void
+adbdev_init(void)
+{
+	if (register_chrdev(ADB_MAJOR, "adb", &adb_fops)) {
+		printk(KERN_ERR "adb: unable to get major %d\n", ADB_MAJOR);
+		return;
+	}
+
+	devfs_mk_cdev(MKDEV(ADB_MAJOR, 0), S_IFCHR | S_IRUSR | S_IWUSR, "adb");
+
+	adb_dev_class = class_simple_create(THIS_MODULE, "adb");
+	if (IS_ERR(adb_dev_class)) {
+		return;
+	}
+	class_simple_device_add(adb_dev_class, MKDEV(ADB_MAJOR, 0), NULL, "adb");
+}
