diff options
Diffstat (limited to 'drivers/scsi/sr.c')
-rw-r--r-- | drivers/scsi/sr.c | 43 |
1 files changed, 12 insertions, 31 deletions
diff --git a/drivers/scsi/sr.c b/drivers/scsi/sr.c index a4d9be7c6874..dd8050392d01 100644 --- a/drivers/scsi/sr.c +++ b/drivers/scsi/sr.c | |||
@@ -44,6 +44,7 @@ | |||
44 | #include <linux/interrupt.h> | 44 | #include <linux/interrupt.h> |
45 | #include <linux/init.h> | 45 | #include <linux/init.h> |
46 | #include <linux/blkdev.h> | 46 | #include <linux/blkdev.h> |
47 | #include <linux/mutex.h> | ||
47 | #include <asm/uaccess.h> | 48 | #include <asm/uaccess.h> |
48 | 49 | ||
49 | #include <scsi/scsi.h> | 50 | #include <scsi/scsi.h> |
@@ -90,7 +91,7 @@ static DEFINE_SPINLOCK(sr_index_lock); | |||
90 | /* This semaphore is used to mediate the 0->1 reference get in the | 91 | /* This semaphore is used to mediate the 0->1 reference get in the |
91 | * face of object destruction (i.e. we can't allow a get on an | 92 | * face of object destruction (i.e. we can't allow a get on an |
92 | * object after last put) */ | 93 | * object after last put) */ |
93 | static DECLARE_MUTEX(sr_ref_sem); | 94 | static DEFINE_MUTEX(sr_ref_mutex); |
94 | 95 | ||
95 | static int sr_open(struct cdrom_device_info *, int); | 96 | static int sr_open(struct cdrom_device_info *, int); |
96 | static void sr_release(struct cdrom_device_info *); | 97 | static void sr_release(struct cdrom_device_info *); |
@@ -133,7 +134,7 @@ static inline struct scsi_cd *scsi_cd_get(struct gendisk *disk) | |||
133 | { | 134 | { |
134 | struct scsi_cd *cd = NULL; | 135 | struct scsi_cd *cd = NULL; |
135 | 136 | ||
136 | down(&sr_ref_sem); | 137 | mutex_lock(&sr_ref_mutex); |
137 | if (disk->private_data == NULL) | 138 | if (disk->private_data == NULL) |
138 | goto out; | 139 | goto out; |
139 | cd = scsi_cd(disk); | 140 | cd = scsi_cd(disk); |
@@ -146,7 +147,7 @@ static inline struct scsi_cd *scsi_cd_get(struct gendisk *disk) | |||
146 | kref_put(&cd->kref, sr_kref_release); | 147 | kref_put(&cd->kref, sr_kref_release); |
147 | cd = NULL; | 148 | cd = NULL; |
148 | out: | 149 | out: |
149 | up(&sr_ref_sem); | 150 | mutex_unlock(&sr_ref_mutex); |
150 | return cd; | 151 | return cd; |
151 | } | 152 | } |
152 | 153 | ||
@@ -154,10 +155,10 @@ static inline void scsi_cd_put(struct scsi_cd *cd) | |||
154 | { | 155 | { |
155 | struct scsi_device *sdev = cd->device; | 156 | struct scsi_device *sdev = cd->device; |
156 | 157 | ||
157 | down(&sr_ref_sem); | 158 | mutex_lock(&sr_ref_mutex); |
158 | kref_put(&cd->kref, sr_kref_release); | 159 | kref_put(&cd->kref, sr_kref_release); |
159 | scsi_device_put(sdev); | 160 | scsi_device_put(sdev); |
160 | up(&sr_ref_sem); | 161 | mutex_unlock(&sr_ref_mutex); |
161 | } | 162 | } |
162 | 163 | ||
163 | /* | 164 | /* |
@@ -237,8 +238,6 @@ static void rw_intr(struct scsi_cmnd * SCpnt) | |||
237 | case ILLEGAL_REQUEST: | 238 | case ILLEGAL_REQUEST: |
238 | if (!(SCpnt->sense_buffer[0] & 0x90)) | 239 | if (!(SCpnt->sense_buffer[0] & 0x90)) |
239 | break; | 240 | break; |
240 | if (!blk_fs_request(SCpnt->request)) | ||
241 | break; | ||
242 | error_sector = (SCpnt->sense_buffer[3] << 24) | | 241 | error_sector = (SCpnt->sense_buffer[3] << 24) | |
243 | (SCpnt->sense_buffer[4] << 16) | | 242 | (SCpnt->sense_buffer[4] << 16) | |
244 | (SCpnt->sense_buffer[5] << 8) | | 243 | (SCpnt->sense_buffer[5] << 8) | |
@@ -317,23 +316,6 @@ static int sr_init_command(struct scsi_cmnd * SCpnt) | |||
317 | } | 316 | } |
318 | 317 | ||
319 | /* | 318 | /* |
320 | * these are already setup, just copy cdb basically | ||
321 | */ | ||
322 | if (SCpnt->request->flags & REQ_BLOCK_PC) { | ||
323 | scsi_setup_blk_pc_cmnd(SCpnt); | ||
324 | |||
325 | if (SCpnt->timeout_per_command) | ||
326 | timeout = SCpnt->timeout_per_command; | ||
327 | |||
328 | goto queue; | ||
329 | } | ||
330 | |||
331 | if (!(SCpnt->request->flags & REQ_CMD)) { | ||
332 | blk_dump_rq_flags(SCpnt->request, "sr unsup command"); | ||
333 | return 0; | ||
334 | } | ||
335 | |||
336 | /* | ||
337 | * we do lazy blocksize switching (when reading XA sectors, | 319 | * we do lazy blocksize switching (when reading XA sectors, |
338 | * see CDROMREADMODE2 ioctl) | 320 | * see CDROMREADMODE2 ioctl) |
339 | */ | 321 | */ |
@@ -421,8 +403,6 @@ static int sr_init_command(struct scsi_cmnd * SCpnt) | |||
421 | */ | 403 | */ |
422 | SCpnt->transfersize = cd->device->sector_size; | 404 | SCpnt->transfersize = cd->device->sector_size; |
423 | SCpnt->underflow = this_count << 9; | 405 | SCpnt->underflow = this_count << 9; |
424 | |||
425 | queue: | ||
426 | SCpnt->allowed = MAX_RETRIES; | 406 | SCpnt->allowed = MAX_RETRIES; |
427 | SCpnt->timeout_per_command = timeout; | 407 | SCpnt->timeout_per_command = timeout; |
428 | 408 | ||
@@ -762,8 +742,9 @@ static void get_capabilities(struct scsi_cd *cd) | |||
762 | /* failed, drive doesn't have capabilities mode page */ | 742 | /* failed, drive doesn't have capabilities mode page */ |
763 | cd->cdi.speed = 1; | 743 | cd->cdi.speed = 1; |
764 | cd->cdi.mask |= (CDC_CD_R | CDC_CD_RW | CDC_DVD_R | | 744 | cd->cdi.mask |= (CDC_CD_R | CDC_CD_RW | CDC_DVD_R | |
765 | CDC_DVD | CDC_DVD_RAM | | 745 | CDC_DVD | CDC_DVD_RAM | |
766 | CDC_SELECT_DISC | CDC_SELECT_SPEED); | 746 | CDC_SELECT_DISC | CDC_SELECT_SPEED | |
747 | CDC_MRW | CDC_MRW_W | CDC_RAM); | ||
767 | kfree(buffer); | 748 | kfree(buffer); |
768 | printk("%s: scsi-1 drive\n", cd->cdi.name); | 749 | printk("%s: scsi-1 drive\n", cd->cdi.name); |
769 | return; | 750 | return; |
@@ -845,7 +826,7 @@ static int sr_packet(struct cdrom_device_info *cdi, | |||
845 | * sr_kref_release - Called to free the scsi_cd structure | 826 | * sr_kref_release - Called to free the scsi_cd structure |
846 | * @kref: pointer to embedded kref | 827 | * @kref: pointer to embedded kref |
847 | * | 828 | * |
848 | * sr_ref_sem must be held entering this routine. Because it is | 829 | * sr_ref_mutex must be held entering this routine. Because it is |
849 | * called on last put, you should always use the scsi_cd_get() | 830 | * called on last put, you should always use the scsi_cd_get() |
850 | * scsi_cd_put() helpers which manipulate the semaphore directly | 831 | * scsi_cd_put() helpers which manipulate the semaphore directly |
851 | * and never do a direct kref_put(). | 832 | * and never do a direct kref_put(). |
@@ -874,9 +855,9 @@ static int sr_remove(struct device *dev) | |||
874 | 855 | ||
875 | del_gendisk(cd->disk); | 856 | del_gendisk(cd->disk); |
876 | 857 | ||
877 | down(&sr_ref_sem); | 858 | mutex_lock(&sr_ref_mutex); |
878 | kref_put(&cd->kref, sr_kref_release); | 859 | kref_put(&cd->kref, sr_kref_release); |
879 | up(&sr_ref_sem); | 860 | mutex_unlock(&sr_ref_mutex); |
880 | 861 | ||
881 | return 0; | 862 | return 0; |
882 | } | 863 | } |