aboutsummaryrefslogtreecommitdiffstats
path: root/xenolinux-2.4.21-pre4-sparse
diff options
context:
space:
mode:
authorkaf24@labyrinth.cl.cam.ac.uk <kaf24@labyrinth.cl.cam.ac.uk>2003-03-07 01:38:49 +0000
committerkaf24@labyrinth.cl.cam.ac.uk <kaf24@labyrinth.cl.cam.ac.uk>2003-03-07 01:38:49 +0000
commitd0ec9023281a5d6ed0aee9341c7889320664e862 (patch)
treecfb9ba8056120e9c67a66a06a2785f7d4073a2d1 /xenolinux-2.4.21-pre4-sparse
parent796305db16ed924df9d4061b70ba110e5978b226 (diff)
downloadxen-d0ec9023281a5d6ed0aee9341c7889320664e862.tar.gz
xen-d0ec9023281a5d6ed0aee9341c7889320664e862.tar.bz2
xen-d0ec9023281a5d6ed0aee9341c7889320664e862.zip
bitkeeper revision 1.110 (3e67f829AwB4Vv_qPsJlN_yjkdepyg)
xl_block.h: new file Many files: Cleaned up new blkdev world. .del-blk.h~f91949f6390760d: Delete: xenolinux-2.4.21-pre4-sparse/include/linux/blk.h .del-xl_block_test.c~b3dce903a84011b8: Delete: xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_block_test.c .del-xeno-major.h~d739160829760724: Delete: xen/include/hypervisor-ifs/xeno-major.h .del-grok.c~eca1f7a23736b451: Delete: xen/drivers/block/grok.c
Diffstat (limited to 'xenolinux-2.4.21-pre4-sparse')
-rw-r--r--xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/Makefile3
-rw-r--r--xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_block.c356
-rw-r--r--xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_block.h64
-rw-r--r--xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_block_test.c255
-rw-r--r--xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_ide.c216
-rw-r--r--xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_scsi.c230
-rw-r--r--xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_segment.c481
-rw-r--r--xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_segment_proc.c364
-rw-r--r--xenolinux-2.4.21-pre4-sparse/include/linux/blk.h420
-rw-r--r--xenolinux-2.4.21-pre4-sparse/include/linux/major.h9
-rw-r--r--xenolinux-2.4.21-pre4-sparse/init/do_mounts.c29
11 files changed, 686 insertions, 1741 deletions
diff --git a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/Makefile b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/Makefile
index fd6b63f51e..6423104172 100644
--- a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/Makefile
+++ b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/Makefile
@@ -1,4 +1,3 @@
O_TARGET := blk.o
-obj-y := xl_block.o xl_ide.o xl_scsi.o xl_segment.o
-obj-y += xl_segment_proc.o xl_block_test.o
+obj-y := xl_block.o xl_ide.o xl_scsi.o xl_segment.o xl_segment_proc.o
include $(TOPDIR)/Rules.make
diff --git a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_block.c b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_block.c
index af270f1aa1..985fda050f 100644
--- a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_block.c
+++ b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_block.c
@@ -5,138 +5,83 @@
*
*/
-#include <linux/config.h>
-#include <linux/module.h>
-
-#include <linux/kernel.h>
-#include <linux/sched.h>
-#include <linux/slab.h>
-#include <linux/string.h>
-#include <linux/errno.h>
-
-#include <linux/fs.h>
-#include <linux/hdreg.h>
-#include <linux/blkdev.h>
-#include <linux/major.h>
-
-#include <asm/hypervisor-ifs/block.h>
-#include <asm/hypervisor-ifs/hypervisor-if.h>
-#include <asm/io.h>
-#include <asm/atomic.h>
-#include <asm/uaccess.h>
-
+#include "xl_block.h"
#include <linux/blk.h>
-/* Copied from linux/ide.h */
-typedef unsigned char byte;
-
-extern int xlide_init(int xidx, int idx);
-extern int xlide_hwsect(int minor);
-extern void xlide_cleanup(void);
-extern int xlscsi_init(int xidx, int idx);
-extern int xlscsi_hwsect(int minor);
-extern void xlscsi_cleanup(void);
-
-static int nide = 0; // number of IDE devices we have
-static int nscsi = 0; // number of SCSI devices we have
-
+typedef unsigned char byte; /* from linux/ide.h */
-#define XLBLK_MAX 32 /* XXX SMH: this the max of XLIDE_MAX and XLSCSI_MAX */
+#define XLBLK_MAX 32
#define XLBLK_RESPONSE_IRQ _EVENT_BLK_RESP
+#define DEBUG_IRQ _EVENT_DEBUG
-#define DEBUG_IRQ _EVENT_DEBUG
-
-#if 0
-#define DPRINTK(_f, _a...) printk ( KERN_ALERT _f , ## _a )
-#define DPRINTK_IOCTL(_f, _a...) printk ( KERN_ALERT _f , ## _a )
-#else
-#define DPRINTK(_f, _a...) ((void)0)
-#define DPRINTK_IOCTL(_f, _a...) ((void)0)
-#endif
+#define PARTN_SHIFT 4
static blk_ring_t *blk_ring;
static unsigned int resp_cons; /* Response consumer for comms ring. */
-
static xen_disk_info_t xlblk_disk_info;
-atomic_t xlblk_control_count;
-
-void xlblk_ide_register_disk(int, unsigned long);
-void do_xlseg_requestX (request_queue_t *rq);
-int hypervisor_request(void * id,
- int operation,
- char * buffer,
- unsigned long block_number,
- unsigned short block_size,
- kdev_t device,
- struct gendisk *gd);
-
-/* ------------------------------------------------------------------------
+static int xlblk_control_msg_pending;
+
+/*
+ * Request queues with outstanding work, but ring is currently full.
+ * We need no special lock here, as we always access this with the
+ * io_request_lock held. We only need a small maximum list.
*/
+#define MAX_PENDING 8
+static request_queue_t *pending_queues[MAX_PENDING];
+static int nr_pending;
-/* Convert from a XenoLinux (major,minor) to the Xen-level 'physical' device */
-static kdev_t xldev_to_physdev(kdev_t xldev)
+/* Convert from a XenoLinux major device to the Xen-level 'physical' device */
+static inline unsigned short xldev_to_physdev(kdev_t xldev)
{
- int xlmajor = MAJOR(xldev);
- int major, minor;
+ unsigned short physdev;
- switch(xlmajor) {
+ switch ( MAJOR(xldev) )
+ {
case XLIDE_MAJOR:
- major = IDE0_MAJOR;
- minor = 0; /* we do minor offsetting manually by addition */
+ physdev = XENDEV_IDE;
break;
case XLSCSI_MAJOR:
- major = SCSI_DISK0_MAJOR;
- minor = 0; /* we do minor offsetting manually by addition */
+ physdev = XENDEV_SCSI;
break;
+ case XLVIRT_MAJOR:
+ physdev = XENDEV_VIRTUAL;
+ break;
+
default:
- panic("xldev_to_physdev: unhandled major %d\n", xlmajor);
- break;
+ BUG();
}
- return MKDEV(major, minor);
+ physdev += (MINOR(xldev) >> PARTN_SHIFT);
+
+ return physdev;
}
-/*
-** Locate the gendisk structure associated with a particular xenolinux disk;
-** this requires a scan of the xen_disk_info[] array currently which kind of
-** sucks. However we can clean this whole area up later (i.e. post SOSP).
-*/
-struct gendisk *xldev_to_gendisk(kdev_t xldev, int *t)
+static inline struct gendisk *xldev_to_gendisk(kdev_t xldev)
{
- int i, j, posn, type;
+ struct gendisk *gd = NULL;
- switch(MAJOR(xldev)) {
-
+ switch ( MAJOR(xldev) )
+ {
case XLIDE_MAJOR:
- type = 1;
- posn = 1;
+ gd = xlide_gendisk;
break;
case XLSCSI_MAJOR:
- type = 2;
- posn = 1;
- break;
-
- default:
- panic("xldev_to_gendisk: unhandled major %d\n", MAJOR(xldev));
+ gd = xlscsi_gendisk;
break;
- }
-
- for ( i = j = 0; i < xen_disk_info.count; i++ ) {
- if(xen_disk_info.disks[i].type == type)
- if(++j == posn)
- break;
+ case XLVIRT_MAJOR:
+ gd = xlsegment_gendisk;
+ break;
}
- if(t)
- *t = type;
+ if ( gd == NULL ) BUG();
- return (xen_disk_info.disks[i].gendisk);
+ return gd;
}
int xenolinux_block_open(struct inode *inode, struct file *filep)
@@ -156,7 +101,6 @@ int xenolinux_block_release(struct inode *inode, struct file *filep)
int xenolinux_block_ioctl(struct inode *inode, struct file *filep,
unsigned command, unsigned long argument)
{
- int minor_dev, type;
struct hd_geometry *geo = (struct hd_geometry *)argument;
struct gendisk *gd;
struct hd_struct *part;
@@ -167,16 +111,13 @@ int xenolinux_block_ioctl(struct inode *inode, struct file *filep,
if (!capable(CAP_SYS_ADMIN)) return -EPERM;
if (!inode) return -EINVAL;
- minor_dev = MINOR(inode->i_rdev);
- if (minor_dev >= XLBLK_MAX) return -ENODEV;
-
- DPRINTK_IOCTL("command: 0x%x, argument: 0x%lx, minor: 0x%x\n",
- command, (long) argument, minor_dev);
+ DPRINTK_IOCTL("command: 0x%x, argument: 0x%lx, dev: 0x%04x\n",
+ command, (long) argument, inode->i_rdev);
- gd = xldev_to_gendisk(inode->i_rdev, &type);
- part = &gd->part[minor_dev];
+ gd = xldev_to_gendisk(inode->i_rdev);
+ part = &gd->part[MINOR(inode->i_rdev)];
- switch (command)
+ switch ( command )
{
case BLKGETSIZE:
DPRINTK_IOCTL(" BLKGETSIZE: %x %lx\n", BLKGETSIZE, part->nr_sects);
@@ -187,24 +128,32 @@ int xenolinux_block_ioctl(struct inode *inode, struct file *filep,
break;
case BLKSSZGET:
- switch(type) {
- case 1:
+ switch ( MAJOR(inode->i_rdev) )
+ {
+ case XLIDE_MAJOR:
DPRINTK_IOCTL(" BLKSSZGET: %x 0x%x\n", BLKSSZGET,
- xlide_hwsect(minor_dev));
- return xlide_hwsect(minor_dev);
- break;
- case 2:
+ xlide_hwsect(MINOR(inode->i_rdev)));
+ return xlide_hwsect(MINOR(inode->i_rdev));
+
+ case XLSCSI_MAJOR:
DPRINTK_IOCTL(" BLKSSZGET: %x 0x%x\n", BLKSSZGET,
- xlscsi_hwsect(minor_dev));
- return xlscsi_hwsect(minor_dev);
- break;
+ xlscsi_hwsect(MINOR(inode->i_rdev)));
+ return xlscsi_hwsect(MINOR(inode->i_rdev));
- default:
- printk("BLKSSZGET ioctl() on bogus type %d disk!\n", type);
- return 0;
+ case XLVIRT_MAJOR:
+ DPRINTK_IOCTL(" BLKSSZGET: %x 0x%x\n", BLKSSZGET,
+ xlsegment_hwsect(MINOR(inode->i_rdev)));
+ return xlsegment_hwsect(MINOR(inode->i_rdev));
+ default:
+ printk(KERN_ALERT "BLKSSZGET ioctl() on bogus disk!\n");
+ return 0;
}
+ case BLKBSZGET: /* get block size */
+ DPRINTK_IOCTL(" BLKBSZGET: %x\n", BLKBSZGET);
+ break;
+
case BLKBSZSET: /* set block size */
DPRINTK_IOCTL(" BLKBSZSET: %x\n", BLKBSZSET);
break;
@@ -217,11 +166,6 @@ int xenolinux_block_ioctl(struct inode *inode, struct file *filep,
DPRINTK_IOCTL(" BLKRAFET: %x\n", BLKRAGET);
break;
- case BLKSSZGET: /* get sector size */
- DPRINTK_IOCTL(" BLKSSZGET: %x 0x%x\n", BLKSSZGET,
- xlblk_hardsect_size[minor_dev]);
- return xlblk_hardsect_size[minor_dev];
-
case HDIO_GETGEO:
/* note: these values are complete garbage */
DPRINTK_IOCTL(" HDIO_GETGEO: %x\n", HDIO_GETGEO);
@@ -273,21 +217,20 @@ int xenolinux_block_revalidate(kdev_t dev)
* virtual address in the guest os.
* block_number: block to read
* block_size: size of each block
- * device: xhd or vhd
- * gd: partition information if XEN_BLOCK_{READ,WRITE}
+ * device: xhd*, ksd*, xvd*, ...
*/
-int hypervisor_request(void * id,
- int operation,
- char * buffer,
- unsigned long block_number,
- unsigned short block_size,
- kdev_t device,
- struct gendisk *gd)
+static int hypervisor_request(void * id,
+ int operation,
+ char * buffer,
+ unsigned long block_number,
+ unsigned short block_size,
+ kdev_t device)
{
int position;
void *buffer_ma;
kdev_t phys_device = (kdev_t) 0;
unsigned long sector_number = 0;
+ struct gendisk *gd;
/*
* Bail if there's no room in the request communication ring. This may be
@@ -311,12 +254,10 @@ int hypervisor_request(void * id,
case XEN_BLOCK_READ:
case XEN_BLOCK_WRITE:
- phys_device = xldev_to_physdev(device);
- if (!IS_XHD_MAJOR(MAJOR(device)))
- phys_device = MAJOR(device);
+ phys_device = xldev_to_physdev(device);
/* Compute real buffer location on disk */
sector_number = block_number;
- gd = xldev_to_gendisk(device, NULL);
+ gd = xldev_to_gendisk(device);
sector_number += gd->part[MINOR(device)].start_sect;
break;
@@ -324,7 +265,7 @@ int hypervisor_request(void * id,
panic("unknown op %d\n", operation);
}
- /* Fill out a communications ring structure & trap to the hypervisor */
+ /* Fill out a communications ring structure. */
position = blk_ring->req_prod;
blk_ring->ring[position].req.id = id;
blk_ring->ring[position].req.operation = operation;
@@ -344,7 +285,7 @@ int hypervisor_request(void * id,
* do_xlblk_request
* read a block; request is in a request queue
*/
-void do_xlblk_request (request_queue_t *rq)
+void do_xlblk_request(request_queue_t *rq)
{
struct request *req;
struct buffer_head *bh;
@@ -373,10 +314,14 @@ void do_xlblk_request (request_queue_t *rq)
{
full = hypervisor_request(
bh, (rw == READ) ? XEN_BLOCK_READ : XEN_BLOCK_WRITE,
- bh->b_data, bh->b_rsector, bh->b_size, bh->b_dev,
- (struct gendisk *)xlblk_disk_info.disks[0].gendisk);
+ bh->b_data, bh->b_rsector, bh->b_size, bh->b_dev);
- if ( full ) goto out;
+ if ( full )
+ {
+ pending_queues[nr_pending++] = rq;
+ if ( nr_pending >= MAX_PENDING ) BUG();
+ goto out;
+ }
queued++;
@@ -411,15 +356,6 @@ void do_xlblk_request (request_queue_t *rq)
}
-static struct block_device_operations xenolinux_block_fops =
-{
- open: xenolinux_block_open,
- release: xenolinux_block_release,
- ioctl: xenolinux_block_ioctl,
- check_media_change: xenolinux_block_check,
- revalidate: xenolinux_block_revalidate,
-};
-
static void xlblk_response_int(int irq, void *dev_id, struct pt_regs *ptregs)
{
int i;
@@ -435,46 +371,56 @@ static void xlblk_response_int(int irq, void *dev_id, struct pt_regs *ptregs)
blk_ring_resp_entry_t *bret = &blk_ring->ring[i].resp;
switch (bret->operation)
{
- case XEN_BLOCK_READ :
- case XEN_BLOCK_WRITE :
+ case XEN_BLOCK_READ:
+ case XEN_BLOCK_WRITE:
if ( (bh = bret->id) != NULL ) bh->b_end_io(bh, 1);
break;
- case XEN_BLOCK_SEG_CREATE :
- case XEN_BLOCK_SEG_DELETE :
- case XEN_BLOCK_PROBE_SEG :
- atomic_dec(&xlblk_control_count);
- break;
+ case XEN_BLOCK_SEG_CREATE:
+ case XEN_BLOCK_SEG_DELETE:
+ case XEN_BLOCK_PROBE_SEG:
+ case XEN_BLOCK_PROBE_BLK:
+ xlblk_control_msg_pending = 0;
+ break;
- default:
- break;
+ default:
+ BUG();
}
}
resp_cons = i;
- /* KAF: We can push work down at this point. We have the lock. */
- for (i = 0; i < xen_disk_info.count; i++) {
- /*
- ** XXX SMH: this is pretty broken ...
- ** a) should really only kick devs w/ outstanding work
- ** b) should cover /all/ devs, not just first IDE & SCSI
- ** KAF will fix this I'm sure.
- */
- do_xlblk_request(BLK_DEFAULT_QUEUE(IDE0_MAJOR));
- do_xlblk_request(BLK_DEFAULT_QUEUE(SCSI_DISK0_MAJOR));
- do_xlseg_requestX(BLK_DEFAULT_QUEUE(XLSEG_MAJOR));
+ /* We kick pending request queues if the ring is reasonably empty. */
+ if ( (nr_pending != 0) &&
+ (((blk_ring->req_prod - resp_cons) & (BLK_RING_SIZE - 1)) <
+ (BLK_RING_SIZE >> 1)) )
+ {
+ do { do_xlblk_request(pending_queues[--nr_pending]); }
+ while ( nr_pending != 0 );
}
spin_unlock_irqrestore(&io_request_lock, flags);
}
+/* Send a synchronous message to Xen. */
+int xenolinux_control_msg(int operation, char *buffer)
+{
+ xlblk_control_msg_pending = 1; barrier();
+ if ( hypervisor_request(NULL, operation, buffer, 0, 0, 0) )
+ return -EAGAIN;
+ HYPERVISOR_block_io_op();
+ while ( xlblk_control_msg_pending ) barrier();
+ return 0;
+}
+
+
int __init xlblk_init(void)
{
- int i, error, result;
+ int error;
- atomic_set(&xlblk_control_count, 0);
+ xlblk_control_msg_pending = 0;
+ nr_pending = 0;
/* This mapping was created early at boot time. */
blk_ring = (blk_ring_t *)fix_to_virt(FIX_BLKRING_BASE);
@@ -482,45 +428,27 @@ int __init xlblk_init(void)
error = request_irq(XLBLK_RESPONSE_IRQ, xlblk_response_int, 0,
"xlblk-response", NULL);
- if (error) {
+ if ( error )
+ {
printk(KERN_ALERT "Could not allocate receive interrupt\n");
goto fail;
}
- /* probe for disk information */
- memset (&xlblk_disk_info, 0, sizeof(xlblk_disk_info));
- xlblk_disk_info.count = 0;
-
- if ( hypervisor_request(NULL, XEN_BLOCK_PROBE_BLK,
- (char *) &xlblk_disk_info,
- 0, 0, (kdev_t) 0,
- (struct gendisk *) NULL))
- BUG();
- HYPERVISOR_block_io_op();
- while ( blk_ring->resp_prod != 1 ) barrier();
- for ( i = 0; i < xlblk_disk_info.count; i++ )
- {
- /*
- ** SMH: initialize all the disks we found; this is complicated a
- ** bit by the fact that we have both IDE and SCSI disks underneath
- */
- printk (KERN_ALERT " %2d: type: %d, capacity: %ld\n",
- i, xlblk_disk_info.disks[i].type,
- xlblk_disk_info.disks[i].capacity);
-
- switch(xen_disk_info.disks[i].type) {
- case 1:
- xlide_init(i, nide++);
- break;
- case 2:
- xlscsi_init(i, nscsi++);
- break;
- default:
- printk("Unknown Xen disk type %d\n", xen_disk_info.disks[i].type);
- break;
- }
+ /* Probe for disk information. */
+ memset(&xlblk_disk_info, 0, sizeof(xlblk_disk_info));
+ error = xenolinux_control_msg(XEN_BLOCK_PROBE_BLK,
+ (char *)&xlblk_disk_info);
+ if ( error )
+ {
+ printk(KERN_ALERT "Could not probe disks (%d)\n", error);
+ free_irq(XLBLK_RESPONSE_IRQ, NULL);
+ goto fail;
}
+ /* Pass the information to our fake IDE and SCSI susbystems. */
+ xlide_init(&xlblk_disk_info);
+ xlscsi_init(&xlblk_disk_info);
+
return 0;
fail:
@@ -529,25 +457,9 @@ int __init xlblk_init(void)
static void __exit xlblk_cleanup(void)
{
- int i;
-
- for ( i = 0; i < xen_disk_info.count; i++ )
- {
- switch(xen_disk_info.disks[i].type) {
- case 1:
- xlide_cleanup();
- break;
- case 2:
- xlscsi_cleanup();
- break;
- default:
- printk("Unknown Xen disk type %d\n", xen_disk_info.disks[i].type);
- break;
- }
-
- }
-
- return;
+ xlide_cleanup();
+ xlscsi_cleanup();
+ free_irq(XLBLK_RESPONSE_IRQ, NULL);
}
diff --git a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_block.h b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_block.h
new file mode 100644
index 0000000000..2140b30d7b
--- /dev/null
+++ b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_block.h
@@ -0,0 +1,64 @@
+/******************************************************************************
+ * xl_block.h
+ *
+ * Shared definitions between all levels of XenoLinux Virtual block devices.
+ */
+
+#ifndef __XL_BLOCK_H__
+#define __XL_BLOCK_H__
+
+#include <linux/config.h>
+#include <linux/module.h>
+
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/slab.h>
+#include <linux/string.h>
+#include <linux/errno.h>
+
+#include <linux/fs.h>
+#include <linux/hdreg.h>
+#include <linux/blkdev.h>
+#include <linux/major.h>
+
+#include <asm/hypervisor-ifs/block.h>
+#include <asm/hypervisor-ifs/hypervisor-if.h>
+#include <asm/io.h>
+#include <asm/atomic.h>
+#include <asm/uaccess.h>
+
+#if 0
+#define DPRINTK(_f, _a...) printk ( KERN_ALERT _f , ## _a )
+#define DPRINTK_IOCTL(_f, _a...) printk ( KERN_ALERT _f , ## _a )
+#else
+#define DPRINTK(_f, _a...) ((void)0)
+#define DPRINTK_IOCTL(_f, _a...) ((void)0)
+#endif
+
+/* Generic layer. */
+extern int xenolinux_control_msg(int operration, char *buffer);
+extern int xenolinux_block_open(struct inode *inode, struct file *filep);
+extern int xenolinux_block_release(struct inode *inode, struct file *filep);
+extern int xenolinux_block_ioctl(struct inode *inode, struct file *filep,
+ unsigned command, unsigned long argument);
+extern int xenolinux_block_check(kdev_t dev);
+extern int xenolinux_block_revalidate(kdev_t dev);
+extern void do_xlblk_request (request_queue_t *rq);
+
+/* Fake IDE subsystem. */
+extern int xlide_init(xen_disk_info_t *xdi);
+extern int xlide_hwsect(int minor);
+extern void xlide_cleanup(void);
+extern struct gendisk *xlide_gendisk;
+
+/* Fake SCSI subsystem. */
+extern int xlscsi_init(xen_disk_info_t *xdi);
+extern int xlscsi_hwsect(int minor);
+extern void xlscsi_cleanup(void);
+extern struct gendisk *xlscsi_gendisk;
+
+/* Virtual block-device subsystem. */
+extern int xlsegment_hwsect(int minor);
+extern struct gendisk *xlsegment_gendisk;
+
+#endif /* __XL_BLOCK_H__ */
diff --git a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_block_test.c b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_block_test.c
deleted file mode 100644
index b239655794..0000000000
--- a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_block_test.c
+++ /dev/null
@@ -1,255 +0,0 @@
-/******************************************************************************
- * xenolinux_block_test.c
- *
- */
-#define EXPORT_SYMTAB
-
-#include <linux/config.h>
-#include <linux/module.h>
-
-#include <linux/kernel.h>
-#include <linux/init.h>
-#include <linux/proc_fs.h>
-#include <linux/sched.h>
-#include <asm/uaccess.h>
-#include <linux/slab.h>
-#include <linux/string.h>
-#include <linux/errno.h>
-#include <linux/delay.h>
-
-#include <asm/hypervisor-ifs/block.h>
-#include <asm/hypervisor-ifs/hypervisor-if.h>
-
-/******************************************************************/
-
-static struct proc_dir_entry *bdt;
-static blk_ring_req_entry_t meta;
-static char * data;
-
-static int proc_read_bdt(char *page, char **start, off_t off,
- int count, int *eof, void *data)
-{
- switch (meta.operation)
- {
- case XEN_BLOCK_READ :
- case XEN_BLOCK_WRITE :
- {
- return proc_dump_block(page, start, off, count, eof, data);
- }
- case XEN_BLOCK_DEBUG :
- {
- return proc_dump_debug(page, start, off, count, eof, data);
- }
- default :
- {
- printk(KERN_ALERT
- "block device test error: unknown operation [%c]\n",
- meta.operation);
- return -EINVAL;
- }
- }
-}
-
-int proc_dump_debug(char *page, char **start, off_t off,
- int count, int *eof, void *data)
-{
- char header[100];
- char dump[1024];
-
- sprintf (header, "Block Device Test: Debug Dump\n\n");
-
- sprintf (dump, "%s\n", meta.buffer);
-
- if (data)
- {
- kfree(data);
- }
-
- strncpy (page, dump, count);
- return strlen(page);
-}
-
-int proc_dump_block(char *page, char **start, off_t off,
- int count, int *eof, void *data)
-{
- char header[100];
- char dump[1024];
- char temp[100];
- int loop;
-
- sprintf (header, "Block Device Test\n\n%s blk num: %ld 0x%lx; size: %d 0x%x; device: 0x%x\n",
- meta.operation == XEN_BLOCK_WRITE ? "write" : "read",
- meta.block_number, meta.block_number,
- meta.block_size, meta.block_size,
- meta.device);
-
- sprintf (dump, "%s", header);
-
- if (meta.buffer)
- {
- for (loop = 0; loop < 100; loop++)
- {
- int i = meta.buffer[loop];
-
- if (loop % 8 == 0)
- {
- sprintf (temp, "[%2d] ", loop);
- strcat(dump, temp);
- }
- else if (loop % 2 == 0)
- {
- strcat(dump, " ");
- }
-
- sprintf (temp, " 0x%02x", i & 255);
- strcat(dump, temp);
- if ((loop + 1) % 8 == 0)
- {
- strcat(dump, "\n");
- }
- }
- strcat(dump, "\n\n");
- }
-
- if (data)
- {
- kfree(data);
- }
-
- strncpy (page, dump, count);
- return strlen(page);
-}
-
-int proc_write_bdt(struct file *file, const char *buffer,
- unsigned long count, void *data)
-{
- char *local = kmalloc((count + 1) * sizeof(char), GFP_KERNEL);
- char opcode;
- int block_number = 0;
- int block_size = 0;
- int device = 0;
-
- if (copy_from_user(local, buffer, count))
- {
- return -EFAULT;
- }
- local[count] = '\0';
-
- sscanf(local, "%c %i %i %i",
- &opcode, &block_number, &block_size, &device);
-
- if (data)
- {
- kfree(data);
- }
-
- if (opcode == 'r' || opcode == 'R')
- {
- meta.operation = XEN_BLOCK_READ;
- }
- else if (opcode == 'w' || opcode == 'W')
- {
- meta.operation = XEN_BLOCK_WRITE;
- }
- else if (opcode == 'd' || opcode == 'D')
- {
- meta.operation = XEN_BLOCK_DEBUG;
- block_size = 10000;
- }
- else if (opcode == 'c' || opcode == 'C')
- {
- xv_disk_t *xvd;
- int loop;
-
- meta.operation = XEN_BLOCK_SEG_CREATE;
- data = kmalloc (sizeof(xv_disk_t), GFP_KERNEL);
- if (data == NULL)
- {
- kfree(local);
- return -ENOMEM;
- }
-
- xvd = (xv_disk_t *)data;
- xvd->mode = XEN_DISK_READ_WRITE;
- xvd->domain = block_number;
- xvd->segment = block_size;
- xvd->ext_count = device;
- for (loop = 0; loop < xvd->ext_count; loop++)
- {
- xvd->extents[loop].disk = block_number + 1; /* random */
- xvd->extents[loop].offset = block_size + 1;
- xvd->extents[loop].size = device + 1;
- }
- }
- else
- {
- printk(KERN_ALERT
- "block device test error: unknown opcode [%c]\n", opcode);
- return -EINVAL;
- }
-
- if (data == NULL)
- {
- data = kmalloc(block_size * sizeof(char), GFP_KERNEL);
- if (data == NULL)
- {
- kfree(local);
- return -ENOMEM;
- }
- }
-
- meta.block_number = block_number;
- meta.block_size = block_size;
- meta.device = device;
- meta.buffer = data;
-
- /* submit request */
- hypervisor_request(0, meta.operation, meta.buffer,
- meta.block_number, meta.block_size,
- meta.device,
- (struct gendisk *) NULL);
- HYPERVISOR_block_io_op();
- mdelay(1000); /* should wait for a proper acknowledgement/response. */
-
- kfree(local);
- return count;
-}
-
-
-static int __init init_module(void)
-{
- int return_value = 0;
-
- /* create proc entry */
- bdt = create_proc_entry("bdt", 0644, NULL);
- if (bdt == NULL)
- {
- return_value = -ENOMEM;
- goto error;
- }
- bdt->data = NULL;
- bdt->read_proc = proc_read_bdt;
- bdt->write_proc = proc_write_bdt;
- bdt->owner = THIS_MODULE;
-
- memset(&meta, 0, sizeof(meta));
-
- /* success */
- printk(KERN_ALERT "XenoLinux Block Device Test installed\n");
- return 0;
-
- error:
- return return_value;
-}
-
-static void __exit cleanup_module(void)
-{
- if (data)
- {
- kfree(data);
- }
- printk(KERN_ALERT "XenoLinux Block Device Test uninstalled\n");
-}
-
-module_init(init_module);
-module_exit(cleanup_module);
diff --git a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_ide.c b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_ide.c
index 50f80038ee..f07c54dcb4 100644
--- a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_ide.c
+++ b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_ide.c
@@ -5,49 +5,20 @@
*
*/
-#include <linux/config.h>
-#include <linux/module.h>
-
-#include <linux/kernel.h>
-#include <linux/sched.h>
-#include <linux/slab.h>
-#include <linux/string.h>
-#include <linux/errno.h>
-
-#include <linux/fs.h>
-#include <linux/hdreg.h>
-#include <linux/blkdev.h>
-#include <linux/major.h>
-
-#define MAJOR_NR XLIDE_MAJOR /* force defns in blk.h, must precede include */
-static int xlide_major = XLIDE_MAJOR;
-#include <linux/blk.h>
+#include "xl_block.h"
-void xlide_ide_register_disk(int, unsigned long);
+#define MAJOR_NR XLIDE_MAJOR
+#include <linux/blk.h>
-#define XLIDE_MAX 32 /* Maximum minor devices we support */
+/* We support up to 16 devices of up to 16 partitions each. */
+#define XLIDE_MAX 256
#define XLIDE_MAJOR_NAME "xhd"
-#define IDE_PARTN_BITS 6 /* from ide.h::PARTN_BITS */
-#define IDE_PARTN_MASK ((1<<IDE_PARTN_BITS)-1) /* from ide.h::PARTN_MASK */
-static int xlide_blk_size[XLIDE_MAX];
+#define IDE_PARTN_BITS 4
static int xlide_blksize_size[XLIDE_MAX];
-static int xlide_read_ahead;
static int xlide_hardsect_size[XLIDE_MAX];
static int xlide_max_sectors[XLIDE_MAX];
-extern xen_disk_info_t xen_disk_info;
-
-
-extern int xenolinux_block_open(struct inode *inode, struct file *filep);
-extern int xenolinux_block_release(struct inode *inode, struct file *filep);
-extern int xenolinux_block_ioctl(struct inode *inode, struct file *filep,
- unsigned command, unsigned long argument);
-extern int xenolinux_block_check(kdev_t dev);
-extern int xenolinux_block_revalidate(kdev_t dev);
-
-
-extern void do_xlblk_request (request_queue_t *rq);
-
+struct gendisk *xlide_gendisk;
static struct block_device_operations xlide_block_fops =
{
@@ -59,109 +30,92 @@ static struct block_device_operations xlide_block_fops =
};
-/* tiny inteface fn */
int xlide_hwsect(int minor)
{
return xlide_hardsect_size[minor];
}
-void xlide_register_disk(int xidx, int idx)
+int xlide_init(xen_disk_info_t *xdi)
{
- int units;
- int minors;
+ int i, result, units, minors, disk;
struct gendisk *gd;
- /* plagarized from ide-probe.c::init_gendisk */
- units = 2; /* from ide.h::MAX_DRIVES */
-
- minors = units * (1<<IDE_PARTN_BITS);
- gd = kmalloc (sizeof(struct gendisk), GFP_KERNEL);
- gd->sizes = kmalloc (minors * sizeof(int), GFP_KERNEL);
- gd->part = kmalloc (minors * sizeof(struct hd_struct), GFP_KERNEL);
- memset(gd->part, 0, minors * sizeof(struct hd_struct));
-
- gd->major = xlide_major; /* XXX should be idx-specific */
- gd->major_name = XLIDE_MAJOR_NAME; /* XXX should be idx-specific */
- gd->minor_shift = IDE_PARTN_BITS;
- gd->max_p = 1<<IDE_PARTN_BITS;
- gd->nr_real = units;
- gd->real_devices = NULL;
- gd->next = NULL;
- gd->fops = &xlide_block_fops;
- gd->de_arr = kmalloc (sizeof *gd->de_arr * units, GFP_KERNEL);
- gd->flags = kmalloc (sizeof *gd->flags * units, GFP_KERNEL);
-
- if (gd->de_arr)
- memset (gd->de_arr, 0, sizeof *gd->de_arr * units);
-
- if (gd->flags)
- memset (gd->flags, 0, sizeof *gd->flags * units);
-
- add_gendisk(gd);
-
- xen_disk_info.disks[xidx].gendisk = gd;
-
- /* XXX major should be idx-specific */
- register_disk(gd, MKDEV(xlide_major, 0), 1<<IDE_PARTN_BITS,
- &xlide_block_fops, xen_disk_info.disks[xidx].capacity);
-
- return;
-}
-
-
-
-/*
-** Initialize a XenoLinux IDE disk; the 'xidx' is the index into the
-** xen_disk_info array so we can grab interesting values; the 'idx' is
-** a count of the number of XLSCSI disks we've seen so far, starting at 0
-** XXX SMH: this is all so ugly because the xen_disk_info() structure and
-** array doesn't really give us what we want. Ho hum. To be tidied someday.
-*/
-int xlide_init(int xidx, int idx)
-{
- int i, major, result;
-
SET_MODULE_OWNER(&xlide_block_fops);
- major = xlide_major + idx; /* XXX assume we have a linear major space */
-
- /* XXX SMH: name below should vary with major */
- result = register_blkdev(major, XLIDE_MAJOR_NAME, &xlide_block_fops);
- if (result < 0) {
- printk (KERN_ALERT "XL IDE: can't get major %d\n",
- major);
+ result = register_blkdev(XLIDE_MAJOR, XLIDE_MAJOR_NAME,
+ &xlide_block_fops);
+ if ( result < 0 )
+ {
+ printk (KERN_ALERT "XL IDE: can't get major %d\n", XLIDE_MAJOR);
return result;
}
- /* initialize global arrays in drivers/block/ll_rw_block.c */
- for (i = 0; i < XLIDE_MAX; i++) {
- xlide_blk_size[i] = xen_disk_info.disks[0].capacity;
+ /* Initialize global arrays. */
+ for ( i = 0; i < XLIDE_MAX; i++ )
+ {
xlide_blksize_size[i] = 512;
xlide_hardsect_size[i] = 512;
xlide_max_sectors[i] = 128;
}
- xlide_read_ahead = 8;
- blk_size[major] = xlide_blk_size;
- blksize_size[major] = xlide_blksize_size;
- hardsect_size[major] = xlide_hardsect_size;
- read_ahead[major] = xlide_read_ahead;
- max_sectors[major] = xlide_max_sectors;
+ blk_size[XLIDE_MAJOR] = NULL;
+ blksize_size[XLIDE_MAJOR] = xlide_blksize_size;
+ hardsect_size[XLIDE_MAJOR] = xlide_hardsect_size;
+ max_sectors[XLIDE_MAJOR] = xlide_max_sectors;
+ read_ahead[XLIDE_MAJOR] = 8;
- blk_init_queue(BLK_DEFAULT_QUEUE(major), do_xlblk_request);
+ blk_init_queue(BLK_DEFAULT_QUEUE(XLIDE_MAJOR), do_xlblk_request);
/*
* Turn off barking 'headactive' mode. We dequeue buffer heads as
* soon as we pass them down to Xen.
*/
- blk_queue_headactive(BLK_DEFAULT_QUEUE(major), 0);
+ blk_queue_headactive(BLK_DEFAULT_QUEUE(XLIDE_MAJOR), 0);
- xlide_register_disk(xidx, idx);
+ /* Count number of IDE devices installed in the system. */
+ units = 0;
+ for ( i = 0; i < xdi->count; i++ )
+ if ( xdi->disks[i].type == XEN_DISK_IDE ) units++;
+ /* Construct an appropriate gendisk structure. */
+ minors = units * (1<<IDE_PARTN_BITS);
+ gd = kmalloc(sizeof(struct gendisk), GFP_KERNEL);
+ gd->sizes = kmalloc(minors * sizeof(int), GFP_KERNEL);
+ gd->part = kmalloc(minors * sizeof(struct hd_struct), GFP_KERNEL);
+ gd->major = XLIDE_MAJOR;
+ gd->major_name = XLIDE_MAJOR_NAME;
+ gd->minor_shift = IDE_PARTN_BITS;
+ gd->max_p = 1<<IDE_PARTN_BITS;
+ gd->nr_real = units;
+ gd->real_devices = NULL;
+ gd->next = NULL;
+ gd->fops = &xlide_block_fops;
+ gd->de_arr = kmalloc(sizeof(*gd->de_arr) * units, GFP_KERNEL);
+ gd->flags = kmalloc(sizeof(*gd->flags) * units, GFP_KERNEL);
+ memset(gd->sizes, 0, minors * sizeof(int));
+ memset(gd->part, 0, minors * sizeof(struct hd_struct));
+ memset(gd->de_arr, 0, sizeof(*gd->de_arr) * units);
+ memset(gd->flags, 0, sizeof(*gd->flags) * units);
+ xlide_gendisk = gd;
+ add_gendisk(gd);
+
+ /* Now register each disk in turn. */
+ disk = 0;
+ for ( i = 0; i < xdi->count; i++ )
+ {
+ if ( xdi->disks[i].type != XEN_DISK_IDE ) continue;
+ register_disk(gd,
+ MKDEV(XLIDE_MAJOR, disk<<IDE_PARTN_BITS),
+ 1<<IDE_PARTN_BITS,
+ &xlide_block_fops,
+ xdi->disks[i].capacity);
+ disk++;
+ }
+
printk(KERN_ALERT
"XenoLinux Virtual IDE Device Driver installed [device: %d]\n",
- major);
+ XLIDE_MAJOR);
return 0;
}
@@ -169,32 +123,34 @@ int xlide_init(int xidx, int idx)
void xlide_cleanup(void)
{
- /* CHANGE FOR MULTIQUEUE */
- blk_cleanup_queue(BLK_DEFAULT_QUEUE(xlide_major));
+ blk_cleanup_queue(BLK_DEFAULT_QUEUE(XLIDE_MAJOR));
- /* clean up global arrays */
- read_ahead[xlide_major] = 0;
+ xlide_gendisk = NULL;
- if (blk_size[xlide_major])
- kfree(blk_size[xlide_major]);
- blk_size[xlide_major] = NULL;
+ read_ahead[XLIDE_MAJOR] = 0;
- if (blksize_size[xlide_major])
- kfree(blksize_size[xlide_major]);
- blksize_size[xlide_major] = NULL;
+ if ( blksize_size[XLIDE_MAJOR] != NULL )
+ {
+ kfree(blksize_size[XLIDE_MAJOR]);
+ blksize_size[XLIDE_MAJOR] = NULL;
+ }
- if (hardsect_size[xlide_major])
- kfree(hardsect_size[xlide_major]);
- hardsect_size[xlide_major] = NULL;
+ if ( hardsect_size[XLIDE_MAJOR] != NULL )
+ {
+ kfree(hardsect_size[XLIDE_MAJOR]);
+ hardsect_size[XLIDE_MAJOR] = NULL;
+ }
+
+ if ( max_sectors[XLIDE_MAJOR] != NULL )
+ {
+ kfree(max_sectors[XLIDE_MAJOR]);
+ max_sectors[XLIDE_MAJOR] = NULL;
+ }
- /* XXX: free each gendisk */
- if (unregister_blkdev(xlide_major, XLIDE_MAJOR_NAME))
+ if ( unregister_blkdev(XLIDE_MAJOR, XLIDE_MAJOR_NAME) != 0 )
+ {
printk(KERN_ALERT
"XenoLinux Virtual IDE Device Driver uninstalled w/ errs\n");
- else
- printk(KERN_ALERT
- "XenoLinux Virtual IDE Device Driver uninstalled\n");
-
- return;
+ }
}
diff --git a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_scsi.c b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_scsi.c
index 3ee86509f1..ddbd22d5f1 100644
--- a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_scsi.c
+++ b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_scsi.c
@@ -5,58 +5,20 @@
*
*/
-#include <linux/config.h>
-#include <linux/module.h>
-
-#include <linux/kernel.h>
-#include <linux/sched.h>
-#include <linux/slab.h>
-#include <linux/string.h>
-#include <linux/errno.h>
-
-#include <linux/fs.h>
-#include <linux/hdreg.h>
-#include <linux/blkdev.h>
-#include <linux/major.h>
-
-#define MAJOR_NR XLSCSI_MAJOR /* force defns in blk.h, must precede include */
-static int xlscsi_major = XLSCSI_MAJOR;
-#include <linux/blk.h>
-
-/* Copied from linux/ide.h */
-typedef unsigned char byte;
+#include "xl_block.h"
-void xlscsi_ide_register_disk(int, unsigned long);
+#define MAJOR_NR XLSCSI_MAJOR
+#include <linux/blk.h>
-#define SCSI_DISKS_PER_MAJOR 16 /* max number of devices per scsi major */
-#define XLSCSI_MAX 32 /* maximum minor devices we support */
+/* We support up to 16 devices of up to 16 partitions each. */
+#define XLSCSI_MAX 256
#define XLSCSI_MAJOR_NAME "xsd"
-
-static int xlscsi_blk_size[XLSCSI_MAX];
+#define SCSI_PARTN_BITS 4
static int xlscsi_blksize_size[XLSCSI_MAX];
-static int xlscsi_read_ahead;
static int xlscsi_hardsect_size[XLSCSI_MAX];
static int xlscsi_max_sectors[XLSCSI_MAX];
-#if 0
-#define DPRINTK(_f, _a...) printk ( KERN_ALERT _f , ## _a )
-#define DPRINTK_IOCTL(_f, _a...) printk ( KERN_ALERT _f , ## _a )
-#else
-#define DPRINTK(_f, _a...) ((void)0)
-#define DPRINTK_IOCTL(_f, _a...) ((void)0)
-#endif
-
-extern xen_disk_info_t xen_disk_info;
-
-extern int xenolinux_block_open(struct inode *inode, struct file *filep);
-extern int xenolinux_block_release(struct inode *inode, struct file *filep);
-extern int xenolinux_block_ioctl(struct inode *inode, struct file *filep,
- unsigned command, unsigned long argument);
-extern int xenolinux_block_check(kdev_t dev);
-extern int xenolinux_block_revalidate(kdev_t dev);
-
-
-extern void do_xlblk_request (request_queue_t *rq);
+struct gendisk *xlscsi_gendisk = NULL;
static struct block_device_operations xlscsi_block_fops =
{
@@ -75,137 +37,121 @@ int xlscsi_hwsect(int minor)
}
-void xlscsi_register_disk(int xidx, int idx)
+int xlscsi_init(xen_disk_info_t *xdi)
{
- int minors;
+ int i, result, units, minors, disk;
struct gendisk *gd;
- unsigned long capacity;
-
- minors = XLSCSI_MAX;
- gd = kmalloc (sizeof(struct gendisk), GFP_KERNEL);
- gd->sizes = kmalloc (minors * sizeof(int), GFP_KERNEL);
- gd->part = kmalloc (minors * sizeof(struct hd_struct), GFP_KERNEL);
- memset(gd->part, 0, minors * sizeof(struct hd_struct));
-
- if(idx > 0)
- printk("xlscsi_register_disk: need fix to handle "
- "multiple SCSI majors!\n");
-
- gd->major = xlscsi_major; /* XXX should be idx-specific */
- gd->major_name = XLSCSI_MAJOR_NAME; /* XXX should be idx-specific */
- gd->minor_shift = 4;
- gd->max_p = 1<<4;
- gd->nr_real = SCSI_DISKS_PER_MAJOR;
- gd->real_devices = NULL;
- gd->next = NULL;
- gd->fops = &xlscsi_block_fops;
- gd->de_arr = kmalloc (sizeof *gd->de_arr * SCSI_DISKS_PER_MAJOR,
- GFP_KERNEL);
- gd->flags = kmalloc (sizeof *gd->flags * SCSI_DISKS_PER_MAJOR,
- GFP_KERNEL);
-
- if (gd->de_arr)
- memset (gd->de_arr, 0, sizeof *gd->de_arr * SCSI_DISKS_PER_MAJOR);
-
- if (gd->flags)
- memset (gd->flags, 0, sizeof *gd->flags * SCSI_DISKS_PER_MAJOR);
-
- add_gendisk(gd);
-
- xen_disk_info.disks[xidx].gendisk = gd;
-
- /* XXX major below should be idx-specific */
- register_disk(gd, MKDEV(xlscsi_major, 0), 1<<4, &xlscsi_block_fops,
- xen_disk_info.disks[xidx].capacity);
-
- return;
-}
-
-
-/*
-** Initialize a XenoLinux SCSI disk; the 'xidx' is the index into the
-** xen_disk_info array so we can grab interesting values; the 'idx' is
-** a count of the number of XLSCSI disks we've seen so far, starting at 0
-** XXX SMH: this is all so ugly because the xen_disk_info() structure and
-** array doesn't really give us what we want. Ho hum. To be tidied someday.
-*/
-int xlscsi_init(int xidx, int idx)
-{
- int i, major, result;
SET_MODULE_OWNER(&xlscsi_block_fops);
- major = xlscsi_major + idx; /* XXX asume we have linear major space */
-
- /* XXX SMH: 'name' below should vary for different major values */
- result = register_blkdev(major, XLSCSI_MAJOR_NAME, &xlscsi_block_fops);
-
- if (result < 0) {
- printk (KERN_ALERT "XL SCSI: can't get major %d\n", major);
+ result = register_blkdev(XLSCSI_MAJOR, XLSCSI_MAJOR_NAME,
+ &xlscsi_block_fops);
+ if ( result < 0 )
+ {
+ printk (KERN_ALERT "XL SCSI: can't get major %d\n", XLSCSI_MAJOR);
return result;
}
- /* initialize global arrays in drivers/block/ll_rw_block.c */
- for (i = 0; i < XLSCSI_MAX; i++) {
- xlscsi_blk_size[i] = xen_disk_info.disks[xidx].capacity;
+ /* Initialize global arrays. */
+ for ( i = 0; i < XLSCSI_MAX; i++ )
+ {
xlscsi_blksize_size[i] = 512;
xlscsi_hardsect_size[i] = 512;
xlscsi_max_sectors[i] = 128;
}
- xlscsi_read_ahead = 8;
- blk_size[major] = xlscsi_blk_size;
- blksize_size[major] = xlscsi_blksize_size;
- hardsect_size[major] = xlscsi_hardsect_size;
- read_ahead[major] = xlscsi_read_ahead;
- max_sectors[major] = xlscsi_max_sectors;
+ blk_size[XLSCSI_MAJOR] = NULL;
+ blksize_size[XLSCSI_MAJOR] = xlscsi_blksize_size;
+ hardsect_size[XLSCSI_MAJOR] = xlscsi_hardsect_size;
+ max_sectors[XLSCSI_MAJOR] = xlscsi_max_sectors;
+ read_ahead[XLSCSI_MAJOR] = 8;
- blk_init_queue(BLK_DEFAULT_QUEUE(major), do_xlblk_request);
+ blk_init_queue(BLK_DEFAULT_QUEUE(XLSCSI_MAJOR), do_xlblk_request);
/*
* Turn off barking 'headactive' mode. We dequeue buffer heads as
* soon as we pass them down to Xen.
*/
- blk_queue_headactive(BLK_DEFAULT_QUEUE(major), 0);
-
- xlscsi_register_disk(xidx, idx);
+ blk_queue_headactive(BLK_DEFAULT_QUEUE(XLSCSI_MAJOR), 0);
+
+ /* Count number of SCSI devices installed in the system. */
+ units = 0;
+ for ( i = 0; i < xdi->count; i++ )
+ if ( xdi->disks[i].type == XEN_DISK_SCSI ) units++;
+
+ /* Construct an appropriate gendisk structure. */
+ minors = units * (1<<SCSI_PARTN_BITS);
+ gd = kmalloc(sizeof(struct gendisk), GFP_KERNEL);
+ gd->sizes = kmalloc(minors * sizeof(int), GFP_KERNEL);
+ gd->part = kmalloc(minors * sizeof(struct hd_struct), GFP_KERNEL);
+ gd->major = XLSCSI_MAJOR;
+ gd->major_name = XLSCSI_MAJOR_NAME;
+ gd->minor_shift = SCSI_PARTN_BITS;
+ gd->max_p = 1<<SCSI_PARTN_BITS;
+ gd->nr_real = units;
+ gd->real_devices = NULL;
+ gd->next = NULL;
+ gd->fops = &xlscsi_block_fops;
+ gd->de_arr = kmalloc(sizeof(*gd->de_arr) * units, GFP_KERNEL);
+ gd->flags = kmalloc(sizeof(*gd->flags) * units, GFP_KERNEL);
+ memset(gd->sizes, 0, minors * sizeof(int));
+ memset(gd->part, 0, minors * sizeof(struct hd_struct));
+ memset(gd->de_arr, 0, sizeof(*gd->de_arr) * units);
+ memset(gd->flags, 0, sizeof(*gd->flags) * units);
+ xlscsi_gendisk = gd;
+ add_gendisk(gd);
+ /* Now register each disk in turn. */
+ disk = 0;
+ for ( i = 0; i < xdi->count; i++ )
+ {
+ if ( xdi->disks[i].type != XEN_DISK_SCSI ) continue;
+ register_disk(gd,
+ MKDEV(XLSCSI_MAJOR, disk<<SCSI_PARTN_BITS),
+ 1<<SCSI_PARTN_BITS,
+ &xlscsi_block_fops,
+ xdi->disks[i].capacity);
+ disk++;
+ }
+
printk(KERN_ALERT
"XenoLinux Virtual SCSI Device Driver installed [device: %d]\n",
- major);
+ XLSCSI_MAJOR);
+
return 0;
}
-
void xlscsi_cleanup(void)
{
- /* CHANGE FOR MULTIQUEUE */
- blk_cleanup_queue(BLK_DEFAULT_QUEUE(xlscsi_major));
+ blk_cleanup_queue(BLK_DEFAULT_QUEUE(XLSCSI_MAJOR));
- /* clean up global arrays */
- read_ahead[xlscsi_major] = 0;
+ xlscsi_gendisk = NULL;
- if (blk_size[xlscsi_major])
- kfree(blk_size[xlscsi_major]);
- blk_size[xlscsi_major] = NULL;
+ read_ahead[XLSCSI_MAJOR] = 0;
- if (blksize_size[xlscsi_major])
- kfree(blksize_size[xlscsi_major]);
- blksize_size[xlscsi_major] = NULL;
+ if ( blksize_size[XLSCSI_MAJOR] != NULL )
+ {
+ kfree(blksize_size[XLSCSI_MAJOR]);
+ blksize_size[XLSCSI_MAJOR] = NULL;
+ }
- if (hardsect_size[xlscsi_major])
- kfree(hardsect_size[xlscsi_major]);
- hardsect_size[xlscsi_major] = NULL;
+ if ( hardsect_size[XLSCSI_MAJOR] != NULL )
+ {
+ kfree(hardsect_size[XLSCSI_MAJOR]);
+ hardsect_size[XLSCSI_MAJOR] = NULL;
+ }
+
+ if ( max_sectors[XLSCSI_MAJOR] != NULL )
+ {
+ kfree(max_sectors[XLSCSI_MAJOR]);
+ max_sectors[XLSCSI_MAJOR] = NULL;
+ }
- /* XXX: free each gendisk */
- if (unregister_blkdev(xlscsi_major, XLSCSI_MAJOR_NAME))
+ if ( unregister_blkdev(XLSCSI_MAJOR, XLSCSI_MAJOR_NAME) != 0 )
+ {
printk(KERN_ALERT
"XenoLinux Virtual SCSI Device Driver uninstalled w/ errs\n");
- else
- printk(KERN_ALERT
- "XenoLinux Virtual SCSI Device Driver uninstalled\n");
-
- return;
+ }
}
diff --git a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_segment.c b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_segment.c
index 0754daa9a3..8dfa24fc09 100644
--- a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_segment.c
+++ b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_segment.c
@@ -5,425 +5,172 @@
*
*/
-#include <linux/config.h>
-#include <linux/module.h>
-
-#include <linux/kernel.h>
-#include <linux/sched.h>
-#include <linux/slab.h>
-#include <linux/string.h>
-#include <linux/errno.h>
-
-#include <linux/fs.h>
-#include <linux/hdreg.h>
-#include <linux/blkdev.h>
-#include <linux/major.h>
-
-#include <asm/hypervisor-ifs/block.h>
-#include <asm/hypervisor-ifs/hypervisor-if.h>
-#include <asm/io.h>
-#include <asm/atomic.h>
-#include <asm/uaccess.h>
-
-#define MAJOR_NR XLSEG_MAJOR /* force defns in blk.h, must precede include */
-static int xlseg_major = XLSEG_MAJOR;
+#include "xl_block.h"
+
+#define MAJOR_NR XLVIRT_MAJOR
#include <linux/blk.h>
/* Copied from linux/ide.h */
-typedef unsigned char byte;
-
-#define XLSEG_MAX 32 /* Maximum minor devices we support */
-#define XLSEG_MAJOR_NAME "xhd"
-
-static int xlseg_blk_size[XLSEG_MAX];
-static int xlseg_blksize_size[XLSEG_MAX];
-static int xlseg_read_ahead;
-static int xlseg_hardsect_size[XLSEG_MAX];
-static int xlseg_max_sectors[XLSEG_MAX];
-
-extern atomic_t xlblk_control_count; /* xl_block.c */
-
-int hypervisor_request(void * id,
- int operation,
- char * buffer,
- unsigned long block_number,
- unsigned short block_size,
- kdev_t device,
- struct gendisk *gd);
-void xlseg_register_disk(int idx, unsigned long capacity);
-
-#if 0
-#define DPRINTK(_f, _a...) printk ( KERN_ALERT _f , ## _a )
-#define DPRINTK_IOCTL(_f, _a...) printk ( KERN_ALERT _f , ## _a )
-#else
-#define DPRINTK(_f, _a...) ((void)0)
-#define DPRINTK_IOCTL(_f, _a...) ((void)0)
-#endif
-
-static xen_disk_info_t xlseg_disk_info;
-
-/* ------------------------------------------------------------------------
- */
-
-static int xenolinux_segment_open(struct inode *inode, struct file *filep)
-{
- DPRINTK("xenolinux_segment_release\n");
- return 0;
-}
-
-static int xenolinux_segment_release(struct inode *inode, struct file *filep)
-{
- DPRINTK("xenolinux_segment_release\n");
- return 0;
-}
-
-static int xenolinux_segment_ioctl(struct inode *inode, struct file *filep,
- unsigned command, unsigned long argument)
-{
- int minor_dev;
- struct hd_geometry *geo = (struct hd_geometry *)argument;
- struct gendisk *gd = (struct gendisk *)xlseg_disk_info.disks[0].gendisk;
-
- DPRINTK("xenolinux_segment_ioctl\n");
-
- /* check permissions */
- if (!capable(CAP_SYS_ADMIN)) return -EPERM;
- if (!inode) return -EINVAL;
- minor_dev = MINOR(inode->i_rdev);
- if (minor_dev >= XLSEG_MAX) return -ENODEV;
-
- DPRINTK_IOCTL("command: 0x%x, argument: 0x%lx, minor: 0x%x\n",
- command, (long) argument, minor_dev);
-
- switch (command)
- {
- case BLKGETSIZE:
- if (gd != NULL)
- {
- printk(KERN_ALERT "minordev: %d\n", minor_dev);
- printk(KERN_ALERT "[0] start: %lx\n", gd->part[0].start_sect);
- printk(KERN_ALERT "[0] count: %lx\n", gd->part[0].nr_sects);
- printk(KERN_ALERT "[1] start: %lx\n", gd->part[1].start_sect);
- printk(KERN_ALERT "[1] count: %lx\n", gd->part[1].nr_sects);
- printk(KERN_ALERT "[2] start: %lx\n", gd->part[2].start_sect);
- printk(KERN_ALERT "[2] count: %lx\n", gd->part[2].nr_sects);
-
- DPRINTK_IOCTL(" BLKGETSIZE gd: %x %lx\n", BLKGETSIZE,
- gd->part[minor_dev].nr_sects);
- return put_user(gd->part[minor_dev].nr_sects,
- (unsigned long *)argument);
- }
- else
- {
- DPRINTK_IOCTL(" BLKGETSIZE disk: %x %lx\n", BLKGETSIZE,
- xlseg_disk_info.disks[0].capacity);
- return put_user(xlseg_disk_info.disks[0].capacity,
- (unsigned long *) argument);
- }
-
- case BLKRRPART:
- DPRINTK_IOCTL(" BLKRRPART: \n");
- /* we don't have re-validate drive yet... so you need to reboot! */
- break;
-
- case BLKSSZGET:
- DPRINTK_IOCTL(" BLKSSZGET: %d\n",
- xlseg_hardsect_size[minor_dev]);
- return xlseg_hardsect_size[minor_dev];
-
- case HDIO_GETGEO:
- /* note: these values are complete garbage */
- DPRINTK_IOCTL(" HDIO_GETGEO: \n");
- if (!argument) return -EINVAL;
- if (put_user(0x00, (unsigned long *) &geo->start)) return -EFAULT;
- if (put_user(0xff, (byte *)&geo->heads)) return -EFAULT;
- if (put_user(0x3f, (byte *)&geo->sectors)) return -EFAULT;
- if (put_user(0x106, (unsigned short *)&geo->cylinders)) return -EFAULT;
- return 0;
-
- case HDIO_GETGEO_BIG:
- /* note: these values are complete garbage */
- DPRINTK_IOCTL(" HDIO_GETGEO_BIG\n");
- if (!argument) return -EINVAL;
- if (put_user(0x00, (unsigned long *) &geo->start)) return -EFAULT;
- if (put_user(0xff, (byte *)&geo->heads)) return -EFAULT;
- if (put_user(0x3f, (byte *)&geo->sectors)) return -EFAULT;
- if (put_user(0x106, (unsigned int *) &geo->cylinders)) return -EFAULT;
- return 0;
-
- default:
- DPRINTK_IOCTL(" eh? unknown ioctl\n");
- break;
- }
-
- return 0;
-}
+typedef unsigned char byte;
-static int xenolinux_segment_check(kdev_t dev)
-{
- DPRINTK("xenolinux_segment_check\n");
- return 0;
-}
+/* We support up to 16 devices of up to 16 partitions each. */
+#define XLVIRT_MAX 256
+#define XLVIRT_MAJOR_NAME "xvd"
+#define VIRT_PARTN_BITS 4
+static int xlseg_blksize_size[XLVIRT_MAX];
+static int xlseg_hardsect_size[XLVIRT_MAX];
+static int xlseg_max_sectors[XLVIRT_MAX];
-static int xenolinux_segment_revalidate(kdev_t dev)
-{
- DPRINTK("xenolinux_segment_revalidate\n");
- return 0;
-}
+struct gendisk *xlsegment_gendisk;
-void do_xlseg_requestX (request_queue_t *rq)
-{
- /* this is a bit dumb. do_xlseg_request is defined in blk.h
- and this is thus static. but we have cooperative
- device drivers... */
- do_xlseg_request(rq);
-}
+static xen_disk_info_t xlseg_disk_info;
-/*
- * do_xlseg_request
- * read a block; request is in a request queue
- */
-static void do_xlseg_request (request_queue_t *rq)
+static struct block_device_operations xlsegment_block_fops =
{
- struct request *req;
- struct buffer_head *bh;
- int rw, nsect, full, queued = 0;
-
- /* DPRINTK("do_xlseg_request for '%s'\n", DEVICE_NAME); */
-
- while ( !rq->plugged && !QUEUE_EMPTY )
- {
- if ( (req = CURRENT) == NULL ) goto out;
-
- DPRINTK("do_xlseg_request %p: cmd %i, sec %lx, (%li/%li) bh:%p\n",
- req, req->cmd, req->sector,
- req->current_nr_sectors, req->nr_sectors, req->bh);
-
- rw = req->cmd;
- if ( rw == READA ) rw = READ;
- if ((rw != READ) && (rw != WRITE))
- panic("XenoLinux Virtual Segment Device: bad cmd: %d\n", rw);
-
- req->errors = 0;
-
- bh = req->bh;
- while ( bh != NULL )
- {
- full = hypervisor_request(
- bh, (rw == READ) ? XEN_BLOCK_READ : XEN_BLOCK_WRITE,
- bh->b_data, bh->b_rsector, bh->b_size, bh->b_dev,
- (struct gendisk *)xlseg_disk_info.disks[0].gendisk);
-
- if ( full )
- {
- goto out;
- }
-
- queued++;
-
- /* Dequeue the buffer head from the request. */
- nsect = bh->b_size >> 9;
- req->bh = bh->b_reqnext;
- bh->b_reqnext = NULL;
- bh = req->bh;
-
- if ( bh != NULL )
- {
- /* There's another buffer head to do. Update the request. */
- req->hard_sector += nsect;
- req->hard_nr_sectors -= nsect;
- req->sector = req->hard_sector;
- req->nr_sectors = req->hard_nr_sectors;
- req->current_nr_sectors = bh->b_size >> 9;
- req->buffer = bh->b_data;
- }
- else
- {
- /* That was the last buffer head. Finalise the request. */
- if ( end_that_request_first(req, 1, "XenSeg") ) BUG();
- blkdev_dequeue_request(req);
- end_that_request_last(req);
- }
- }
- }
-
- out:
- if ( queued != 0 ) HYPERVISOR_block_io_op();
-}
+ open: xenolinux_block_open,
+ release: xenolinux_block_release,
+ ioctl: xenolinux_block_ioctl,
+ check_media_change: xenolinux_block_check,
+ revalidate: xenolinux_block_revalidate,
+};
-static struct block_device_operations xenolinux_segment_fops =
+int xlsegment_hwsect(int minor)
{
- open: xenolinux_segment_open,
- release: xenolinux_segment_release,
- ioctl: xenolinux_segment_ioctl,
- check_media_change: xenolinux_segment_check,
- revalidate: xenolinux_segment_revalidate,
-};
+ return xlseg_hardsect_size[minor];
+}
int __init xlseg_init(void)
{
- int i, result;
- int counter;
+ int i, result, units, minors, disk;
+ xen_disk_info_t *xdi = &xlseg_disk_info;
+ struct gendisk *gd;
- /* probe for disk information */
- memset (&xlseg_disk_info, 0, sizeof(xlseg_disk_info));
- xlseg_disk_info.count = 0;
+ SET_MODULE_OWNER(&xlsegment_block_fops);
+ /* Probe for disk information. */
+ memset(xdi, 0, sizeof(*xdi));
+ xenolinux_control_msg(XEN_BLOCK_PROBE_SEG, (char *)xdi);
- {
- /* get lock xlblk_control_lock */
- counter = atomic_read(&xlblk_control_count);
- atomic_inc(&xlblk_control_count);
- /* release lock xlblk_control_lock */
- }
- if ( hypervisor_request(NULL, XEN_BLOCK_PROBE_SEG,
- (char *) &xlseg_disk_info,
- 0, 0, (kdev_t) 0,
- (struct gendisk *)NULL) )
- BUG();
- HYPERVISOR_block_io_op();
- while (atomic_read(&xlblk_control_count) != counter) barrier();
-
- printk (KERN_ALERT "vhd block device probe:\n");
- for ( i = 0; i < xlseg_disk_info.count; i++ )
+ DPRINTK("vhd block device probe:\n");
+ for ( i = 0; i < xdi->count; i++ )
{
- printk (KERN_ALERT " %2d: type: %d, capacity: %ld\n",
- i, xlseg_disk_info.disks[i].type,
- xlseg_disk_info.disks[i].capacity);
+ DPRINTK(" %2d: type: %d, capacity: %ld\n",
+ i, xdi->disks[i].type, xdi->disks[i].capacity);
}
- SET_MODULE_OWNER(&xenolinux_segment_fops);
- result = register_blkdev(xlseg_major, "segment", &xenolinux_segment_fops);
- if (result < 0) {
- printk (KERN_ALERT "xenolinux segment: can't get major %d\n",
- xlseg_major);
+ result = register_blkdev(XLVIRT_MAJOR, XLVIRT_MAJOR_NAME,
+ &xlsegment_block_fops);
+ if ( result < 0 )
+ {
+ printk(KERN_ALERT "XL Segment: can't get major %d\n", XLVIRT_MAJOR);
return result;
}
- /* initialize global arrays in drivers/block/ll_rw_block.c */
- for (i = 0; i < XLSEG_MAX; i++)
+ /* Initialize global arrays. */
+ for (i = 0; i < XLVIRT_MAX; i++)
{
- xlseg_blk_size[i] = xlseg_disk_info.disks[0].capacity ;
- xlseg_blksize_size[i] = 512;
- xlseg_hardsect_size[i] = 512;
- xlseg_max_sectors[i] = 128;
+ xlseg_blksize_size[i] = 512;
+ xlseg_hardsect_size[i] = 512;
+ xlseg_max_sectors[i] = 128;
}
- xlseg_read_ahead = 8;
- blk_size[xlseg_major] = xlseg_blk_size;
- blksize_size[xlseg_major] = xlseg_blksize_size;
- hardsect_size[xlseg_major] = xlseg_hardsect_size;
- read_ahead[xlseg_major] = xlseg_read_ahead;
- max_sectors[xlseg_major] = xlseg_max_sectors;
+ blk_size[XLVIRT_MAJOR] = NULL;
+ blksize_size[XLVIRT_MAJOR] = xlseg_blksize_size;
+ hardsect_size[XLVIRT_MAJOR] = xlseg_hardsect_size;
+ max_sectors[XLVIRT_MAJOR] = xlseg_max_sectors;
+ read_ahead[XLVIRT_MAJOR] = 8;
- blk_init_queue(BLK_DEFAULT_QUEUE(xlseg_major), do_xlseg_request);
+ blk_init_queue(BLK_DEFAULT_QUEUE(XLVIRT_MAJOR), do_xlblk_request);
/*
* Turn off barking 'headactive' mode. We dequeue buffer heads as
* soon as we pass them down to Xen.
*/
- blk_queue_headactive(BLK_DEFAULT_QUEUE(xlseg_major), 0);
-
- xlseg_register_disk(0, xlseg_disk_info.disks[0].capacity);
-
- printk(KERN_ALERT
- "XenoLinux Virtual Segment Device Driver installed [device: %d]\n",
- xlseg_major);
- return 0;
-}
-
-void xlseg_register_disk(int idx, unsigned long capacity)
-{
- int units;
- int minors;
- struct gendisk *gd;
-
- /* plagarized from ide-probe.c::init_gendisk */
-
- units = 2; /* from ide.h::MAX_DRIVES */
-
-#define IDE_PARTN_BITS 6 /* from ide.h::PARTN_BITS */
-
- minors = units * (1<<IDE_PARTN_BITS);
- gd = kmalloc (sizeof(struct gendisk), GFP_KERNEL);
- gd->sizes = kmalloc (minors * sizeof(int), GFP_KERNEL);
- gd->part = kmalloc (minors * sizeof(struct hd_struct), GFP_KERNEL);
- memset(gd->part, 0, minors * sizeof(struct hd_struct));
-
- gd->major = xlseg_major;
- gd->major_name = XLSEG_MAJOR_NAME;
- gd->minor_shift = IDE_PARTN_BITS;
- gd->max_p = 1<<IDE_PARTN_BITS;
+ blk_queue_headactive(BLK_DEFAULT_QUEUE(XLVIRT_MAJOR), 0);
+
+
+ /* Count number of virtual devices installed in the system. */
+ units = 0;
+ for ( i = 0; i < xdi->count; i++ )
+ if ( xdi->disks[i].type == XEN_DISK_VIRTUAL ) units++;
+
+ /* Construct an appropriate gendisk structure. */
+ minors = units * (1<<VIRT_PARTN_BITS);
+ gd = kmalloc(sizeof(struct gendisk), GFP_KERNEL);
+ gd->sizes = kmalloc(minors * sizeof(int), GFP_KERNEL);
+ gd->part = kmalloc(minors * sizeof(struct hd_struct), GFP_KERNEL);
+ gd->major = XLVIRT_MAJOR;
+ gd->major_name = XLVIRT_MAJOR_NAME;
+ gd->minor_shift = VIRT_PARTN_BITS;
+ gd->max_p = 1<<VIRT_PARTN_BITS;
gd->nr_real = units;
gd->real_devices = NULL;
gd->next = NULL;
- gd->fops = &xenolinux_segment_fops;
- gd->de_arr = kmalloc (sizeof *gd->de_arr * units, GFP_KERNEL);
- gd->flags = kmalloc (sizeof *gd->flags * units, GFP_KERNEL);
-
- if (gd->de_arr)
- memset (gd->de_arr, 0, sizeof *gd->de_arr * units);
-
- if (gd->flags)
- memset (gd->flags, 0, sizeof *gd->flags * units);
-
+ gd->fops = &xlsegment_block_fops;
+ gd->de_arr = kmalloc(sizeof(*gd->de_arr) * units, GFP_KERNEL);
+ gd->flags = kmalloc(sizeof(*gd->flags) * units, GFP_KERNEL);
+ memset(gd->sizes, 0, minors * sizeof(int));
+ memset(gd->part, 0, minors * sizeof(struct hd_struct));
+ memset(gd->de_arr, 0, sizeof(*gd->de_arr) * units);
+ memset(gd->flags, 0, sizeof(*gd->flags) * units);
+ xlsegment_gendisk = gd;
add_gendisk(gd);
- xlseg_disk_info.disks[idx].gendisk = gd;
-
- register_disk(gd, MKDEV(xlseg_major, 0), 1<<IDE_PARTN_BITS,
- &xenolinux_segment_fops, capacity);
-
+ /* Now register each disk in turn. */
+ disk = 0;
+ for ( i = 0; i < xdi->count; i++ )
{
- int loop = 0;
- printk (KERN_ALERT "Partition Table: (capacity: %lx)\n", capacity);
- for (loop = 0; loop < minors; loop++)
- {
- if (gd->part[loop].start_sect && gd->part[loop].nr_sects)
- {
- printk (KERN_ALERT
- " %2d: 0x%6lx %8ld 0x%6lx %7ld\n", loop,
- gd->part[loop].start_sect, gd->part[loop].start_sect,
- gd->part[loop].nr_sects, gd->part[loop].nr_sects);
- }
- }
+ if ( xdi->disks[i].type != XEN_DISK_VIRTUAL ) continue;
+ register_disk(gd,
+ MKDEV(XLVIRT_MAJOR, disk<<VIRT_PARTN_BITS),
+ 1<<VIRT_PARTN_BITS,
+ &xlsegment_block_fops,
+ xdi->disks[i].capacity);
+ disk++;
}
- return;
+ printk(KERN_ALERT
+ "XenoLinux Virtual Segment Device Driver installed [device: %d]\n",
+ XLVIRT_MAJOR);
+
+ return 0;
}
static void __exit xlseg_cleanup(void)
{
- /* CHANGE FOR MULTIQUEUE */
- blk_cleanup_queue(BLK_DEFAULT_QUEUE(xlseg_major));
+ blk_cleanup_queue(BLK_DEFAULT_QUEUE(XLVIRT_MAJOR));
- /* clean up global arrays */
- read_ahead[xlseg_major] = 0;
+ xlsegment_gendisk = NULL;
- if (blk_size[xlseg_major])
- kfree(blk_size[xlseg_major]);
- blk_size[xlseg_major] = NULL;
+ read_ahead[XLVIRT_MAJOR] = 0;
- if (blksize_size[xlseg_major])
- kfree(blksize_size[xlseg_major]);
- blksize_size[xlseg_major] = NULL;
+ if ( blksize_size[XLVIRT_MAJOR] != NULL )
+ {
+ kfree(blksize_size[XLVIRT_MAJOR]);
+ blksize_size[XLVIRT_MAJOR] = NULL;
+ }
- if (hardsect_size[xlseg_major])
- kfree(hardsect_size[xlseg_major]);
- hardsect_size[xlseg_major] = NULL;
+ if ( hardsect_size[XLVIRT_MAJOR] != NULL )
+ {
+ kfree(hardsect_size[XLVIRT_MAJOR]);
+ hardsect_size[XLVIRT_MAJOR] = NULL;
+ }
- /* XXX: free each gendisk */
- if (unregister_blkdev(xlseg_major, "block"))
+ if ( max_sectors[XLVIRT_MAJOR] != NULL )
+ {
+ kfree(max_sectors[XLVIRT_MAJOR]);
+ max_sectors[XLVIRT_MAJOR] = NULL;
+ }
+
+ if ( unregister_blkdev(XLVIRT_MAJOR, XLVIRT_MAJOR_NAME) != 0 )
+ {
printk(KERN_ALERT
- "XenoLinux Virtual Segment Device Driver uninstalled w/ errs\n");
- else
- printk(KERN_ALERT
- "XenoLinux Virtual Segment Device Driver uninstalled\n");
-
- return;
+ "XenoLinux Virtual Segment Device Driver"
+ " uninstalled w/ errs\n");
+ }
}
diff --git a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_segment_proc.c b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_segment_proc.c
index 8525d7855e..e7c121b683 100644
--- a/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_segment_proc.c
+++ b/xenolinux-2.4.21-pre4-sparse/arch/xeno/drivers/block/xl_segment_proc.c
@@ -4,37 +4,16 @@
* XenoLinux virtual disk proc interface .
*/
-
-#include <linux/config.h>
-#include <linux/module.h>
-
+#include "xl_block.h"
#include <linux/proc_fs.h>
#include <linux/delay.h>
-#include <asm/uaccess.h>
-#include <asm/atomic.h>
-
-#include <asm/hypervisor-ifs/block.h>
-#include <asm/hypervisor-ifs/hypervisor-if.h>
static struct proc_dir_entry *vhd;
-xv_disk_t xvd;
-
-extern atomic_t xlblk_control_count; /* xl_block.c */
-
-int hypervisor_request(void * id,
- int operation,
- char * buffer,
- unsigned long block_number,
- unsigned short block_size,
- kdev_t device,
- struct gendisk *gd);
-
-/******************************************************************/
static int proc_read_vhd(char *page, char **start, off_t off,
int count, int *eof, void *data)
{
- return 0;
+ return 0;
}
#define isdelim(c) \
@@ -42,236 +21,221 @@ static int proc_read_vhd(char *page, char **start, off_t off,
char *get_string(char *string) /* a bit like strtok */
{
- static char *temp;
- int loop = 0;
+ static char *temp;
+ int loop = 0;
- if (string != NULL)
- temp = string;
- else
- string = temp;
+ if (string != NULL)
+ temp = string;
+ else
+ string = temp;
try_again:
- while (!isdelim(string[loop]))
- {
- if (string[loop] == '\0')
- return NULL;
- loop++;
- }
+ while (!isdelim(string[loop]))
+ {
+ if (string[loop] == '\0')
+ return NULL;
+ loop++;
+ }
- string[loop] = '\0';
- temp = (string + loop + 1);
+ string[loop] = '\0';
+ temp = (string + loop + 1);
- if (loop == 0)
- {
- string = temp;
- goto try_again;
- }
+ if (loop == 0)
+ {
+ string = temp;
+ goto try_again;
+ }
- return string;
+ return string;
}
#define isdigit(c) (c >= '0' && c <= '9' ? 1 : 0)
unsigned long to_number(char *string) /* atoi */
{
- unsigned long value = 0;
+ unsigned long value = 0;
- if (string == NULL) return 0;
+ if (string == NULL) return 0;
- while (!isdigit(*string) && *string != '\0') string++;
+ while (!isdigit(*string) && *string != '\0') string++;
- while (isdigit(*string))
- {
- value = value * 10 + (*string - '0');
- string++;
- }
+ while (isdigit(*string))
+ {
+ value = value * 10 + (*string - '0');
+ string++;
+ }
- return value;
+ return value;
}
static int proc_write_vhd(struct file *file, const char *buffer,
unsigned long count, void *data)
{
- char *local = kmalloc((count + 1) * sizeof(char), GFP_KERNEL);
- char *string;
- int loop;
- int counter;
- xv_disk_t xvd;
-
- memset (&xvd, 0, sizeof(xvd));
-
- if (copy_from_user(local, buffer, count))
- {
- return -EFAULT;
- }
- local[count] = '\0';
-
- string = get_string(local); /* look for Domain */
- if (string == NULL) /* empty string */
- {
- return count;
- }
- if (*string != 'd' && *string != 'D')
- {
- printk (KERN_ALERT
- "error: domain specifier missing [%s]. should be \"domain\".\n",
- string);
- return count;
- }
+ char *local = kmalloc((count + 1) * sizeof(char), GFP_KERNEL);
+ char *string;
+ int loop;
+ xv_disk_t xvd;
- string = get_string(NULL); /* domain number */
- if (string == NULL)
- {
- printk (KERN_ALERT "error: domain number missing\n");
- return count;
- }
- xvd.domain = (int) to_number(string);
-
- string = get_string(NULL);
- if (string && (strcmp(string, "RO") == 0 || strcmp(string, "ro") == 0))
- {
- xvd.mode = XEN_DISK_READ_ONLY;
- }
- else if (string && (strcmp(string, "RW") == 0 || strcmp(string, "rw") == 0))
- {
- xvd.mode = XEN_DISK_READ_WRITE;
- }
- else
- {
- printk (KERN_ALERT
- "error: bad mode [%s]. should be \"rw\" or \"ro\".\n",
- string);
- return count;
- }
-
- string = get_string(NULL); /* look for Segment */
- if (string == NULL || (*string != 's' && *string != 'S'))
- {
- printk (KERN_ALERT
- "error: segment specifier missing [%s]. should be \"segment\".\n",
- string);
- return count;
- }
+ memset (&xvd, 0, sizeof(xvd));
- string = get_string(NULL); /* segment number */
- if (string == NULL)
- {
- printk (KERN_ALERT "error: segment number missing\n");
- return count;
- }
- xvd.segment = (int) to_number(string);
-
- string = get_string(NULL); /* look for Extents */
- if (string == NULL || (*string != 'e' && *string != 'E'))
- {
- printk (KERN_ALERT
- "error: extents specifier missing [%s]. should be \"extents\".\n",
- string);
- return count;
- }
+ if (copy_from_user(local, buffer, count))
+ {
+ return -EFAULT;
+ }
+ local[count] = '\0';
- string = get_string(NULL); /* number of extents */
- if (string == NULL)
- {
- printk (KERN_ALERT "error: number of extents missing\n");
- return count;
- }
- xvd.ext_count = (int) to_number(string);
+ string = get_string(local); /* domain specifier */
+ if (string == NULL)
+ {
+ return count;
+ }
+ if (*string != 'd' && *string != 'D')
+ {
+ printk (KERN_ALERT
+ "error: domain specifier missing [%s]. should be \"domain\".\n",
+ string);
+ return count;
+ }
- /* ignore parenthesis */
+ string = get_string(NULL); /* domain number */
+ if (string == NULL)
+ {
+ printk (KERN_ALERT "error: domain number missing\n");
+ return count;
+ }
+ xvd.domain = (int) to_number(string);
- for (loop = 0; loop < xvd.ext_count; loop++)
- {
- string = get_string(NULL); /* look for Disk */
- if (string == NULL || (*string != 'd' && *string != 'D'))
+ string = get_string(NULL);
+ if (string && (strcmp(string, "RO") == 0 || strcmp(string, "ro") == 0))
{
- printk (KERN_ALERT
- "hmm, extent disk specifier missing [%s]. should be \"disk\".\n",
- string);
- return count;
+ xvd.mode = XEN_DISK_READ_ONLY;
}
- string = get_string(NULL); /* disk number */
- if (string == NULL)
+ else if (string && (strcmp(string, "RW") == 0 || strcmp(string, "rw") == 0))
+ {
+ xvd.mode = XEN_DISK_READ_WRITE;
+ }
+ else
{
- printk (KERN_ALERT "error: disk number missing\n");
- return count;
+ printk (KERN_ALERT
+ "error: bad mode [%s]. should be \"rw\" or \"ro\".\n",
+ string);
+ return count;
}
- xvd.extents[loop].disk = (int) to_number(string);
- string = get_string(NULL); /* look for Offset */
- if (string == NULL || (*string != 'o' && *string != 'O'))
+ string = get_string(NULL); /* look for Segment */
+ if (string == NULL || (*string != 's' && *string != 'S'))
{
- printk (KERN_ALERT
- "error: disk offset missing [%s]. should be \"offset\".\n",
- string);
- return count;
+ printk (KERN_ALERT
+ "error: segment specifier missing [%s]. should be \"segment\".\n",
+ string);
+ return count;
}
- string = get_string(NULL); /* offset */
+
+ string = get_string(NULL); /* segment number */
if (string == NULL)
{
- printk (KERN_ALERT "error: offset missing\n");
- return count;
+ printk (KERN_ALERT "error: segment number missing\n");
+ return count;
}
- xvd.extents[loop].offset = to_number(string);
+ xvd.segment = (int) to_number(string);
- string = get_string(NULL); /* look for Size */
- if (string == NULL || (*string != 's' && *string != 'S'))
+ string = get_string(NULL); /* look for Extents */
+ if (string == NULL || (*string != 'e' && *string != 'E'))
{
- printk (KERN_ALERT
- "error: extent size missing [%s]. should be \"size\".\n",
- string);
- return count;
+ printk (KERN_ALERT
+ "error: extents specifier missing [%s]. should be \"extents\".\n",
+ string);
+ return count;
}
- string = get_string(NULL); /* size */
+
+ string = get_string(NULL); /* number of extents */
if (string == NULL)
{
- printk (KERN_ALERT "error: extent size missing\n");
- return count;
+ printk (KERN_ALERT "error: number of extents missing\n");
+ return count;
+ }
+ xvd.ext_count = (int) to_number(string);
+
+ /* ignore parenthesis */
+
+ for (loop = 0; loop < xvd.ext_count; loop++)
+ {
+ string = get_string(NULL); /* look for Disk */
+ if (string == NULL || (*string != 'd' && *string != 'D'))
+ {
+ printk (KERN_ALERT
+ "hmm, extent disk specifier missing [%s]. should be \"disk\".\n",
+ string);
+ return count;
+ }
+ string = get_string(NULL); /* disk number */
+ if (string == NULL)
+ {
+ printk (KERN_ALERT "error: disk number missing\n");
+ return count;
+ }
+ xvd.extents[loop].disk = (int) to_number(string);
+
+ string = get_string(NULL); /* look for Offset */
+ if (string == NULL || (*string != 'o' && *string != 'O'))
+ {
+ printk (KERN_ALERT
+ "error: disk offset missing [%s]. should be \"offset\".\n",
+ string);
+ return count;
+ }
+ string = get_string(NULL); /* offset */
+ if (string == NULL)
+ {
+ printk (KERN_ALERT "error: offset missing\n");
+ return count;
+ }
+ xvd.extents[loop].offset = to_number(string);
+
+ string = get_string(NULL); /* look for Size */
+ if (string == NULL || (*string != 's' && *string != 'S'))
+ {
+ printk (KERN_ALERT
+ "error: extent size missing [%s]. should be \"size\".\n",
+ string);
+ return count;
+ }
+ string = get_string(NULL); /* size */
+ if (string == NULL)
+ {
+ printk (KERN_ALERT "error: extent size missing\n");
+ return count;
+ }
+ xvd.extents[loop].size = to_number(string);
}
- xvd.extents[loop].size = to_number(string);
- }
-
- {
- /* get lock xlblk_control_lock */
- counter = atomic_read(&xlblk_control_count);
- atomic_inc(&xlblk_control_count);
- /* release lock xlblk_control_lock */
- }
- if (hypervisor_request (NULL, XEN_BLOCK_SEG_CREATE, (char *)&xvd,
- 0, 0, (kdev_t) 0,
- (struct gendisk *)NULL))
- BUG();
- HYPERVISOR_block_io_op();
-
- while (atomic_read(&xlblk_control_count) != counter) barrier();
-
- return count;
+
+ xenolinux_control_msg(XEN_BLOCK_SEG_CREATE, (char *)&xvd);
+
+ return count;
}
/******************************************************************/
int __init xlseg_proc_init(void)
{
- vhd = create_proc_entry("xeno/dom0/vhd", 0644, NULL);
- if (vhd == NULL)
- {
- panic ("xlseg_init: unable to create vhd proc entry\n");
- }
- vhd->data = NULL;
- vhd->read_proc = proc_read_vhd;
- vhd->write_proc = proc_write_vhd;
- vhd->owner = THIS_MODULE;
-
- memset(&xvd, 0, sizeof(xvd));
-
- printk(KERN_ALERT "XenoLinux Virtual Disk Device Monitor installed\n");
- return 0;
+ vhd = create_proc_entry("xeno/dom0/vhd", 0644, NULL);
+ if (vhd == NULL)
+ {
+ panic ("xlseg_init: unable to create vhd proc entry\n");
+ }
+ vhd->data = NULL;
+ vhd->read_proc = proc_read_vhd;
+ vhd->write_proc = proc_write_vhd;
+ vhd->owner = THIS_MODULE;
+
+ printk(KERN_ALERT "XenoLinux Virtual Disk Device Monitor installed\n");
+ return 0;
}
static void __exit xlseg_proc_cleanup(void)
{
- printk(KERN_ALERT "XenoLinux Virtual Disk Device Monitor uninstalled\n");
+ printk(KERN_ALERT "XenoLinux Virtual Disk Device Monitor uninstalled\n");
}
#ifdef MODULE
diff --git a/xenolinux-2.4.21-pre4-sparse/include/linux/blk.h b/xenolinux-2.4.21-pre4-sparse/include/linux/blk.h
deleted file mode 100644
index e7fa201955..0000000000
--- a/xenolinux-2.4.21-pre4-sparse/include/linux/blk.h
+++ /dev/null
@@ -1,420 +0,0 @@
-#ifndef _BLK_H
-#define _BLK_H
-
-#include <linux/blkdev.h>
-#include <linux/locks.h>
-#include <linux/config.h>
-#include <linux/spinlock.h>
-
-/*
- * Spinlock for protecting the request queue which
- * is mucked around with in interrupts on potentially
- * multiple CPU's..
- */
-extern spinlock_t io_request_lock;
-
-/*
- * Initialization functions.
- */
-extern int isp16_init(void);
-extern int cdu31a_init(void);
-extern int acsi_init(void);
-extern int mcd_init(void);
-extern int mcdx_init(void);
-extern int sbpcd_init(void);
-extern int aztcd_init(void);
-extern int sony535_init(void);
-extern int gscd_init(void);
-extern int cm206_init(void);
-extern int optcd_init(void);
-extern int sjcd_init(void);
-extern int cdi_init(void);
-extern int hd_init(void);
-extern int ide_init(void);
-extern int xd_init(void);
-extern int mfm_init(void);
-extern int loop_init(void);
-extern int md_init(void);
-extern int ap_init(void);
-extern int ddv_init(void);
-extern int z2_init(void);
-extern int swim3_init(void);
-extern int swimiop_init(void);
-extern int amiga_floppy_init(void);
-extern int atari_floppy_init(void);
-extern int ez_init(void);
-extern int bpcd_init(void);
-extern int ps2esdi_init(void);
-extern int jsfd_init(void);
-extern int viodasd_init(void);
-extern int viocd_init(void);
-extern int xlblk_init(void);
-
-#if defined(CONFIG_ARCH_S390)
-extern int dasd_init(void);
-extern int xpram_init(void);
-extern int tapeblock_init(void);
-#endif /* CONFIG_ARCH_S390 */
-
-extern void set_device_ro(kdev_t dev,int flag);
-void add_blkdev_randomness(int major);
-
-extern int floppy_init(void);
-extern int rd_doload; /* 1 = load ramdisk, 0 = don't load */
-extern int rd_prompt; /* 1 = prompt for ramdisk, 0 = don't prompt */
-extern int rd_image_start; /* starting block # of image */
-
-#ifdef CONFIG_BLK_DEV_INITRD
-
-#define INITRD_MINOR 250 /* shouldn't collide with /dev/ram* too soon ... */
-
-extern unsigned long initrd_start,initrd_end;
-extern int initrd_below_start_ok; /* 1 if it is not an error if initrd_start < memory_start */
-void initrd_init(void);
-
-#endif
-
-
-/*
- * end_request() and friends. Must be called with the request queue spinlock
- * acquired. All functions called within end_request() _must_be_ atomic.
- *
- * Several drivers define their own end_request and call
- * end_that_request_first() and end_that_request_last()
- * for parts of the original function. This prevents
- * code duplication in drivers.
- */
-
-static inline void blkdev_dequeue_request(struct request * req)
-{
- list_del(&req->queue);
-}
-
-int end_that_request_first(struct request *req, int uptodate, char *name);
-void end_that_request_last(struct request *req);
-
-#if defined(MAJOR_NR) || defined(IDE_DRIVER)
-
-#undef DEVICE_ON
-#undef DEVICE_OFF
-
-/*
- * Add entries as needed.
- */
-
-#ifdef IDE_DRIVER
-
-#define DEVICE_NR(device) (MINOR(device) >> PARTN_BITS)
-#define DEVICE_NAME "ide"
-
-#elif (MAJOR_NR == RAMDISK_MAJOR)
-
-/* ram disk */
-#define DEVICE_NAME "ramdisk"
-#define DEVICE_NR(device) (MINOR(device))
-#define DEVICE_NO_RANDOM
-
-#elif (MAJOR_NR == Z2RAM_MAJOR)
-
-/* Zorro II Ram */
-#define DEVICE_NAME "Z2RAM"
-#define DEVICE_REQUEST do_z2_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == FLOPPY_MAJOR)
-
-static void floppy_off(unsigned int nr);
-
-#define DEVICE_NAME "floppy"
-#define DEVICE_INTR do_floppy
-#define DEVICE_REQUEST do_fd_request
-#define DEVICE_NR(device) ( (MINOR(device) & 3) | ((MINOR(device) & 0x80 ) >> 5 ))
-#define DEVICE_OFF(device) floppy_off(DEVICE_NR(device))
-
-#elif (MAJOR_NR == HD_MAJOR)
-
-/* Hard disk: timeout is 6 seconds. */
-#define DEVICE_NAME "hard disk"
-#define DEVICE_INTR do_hd
-#define TIMEOUT_VALUE (6*HZ)
-#define DEVICE_REQUEST do_hd_request
-#define DEVICE_NR(device) (MINOR(device)>>6)
-
-#elif (SCSI_DISK_MAJOR(MAJOR_NR))
-
-#define DEVICE_NAME "scsidisk"
-#define TIMEOUT_VALUE (2*HZ)
-#define DEVICE_NR(device) (((MAJOR(device) & SD_MAJOR_MASK) << (8 - 4)) + (MINOR(device) >> 4))
-
-/* Kludge to use the same number for both char and block major numbers */
-#elif (MAJOR_NR == MD_MAJOR) && defined(MD_DRIVER)
-
-#define DEVICE_NAME "Multiple devices driver"
-#define DEVICE_REQUEST do_md_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == SCSI_TAPE_MAJOR)
-
-#define DEVICE_NAME "scsitape"
-#define DEVICE_INTR do_st
-#define DEVICE_NR(device) (MINOR(device) & 0x7f)
-
-#elif (MAJOR_NR == OSST_MAJOR)
-
-#define DEVICE_NAME "onstream"
-#define DEVICE_INTR do_osst
-#define DEVICE_NR(device) (MINOR(device) & 0x7f)
-#define DEVICE_ON(device)
-#define DEVICE_OFF(device)
-
-#elif (MAJOR_NR == SCSI_CDROM_MAJOR)
-
-#define DEVICE_NAME "CD-ROM"
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == XT_DISK_MAJOR)
-
-#define DEVICE_NAME "xt disk"
-#define DEVICE_REQUEST do_xd_request
-#define DEVICE_NR(device) (MINOR(device) >> 6)
-
-#elif (MAJOR_NR == PS2ESDI_MAJOR)
-
-#define DEVICE_NAME "PS/2 ESDI"
-#define DEVICE_REQUEST do_ps2esdi_request
-#define DEVICE_NR(device) (MINOR(device) >> 6)
-
-#elif (MAJOR_NR == CDU31A_CDROM_MAJOR)
-
-#define DEVICE_NAME "CDU31A"
-#define DEVICE_REQUEST do_cdu31a_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == ACSI_MAJOR) && (defined(CONFIG_ATARI_ACSI) || defined(CONFIG_ATARI_ACSI_MODULE))
-
-#define DEVICE_NAME "ACSI"
-#define DEVICE_INTR do_acsi
-#define DEVICE_REQUEST do_acsi_request
-#define DEVICE_NR(device) (MINOR(device) >> 4)
-
-#elif (MAJOR_NR == MITSUMI_CDROM_MAJOR)
-
-#define DEVICE_NAME "Mitsumi CD-ROM"
-/* #define DEVICE_INTR do_mcd */
-#define DEVICE_REQUEST do_mcd_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == MITSUMI_X_CDROM_MAJOR)
-
-#define DEVICE_NAME "Mitsumi CD-ROM"
-/* #define DEVICE_INTR do_mcdx */
-#define DEVICE_REQUEST do_mcdx_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == MATSUSHITA_CDROM_MAJOR)
-
-#define DEVICE_NAME "Matsushita CD-ROM controller #1"
-#define DEVICE_REQUEST do_sbpcd_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == MATSUSHITA_CDROM2_MAJOR)
-
-#define DEVICE_NAME "Matsushita CD-ROM controller #2"
-#define DEVICE_REQUEST do_sbpcd2_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == MATSUSHITA_CDROM3_MAJOR)
-
-#define DEVICE_NAME "Matsushita CD-ROM controller #3"
-#define DEVICE_REQUEST do_sbpcd3_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == MATSUSHITA_CDROM4_MAJOR)
-
-#define DEVICE_NAME "Matsushita CD-ROM controller #4"
-#define DEVICE_REQUEST do_sbpcd4_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == AZTECH_CDROM_MAJOR)
-
-#define DEVICE_NAME "Aztech CD-ROM"
-#define DEVICE_REQUEST do_aztcd_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == CDU535_CDROM_MAJOR)
-
-#define DEVICE_NAME "SONY-CDU535"
-#define DEVICE_INTR do_cdu535
-#define DEVICE_REQUEST do_cdu535_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == GOLDSTAR_CDROM_MAJOR)
-
-#define DEVICE_NAME "Goldstar R420"
-#define DEVICE_REQUEST do_gscd_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == CM206_CDROM_MAJOR)
-#define DEVICE_NAME "Philips/LMS CD-ROM cm206"
-#define DEVICE_REQUEST do_cm206_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == OPTICS_CDROM_MAJOR)
-
-#define DEVICE_NAME "DOLPHIN 8000AT CD-ROM"
-#define DEVICE_REQUEST do_optcd_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == SANYO_CDROM_MAJOR)
-
-#define DEVICE_NAME "Sanyo H94A CD-ROM"
-#define DEVICE_REQUEST do_sjcd_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == APBLOCK_MAJOR)
-
-#define DEVICE_NAME "apblock"
-#define DEVICE_REQUEST ap_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == DDV_MAJOR)
-
-#define DEVICE_NAME "ddv"
-#define DEVICE_REQUEST ddv_request
-#define DEVICE_NR(device) (MINOR(device)>>PARTN_BITS)
-
-#elif (MAJOR_NR == MFM_ACORN_MAJOR)
-
-#define DEVICE_NAME "mfm disk"
-#define DEVICE_INTR do_mfm
-#define DEVICE_REQUEST do_mfm_request
-#define DEVICE_NR(device) (MINOR(device) >> 6)
-
-#elif (MAJOR_NR == NBD_MAJOR)
-
-#define DEVICE_NAME "nbd"
-#define DEVICE_REQUEST do_nbd_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == MDISK_MAJOR)
-
-#define DEVICE_NAME "mdisk"
-#define DEVICE_REQUEST mdisk_request
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == DASD_MAJOR)
-
-#define DEVICE_NAME "dasd"
-#define DEVICE_REQUEST do_dasd_request
-#define DEVICE_NR(device) (MINOR(device) >> PARTN_BITS)
-
-#elif (MAJOR_NR == I2O_MAJOR)
-
-#define DEVICE_NAME "I2O block"
-#define DEVICE_REQUEST i2ob_request
-#define DEVICE_NR(device) (MINOR(device)>>4)
-
-#elif (MAJOR_NR == COMPAQ_SMART2_MAJOR)
-
-#define DEVICE_NAME "ida"
-#define TIMEOUT_VALUE (25*HZ)
-#define DEVICE_REQUEST do_ida_request
-#define DEVICE_NR(device) (MINOR(device) >> 4)
-
-#elif (MAJOR_NR == XLBLK_MAJOR)
-
-#define DEVICE_NAME "xeno disk"
-#define DEVICE_REQUEST do_xlblk_request
-/* #define DEVICE_INTR */
-#define DEVICE_NR(device) (MINOR(device))
-
-#elif (MAJOR_NR == XLSEG_MAJOR)
-
-#define DEVICE_NAME "xeno segment"
-#define DEVICE_REQUEST do_xlseg_request
-/* #define DEVICE_INTR */
-#define DEVICE_NR(device) (MINOR(device))
-
-#endif /* MAJOR_NR == whatever */
-
-/* provide DEVICE_xxx defaults, if not explicitly defined
- * above in the MAJOR_NR==xxx if-elif tree */
-#ifndef DEVICE_ON
-#define DEVICE_ON(device) do {} while (0)
-#endif
-#ifndef DEVICE_OFF
-#define DEVICE_OFF(device) do {} while (0)
-#endif
-
-#if (MAJOR_NR != SCSI_TAPE_MAJOR) && (MAJOR_NR != OSST_MAJOR)
-#if !defined(IDE_DRIVER)
-
-#ifndef CURRENT
-#define CURRENT blkdev_entry_next_request(&blk_dev[MAJOR_NR].request_queue.queue_head)
-#endif
-#ifndef QUEUE_EMPTY
-#define QUEUE_EMPTY list_empty(&blk_dev[MAJOR_NR].request_queue.queue_head)
-#endif
-
-#ifndef DEVICE_NAME
-#define DEVICE_NAME "unknown"
-#endif
-
-#define CURRENT_DEV DEVICE_NR(CURRENT->rq_dev)
-
-#ifdef DEVICE_INTR
-static void (*DEVICE_INTR)(void) = NULL;
-#endif
-
-#define SET_INTR(x) (DEVICE_INTR = (x))
-
-#ifdef DEVICE_REQUEST
-static void (DEVICE_REQUEST)(request_queue_t *);
-#endif
-
-#ifdef DEVICE_INTR
-#define CLEAR_INTR SET_INTR(NULL)
-#else
-#define CLEAR_INTR
-#endif
-
-#define INIT_REQUEST \
- if (QUEUE_EMPTY) {\
- CLEAR_INTR; \
- return; \
- } \
- if (MAJOR(CURRENT->rq_dev) != MAJOR_NR) \
- panic(DEVICE_NAME ": request list destroyed"); \
- if (CURRENT->bh) { \
- if (!buffer_locked(CURRENT->bh)) \
- panic(DEVICE_NAME ": block not locked"); \
- }
-
-#endif /* !defined(IDE_DRIVER) */
-
-
-#ifndef LOCAL_END_REQUEST /* If we have our own end_request, we do not want to include this mess */
-
-#if ! SCSI_BLK_MAJOR(MAJOR_NR) && (MAJOR_NR != COMPAQ_SMART2_MAJOR)
-
-static inline void end_request(int uptodate) {
- struct request *req = CURRENT;
-
- if (end_that_request_first(req, uptodate, DEVICE_NAME))
- return;
-
-#ifndef DEVICE_NO_RANDOM
- add_blkdev_randomness(MAJOR(req->rq_dev));
-#endif
- DEVICE_OFF(req->rq_dev);
- blkdev_dequeue_request(req);
- end_that_request_last(req);
-}
-
-#endif /* ! SCSI_BLK_MAJOR(MAJOR_NR) */
-#endif /* LOCAL_END_REQUEST */
-
-#endif /* (MAJOR_NR != SCSI_TAPE_MAJOR) */
-#endif /* defined(MAJOR_NR) || defined(IDE_DRIVER) */
-
-#endif /* _BLK_H */
diff --git a/xenolinux-2.4.21-pre4-sparse/include/linux/major.h b/xenolinux-2.4.21-pre4-sparse/include/linux/major.h
index a838d477d1..0fd779a170 100644
--- a/xenolinux-2.4.21-pre4-sparse/include/linux/major.h
+++ b/xenolinux-2.4.21-pre4-sparse/include/linux/major.h
@@ -145,8 +145,15 @@
#define UMEM_MAJOR 116 /* http://www.umem.com/ Battery Backed RAM */
+/*
+ * Each of these majors supports up to 16 devices of <= 16 partitions each.
+ * eg. xhda == (123, 0), xhdb == (123, 16), ...
+ * xsda == (124, 0), xsdb == (124, 16), ...
+ * xvda == (125, 0), xvdb == (125, 16), ...
+ */
#define XLIDE_MAJOR 123 /* XenoLinux IDE Device */
-#define XLSCSI_MAJOR 133 /* XenoLinux SCSI Device */
+#define XLSCSI_MAJOR 124 /* XenoLinux SCSI Device */
+#define XLVIRT_MAJOR 125 /* XenoLinux Virtual Device */
#define RTF_MAJOR 150
#define RAW_MAJOR 162
diff --git a/xenolinux-2.4.21-pre4-sparse/init/do_mounts.c b/xenolinux-2.4.21-pre4-sparse/init/do_mounts.c
index 68c1a4a002..4e876b6e0c 100644
--- a/xenolinux-2.4.21-pre4-sparse/init/do_mounts.c
+++ b/xenolinux-2.4.21-pre4-sparse/init/do_mounts.c
@@ -231,8 +231,33 @@ static struct dev_name_struct {
{ "ataraid/d14p",0x72E0 },
{ "ataraid/d15p",0x72F0 },
#if defined(CONFIG_XENOLINUX_BLOCK)
- { "xhda", 0x7B00 },
- { "xsda", 0x8500 },
+ /* XenoLinux IDE Devices */
+ { "xhda", 0x7B00 }, { "xhdb", 0x7B10 },
+ { "xhdc", 0x7B20 }, { "xhdd", 0x7B30 },
+ { "xhde", 0x7B40 }, { "xhdf", 0x7B50 },
+ { "xhdg", 0x7B60 }, { "xhdh", 0x7B70 },
+ { "xhdi", 0x7B80 }, { "xhdj", 0x7B90 },
+ { "xhdk", 0x7BA0 }, { "xhdl", 0x7BB0 },
+ { "xhdm", 0x7BC0 }, { "xhdn", 0x7BD0 },
+ { "xhdo", 0x7BE0 }, { "xhdp", 0x7BF0 },
+ /* Xenolinux SCSI Devices */
+ { "xsda", 0x7C00 }, { "xsdb", 0x7C10 },
+ { "xsdc", 0x7C20 }, { "xsdd", 0x7C30 },
+ { "xsde", 0x7C40 }, { "xsdf", 0x7C50 },
+ { "xsdg", 0x7C60 }, { "xsdh", 0x7C70 },
+ { "xsdi", 0x7C80 }, { "xsdj", 0x7C90 },
+ { "xsdk", 0x7CA0 }, { "xsdl", 0x7CB0 },
+ { "xsdm", 0x7CC0 }, { "xsdn", 0x7CD0 },
+ { "xsdo", 0x7CE0 }, { "xsdp", 0x7CF0 },
+ /* XenoLinux Virtual Devices */
+ { "xvda", 0x7D00 }, { "xvdb", 0x7D10 },
+ { "xvdc", 0x7D20 }, { "xvdd", 0x7D30 },
+ { "xvde", 0x7D40 }, { "xvdf", 0x7D50 },
+ { "xvdg", 0x7D60 }, { "xvdh", 0x7D70 },
+ { "xvdi", 0x7D80 }, { "xvdj", 0x7D90 },
+ { "xvdk", 0x7DA0 }, { "xvdl", 0x7DB0 },
+ { "xvdm", 0x7DC0 }, { "xvdn", 0x7DD0 },
+ { "xvdo", 0x7DE0 }, { "xvdp", 0x7DF0 },
#endif
{ "nftla", 0x5d00 },
{ "nftlb", 0x5d10 },