--- /usr/src/linux-2.2.9/include/linux/blk.h	Mon Feb 22 23:51:55 1999
+++ linux/include/linux/blk.h	Fri Jul 30 22:27:10 1999
@@ -49,6 +49,7 @@
 extern int cdi_init(void);
 extern int hd_init(void);
 extern int ide_init(void);
+extern int cldd_init(void);
 extern int xd_init(void);
 extern int mfm_init(void);
 extern int loop_init(void);
--- /usr/src/linux-2.2.9/include/linux/blkdev.h	Mon Feb 22 23:50:27 1999
+++ linux/include/linux/blkdev.h	Fri Jul 30 22:27:05 1999
@@ -60,6 +60,9 @@
 extern void unplug_device(void * data);
 extern void make_request(int major,int rw, struct buffer_head * bh);
 
+extern int cldd_map (int minor, kdev_t *rdev, unsigned long *rsector, unsigned long size, int rw);
+extern int cldd_make_request (int minor, int rw, struct buffer_head * bh);
+
 /* md needs this function to remap requests */
 extern int md_map (int minor, kdev_t *rdev, unsigned long *rsector, unsigned long size);
 extern int md_make_request (int minor, int rw, struct buffer_head * bh);
--- /usr/src/linux-2.2.9/include/linux/cldd.h	Sun Aug  1 18:29:00 1999
+++ linux/include/linux/cldd.h	Sun Aug  1 11:48:03 1999
@@ -0,0 +1,105 @@
+/*
+ *  include/linux/cldd.h
+ *
+ *  Copyright 1999 by Allan Latham <alatham@flexsys-group.com>  
+ *
+ */
+
+#ifndef _LINUX_CLDD_H
+#define _LINUX_CLDD_H
+
+#define CLDD_BMAP_SIZE	128 	/* in units of 1024 blocks */
+#define CLDD_NAME_SIZE	256
+#define CLDD_VERSION	2
+
+#ifdef __KERNEL__
+
+#include <linux/version.h>
+#include <linux/kdev_t.h>
+
+#define CLDD_GET_DEVICE(a,b) a = b & 63;
+#define CLDD_GET_SLAVE(a,b) a = (b >> 6) & 1;
+#define CLDD_SLAVE_FROM_MASTER(a,b) a = b + 64;
+#define CLDD_MASTER_FROM_SLAVE(a,b) a = b - 64;
+
+#if LINUX_VERSION_CODE >= 0x020200
+
+#include <asm/uaccess.h>
+
+#define CLDD_GET_INODE(a,b) a = b->f_dentry->d_inode;
+#define CLDD_PUT_USER_LONG(a,b,c) a = put_user(b,(long*)c);
+#define CLDD_COPY_TO_USER(a,b,c) a = copy_to_user(b,&c,sizeof(c));
+#define CLDD_COPY_FROM_USER(a,b,c) a = copy_from_user(&b,c,sizeof(b));
+
+#else
+
+#define CLDD_GET_INODE(a,b) a = b->f_inode;
+#define CLDD_PUT_USER_LONG(a,b,c) \
+if (!(a = verify_area(VERIFY_WRITE,(long*)c,sizeof(long)))) \
+ put_fs_long(b,(long*)c);
+#define CLDD_COPY_TO_USER(a,b,c) \
+if (!(a = verify_area(VERIFY_WRITE,b,sizeof(c)))) \
+ memcpy_tofs(b,&c,sizeof(c));
+#define CLDD_COPY_FROM_USER(a,b,c) \
+if (!(a = verify_area(VERIFY_READ,c,sizeof(b)))) \
+ memcpy_fromfs(&b,c,sizeof(b));
+
+#endif
+
+struct cldd_device {
+	int			number;
+	int			blocksize;
+	int			flags;
+	int			status;
+	int			real_size;
+	int			report_size;
+	int			bmap_size;
+	int			refcnt[2];
+	kdev_t			rdev;
+	unsigned char		*bmap;
+	struct inode		*inode;
+	struct timeval		mtv;
+	struct timeval		stv;
+	char			name[CLDD_NAME_SIZE];
+};
+
+/*
+ * cldd flags
+ */
+#define CLDD_FLAGS_READ_ONLY	0x00000002
+
+#endif /* __KERNEL__ */
+
+#define CLDD_STATUS_CLOSED	0x00000000
+#define CLDD_STATUS_MASTER	0x00000001
+#define CLDD_STATUS_SLAVED	0x00000002
+#define CLDD_STATUS_SYNCH 	0x00000004
+
+struct cldd_info {
+	int			number;				/* ioctl r/o */
+	int			flags;				/* ioctl r/o */
+	int			status;				/* ioctl r/o */
+	int			driver_version;			/* ioctl r/o */
+	int			blocksize;			/* ioctl r/o */
+	int			filesize;
+	unsigned long		rdevice;			/* ioctl r/o */
+	unsigned long		inode; 				/* ioctl r/o */
+	struct timeval		mtv;
+	struct timeval		stv;
+	char			name[CLDD_NAME_SIZE];
+	char			reserved[4];
+};
+
+/*
+ * IOCTL commands --- we will commandeer 0x4C ('L')
+ */
+
+#define CLDD_SET_MASTER		0x4C30
+#define CLDD_CLR_MASTER		0x4C31
+#define CLDD_SET_STATUS		0x4C32
+#define CLDD_GET_STATUS		0x4C33
+#define CLDD_SET_SLAVE 		0x4C34
+#define CLDD_CLR_SLAVE 		0x4C35
+
+#endif
+
--- /usr/src/linux-2.2.9/include/linux/major.h	Wed Oct 14 20:43:14 1998
+++ linux/include/linux/major.h	Fri Jul 30 22:31:13 1999
@@ -81,6 +81,8 @@
 #define IDE4_MAJOR	56
 #define IDE5_MAJOR	57
 
