Commit d103bdbf authored by Linus Torvalds's avatar Linus Torvalds

Merge Al/Jens clashes

parents c055ad89 0aa8a47e
...@@ -670,12 +670,10 @@ void blk_dump_rq_flags(struct request *rq, char *msg) ...@@ -670,12 +670,10 @@ void blk_dump_rq_flags(struct request *rq, char *msg)
bit++; bit++;
} while (bit < __REQ_NR_BITS); } while (bit < __REQ_NR_BITS);
if (rq->flags & REQ_CMD) printk("sector %llu, nr/cnr %lu/%u\n", (unsigned long long)rq->sector,
printk("sector %llu, nr/cnr %lu/%u\n", (unsigned long long)rq->sector,
rq->nr_sectors, rq->nr_sectors,
rq->current_nr_sectors); rq->current_nr_sectors);
printk("bio %p, biotail %p\n", rq->bio, rq->biotail);
printk("\n");
} }
void blk_recount_segments(request_queue_t *q, struct bio *bio) void blk_recount_segments(request_queue_t *q, struct bio *bio)
...@@ -1927,7 +1925,7 @@ inline void blk_recalc_rq_segments(struct request *rq) ...@@ -1927,7 +1925,7 @@ inline void blk_recalc_rq_segments(struct request *rq)
inline void blk_recalc_rq_sectors(struct request *rq, int nsect) inline void blk_recalc_rq_sectors(struct request *rq, int nsect)
{ {
if (rq->flags & REQ_CMD) { if (rq->bio) {
rq->hard_sector += nsect; rq->hard_sector += nsect;
rq->nr_sectors = rq->hard_nr_sectors -= nsect; rq->nr_sectors = rq->hard_nr_sectors -= nsect;
rq->sector = rq->hard_sector; rq->sector = rq->hard_sector;
...@@ -1968,20 +1966,28 @@ int end_that_request_first(struct request *req, int uptodate, int nr_sectors) ...@@ -1968,20 +1966,28 @@ int end_that_request_first(struct request *req, int uptodate, int nr_sectors)
req->errors = 0; req->errors = 0;
if (!uptodate) { if (!uptodate) {
printk("end_request: I/O error, dev %s, sector %llu\n",
kdevname(req->rq_dev), (unsigned long long)req->sector);
error = -EIO; error = -EIO;
if (!(req->flags & REQ_QUIET))
printk("end_request: I/O error, dev %s, sector %llu\n",
kdevname(req->rq_dev),
(unsigned long long)req->sector);
} }
while ((bio = req->bio)) { while ((bio = req->bio)) {
const int nsect = bio_iovec(bio)->bv_len >> 9; int new_bio = 0, nsect;
int new_bio = 0;
if (unlikely(bio->bi_idx >= bio->bi_vcnt)) {
printk("%s: bio idx %d >= vcnt %d\n", __FUNCTION__,
bio->bi_idx, bio->bi_vcnt);
break;
}
BIO_BUG_ON(bio_iovec(bio)->bv_len > bio->bi_size); BIO_BUG_ON(bio_iovec(bio)->bv_len > bio->bi_size);
/* /*
* not a complete bvec done * not a complete bvec done
*/ */
nsect = bio_iovec(bio)->bv_len >> 9;
if (unlikely(nsect > nr_sectors)) { if (unlikely(nsect > nr_sectors)) {
int partial = nr_sectors << 9; int partial = nr_sectors << 9;
......
...@@ -267,6 +267,7 @@ ...@@ -267,6 +267,7 @@
#include <linux/blkpg.h> #include <linux/blkpg.h>
#include <linux/init.h> #include <linux/init.h>
#include <linux/fcntl.h> #include <linux/fcntl.h>
#include <linux/blkdev.h>
#include <asm/uaccess.h> #include <asm/uaccess.h>
...@@ -1436,6 +1437,11 @@ int cdrom_ioctl(struct cdrom_device_info *cdi, struct inode *ip, ...@@ -1436,6 +1437,11 @@ int cdrom_ioctl(struct cdrom_device_info *cdi, struct inode *ip,
struct cdrom_device_ops *cdo = cdi->ops; struct cdrom_device_ops *cdo = cdi->ops;
int ret; int ret;
/* Try the generic SCSI command ioctl's first.. */
ret = scsi_cmd_ioctl(ip->i_bdev, cmd, arg);
if (ret != -ENOTTY)
return ret;
/* the first few commands do not deal with audio drive_info, but /* the first few commands do not deal with audio drive_info, but
only with routines in cdrom device operations. */ only with routines in cdrom device operations. */
switch (cmd) { switch (cmd) {
......
...@@ -3026,14 +3026,7 @@ int ide_cdrom_ioctl (ide_drive_t *drive, ...@@ -3026,14 +3026,7 @@ int ide_cdrom_ioctl (ide_drive_t *drive,
unsigned int cmd, unsigned long arg) unsigned int cmd, unsigned long arg)
{ {
struct cdrom_info *info = drive->driver_data; struct cdrom_info *info = drive->driver_data;
int error;
/* Try the generic SCSI command ioctl's first.. */
error = scsi_cmd_ioctl(inode->i_bdev, cmd, arg);
if (error != -ENOTTY)
return error;
/* Then the generic cdrom ioctl's.. */
return cdrom_ioctl(&info->devinfo, inode, cmd, arg); return cdrom_ioctl(&info->devinfo, inode, cmd, arg);
} }
......
...@@ -857,7 +857,7 @@ void scsi_request_fn(request_queue_t * q) ...@@ -857,7 +857,7 @@ void scsi_request_fn(request_queue_t * q)
scsi_init_cmd_from_req(SCpnt, SRpnt); scsi_init_cmd_from_req(SCpnt, SRpnt);
} }
} else if (req->flags & REQ_CMD) { } else if (req->flags & (REQ_CMD | REQ_BLOCK_PC)) {
SRpnt = NULL; SRpnt = NULL;
STpnt = scsi_get_request_dev(req); STpnt = scsi_get_request_dev(req);
if (!STpnt) { if (!STpnt) {
...@@ -919,7 +919,7 @@ void scsi_request_fn(request_queue_t * q) ...@@ -919,7 +919,7 @@ void scsi_request_fn(request_queue_t * q)
req = NULL; req = NULL;
spin_unlock_irq(q->queue_lock); spin_unlock_irq(q->queue_lock);
if (SCpnt->request->flags & REQ_CMD) { if (SCpnt->request->flags & (REQ_CMD | REQ_BLOCK_PC)) {
/* /*
* This will do a couple of things: * This will do a couple of things:
* 1) Fill in the actual SCSI command. * 1) Fill in the actual SCSI command.
......
...@@ -62,16 +62,28 @@ int scsi_init_io(Scsi_Cmnd *SCpnt) ...@@ -62,16 +62,28 @@ int scsi_init_io(Scsi_Cmnd *SCpnt)
int count, gfp_mask; int count, gfp_mask;
/* /*
* First we need to know how many scatter gather segments are needed. * non-sg block request. FIXME: check bouncing for isa hosts!
*/ */
count = req->nr_phys_segments; if ((req->flags & REQ_BLOCK_PC) && !req->bio) {
/*
* FIXME: isa bouncing
*/
if (SCpnt->host->unchecked_isa_dma)
goto fail;
SCpnt->request_bufflen = req->data_len;
SCpnt->request_buffer = req->data;
req->buffer = req->data;
SCpnt->use_sg = 0;
return 1;
}
/* /*
* we used to not use scatter-gather for single segment request, * we used to not use scatter-gather for single segment request,
* but now we do (it makes highmem I/O easier to support without * but now we do (it makes highmem I/O easier to support without
* kmapping pages) * kmapping pages)
*/ */
SCpnt->use_sg = count; SCpnt->use_sg = req->nr_phys_segments;
gfp_mask = GFP_NOIO; gfp_mask = GFP_NOIO;
if (in_interrupt()) { if (in_interrupt()) {
...@@ -111,6 +123,7 @@ int scsi_init_io(Scsi_Cmnd *SCpnt) ...@@ -111,6 +123,7 @@ int scsi_init_io(Scsi_Cmnd *SCpnt)
/* /*
* kill it. there should be no leftover blocks in this request * kill it. there should be no leftover blocks in this request
*/ */
fail:
SCpnt = scsi_end_request(SCpnt, 0, req->nr_sectors); SCpnt = scsi_end_request(SCpnt, 0, req->nr_sectors);
BUG_ON(SCpnt); BUG_ON(SCpnt);
return 0; return 0;
......
...@@ -191,6 +191,7 @@ static int sd_ioctl(struct inode * inode, struct file * filp, ...@@ -191,6 +191,7 @@ static int sd_ioctl(struct inode * inode, struct file * filp,
Scsi_Device *sdp = sdkp->device; Scsi_Device *sdp = sdkp->device;
struct Scsi_Host *host; struct Scsi_Host *host;
int diskinfo[4]; int diskinfo[4];
int error;
SCSI_LOG_IOCTL(1, printk("sd_ioctl: disk=%s, cmd=0x%x\n", SCSI_LOG_IOCTL(1, printk("sd_ioctl: disk=%s, cmd=0x%x\n",
disk->disk_name, cmd)); disk->disk_name, cmd));
...@@ -206,6 +207,10 @@ static int sd_ioctl(struct inode * inode, struct file * filp, ...@@ -206,6 +207,10 @@ static int sd_ioctl(struct inode * inode, struct file * filp,
if( !scsi_block_when_processing_errors(sdp) ) if( !scsi_block_when_processing_errors(sdp) )
return -ENODEV; return -ENODEV;
error = scsi_cmd_ioctl(inode->i_bdev, cmd, arg);
if (error != -ENOTTY)
return error;
switch (cmd) switch (cmd)
{ {
case HDIO_GETGEO: /* Return BIOS disk parameters */ case HDIO_GETGEO: /* Return BIOS disk parameters */
...@@ -273,12 +278,41 @@ static struct gendisk **sd_disks; ...@@ -273,12 +278,41 @@ static struct gendisk **sd_disks;
**/ **/
static int sd_init_command(Scsi_Cmnd * SCpnt) static int sd_init_command(Scsi_Cmnd * SCpnt)
{ {
int this_count; int this_count, timeout;
struct gendisk *disk; struct gendisk *disk;
sector_t block; sector_t block;
Scsi_Device *sdp; Scsi_Device *sdp = SCpnt->device;
timeout = SD_TIMEOUT;
if (SCpnt->device->type != TYPE_DISK)
timeout = SD_MOD_TIMEOUT;
/*
* these are already setup, just copy cdb basically
*/
if (SCpnt->request->flags & REQ_BLOCK_PC) {
struct request *rq = SCpnt->request;
if (sizeof(rq->cmd) > sizeof(SCpnt->cmnd))
return 0;
memcpy(SCpnt->cmnd, rq->cmd, sizeof(SCpnt->cmnd));
if (rq_data_dir(rq) == WRITE)
SCpnt->sc_data_direction = SCSI_DATA_WRITE;
else if (rq->data_len)
SCpnt->sc_data_direction = SCSI_DATA_READ;
else
SCpnt->sc_data_direction = SCSI_DATA_NONE;
this_count = rq->data_len;
if (rq->timeout)
timeout = rq->timeout;
goto queue;
}
/* /*
* don't support specials for nwo * we only do REQ_CMD and REQ_BLOCK_PC
*/ */
if (!(SCpnt->request->flags & REQ_CMD)) if (!(SCpnt->request->flags & REQ_CMD))
return 0; return 0;
...@@ -290,7 +324,6 @@ static int sd_init_command(Scsi_Cmnd * SCpnt) ...@@ -290,7 +324,6 @@ static int sd_init_command(Scsi_Cmnd * SCpnt)
SCSI_LOG_HLQUEUE(1, printk("sd_command_init: disk=%s, block=%llu, " SCSI_LOG_HLQUEUE(1, printk("sd_command_init: disk=%s, block=%llu, "
"count=%d\n", disk->disk_name, (unsigned long long)block, this_count)); "count=%d\n", disk->disk_name, (unsigned long long)block, this_count));
sdp = SCpnt->device;
if (!sdp || !sdp->online || if (!sdp || !sdp->online ||
block + SCpnt->request->nr_sectors > get_capacity(disk)) { block + SCpnt->request->nr_sectors > get_capacity(disk)) {
SCSI_LOG_HLQUEUE(2, printk("Finishing %ld sectors\n", SCSI_LOG_HLQUEUE(2, printk("Finishing %ld sectors\n",
...@@ -398,12 +431,12 @@ static int sd_init_command(Scsi_Cmnd * SCpnt) ...@@ -398,12 +431,12 @@ static int sd_init_command(Scsi_Cmnd * SCpnt)
* host adapter, it's safe to assume that we can at least transfer * host adapter, it's safe to assume that we can at least transfer
* this many bytes between each connect / disconnect. * this many bytes between each connect / disconnect.
*/ */
queue:
SCpnt->transfersize = sdp->sector_size; SCpnt->transfersize = sdp->sector_size;
SCpnt->underflow = this_count << 9; SCpnt->underflow = this_count << 9;
SCpnt->allowed = MAX_RETRIES; SCpnt->allowed = MAX_RETRIES;
SCpnt->timeout_per_command = (SCpnt->device->type == TYPE_DISK ? SCpnt->timeout_per_command = timeout;
SD_TIMEOUT : SD_MOD_TIMEOUT);
/* /*
* This is the completion routine we use. This is matched in terms * This is the completion routine we use. This is matched in terms
......
...@@ -247,7 +247,7 @@ static void rw_intr(Scsi_Cmnd * SCpnt) ...@@ -247,7 +247,7 @@ static void rw_intr(Scsi_Cmnd * SCpnt)
static int sr_init_command(Scsi_Cmnd * SCpnt) static int sr_init_command(Scsi_Cmnd * SCpnt)
{ {
int block=0, this_count, s_size; int block=0, this_count, s_size, timeout = SR_TIMEOUT;
Scsi_CD *cd = SCpnt->request->rq_disk->private_data; Scsi_CD *cd = SCpnt->request->rq_disk->private_data;
SCSI_LOG_HLQUEUE(1, printk("Doing sr request, dev = %s, block = %d\n", disk->disk_name, block)); SCSI_LOG_HLQUEUE(1, printk("Doing sr request, dev = %s, block = %d\n", disk->disk_name, block));
...@@ -266,6 +266,30 @@ static int sr_init_command(Scsi_Cmnd * SCpnt) ...@@ -266,6 +266,30 @@ static int sr_init_command(Scsi_Cmnd * SCpnt)
return 0; return 0;
} }
/*
* these are already setup, just copy cdb basically
*/
if (SCpnt->request->flags & REQ_BLOCK_PC) {
struct request *rq = SCpnt->request;
if (sizeof(rq->cmd) > sizeof(SCpnt->cmnd))
return 0;
memcpy(SCpnt->cmnd, rq->cmd, sizeof(SCpnt->cmnd));
if (rq_data_dir(rq) == WRITE)
SCpnt->sc_data_direction = SCSI_DATA_WRITE;
else if (rq->data_len)
SCpnt->sc_data_direction = SCSI_DATA_READ;
else
SCpnt->sc_data_direction = SCSI_DATA_NONE;
this_count = rq->data_len;
if (rq->timeout)
timeout = rq->timeout;
goto queue;
}
if (!(SCpnt->request->flags & REQ_CMD)) { if (!(SCpnt->request->flags & REQ_CMD)) {
blk_dump_rq_flags(SCpnt->request, "sr unsup command"); blk_dump_rq_flags(SCpnt->request, "sr unsup command");
return 0; return 0;
...@@ -336,11 +360,12 @@ static int sr_init_command(Scsi_Cmnd * SCpnt) ...@@ -336,11 +360,12 @@ static int sr_init_command(Scsi_Cmnd * SCpnt)
* host adapter, it's safe to assume that we can at least transfer * host adapter, it's safe to assume that we can at least transfer
* this many bytes between each connect / disconnect. * this many bytes between each connect / disconnect.
*/ */
queue:
SCpnt->transfersize = cd->device->sector_size; SCpnt->transfersize = cd->device->sector_size;
SCpnt->underflow = this_count << 9; SCpnt->underflow = this_count << 9;
SCpnt->allowed = MAX_RETRIES; SCpnt->allowed = MAX_RETRIES;
SCpnt->timeout_per_command = SR_TIMEOUT; SCpnt->timeout_per_command = timeout;
/* /*
* This is the completion routine we use. This is matched in terms * This is the completion routine we use. This is matched in terms
......
...@@ -235,6 +235,7 @@ struct request_queue ...@@ -235,6 +235,7 @@ struct request_queue
#define blk_queue_tagged(q) test_bit(QUEUE_FLAG_QUEUED, &(q)->queue_flags) #define blk_queue_tagged(q) test_bit(QUEUE_FLAG_QUEUED, &(q)->queue_flags)
#define blk_queue_empty(q) elv_queue_empty(q) #define blk_queue_empty(q) elv_queue_empty(q)
#define blk_fs_request(rq) ((rq)->flags & REQ_CMD) #define blk_fs_request(rq) ((rq)->flags & REQ_CMD)
#define blk_pc_request(rq) ((rq)->flags & REQ_BLOCK_PC)
#define list_entry_rq(ptr) list_entry((ptr), struct request, queuelist) #define list_entry_rq(ptr) list_entry((ptr), struct request, queuelist)
#define rq_data_dir(rq) ((rq)->flags & 1) #define rq_data_dir(rq) ((rq)->flags & 1)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment