diff options
| -rw-r--r-- | drivers/scsi/scsi_lib.c | 51 | ||||
| -rw-r--r-- | drivers/scsi/scsi_scan.c | 112 | ||||
| -rw-r--r-- | include/scsi/scsi_request.h | 3 |
3 files changed, 102 insertions, 64 deletions
diff --git a/drivers/scsi/scsi_lib.c b/drivers/scsi/scsi_lib.c index 60f07b6a5ffc..b8212c563fed 100644 --- a/drivers/scsi/scsi_lib.c +++ b/drivers/scsi/scsi_lib.c | |||
| @@ -246,7 +246,7 @@ void scsi_wait_req(struct scsi_request *sreq, const void *cmnd, void *buffer, | |||
| 246 | unsigned bufflen, int timeout, int retries) | 246 | unsigned bufflen, int timeout, int retries) |
| 247 | { | 247 | { |
| 248 | DECLARE_COMPLETION(wait); | 248 | DECLARE_COMPLETION(wait); |
| 249 | int write = sreq->sr_data_direction == DMA_TO_DEVICE; | 249 | int write = (sreq->sr_data_direction == DMA_TO_DEVICE); |
| 250 | struct request *req; | 250 | struct request *req; |
| 251 | 251 | ||
| 252 | req = blk_get_request(sreq->sr_device->request_queue, write, | 252 | req = blk_get_request(sreq->sr_device->request_queue, write, |
| @@ -281,6 +281,55 @@ void scsi_wait_req(struct scsi_request *sreq, const void *cmnd, void *buffer, | |||
| 281 | 281 | ||
| 282 | EXPORT_SYMBOL(scsi_wait_req); | 282 | EXPORT_SYMBOL(scsi_wait_req); |
| 283 | 283 | ||
| 284 | /** | ||
| 285 | * scsi_execute_req - insert request and wait for the result | ||
| 286 | * @sdev: scsi device | ||
| 287 | * @cmd: scsi command | ||
| 288 | * @data_direction: data direction | ||
| 289 | * @buffer: data buffer | ||
| 290 | * @bufflen: len of buffer | ||
| 291 | * @sense: optional sense buffer | ||
| 292 | * @timeout: request timeout in seconds | ||
| 293 | * @retries: number of times to retry request | ||
| 294 | * | ||
| 295 | * scsi_execute_req returns the req->errors value which is the | ||
| 296 | * the scsi_cmnd result field. | ||
| 297 | **/ | ||
| 298 | int scsi_execute_req(struct scsi_device *sdev, unsigned char *cmd, | ||
| 299 | int data_direction, void *buffer, unsigned bufflen, | ||
| 300 | unsigned char *sense, int timeout, int retries) | ||
| 301 | { | ||
| 302 | struct request *req; | ||
| 303 | int write = (data_direction == DMA_TO_DEVICE); | ||
| 304 | int ret = DRIVER_ERROR << 24; | ||
| 305 | |||
| 306 | req = blk_get_request(sdev->request_queue, write, __GFP_WAIT); | ||
| 307 | |||
| 308 | if (bufflen && blk_rq_map_kern(sdev->request_queue, req, | ||
| 309 | buffer, bufflen, __GFP_WAIT)) | ||
| 310 | goto out; | ||
| 311 | |||
| 312 | req->cmd_len = COMMAND_SIZE(cmd[0]); | ||
| 313 | memcpy(req->cmd, cmd, req->cmd_len); | ||
| 314 | req->sense = sense; | ||
| 315 | req->sense_len = 0; | ||
| 316 | req->timeout = timeout; | ||
| 317 | req->flags |= REQ_BLOCK_PC | REQ_SPECIAL; | ||
| 318 | |||
| 319 | /* | ||
| 320 | * head injection *required* here otherwise quiesce won't work | ||
| 321 | */ | ||
| 322 | blk_execute_rq(req->q, NULL, req, 1); | ||
| 323 | |||
| 324 | ret = req->errors; | ||
| 325 | out: | ||
| 326 | blk_put_request(req); | ||
| 327 | |||
| 328 | return ret; | ||
| 329 | } | ||
| 330 | |||
| 331 | EXPORT_SYMBOL(scsi_execute_req); | ||
| 332 | |||
| 284 | /* | 333 | /* |
| 285 | * Function: scsi_init_cmd_errh() | 334 | * Function: scsi_init_cmd_errh() |
| 286 | * | 335 | * |
diff --git a/drivers/scsi/scsi_scan.c b/drivers/scsi/scsi_scan.c index 48edd67982a5..d2ca4b8fbc13 100644 --- a/drivers/scsi/scsi_scan.c +++ b/drivers/scsi/scsi_scan.c | |||
| @@ -111,15 +111,14 @@ MODULE_PARM_DESC(inq_timeout, | |||
| 111 | 111 | ||
| 112 | /** | 112 | /** |
| 113 | * scsi_unlock_floptical - unlock device via a special MODE SENSE command | 113 | * scsi_unlock_floptical - unlock device via a special MODE SENSE command |
| 114 | * @sreq: used to send the command | 114 | * @sdev: scsi device to send command to |
| 115 | * @result: area to store the result of the MODE SENSE | 115 | * @result: area to store the result of the MODE SENSE |
| 116 | * | 116 | * |
| 117 | * Description: | 117 | * Description: |
| 118 | * Send a vendor specific MODE SENSE (not a MODE SELECT) command using | 118 | * Send a vendor specific MODE SENSE (not a MODE SELECT) command. |
| 119 | * @sreq to unlock a device, storing the (unused) results into result. | ||
| 120 | * Called for BLIST_KEY devices. | 119 | * Called for BLIST_KEY devices. |
| 121 | **/ | 120 | **/ |
| 122 | static void scsi_unlock_floptical(struct scsi_request *sreq, | 121 | static void scsi_unlock_floptical(struct scsi_device *sdev, |
| 123 | unsigned char *result) | 122 | unsigned char *result) |
| 124 | { | 123 | { |
| 125 | unsigned char scsi_cmd[MAX_COMMAND_SIZE]; | 124 | unsigned char scsi_cmd[MAX_COMMAND_SIZE]; |
| @@ -129,11 +128,10 @@ static void scsi_unlock_floptical(struct scsi_request *sreq, | |||
| 129 | scsi_cmd[1] = 0; | 128 | scsi_cmd[1] = 0; |
| 130 | scsi_cmd[2] = 0x2e; | 129 | scsi_cmd[2] = 0x2e; |
| 131 | scsi_cmd[3] = 0; | 130 | scsi_cmd[3] = 0; |
| 132 | scsi_cmd[4] = 0x2a; /* size */ | 131 | scsi_cmd[4] = 0x2a; /* size */ |
| 133 | scsi_cmd[5] = 0; | 132 | scsi_cmd[5] = 0; |
| 134 | sreq->sr_cmd_len = 0; | 133 | scsi_execute_req(sdev, scsi_cmd, DMA_FROM_DEVICE, result, 0x2a, NULL, |
| 135 | sreq->sr_data_direction = DMA_FROM_DEVICE; | 134 | SCSI_TIMEOUT, 3); |
| 136 | scsi_wait_req(sreq, scsi_cmd, result, 0x2a /* size */, SCSI_TIMEOUT, 3); | ||
| 137 | } | 135 | } |
| 138 | 136 | ||
| 139 | /** | 137 | /** |
| @@ -433,26 +431,26 @@ void scsi_target_reap(struct scsi_target *starget) | |||
| 433 | 431 | ||
| 434 | /** | 432 | /** |
| 435 | * scsi_probe_lun - probe a single LUN using a SCSI INQUIRY | 433 | * scsi_probe_lun - probe a single LUN using a SCSI INQUIRY |
| 436 | * @sreq: used to send the INQUIRY | 434 | * @sdev: scsi_device to probe |
| 437 | * @inq_result: area to store the INQUIRY result | 435 | * @inq_result: area to store the INQUIRY result |
| 436 | * @result_len: len of inq_result | ||
| 438 | * @bflags: store any bflags found here | 437 | * @bflags: store any bflags found here |
| 439 | * | 438 | * |
| 440 | * Description: | 439 | * Description: |
| 441 | * Probe the lun associated with @sreq using a standard SCSI INQUIRY; | 440 | * Probe the lun associated with @req using a standard SCSI INQUIRY; |
| 442 | * | 441 | * |
| 443 | * If the INQUIRY is successful, sreq->sr_result is zero and: the | 442 | * If the INQUIRY is successful, zero is returned and the |
| 444 | * INQUIRY data is in @inq_result; the scsi_level and INQUIRY length | 443 | * INQUIRY data is in @inq_result; the scsi_level and INQUIRY length |
| 445 | * are copied to the Scsi_Device at @sreq->sr_device (sdev); | 444 | * are copied to the Scsi_Device any flags value is stored in *@bflags. |
| 446 | * any flags value is stored in *@bflags. | ||
| 447 | **/ | 445 | **/ |
| 448 | static void scsi_probe_lun(struct scsi_request *sreq, char *inq_result, | 446 | static int scsi_probe_lun(struct scsi_device *sdev, char *inq_result, |
| 449 | int *bflags) | 447 | int result_len, int *bflags) |
| 450 | { | 448 | { |
| 451 | struct scsi_device *sdev = sreq->sr_device; /* a bit ugly */ | 449 | char sense[SCSI_SENSE_BUFFERSIZE]; |
| 452 | unsigned char scsi_cmd[MAX_COMMAND_SIZE]; | 450 | unsigned char scsi_cmd[MAX_COMMAND_SIZE]; |
| 453 | int first_inquiry_len, try_inquiry_len, next_inquiry_len; | 451 | int first_inquiry_len, try_inquiry_len, next_inquiry_len; |
| 454 | int response_len = 0; | 452 | int response_len = 0; |
| 455 | int pass, count; | 453 | int pass, count, result; |
| 456 | struct scsi_sense_hdr sshdr; | 454 | struct scsi_sense_hdr sshdr; |
| 457 | 455 | ||
| 458 | *bflags = 0; | 456 | *bflags = 0; |
| @@ -475,28 +473,28 @@ static void scsi_probe_lun(struct scsi_request *sreq, char *inq_result, | |||
| 475 | memset(scsi_cmd, 0, 6); | 473 | memset(scsi_cmd, 0, 6); |
| 476 | scsi_cmd[0] = INQUIRY; | 474 | scsi_cmd[0] = INQUIRY; |
| 477 | scsi_cmd[4] = (unsigned char) try_inquiry_len; | 475 | scsi_cmd[4] = (unsigned char) try_inquiry_len; |
| 478 | sreq->sr_cmd_len = 0; | ||
| 479 | sreq->sr_data_direction = DMA_FROM_DEVICE; | ||
| 480 | 476 | ||
| 477 | memset(sense, 0, sizeof(sense)); | ||
| 481 | memset(inq_result, 0, try_inquiry_len); | 478 | memset(inq_result, 0, try_inquiry_len); |
| 482 | scsi_wait_req(sreq, (void *) scsi_cmd, (void *) inq_result, | 479 | |
| 483 | try_inquiry_len, | 480 | result = scsi_execute_req(sdev, scsi_cmd, DMA_FROM_DEVICE, |
| 484 | HZ/2 + HZ*scsi_inq_timeout, 3); | 481 | inq_result, try_inquiry_len, sense, |
| 482 | HZ / 2 + HZ * scsi_inq_timeout, 3); | ||
| 485 | 483 | ||
| 486 | SCSI_LOG_SCAN_BUS(3, printk(KERN_INFO "scsi scan: INQUIRY %s " | 484 | SCSI_LOG_SCAN_BUS(3, printk(KERN_INFO "scsi scan: INQUIRY %s " |
| 487 | "with code 0x%x\n", | 485 | "with code 0x%x\n", |
| 488 | sreq->sr_result ? "failed" : "successful", | 486 | result ? "failed" : "successful", result)); |
| 489 | sreq->sr_result)); | ||
| 490 | 487 | ||
| 491 | if (sreq->sr_result) { | 488 | if (result) { |
| 492 | /* | 489 | /* |
| 493 | * not-ready to ready transition [asc/ascq=0x28/0x0] | 490 | * not-ready to ready transition [asc/ascq=0x28/0x0] |
| 494 | * or power-on, reset [asc/ascq=0x29/0x0], continue. | 491 | * or power-on, reset [asc/ascq=0x29/0x0], continue. |
| 495 | * INQUIRY should not yield UNIT_ATTENTION | 492 | * INQUIRY should not yield UNIT_ATTENTION |
| 496 | * but many buggy devices do so anyway. | 493 | * but many buggy devices do so anyway. |
| 497 | */ | 494 | */ |
| 498 | if ((driver_byte(sreq->sr_result) & DRIVER_SENSE) && | 495 | if ((driver_byte(result) & DRIVER_SENSE) && |
| 499 | scsi_request_normalize_sense(sreq, &sshdr)) { | 496 | scsi_normalize_sense(sense, sizeof(sense), |
| 497 | &sshdr)) { | ||
| 500 | if ((sshdr.sense_key == UNIT_ATTENTION) && | 498 | if ((sshdr.sense_key == UNIT_ATTENTION) && |
| 501 | ((sshdr.asc == 0x28) || | 499 | ((sshdr.asc == 0x28) || |
| 502 | (sshdr.asc == 0x29)) && | 500 | (sshdr.asc == 0x29)) && |
| @@ -507,7 +505,7 @@ static void scsi_probe_lun(struct scsi_request *sreq, char *inq_result, | |||
| 507 | break; | 505 | break; |
| 508 | } | 506 | } |
| 509 | 507 | ||
| 510 | if (sreq->sr_result == 0) { | 508 | if (result == 0) { |
| 511 | response_len = (unsigned char) inq_result[4] + 5; | 509 | response_len = (unsigned char) inq_result[4] + 5; |
| 512 | if (response_len > 255) | 510 | if (response_len > 255) |
| 513 | response_len = first_inquiry_len; /* sanity */ | 511 | response_len = first_inquiry_len; /* sanity */ |
| @@ -556,8 +554,8 @@ static void scsi_probe_lun(struct scsi_request *sreq, char *inq_result, | |||
| 556 | 554 | ||
| 557 | /* If the last transfer attempt got an error, assume the | 555 | /* If the last transfer attempt got an error, assume the |
| 558 | * peripheral doesn't exist or is dead. */ | 556 | * peripheral doesn't exist or is dead. */ |
| 559 | if (sreq->sr_result) | 557 | if (result) |
| 560 | return; | 558 | return -EIO; |
| 561 | 559 | ||
| 562 | /* Don't report any more data than the device says is valid */ | 560 | /* Don't report any more data than the device says is valid */ |
| 563 | sdev->inquiry_len = min(try_inquiry_len, response_len); | 561 | sdev->inquiry_len = min(try_inquiry_len, response_len); |
| @@ -593,7 +591,7 @@ static void scsi_probe_lun(struct scsi_request *sreq, char *inq_result, | |||
| 593 | (sdev->scsi_level == 1 && (inq_result[3] & 0x0f) == 1)) | 591 | (sdev->scsi_level == 1 && (inq_result[3] & 0x0f) == 1)) |
| 594 | sdev->scsi_level++; | 592 | sdev->scsi_level++; |
| 595 | 593 | ||
| 596 | return; | 594 | return 0; |
| 597 | } | 595 | } |
| 598 | 596 | ||
| 599 | /** | 597 | /** |
| @@ -800,9 +798,8 @@ static int scsi_probe_and_add_lun(struct scsi_target *starget, | |||
| 800 | void *hostdata) | 798 | void *hostdata) |
| 801 | { | 799 | { |
| 802 | struct scsi_device *sdev; | 800 | struct scsi_device *sdev; |
| 803 | struct scsi_request *sreq; | ||
| 804 | unsigned char *result; | 801 | unsigned char *result; |
| 805 | int bflags, res = SCSI_SCAN_NO_RESPONSE; | 802 | int bflags, res = SCSI_SCAN_NO_RESPONSE, result_len = 256; |
| 806 | struct Scsi_Host *shost = dev_to_shost(starget->dev.parent); | 803 | struct Scsi_Host *shost = dev_to_shost(starget->dev.parent); |
| 807 | 804 | ||
| 808 | /* | 805 | /* |
| @@ -831,16 +828,13 @@ static int scsi_probe_and_add_lun(struct scsi_target *starget, | |||
| 831 | sdev = scsi_alloc_sdev(starget, lun, hostdata); | 828 | sdev = scsi_alloc_sdev(starget, lun, hostdata); |
| 832 | if (!sdev) | 829 | if (!sdev) |
| 833 | goto out; | 830 | goto out; |
| 834 | sreq = scsi_allocate_request(sdev, GFP_ATOMIC); | 831 | |
| 835 | if (!sreq) | 832 | result = kmalloc(result_len, GFP_ATOMIC | |
| 836 | goto out_free_sdev; | ||
| 837 | result = kmalloc(256, GFP_ATOMIC | | ||
| 838 | ((shost->unchecked_isa_dma) ? __GFP_DMA : 0)); | 833 | ((shost->unchecked_isa_dma) ? __GFP_DMA : 0)); |
| 839 | if (!result) | 834 | if (!result) |
| 840 | goto out_free_sreq; | 835 | goto out_free_sdev; |
| 841 | 836 | ||
| 842 | scsi_probe_lun(sreq, result, &bflags); | 837 | if (scsi_probe_lun(sdev, result, result_len, &bflags)) |
| 843 | if (sreq->sr_result) | ||
| 844 | goto out_free_result; | 838 | goto out_free_result; |
| 845 | 839 | ||
| 846 | /* | 840 | /* |
| @@ -868,7 +862,7 @@ static int scsi_probe_and_add_lun(struct scsi_target *starget, | |||
| 868 | if (res == SCSI_SCAN_LUN_PRESENT) { | 862 | if (res == SCSI_SCAN_LUN_PRESENT) { |
| 869 | if (bflags & BLIST_KEY) { | 863 | if (bflags & BLIST_KEY) { |
| 870 | sdev->lockable = 0; | 864 | sdev->lockable = 0; |
| 871 | scsi_unlock_floptical(sreq, result); | 865 | scsi_unlock_floptical(sdev, result); |
| 872 | } | 866 | } |
| 873 | if (bflagsp) | 867 | if (bflagsp) |
| 874 | *bflagsp = bflags; | 868 | *bflagsp = bflags; |
| @@ -876,8 +870,6 @@ static int scsi_probe_and_add_lun(struct scsi_target *starget, | |||
| 876 | 870 | ||
| 877 | out_free_result: | 871 | out_free_result: |
| 878 | kfree(result); | 872 | kfree(result); |
| 879 | out_free_sreq: | ||
| 880 | scsi_release_request(sreq); | ||
| 881 | out_free_sdev: | 873 | out_free_sdev: |
| 882 | if (res == SCSI_SCAN_LUN_PRESENT) { | 874 | if (res == SCSI_SCAN_LUN_PRESENT) { |
| 883 | if (sdevp) { | 875 | if (sdevp) { |
| @@ -1065,13 +1057,14 @@ static int scsi_report_lun_scan(struct scsi_device *sdev, int bflags, | |||
| 1065 | int rescan) | 1057 | int rescan) |
| 1066 | { | 1058 | { |
| 1067 | char devname[64]; | 1059 | char devname[64]; |
| 1060 | char sense[SCSI_SENSE_BUFFERSIZE]; | ||
| 1068 | unsigned char scsi_cmd[MAX_COMMAND_SIZE]; | 1061 | unsigned char scsi_cmd[MAX_COMMAND_SIZE]; |
| 1069 | unsigned int length; | 1062 | unsigned int length; |
| 1070 | unsigned int lun; | 1063 | unsigned int lun; |
| 1071 | unsigned int num_luns; | 1064 | unsigned int num_luns; |
| 1072 | unsigned int retries; | 1065 | unsigned int retries; |
| 1066 | int result; | ||
| 1073 | struct scsi_lun *lunp, *lun_data; | 1067 | struct scsi_lun *lunp, *lun_data; |
| 1074 | struct scsi_request *sreq; | ||
| 1075 | u8 *data; | 1068 | u8 *data; |
| 1076 | struct scsi_sense_hdr sshdr; | 1069 | struct scsi_sense_hdr sshdr; |
| 1077 | struct scsi_target *starget = scsi_target(sdev); | 1070 | struct scsi_target *starget = scsi_target(sdev); |
| @@ -1089,10 +1082,6 @@ static int scsi_report_lun_scan(struct scsi_device *sdev, int bflags, | |||
| 1089 | if (bflags & BLIST_NOLUN) | 1082 | if (bflags & BLIST_NOLUN) |
| 1090 | return 0; | 1083 | return 0; |
| 1091 | 1084 | ||
| 1092 | sreq = scsi_allocate_request(sdev, GFP_ATOMIC); | ||
| 1093 | if (!sreq) | ||
| 1094 | goto out; | ||
| 1095 | |||
| 1096 | sprintf(devname, "host %d channel %d id %d", | 1085 | sprintf(devname, "host %d channel %d id %d", |
| 1097 | sdev->host->host_no, sdev->channel, sdev->id); | 1086 | sdev->host->host_no, sdev->channel, sdev->id); |
| 1098 | 1087 | ||
| @@ -1110,7 +1099,7 @@ static int scsi_report_lun_scan(struct scsi_device *sdev, int bflags, | |||
| 1110 | lun_data = kmalloc(length, GFP_ATOMIC | | 1099 | lun_data = kmalloc(length, GFP_ATOMIC | |
| 1111 | (sdev->host->unchecked_isa_dma ? __GFP_DMA : 0)); | 1100 | (sdev->host->unchecked_isa_dma ? __GFP_DMA : 0)); |
| 1112 | if (!lun_data) | 1101 | if (!lun_data) |
| 1113 | goto out_release_request; | 1102 | goto out; |
| 1114 | 1103 | ||
| 1115 | scsi_cmd[0] = REPORT_LUNS; | 1104 | scsi_cmd[0] = REPORT_LUNS; |
| 1116 | 1105 | ||
| @@ -1129,8 +1118,6 @@ static int scsi_report_lun_scan(struct scsi_device *sdev, int bflags, | |||
| 1129 | 1118 | ||
| 1130 | scsi_cmd[10] = 0; /* reserved */ | 1119 | scsi_cmd[10] = 0; /* reserved */ |
| 1131 | scsi_cmd[11] = 0; /* control */ | 1120 | scsi_cmd[11] = 0; /* control */ |
| 1132 | sreq->sr_cmd_len = 0; | ||
| 1133 | sreq->sr_data_direction = DMA_FROM_DEVICE; | ||
| 1134 | 1121 | ||
| 1135 | /* | 1122 | /* |
| 1136 | * We can get a UNIT ATTENTION, for example a power on/reset, so | 1123 | * We can get a UNIT ATTENTION, for example a power on/reset, so |
| @@ -1146,29 +1133,30 @@ static int scsi_report_lun_scan(struct scsi_device *sdev, int bflags, | |||
| 1146 | SCSI_LOG_SCAN_BUS(3, printk (KERN_INFO "scsi scan: Sending" | 1133 | SCSI_LOG_SCAN_BUS(3, printk (KERN_INFO "scsi scan: Sending" |
| 1147 | " REPORT LUNS to %s (try %d)\n", devname, | 1134 | " REPORT LUNS to %s (try %d)\n", devname, |
| 1148 | retries)); | 1135 | retries)); |
| 1149 | scsi_wait_req(sreq, scsi_cmd, lun_data, length, | 1136 | |
| 1150 | SCSI_TIMEOUT + 4*HZ, 3); | 1137 | memset(sense, 0, sizeof(sense)); |
| 1138 | result = scsi_execute_req(sdev, scsi_cmd, DMA_FROM_DEVICE, | ||
| 1139 | lun_data, length, sense, | ||
| 1140 | SCSI_TIMEOUT + 4 * HZ, 3); | ||
| 1141 | |||
| 1151 | SCSI_LOG_SCAN_BUS(3, printk (KERN_INFO "scsi scan: REPORT LUNS" | 1142 | SCSI_LOG_SCAN_BUS(3, printk (KERN_INFO "scsi scan: REPORT LUNS" |
| 1152 | " %s (try %d) result 0x%x\n", sreq->sr_result | 1143 | " %s (try %d) result 0x%x\n", result |
| 1153 | ? "failed" : "successful", retries, | 1144 | ? "failed" : "successful", retries, result)); |
| 1154 | sreq->sr_result)); | 1145 | if (result == 0) |
| 1155 | if (sreq->sr_result == 0) | ||
| 1156 | break; | 1146 | break; |
| 1157 | else if (scsi_request_normalize_sense(sreq, &sshdr)) { | 1147 | else if (scsi_normalize_sense(sense, sizeof(sense), &sshdr)) { |
| 1158 | if (sshdr.sense_key != UNIT_ATTENTION) | 1148 | if (sshdr.sense_key != UNIT_ATTENTION) |
| 1159 | break; | 1149 | break; |
| 1160 | } | 1150 | } |
| 1161 | } | 1151 | } |
| 1162 | 1152 | ||
| 1163 | if (sreq->sr_result) { | 1153 | if (result) { |
| 1164 | /* | 1154 | /* |
| 1165 | * The device probably does not support a REPORT LUN command | 1155 | * The device probably does not support a REPORT LUN command |
| 1166 | */ | 1156 | */ |
| 1167 | kfree(lun_data); | 1157 | kfree(lun_data); |
| 1168 | scsi_release_request(sreq); | ||
| 1169 | return 1; | 1158 | return 1; |
| 1170 | } | 1159 | } |
| 1171 | scsi_release_request(sreq); | ||
| 1172 | 1160 | ||
| 1173 | /* | 1161 | /* |
| 1174 | * Get the length from the first four bytes of lun_data. | 1162 | * Get the length from the first four bytes of lun_data. |
| @@ -1242,8 +1230,6 @@ static int scsi_report_lun_scan(struct scsi_device *sdev, int bflags, | |||
| 1242 | kfree(lun_data); | 1230 | kfree(lun_data); |
| 1243 | return 0; | 1231 | return 0; |
| 1244 | 1232 | ||
| 1245 | out_release_request: | ||
| 1246 | scsi_release_request(sreq); | ||
| 1247 | out: | 1233 | out: |
| 1248 | /* | 1234 | /* |
| 1249 | * We are out of memory, don't try scanning any further. | 1235 | * We are out of memory, don't try scanning any further. |
diff --git a/include/scsi/scsi_request.h b/include/scsi/scsi_request.h index 98719407d554..d64903a617c3 100644 --- a/include/scsi/scsi_request.h +++ b/include/scsi/scsi_request.h | |||
| @@ -54,6 +54,9 @@ extern void scsi_do_req(struct scsi_request *, const void *cmnd, | |||
| 54 | void *buffer, unsigned bufflen, | 54 | void *buffer, unsigned bufflen, |
| 55 | void (*done) (struct scsi_cmnd *), | 55 | void (*done) (struct scsi_cmnd *), |
| 56 | int timeout, int retries); | 56 | int timeout, int retries); |
| 57 | extern int scsi_execute_req(struct scsi_device *sdev, unsigned char *cmd, | ||
| 58 | int data_direction, void *buffer, unsigned bufflen, | ||
| 59 | unsigned char *sense, int timeout, int retries); | ||
| 57 | 60 | ||
| 58 | struct scsi_mode_data { | 61 | struct scsi_mode_data { |
| 59 | __u32 length; | 62 | __u32 length; |
