aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/ide/ide-cd.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/ide/ide-cd.c')
-rw-r--r--drivers/ide/ide-cd.c160
1 files changed, 77 insertions, 83 deletions
diff --git a/drivers/ide/ide-cd.c b/drivers/ide/ide-cd.c
index d99847157186..6e29dd532090 100644
--- a/drivers/ide/ide-cd.c
+++ b/drivers/ide/ide-cd.c
@@ -517,14 +517,9 @@ static ide_startstop_t cdrom_start_packet_command(ide_drive_t *drive,
517 int xferlen, 517 int xferlen,
518 ide_handler_t *handler) 518 ide_handler_t *handler)
519{ 519{
520 ide_startstop_t startstop;
521 struct cdrom_info *info = drive->driver_data; 520 struct cdrom_info *info = drive->driver_data;
522 ide_hwif_t *hwif = drive->hwif; 521 ide_hwif_t *hwif = drive->hwif;
523 522
524 /* wait for the controller to be idle */
525 if (ide_wait_stat(&startstop, drive, 0, BUSY_STAT, WAIT_READY))
526 return startstop;
527
528 /* FIXME: for Virtual DMA we must check harder */ 523 /* FIXME: for Virtual DMA we must check harder */
529 if (info->dma) 524 if (info->dma)
530 info->dma = !hwif->dma_ops->dma_setup(drive); 525 info->dma = !hwif->dma_ops->dma_setup(drive);
@@ -604,28 +599,6 @@ static ide_startstop_t cdrom_transfer_packet_command(ide_drive_t *drive,
604} 599}
605 600
606/* 601/*
607 * Block read functions.
608 */
609static void ide_cd_pad_transfer(ide_drive_t *drive, xfer_func_t *xf, int len)
610{
611 while (len > 0) {
612 int dum = 0;
613 xf(drive, NULL, &dum, sizeof(dum));
614 len -= sizeof(dum);
615 }
616}
617
618static void ide_cd_drain_data(ide_drive_t *drive, int nsects)
619{
620 while (nsects > 0) {
621 static char dum[SECTOR_SIZE];
622
623 drive->hwif->input_data(drive, NULL, dum, sizeof(dum));
624 nsects--;
625 }
626}
627
628/*
629 * Check the contents of the interrupt reason register from the cdrom 602 * Check the contents of the interrupt reason register from the cdrom
630 * and attempt to recover if there are problems. Returns 0 if everything's 603 * and attempt to recover if there are problems. Returns 0 if everything's
631 * ok; nonzero if the request has been terminated. 604 * ok; nonzero if the request has been terminated.
@@ -640,15 +613,12 @@ static int ide_cd_check_ireason(ide_drive_t *drive, struct request *rq,
640 if (ireason == (!rw << 1)) 613 if (ireason == (!rw << 1))
641 return 0; 614 return 0;
642 else if (ireason == (rw << 1)) { 615 else if (ireason == (rw << 1)) {
643 ide_hwif_t *hwif = drive->hwif;
644 xfer_func_t *xf;
645 616
646 /* whoops... */ 617 /* whoops... */
647 printk(KERN_ERR "%s: %s: wrong transfer direction!\n", 618 printk(KERN_ERR "%s: %s: wrong transfer direction!\n",
648 drive->name, __func__); 619 drive->name, __func__);
649 620
650 xf = rw ? hwif->output_data : hwif->input_data; 621 ide_pad_transfer(drive, rw, len);
651 ide_cd_pad_transfer(drive, xf, len);
652 } else if (rw == 0 && ireason == 1) { 622 } else if (rw == 0 && ireason == 1) {
653 /* 623 /*
654 * Some drives (ASUS) seem to tell us that status info is 624 * Some drives (ASUS) seem to tell us that status info is
@@ -696,16 +666,9 @@ static int ide_cd_check_transfer_size(ide_drive_t *drive, int len)
696 666
697static ide_startstop_t cdrom_newpc_intr(ide_drive_t *); 667static ide_startstop_t cdrom_newpc_intr(ide_drive_t *);
698 668
699/* 669static ide_startstop_t ide_cd_prepare_rw_request(ide_drive_t *drive,
700 * Routine to send a read/write packet command to the drive. This is usually 670 struct request *rq)
701 * called directly from cdrom_start_{read,write}(). However, for drq_interrupt
702 * devices, it is called from an interrupt when the drive is ready to accept
703 * the command.
704 */
705static ide_startstop_t cdrom_start_rw_cont(ide_drive_t *drive)
706{ 671{
707 struct request *rq = HWGROUP(drive)->rq;
708
709 if (rq_data_dir(rq) == READ) { 672 if (rq_data_dir(rq) == READ) {
710 unsigned short sectors_per_frame = 673 unsigned short sectors_per_frame =
711 queue_hardsect_size(drive->queue) >> SECTOR_BITS; 674 queue_hardsect_size(drive->queue) >> SECTOR_BITS;
@@ -742,6 +705,19 @@ static ide_startstop_t cdrom_start_rw_cont(ide_drive_t *drive)
742 /* set up the command */ 705 /* set up the command */
743 rq->timeout = ATAPI_WAIT_PC; 706 rq->timeout = ATAPI_WAIT_PC;
744 707
708 return ide_started;
709}
710
711/*
712 * Routine to send a read/write packet command to the drive. This is usually
713 * called directly from cdrom_start_{read,write}(). However, for drq_interrupt
714 * devices, it is called from an interrupt when the drive is ready to accept
715 * the command.
716 */
717static ide_startstop_t cdrom_start_rw_cont(ide_drive_t *drive)
718{
719 struct request *rq = drive->hwif->hwgroup->rq;
720
745 /* send the command to the drive and return */ 721 /* send the command to the drive and return */
746 return cdrom_transfer_packet_command(drive, rq, cdrom_newpc_intr); 722 return cdrom_transfer_packet_command(drive, rq, cdrom_newpc_intr);
747} 723}
@@ -768,9 +744,8 @@ static ide_startstop_t cdrom_seek_intr(ide_drive_t *drive)
768 return ide_stopped; 744 return ide_stopped;
769} 745}
770 746
771static ide_startstop_t cdrom_start_seek_continuation(ide_drive_t *drive) 747static void ide_cd_prepare_seek_request(ide_drive_t *drive, struct request *rq)
772{ 748{
773 struct request *rq = HWGROUP(drive)->rq;
774 sector_t frame = rq->sector; 749 sector_t frame = rq->sector;
775 750
776 sector_div(frame, queue_hardsect_size(drive->queue) >> SECTOR_BITS); 751 sector_div(frame, queue_hardsect_size(drive->queue) >> SECTOR_BITS);
@@ -780,17 +755,13 @@ static ide_startstop_t cdrom_start_seek_continuation(ide_drive_t *drive)
780 put_unaligned(cpu_to_be32(frame), (unsigned int *) &rq->cmd[2]); 755 put_unaligned(cpu_to_be32(frame), (unsigned int *) &rq->cmd[2]);
781 756
782 rq->timeout = ATAPI_WAIT_PC; 757 rq->timeout = ATAPI_WAIT_PC;
783 return cdrom_transfer_packet_command(drive, rq, &cdrom_seek_intr);
784} 758}
785 759
786static ide_startstop_t cdrom_start_seek(ide_drive_t *drive, unsigned int block) 760static ide_startstop_t cdrom_start_seek_continuation(ide_drive_t *drive)
787{ 761{
788 struct cdrom_info *info = drive->driver_data; 762 struct request *rq = drive->hwif->hwgroup->rq;
789 763
790 info->dma = 0; 764 return cdrom_transfer_packet_command(drive, rq, &cdrom_seek_intr);
791 info->start_seek = jiffies;
792 return cdrom_start_packet_command(drive, 0,
793 cdrom_start_seek_continuation);
794} 765}
795 766
796/* 767/*
@@ -1011,7 +982,7 @@ static ide_startstop_t cdrom_newpc_intr(ide_drive_t *drive)
1011 - bio_cur_sectors(rq->bio), 982 - bio_cur_sectors(rq->bio),
1012 thislen >> 9); 983 thislen >> 9);
1013 if (nskip > 0) { 984 if (nskip > 0) {
1014 ide_cd_drain_data(drive, nskip); 985 ide_pad_transfer(drive, write, nskip << 9);
1015 rq->current_nr_sectors -= nskip; 986 rq->current_nr_sectors -= nskip;
1016 thislen -= (nskip << 9); 987 thislen -= (nskip << 9);
1017 } 988 }
@@ -1048,7 +1019,7 @@ static ide_startstop_t cdrom_newpc_intr(ide_drive_t *drive)
1048 * If the buffers are full, pipe the rest into 1019 * If the buffers are full, pipe the rest into
1049 * oblivion. 1020 * oblivion.
1050 */ 1021 */
1051 ide_cd_drain_data(drive, thislen >> 9); 1022 ide_pad_transfer(drive, 0, thislen);
1052 else { 1023 else {
1053 printk(KERN_ERR "%s: confused, missing data\n", 1024 printk(KERN_ERR "%s: confused, missing data\n",
1054 drive->name); 1025 drive->name);
@@ -1096,7 +1067,7 @@ static ide_startstop_t cdrom_newpc_intr(ide_drive_t *drive)
1096 1067
1097 /* pad, if necessary */ 1068 /* pad, if necessary */
1098 if (!blk_fs_request(rq) && len > 0) 1069 if (!blk_fs_request(rq) && len > 0)
1099 ide_cd_pad_transfer(drive, xferfunc, len); 1070 ide_pad_transfer(drive, write, len);
1100 1071
1101 if (blk_pc_request(rq)) { 1072 if (blk_pc_request(rq)) {
1102 timeout = rq->timeout; 1073 timeout = rq->timeout;
@@ -1165,21 +1136,17 @@ static ide_startstop_t cdrom_start_rw(ide_drive_t *drive, struct request *rq)
1165 if (write) 1136 if (write)
1166 cd->devinfo.media_written = 1; 1137 cd->devinfo.media_written = 1;
1167 1138
1168 /* start sending the read/write request to the drive */ 1139 return ide_started;
1169 return cdrom_start_packet_command(drive, 32768, cdrom_start_rw_cont);
1170} 1140}
1171 1141
1172static ide_startstop_t cdrom_do_newpc_cont(ide_drive_t *drive) 1142static ide_startstop_t cdrom_do_newpc_cont(ide_drive_t *drive)
1173{ 1143{
1174 struct request *rq = HWGROUP(drive)->rq; 1144 struct request *rq = HWGROUP(drive)->rq;
1175 1145
1176 if (!rq->timeout)
1177 rq->timeout = ATAPI_WAIT_PC;
1178
1179 return cdrom_transfer_packet_command(drive, rq, cdrom_newpc_intr); 1146 return cdrom_transfer_packet_command(drive, rq, cdrom_newpc_intr);
1180} 1147}
1181 1148
1182static ide_startstop_t cdrom_do_block_pc(ide_drive_t *drive, struct request *rq) 1149static void cdrom_do_block_pc(ide_drive_t *drive, struct request *rq)
1183{ 1150{
1184 struct cdrom_info *info = drive->driver_data; 1151 struct cdrom_info *info = drive->driver_data;
1185 1152
@@ -1191,10 +1158,16 @@ static ide_startstop_t cdrom_do_block_pc(ide_drive_t *drive, struct request *rq)
1191 info->dma = 0; 1158 info->dma = 0;
1192 1159
1193 /* sg request */ 1160 /* sg request */
1194 if (rq->bio) { 1161 if (rq->bio || ((rq->cmd_type == REQ_TYPE_ATA_PC) && rq->data_len)) {
1195 int mask = drive->queue->dma_alignment; 1162 struct request_queue *q = drive->queue;
1196 unsigned long addr = 1163 unsigned int alignment;
1197 (unsigned long)page_address(bio_page(rq->bio)); 1164 unsigned long addr;
1165 unsigned long stack_mask = ~(THREAD_SIZE - 1);
1166
1167 if (rq->bio)
1168 addr = (unsigned long)bio_data(rq->bio);
1169 else
1170 addr = (unsigned long)rq->data;
1198 1171
1199 info->dma = drive->using_dma; 1172 info->dma = drive->using_dma;
1200 1173
@@ -1204,23 +1177,25 @@ static ide_startstop_t cdrom_do_block_pc(ide_drive_t *drive, struct request *rq)
1204 * NOTE! The "len" and "addr" checks should possibly have 1177 * NOTE! The "len" and "addr" checks should possibly have
1205 * separate masks. 1178 * separate masks.
1206 */ 1179 */
1207 if ((rq->data_len & 15) || (addr & mask)) 1180 alignment = queue_dma_alignment(q) | q->dma_pad_mask;
1181 if (addr & alignment || rq->data_len & alignment)
1208 info->dma = 0; 1182 info->dma = 0;
1209 }
1210 1183
1211 /* start sending the command to the drive */ 1184 if (!((addr & stack_mask) ^
1212 return cdrom_start_packet_command(drive, rq->data_len, 1185 ((unsigned long)current->stack & stack_mask)))
1213 cdrom_do_newpc_cont); 1186 info->dma = 0;
1187 }
1214} 1188}
1215 1189
1216/* 1190/*
1217 * cdrom driver request routine. 1191 * cdrom driver request routine.
1218 */ 1192 */
1219static ide_startstop_t ide_do_rw_cdrom(ide_drive_t *drive, struct request *rq, 1193static ide_startstop_t ide_cd_do_request(ide_drive_t *drive, struct request *rq,
1220 sector_t block) 1194 sector_t block)
1221{ 1195{
1222 ide_startstop_t action;
1223 struct cdrom_info *info = drive->driver_data; 1196 struct cdrom_info *info = drive->driver_data;
1197 ide_handler_t *fn;
1198 int xferlen;
1224 1199
1225 if (blk_fs_request(rq)) { 1200 if (blk_fs_request(rq)) {
1226 if (info->cd_flags & IDE_CD_FLAG_SEEKING) { 1201 if (info->cd_flags & IDE_CD_FLAG_SEEKING) {
@@ -1240,29 +1215,48 @@ static ide_startstop_t ide_do_rw_cdrom(ide_drive_t *drive, struct request *rq,
1240 } 1215 }
1241 if (rq_data_dir(rq) == READ && 1216 if (rq_data_dir(rq) == READ &&
1242 IDE_LARGE_SEEK(info->last_block, block, 1217 IDE_LARGE_SEEK(info->last_block, block,
1243 IDECD_SEEK_THRESHOLD) && 1218 IDECD_SEEK_THRESHOLD) &&
1244 drive->dsc_overlap) 1219 drive->dsc_overlap) {
1245 action = cdrom_start_seek(drive, block); 1220 xferlen = 0;
1246 else 1221 fn = cdrom_start_seek_continuation;
1247 action = cdrom_start_rw(drive, rq); 1222
1223 info->dma = 0;
1224 info->start_seek = jiffies;
1225
1226 ide_cd_prepare_seek_request(drive, rq);
1227 } else {
1228 xferlen = 32768;
1229 fn = cdrom_start_rw_cont;
1230
1231 if (cdrom_start_rw(drive, rq) == ide_stopped)
1232 return ide_stopped;
1233
1234 if (ide_cd_prepare_rw_request(drive, rq) == ide_stopped)
1235 return ide_stopped;
1236 }
1248 info->last_block = block; 1237 info->last_block = block;
1249 return action;
1250 } else if (blk_sense_request(rq) || blk_pc_request(rq) || 1238 } else if (blk_sense_request(rq) || blk_pc_request(rq) ||
1251 rq->cmd_type == REQ_TYPE_ATA_PC) { 1239 rq->cmd_type == REQ_TYPE_ATA_PC) {
1252 return cdrom_do_block_pc(drive, rq); 1240 xferlen = rq->data_len;
1241 fn = cdrom_do_newpc_cont;
1242
1243 if (!rq->timeout)
1244 rq->timeout = ATAPI_WAIT_PC;
1245
1246 cdrom_do_block_pc(drive, rq);
1253 } else if (blk_special_request(rq)) { 1247 } else if (blk_special_request(rq)) {
1254 /* right now this can only be a reset... */ 1248 /* right now this can only be a reset... */
1255 cdrom_end_request(drive, 1); 1249 cdrom_end_request(drive, 1);
1256 return ide_stopped; 1250 return ide_stopped;
1251 } else {
1252 blk_dump_rq_flags(rq, "ide-cd bad flags");
1253 cdrom_end_request(drive, 0);
1254 return ide_stopped;
1257 } 1255 }
1258 1256
1259 blk_dump_rq_flags(rq, "ide-cd bad flags"); 1257 return cdrom_start_packet_command(drive, xferlen, fn);
1260 cdrom_end_request(drive, 0);
1261 return ide_stopped;
1262} 1258}
1263 1259
1264
1265
1266/* 1260/*
1267 * Ioctl handling. 1261 * Ioctl handling.
1268 * 1262 *
@@ -1872,6 +1866,7 @@ static int ide_cdrom_setup(ide_drive_t *drive)
1872 1866
1873 blk_queue_prep_rq(drive->queue, ide_cdrom_prep_fn); 1867 blk_queue_prep_rq(drive->queue, ide_cdrom_prep_fn);
1874 blk_queue_dma_alignment(drive->queue, 31); 1868 blk_queue_dma_alignment(drive->queue, 31);
1869 blk_queue_update_dma_pad(drive->queue, 15);
1875 drive->queue->unplug_delay = (1 * HZ) / 1000; 1870 drive->queue->unplug_delay = (1 * HZ) / 1000;
1876 if (!drive->queue->unplug_delay) 1871 if (!drive->queue->unplug_delay)
1877 drive->queue->unplug_delay = 1; 1872 drive->queue->unplug_delay = 1;
@@ -1954,10 +1949,9 @@ static ide_driver_t ide_cdrom_driver = {
1954 .version = IDECD_VERSION, 1949 .version = IDECD_VERSION,
1955 .media = ide_cdrom, 1950 .media = ide_cdrom,
1956 .supports_dsc_overlap = 1, 1951 .supports_dsc_overlap = 1,
1957 .do_request = ide_do_rw_cdrom, 1952 .do_request = ide_cd_do_request,
1958 .end_request = ide_end_request, 1953 .end_request = ide_end_request,
1959 .error = __ide_error, 1954 .error = __ide_error,
1960 .abort = __ide_abort,
1961#ifdef CONFIG_IDE_PROC_FS 1955#ifdef CONFIG_IDE_PROC_FS
1962 .proc = idecd_proc, 1956 .proc = idecd_proc,
1963#endif 1957#endif