+#define CLDD_MAJOR	62
+
 #define SCSI_DISK1_MAJOR	65
 #define SCSI_DISK2_MAJOR	66
 #define SCSI_DISK3_MAJOR	67
--- /usr/src/linux-2.2.9/drivers/block/Config.in	Sun Aug  1 18:22:01 1999
+++ linux/drivers/block/Config.in	Fri Jul 30 22:29:27 1999
@@ -99,6 +99,9 @@
 if [ "$CONFIG_NET" = "y" ]; then
   tristate 'Network block device support' CONFIG_BLK_DEV_NBD
 fi
+
+tristate 'CLD device support' CONFIG_BLK_DEV_CLDD
+
 bool 'Multiple devices driver support' CONFIG_BLK_DEV_MD
 if [ "$CONFIG_BLK_DEV_MD" = "y" ]; then
   tristate '   Linear (append) mode' CONFIG_MD_LINEAR
--- /usr/src/linux-2.2.9/drivers/block/Makefile	Sun Aug  1 18:21:45 1999
+++ linux/drivers/block/Makefile	Fri Jul 30 22:29:17 1999
@@ -94,6 +94,14 @@
   endif
 endif
 
+ifeq ($(CONFIG_BLK_DEV_CLDD),y)
+LX_OBJS += cldd.o
+else
+  ifeq ($(CONFIG_BLK_DEV_CLDD),m)
+  MX_OBJS += cldd.o
+  endif
+endif
+
 ifeq ($(CONFIG_BLK_DEV_HD),y)
 L_OBJS += hd.o
 endif
