0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030
0031
0032
0033
0034
0035
0036
0037
0038 #include <linux/cdrom.h>
0039 #include <linux/errno.h>
0040 #include <linux/string.h>
0041 #include <linux/bcd.h>
0042 #include <linux/blkdev.h>
0043 #include <linux/slab.h>
0044
0045 #include <scsi/scsi.h>
0046 #include <scsi/scsi_cmnd.h>
0047 #include <scsi/scsi_device.h>
0048 #include <scsi/scsi_host.h>
0049 #include <scsi/scsi_ioctl.h>
0050
0051 #include "sr.h"
0052
0053 #if 0
0054 #define DEBUG
0055 #endif
0056
0057
0058
0059 #define VENDOR_SCSI3 1
0060
0061 #define VENDOR_NEC 2
0062 #define VENDOR_TOSHIBA 3
0063 #define VENDOR_WRITER 4
0064 #define VENDOR_CYGNAL_85ED 5
0065
0066 #define VENDOR_TIMEOUT 30*HZ
0067
0068 void sr_vendor_init(Scsi_CD *cd)
0069 {
0070 const char *vendor = cd->device->vendor;
0071 const char *model = cd->device->model;
0072
0073
0074 cd->vendor = VENDOR_SCSI3;
0075 if (cd->readcd_known)
0076
0077 return;
0078
0079 if (cd->device->type == TYPE_WORM) {
0080 cd->vendor = VENDOR_WRITER;
0081
0082 } else if (!strncmp(vendor, "NEC", 3)) {
0083 cd->vendor = VENDOR_NEC;
0084 if (!strncmp(model, "CD-ROM DRIVE:25", 15) ||
0085 !strncmp(model, "CD-ROM DRIVE:36", 15) ||
0086 !strncmp(model, "CD-ROM DRIVE:83", 15) ||
0087 !strncmp(model, "CD-ROM DRIVE:84 ", 16)
0088 #if 0
0089
0090
0091 || !strncmp(model, "CD-ROM DRIVE:500", 16)
0092 #endif
0093 )
0094
0095 cd->cdi.mask |= CDC_MULTI_SESSION;
0096
0097 } else if (!strncmp(vendor, "TOSHIBA", 7)) {
0098 cd->vendor = VENDOR_TOSHIBA;
0099
0100 } else if (!strncmp(vendor, "Beurer", 6) &&
0101 !strncmp(model, "Gluco Memory", 12)) {
0102
0103
0104
0105
0106
0107
0108
0109 cd->vendor = VENDOR_CYGNAL_85ED;
0110 cd->cdi.mask |= (
0111 CDC_MULTI_SESSION |
0112 CDC_CLOSE_TRAY | CDC_OPEN_TRAY |
0113 CDC_LOCK |
0114 CDC_GENERIC_PACKET |
0115 CDC_PLAY_AUDIO
0116 );
0117 }
0118 }
0119
0120
0121
0122
0123
0124 int sr_set_blocklength(Scsi_CD *cd, int blocklength)
0125 {
0126 unsigned char *buffer;
0127 struct packet_command cgc;
0128 struct ccs_modesel_head *modesel;
0129 int rc, density = 0;
0130
0131 if (cd->vendor == VENDOR_TOSHIBA)
0132 density = (blocklength > 2048) ? 0x81 : 0x83;
0133
0134 buffer = kmalloc(512, GFP_KERNEL);
0135 if (!buffer)
0136 return -ENOMEM;
0137
0138 #ifdef DEBUG
0139 sr_printk(KERN_INFO, cd, "MODE SELECT 0x%x/%d\n", density, blocklength);
0140 #endif
0141 memset(&cgc, 0, sizeof(struct packet_command));
0142 cgc.cmd[0] = MODE_SELECT;
0143 cgc.cmd[1] = (1 << 4);
0144 cgc.cmd[4] = 12;
0145 modesel = (struct ccs_modesel_head *) buffer;
0146 memset(modesel, 0, sizeof(*modesel));
0147 modesel->block_desc_length = 0x08;
0148 modesel->density = density;
0149 modesel->block_length_med = (blocklength >> 8) & 0xff;
0150 modesel->block_length_lo = blocklength & 0xff;
0151 cgc.buffer = buffer;
0152 cgc.buflen = sizeof(*modesel);
0153 cgc.data_direction = DMA_TO_DEVICE;
0154 cgc.timeout = VENDOR_TIMEOUT;
0155 if (0 == (rc = sr_do_ioctl(cd, &cgc))) {
0156 cd->device->sector_size = blocklength;
0157 }
0158 #ifdef DEBUG
0159 else
0160 sr_printk(KERN_INFO, cd,
0161 "switching blocklength to %d bytes failed\n",
0162 blocklength);
0163 #endif
0164 kfree(buffer);
0165 return rc;
0166 }
0167
0168
0169
0170
0171 int sr_cd_check(struct cdrom_device_info *cdi)
0172 {
0173 Scsi_CD *cd = cdi->handle;
0174 unsigned long sector;
0175 unsigned char *buffer;
0176 struct packet_command cgc;
0177 int rc, no_multi;
0178
0179 if (cd->cdi.mask & CDC_MULTI_SESSION)
0180 return 0;
0181
0182 buffer = kmalloc(512, GFP_KERNEL);
0183 if (!buffer)
0184 return -ENOMEM;
0185
0186 sector = 0;
0187 no_multi = 0;
0188 rc = 0;
0189
0190 memset(&cgc, 0, sizeof(struct packet_command));
0191
0192 switch (cd->vendor) {
0193
0194 case VENDOR_SCSI3:
0195 cgc.cmd[0] = READ_TOC;
0196 cgc.cmd[8] = 12;
0197 cgc.cmd[9] = 0x40;
0198 cgc.buffer = buffer;
0199 cgc.buflen = 12;
0200 cgc.quiet = 1;
0201 cgc.data_direction = DMA_FROM_DEVICE;
0202 cgc.timeout = VENDOR_TIMEOUT;
0203 rc = sr_do_ioctl(cd, &cgc);
0204 if (rc != 0)
0205 break;
0206 if ((buffer[0] << 8) + buffer[1] < 0x0a) {
0207 sr_printk(KERN_INFO, cd, "Hmm, seems the drive "
0208 "doesn't support multisession CD's\n");
0209 no_multi = 1;
0210 break;
0211 }
0212 sector = buffer[11] + (buffer[10] << 8) +
0213 (buffer[9] << 16) + (buffer[8] << 24);
0214 if (buffer[6] <= 1) {
0215
0216 sector = 0;
0217 }
0218 break;
0219
0220 case VENDOR_NEC:{
0221 unsigned long min, sec, frame;
0222 cgc.cmd[0] = 0xde;
0223 cgc.cmd[1] = 0x03;
0224 cgc.cmd[2] = 0xb0;
0225 cgc.buffer = buffer;
0226 cgc.buflen = 0x16;
0227 cgc.quiet = 1;
0228 cgc.data_direction = DMA_FROM_DEVICE;
0229 cgc.timeout = VENDOR_TIMEOUT;
0230 rc = sr_do_ioctl(cd, &cgc);
0231 if (rc != 0)
0232 break;
0233 if (buffer[14] != 0 && buffer[14] != 0xb0) {
0234 sr_printk(KERN_INFO, cd, "Hmm, seems the cdrom "
0235 "doesn't support multisession CD's\n");
0236
0237 no_multi = 1;
0238 break;
0239 }
0240 min = bcd2bin(buffer[15]);
0241 sec = bcd2bin(buffer[16]);
0242 frame = bcd2bin(buffer[17]);
0243 sector = min * CD_SECS * CD_FRAMES + sec * CD_FRAMES + frame;
0244 break;
0245 }
0246
0247 case VENDOR_TOSHIBA:{
0248 unsigned long min, sec, frame;
0249
0250
0251
0252 cgc.cmd[0] = 0xc7;
0253 cgc.cmd[1] = 0x03;
0254 cgc.buffer = buffer;
0255 cgc.buflen = 4;
0256 cgc.quiet = 1;
0257 cgc.data_direction = DMA_FROM_DEVICE;
0258 cgc.timeout = VENDOR_TIMEOUT;
0259 rc = sr_do_ioctl(cd, &cgc);
0260 if (rc == -EINVAL) {
0261 sr_printk(KERN_INFO, cd, "Hmm, seems the drive "
0262 "doesn't support multisession CD's\n");
0263 no_multi = 1;
0264 break;
0265 }
0266 if (rc != 0)
0267 break;
0268 min = bcd2bin(buffer[1]);
0269 sec = bcd2bin(buffer[2]);
0270 frame = bcd2bin(buffer[3]);
0271 sector = min * CD_SECS * CD_FRAMES + sec * CD_FRAMES + frame;
0272 if (sector)
0273 sector -= CD_MSF_OFFSET;
0274 sr_set_blocklength(cd, 2048);
0275 break;
0276 }
0277
0278 case VENDOR_WRITER:
0279 cgc.cmd[0] = READ_TOC;
0280 cgc.cmd[8] = 0x04;
0281 cgc.cmd[9] = 0x40;
0282 cgc.buffer = buffer;
0283 cgc.buflen = 0x04;
0284 cgc.quiet = 1;
0285 cgc.data_direction = DMA_FROM_DEVICE;
0286 cgc.timeout = VENDOR_TIMEOUT;
0287 rc = sr_do_ioctl(cd, &cgc);
0288 if (rc != 0) {
0289 break;
0290 }
0291 if ((rc = buffer[2]) == 0) {
0292 sr_printk(KERN_WARNING, cd,
0293 "No finished session\n");
0294 break;
0295 }
0296 cgc.cmd[0] = READ_TOC;
0297 cgc.cmd[6] = rc & 0x7f;
0298 cgc.cmd[8] = 0x0c;
0299 cgc.cmd[9] = 0x40;
0300 cgc.buffer = buffer;
0301 cgc.buflen = 12;
0302 cgc.quiet = 1;
0303 cgc.data_direction = DMA_FROM_DEVICE;
0304 cgc.timeout = VENDOR_TIMEOUT;
0305 rc = sr_do_ioctl(cd, &cgc);
0306 if (rc != 0) {
0307 break;
0308 }
0309 sector = buffer[11] + (buffer[10] << 8) +
0310 (buffer[9] << 16) + (buffer[8] << 24);
0311 break;
0312
0313 default:
0314
0315 sr_printk(KERN_WARNING, cd,
0316 "unknown vendor code (%i), not initialized ?\n",
0317 cd->vendor);
0318 sector = 0;
0319 no_multi = 1;
0320 break;
0321 }
0322 cd->ms_offset = sector;
0323 cd->xa_flag = 0;
0324 if (CDS_AUDIO != sr_disk_status(cdi) && 1 == sr_is_xa(cd))
0325 cd->xa_flag = 1;
0326
0327 if (2048 != cd->device->sector_size) {
0328 sr_set_blocklength(cd, 2048);
0329 }
0330 if (no_multi)
0331 cdi->mask |= CDC_MULTI_SESSION;
0332
0333 #ifdef DEBUG
0334 if (sector)
0335 sr_printk(KERN_DEBUG, cd, "multisession offset=%lu\n",
0336 sector);
0337 #endif
0338 kfree(buffer);
0339 return rc;
0340 }