--- /usr/src/linux-2.2.9/drivers/block/cldd.c	Sun Aug  1 18:29:10 1999
+++ linux/drivers/block/cldd.c	Sun Aug  1 18:07:25 1999
@@ -0,0 +1,558 @@
+/*
+ *  linux/drivers/block/cldd.c
+ * 
+ *  Copyright 1999 by Allan Latham <alatham@flexsys-group.com>  
+ *
+ */
+
+#include <linux/module.h>
+#include <linux/config.h>
+#include <linux/major.h>
+#include <linux/malloc.h>
+#include <linux/cldd.h>		
+
+#define MAJOR_NR CLDD_MAJOR
+
+#define DEVICE_NAME "cldd"
+#define DEVICE_REQUEST do_request
+#define DEVICE_NR(device) (MINOR(device))
+#define DEVICE_ON(device)
+#define DEVICE_OFF(device)
+#define DEVICE_NO_RANDOM
+#define MAX_DISK_SIZE 1024*1024*1024
+#define TIMEOUT_VALUE (6 * HZ)
+
+#include <linux/blk.h>
+
+#define MAX_CLDD 8
+
+static struct cldd_device cldd_dev[MAX_CLDD];
+static int cldd_sizes[256];
+static int cldd_blksizes[256];
+
+static int get_bitmap(unsigned int block, unsigned char* map)
+{
+	int 		a, b;
+	unsigned char 	m;
+
+	a = block & 7;
+	m = 128;
+	m = m >> a;
+	b = block >> 3;
+
+	return (0 || (map[b] & m));
+}
+
+static void put_bitmap(unsigned int block, unsigned char* map, int bit)
+{
+	int 		a, b;
+	unsigned char 	m;
+
+	a = block & 7;
+	m = 128;
+	m = m >> a;
+	b = block >> 3;
+
+	if (bit) {
+		map[b] |= m;	 
+	} else {
+		map[b] &= ~m;
+	}
+}
+
+static void do_request(void)
+{
+	printk ("Got cldd request, not good...");
+}
+
+static int cldd_set_master(struct cldd_device *lo, kdev_t dev, unsigned int arg)
+{
+	int			minor;
+	struct file		*file;
+	struct inode		*inode;
+
+	if (sizeof(unsigned long) != 4) {
+		printk("cldd: error 012, unsigned long is %d bytes, I expected 4\n", sizeof(unsigned long));
+		return -EINVAL;
+        }
+
+	if (arg >= NR_OPEN || !(file = current->files->fd[arg]))
+		return -EBADF;
+
+	if (lo->inode)
+		return -EBUSY;
+
+	CLDD_GET_INODE (inode,file)
+	if (!inode) {
+		return -EFAULT;
+	}
+
+	if (S_ISBLK(inode->i_mode)) {
+		int error = blkdev_open(inode, file);
+		if (error)
+			return error;
+		lo->rdev = inode->i_rdev;
+	} else {
+		return -EINVAL;
+	}
+
+	lo->status = CLDD_STATUS_MASTER;
+       	lo->bmap_size = 0;
+       	lo->bmap = NULL;
+	do_gettimeofday(&lo->mtv);
+	memset(&lo->stv,0,sizeof(struct timeval));
+
+	if (IS_RDONLY (inode) || is_read_only(lo->rdev)) {
+		lo->flags |= CLDD_FLAGS_READ_ONLY;
+		set_device_ro(dev, 1);
+	} else {
+		invalidate_inode_pages (inode);
+		set_device_ro(dev, 0);
+	}
+
+	minor = MINOR(dev);
+
+	cldd_blksizes[minor] = BLOCK_SIZE;
+
+        if (blk_size[MAJOR(lo->rdev)]) {
+		cldd_sizes[minor] = blk_size[MAJOR(lo->rdev)][MINOR(lo->rdev)];
+        } else {
+		cldd_sizes[minor] = MAX_DISK_SIZE;
+	}
+
+	lo->real_size = cldd_sizes[minor];
+	lo->report_size = cldd_sizes[minor] >> 1;
+
+	if (lo->report_size > 1024 * 1024) {
+		lo->report_size = 1024 * 1024;
+	}
+
+	cldd_sizes[minor] = lo->report_size;
+
+	lo->inode = inode;
+	lo->inode->i_count++;
+	MOD_INC_USE_COUNT;
+	invalidate_buffers(dev);
+	return 0;
+}
+
+static int cldd_set_slave(struct cldd_device *lo, kdev_t dev)
+{
+	int	minor;
+	kdev_t 	device;
+
+	if (!lo->inode)
+		return -EINVAL;
+
+	if (lo->status != CLDD_STATUS_MASTER)
+		return -EBUSY;
+
+       	lo->bmap_size = 128 * 1024;
+       	lo->bmap = kmalloc(lo->bmap_size, GFP_KERNEL);
+	if (lo->bmap == NULL) {
+       		lo->bmap_size = 0;
+		return -EINVAL;
+	}
+	memset(lo->bmap,0,lo->bmap_size);
+
+	minor = MINOR(dev);
+        device = MKDEV(CLDD_MAJOR,lo->number);
+
+// at this point dev      is the slave device
+//               device   is the master device
+//               lo->rdev is the real device
+
+	do_gettimeofday(&lo->stv);
+
+	fsync_dev(device);
+	fsync_dev(lo->rdev);
+	set_device_ro(dev, 1);
+
+	cldd_sizes[minor] = lo->report_size;
+	lo->inode->i_count++;
+	MOD_INC_USE_COUNT;
+	invalidate_buffers(dev);
+	lo->status = CLDD_STATUS_SLAVED;
+	return 0;
+}
+
+
+static int cldd_clr_master(struct cldd_device *lo, kdev_t dev)
+{
+
+	if (lo->status != CLDD_STATUS_MASTER)
+		return -ENXIO;
+
+	if (lo->refcnt[0] > 1) /* we needed one fd for the ioctl */
+		return -EBUSY;
+
+// at this point dev      is the master device
+//               lo->rdev is the real device
+
+	fsync_dev(dev);
+	fsync_dev(lo->rdev);
+
+	if (!IS_RDONLY(lo->inode)
+	 && !is_read_only(lo->rdev)) 
+		invalidate_inode_pages (lo->inode);
+	if (S_ISBLK(lo->inode->i_mode))
+		blkdev_release (lo->inode);
+	iput(lo->inode);
+	lo->inode = NULL;
+	lo->name[0] = 0;
+	lo->rdev = 0;
+	lo->status = CLDD_STATUS_CLOSED;
+	cldd_sizes[lo->number] = 0;
+
+	invalidate_buffers(dev);
+	MOD_DEC_USE_COUNT;
+	return 0;
+}
+
+static int cldd_clr_slave(struct cldd_device *lo, kdev_t dev)
+{
+        struct buffer_head *bhr;
+	int minor;
+	kdev_t device;
+	int i;
+	int count;
+
+
+	if (lo->status != CLDD_STATUS_SLAVED)
+		return -ENXIO;
+
+	if (lo->refcnt[1] > 1) /* we needed one fd for the ioctl */
+		return -EBUSY;
+
+	lo->status = CLDD_STATUS_SYNCH;
+        device = MKDEV(CLDD_MAJOR,lo->number);
+	minor = MINOR(dev);
+
+// at this point dev      is the slave device
+//               device   is the master device
+//               lo->rdev is the real device
+
+	fsync_dev(device);
+	fsync_dev(lo->rdev);
+	for (i = 0; i < (lo->bmap_size << 3); i++) {
+                if (get_bitmap(i, lo->bmap)) {
+                    	bhr = getblk(device, i, 1024);
+			if (!bhr) {
+                                printk(KERN_ERR "cldd bhr error 1\n");
+                                brelse(bhr);
+                        }
+                        if (!buffer_uptodate(bhr)) {
+                                ll_rw_block(READ, 1, &bhr);
+                                wait_on_buffer(bhr);
+			}
+                        if (!buffer_uptodate(bhr)) {
+                                printk(KERN_ERR "cldd bhr error 2, rdev = %d %d:%d\n", lo->rdev, MAJOR(lo->rdev), MINOR(lo->rdev));
+                                brelse(bhr);
+			}
+                        mark_buffer_dirty(bhr, 1);
+                        brelse(bhr);
+                }
+	}
+
+	fsync_dev(device);
+	fsync_dev(lo->rdev);
+
+	count = 0;
+	for (i = 0; i < (lo->bmap_size << 3); i++) {
+                if (get_bitmap(i, lo->bmap)) {
+			count++;
+		}
+	}
+	if (count) {
+        	printk("cldd unsynched blocks = %d, should be zero.\n",count);
+	}
+
+	kfree(lo->bmap);
+	lo->bmap = NULL;
+       	lo->bmap_size = 0;
+	lo->status = CLDD_STATUS_MASTER;
+
+	invalidate_buffers(dev);
+	MOD_DEC_USE_COUNT;
+	return 0;
+}
+
+
+static int cldd_set_status(struct cldd_device *lo, kdev_t dev, int slave,
+						struct cldd_info *arg)
+{
+	struct 	cldd_info info;
+	int 	reply;
+
+	if (!lo->inode)
+		return -ENXIO;
+	if (!arg)
+		return -EINVAL;
+	CLDD_COPY_FROM_USER (reply, info, arg)
+	if (reply) return -EFAULT; 
+	strncpy(lo->name, info.name, CLDD_NAME_SIZE);
+	invalidate_buffers(dev);
+	return 0;
+}
+
+
+static int cldd_get_status(struct cldd_device *lo, struct cldd_info *arg)
+{
+	struct cldd_info	info;
+	int 			reply;
+	
+	if (!lo->inode)
+		return -ENXIO;
+	if (!arg)
+		return -EINVAL;
+	memset(&info, 0, sizeof(info));
+	info.number = lo->number;
+	info.blocksize = lo->blocksize;
+	info.flags = lo->flags;
+	info.status = lo->status;
+	info.driver_version = CLDD_VERSION;
+	memcpy(&info.mtv,&lo->mtv,sizeof(struct timeval));
+	memcpy(&info.stv,&lo->stv,sizeof(struct timeval));
+
+    	if (lo->inode) {
+	        info.inode = lo->inode->i_ino;
+	}
+	strncpy(info.name, lo->name, CLDD_NAME_SIZE);
+
+	CLDD_COPY_TO_USER (reply, arg, info)
+	if (reply) return -EFAULT;
+	return 0;
+}
+
+
+static int cldd_ioctl(struct inode *inode, struct file *file,
+	unsigned int cmd, unsigned long arg)
+{
+	struct cldd_device *lo;
+	int    idev, slave, dev, reply;
+
+	if (!inode)
+		return -EINVAL;
+	if (MAJOR(inode->i_rdev) != MAJOR_NR) {
+		return -ENODEV;
+	}
+	idev = MINOR(inode->i_rdev);
+	CLDD_GET_DEVICE(dev, idev)
+	CLDD_GET_SLAVE(slave, idev)
+	if (dev >= MAX_CLDD)
+		return -ENODEV;
+	lo = &cldd_dev[dev];
+	switch (cmd) {
+	case CLDD_SET_MASTER:
+		if (slave) return -EINVAL;
+		return cldd_set_master(lo, inode->i_rdev, arg);
+	case CLDD_CLR_MASTER:
+		if (slave) return -EINVAL;
+		return cldd_clr_master(lo, inode->i_rdev);
+	case CLDD_SET_SLAVE:
+		if (!slave) return -EINVAL;
+		return cldd_set_slave(lo, inode->i_rdev);
+	case CLDD_CLR_SLAVE:
+		if (!slave) return -EINVAL;
+		return cldd_clr_slave(lo, inode->i_rdev);
+	case CLDD_SET_STATUS:
+		return cldd_set_status(lo, inode->i_rdev, slave,
+					(struct cldd_info *) arg);
+	case CLDD_GET_STATUS:
+		return cldd_get_status(lo, (struct cldd_info *) arg);
+	case BLKGETSIZE:   /* Return device size */
+		if (!lo->inode)
+			return -ENXIO;
+		if (!arg)  return -EINVAL;
+		CLDD_PUT_USER_LONG (reply, cldd_sizes[lo->number]<<1, arg)
+		if (reply) return -EINVAL;
+		return 0;
+	default:
+                return -EINVAL;
+	}
+	return 0;
+}
+
+
+static int cldd_open(struct inode *inode, struct file *file)
+{
+	struct cldd_device *lo;
+	int	idev, dev, slave;
+
+	if (!inode)
+		return -EINVAL;
+	if (MAJOR(inode->i_rdev) != MAJOR_NR) {
+		return -ENODEV;
+	}
+	idev = MINOR(inode->i_rdev);
+	CLDD_GET_DEVICE(dev, idev)
+	CLDD_GET_SLAVE(slave, idev)
+	if (dev >= MAX_CLDD)
+		return -ENODEV;
+	lo = &cldd_dev[dev];
+	lo->refcnt[slave]++;
+	MOD_INC_USE_COUNT;
+	return 0;
+}
+
+
+static int cldd_release_int(struct inode *inode, struct file *file)
+{
+	struct cldd_device *lo;
+	int	idev, dev, slave;
+
+	if (!inode)
+		return -EINVAL;
+	if (MAJOR(inode->i_rdev) != MAJOR_NR)
+		return -ENODEV;
+	idev = MINOR(inode->i_rdev);
+	CLDD_GET_DEVICE(dev, idev)
+	CLDD_GET_SLAVE(slave, idev)
+	if (dev >= MAX_CLDD)
+		return -ENODEV;
+	fsync_dev(inode->i_rdev);
+	lo = &cldd_dev[dev];
+	if (lo->refcnt[slave] > 0) {
+		lo->refcnt[slave]--;
+		MOD_DEC_USE_COUNT;
+	}
+	return 0;
+}
+
+
+#if LINUX_VERSION_CODE < 0x020100
+
+static void cldd_release_void(struct inode *inode, struct file *file)
+{
+	cldd_release_int(inode, file);
+}
+
+#endif
+
+int cldd_make_request (int minor, int rw, struct buffer_head * bh)
+{
+	make_request (MAJOR(bh->b_rdev), rw, bh);
+	return 0;
+}
+
+int cldd_map (int cldd_minor, kdev_t *rdev, unsigned long *rsector, unsigned long size, int rw)
+{
+	struct cldd_device *lo;
+	unsigned long new_rsector;
+	unsigned long shift_rsector;
+	unsigned long block;
+	int minor;
+	int slave;
+
+	if (size != 2) {
+    		printk ("Bad cldd size %ld\n", size);
+		return (-1);
+	}
+
+	CLDD_GET_DEVICE (minor, cldd_minor)
+
+	if (minor >= MAX_CLDD) {
+    		printk ("Bad cldd device %d\n", cldd_minor);
+		return (-1);
+	}
+
+	lo = &cldd_dev[minor];
+
+	*rdev = lo->rdev;
+	new_rsector = *rsector;
+
+	CLDD_GET_SLAVE(slave, cldd_minor)
+
+	if (!slave) {
+	    shift_rsector = *rsector + (cldd_sizes[minor] << 1);
+	    block = *rsector >> 1;
+	    if (lo->status == CLDD_STATUS_SLAVED) {
+		if (rw) {
+			new_rsector = shift_rsector;
+			put_bitmap(block, lo->bmap, 1);
+		} else {
+			if (get_bitmap(block, lo->bmap)) {
+			    new_rsector = shift_rsector;
+			}
+		}
+	    } else {
+	        if (lo->status == CLDD_STATUS_SYNCH) {
+		    if (rw) {
+			put_bitmap(block, lo->bmap, 0);
+		    } else {
+			if (get_bitmap(block, lo->bmap)) {
+			    new_rsector = shift_rsector;
+			}
+		    }
+		}
+	    }
+	}
+
+//	printk ("clddmap: slave = %d, rw = %d, old = %d, new = %d\n", slave, rw, *rsector, new_rsector);
+
+	*rsector = new_rsector;
+
+	return 0;
+}
+
+static struct file_operations fops = {
+	NULL,			/* lseek - default */
+	block_read,		/* read - general block-dev read */
+	block_write,		/* write - general block-dev write */
+	NULL,			/* readdir - bad */
+	NULL,			/* poll */
+	cldd_ioctl,		/* ioctl */
+	NULL,			/* mmap */
+	cldd_open,		/* open */
+#if LINUX_VERSION_CODE >= 0x020200
+	NULL,			/* flush */
+	cldd_release_int	/* release */
+#else
+	cldd_release_void	/* release */
+#endif
+};
+
+/*
+ * And now the modules code and kernel interface.
+ */
+#ifdef MODULE
+#define cldd_init init_module
+#endif
+
+int cldd_init(void) {
+	int	i;
+	char    title[10];
+
+	sprintf(title,"cldd-%d.%d", CLDD_VERSION/10, CLDD_VERSION%10);
+	if (register_blkdev(MAJOR_NR, DEVICE_NAME, &fops)) {
+		printk("cldd: Error 006, Unable to get major number %d for cldd device.\n",
+		       MAJOR_NR);
+		return -EIO;
+	}
+// #ifndef MODULE
+	printk("%s (c) 1999 Allan Latham <alatham@flexsys-group.com>\n",title);
+	printk("%s: registered device at major %d\n", title, MAJOR_NR);
+// #endif
+
+	blk_dev[MAJOR_NR].request_fn = DEVICE_REQUEST;
+	for (i=0; i < MAX_CLDD; i++) {
+		memset(&cldd_dev[i], 0, sizeof(struct cldd_device));
+		cldd_dev[i].number = i;
+	}
+	memset(&cldd_sizes, 0, sizeof(cldd_sizes));
+	memset(&cldd_blksizes, 0, sizeof(cldd_blksizes));
+	blk_size[MAJOR_NR] = cldd_sizes;
+	blksize_size[MAJOR_NR] = cldd_blksizes;
+
+	return 0;
+}
+
+#ifdef MODULE
+void cleanup_module( void ) {
+	int 	reply;
+
+  	reply = unregister_blkdev(MAJOR_NR, DEVICE_NAME);
+  	if (reply)
+		printk("cldd: Error 007, cleanup_module failed %d.\n",reply);
+}
+#endif
--- /usr/src/linux-2.2.9/drivers/block/ll_rw_blk.c	Sun Aug  1 18:21:39 1999
+++ linux/drivers/block/ll_rw_blk.c	Fri Jul 30 22:28:55 1999
@@ -461,6 +461,7 @@
 	if (!req) {
 		/* MD and loop can't handle plugging without deadlocking */
 		if (major != MD_MAJOR && major != LOOP_MAJOR && 
+		    major != CLDD_MAJOR && 
 		    major != DDV_MAJOR && major != NBD_MAJOR)
 			plug_device(blk_dev + major); /* is atomic */
 	} else switch (major) {
@@ -611,6 +612,16 @@
 		/* Md remaps blocks now */
 		bh[i]->b_rdev = bh[i]->b_dev;
 		bh[i]->b_rsector=bh[i]->b_blocknr*(bh[i]->b_size >> 9);
+// #ifdef CONFIG_BLK_DEV_CLDD
+		if (major==CLDD_MAJOR &&
+		    cldd_map (MINOR(bh[i]->b_dev), &bh[i]->b_rdev,
+			    &bh[i]->b_rsector, bh[i]->b_size >> 9,
+				(rw == WRITE || rw == WRITEA))) {
+		        printk (KERN_ERR
+				"Bad cldd_map in ll_rw_block\n");
+		        goto sorry;
+		}
+// #endif
 #ifdef CONFIG_BLK_DEV_MD
 		if (major==MD_MAJOR &&
 		    md_map (MINOR(bh[i]->b_dev), &bh[i]->b_rdev,
@@ -631,6 +642,12 @@
 	for (i = 0; i < nr; i++) {
 		if (bh[i]) {
 			set_bit(BH_Req, &bh[i]->b_state);
+// #ifdef CONFIG_BLK_DEV_CLDD
+			if (MAJOR(bh[i]->b_dev) == CLDD_MAJOR) {
+				cldd_make_request(MINOR (bh[i]->b_dev), rw, bh[i]);
+				continue;
+			}
+// #endif
 #ifdef CONFIG_BLK_DEV_MD
 			if (MAJOR(bh[i]->b_dev) == MD_MAJOR) {
 				md_make_request(MINOR (bh[i]->b_dev), rw, bh[i]);
@@ -817,6 +834,9 @@
 #ifdef CONFIG_SJCD
 	sjcd_init();
 #endif CONFIG_SJCD
+#ifdef CONFIG_BLK_DEV_CLDD
+	cldd_init();
+#endif CONFIG_BLK_DEV_CLDD
 #ifdef CONFIG_BLK_DEV_MD
 	md_init();
 #endif CONFIG_BLK_DEV_MD
