diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2011-03-26 00:06:13 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2011-03-26 00:06:13 -0400 |
commit | 9f34217c846a96dea03f4418e2f27423658d3542 (patch) | |
tree | 5b137af50db5758261700015911afb197ac8fc9f /drivers/scsi/sd.c | |
parent | 95e14ed7fc4b2db62eb597a70850a0fede48b78a (diff) | |
parent | 3703b2c5d041a68095cdd22380c23ce27d449ad7 (diff) |
Merge git://git.kernel.org/pub/scm/linux/kernel/git/jejb/scsi-misc-2.6
* git://git.kernel.org/pub/scm/linux/kernel/git/jejb/scsi-misc-2.6: (55 commits)
[SCSI] tcm_loop: Add multi-fabric Linux/SCSI LLD fabric module
[SCSI] qla4xxx: Use polling mode for disable interrupt mailbox completion
[SCSI] Revert "[SCSI] Retrieve the Caching mode page"
[SCSI] bnx2fc: IO completion not processed due to missed wakeup
[SCSI] qla4xxx: Update driver version to 5.02.00-k6
[SCSI] qla4xxx: masking required bits of add_fw_options during initialization
[SCSI] qla4xxx: added new function qla4xxx_relogin_all_devices
[SCSI] qla4xxx: add support for ql4xsess_recovery_tmo cmd line param
[SCSI] qla4xxx: Add support for ql4xmaxqdepth command line parameter
[SCSI] qla4xxx: cleanup function qla4xxx_process_ddb_changed
[SCSI] qla4xxx: Prevent other port reinitialization during remove_adapter
[SCSI] qla4xxx: remove unused ddb flag DF_NO_RELOGIN
[SCSI] qla4xxx: cleanup DDB relogin logic during initialization
[SCSI] qla4xxx: Do not retry ISP82XX initialization if H/W state is failed
[SCSI] qla4xxx: Do not send mbox command if FW is in failed state
[SCSI] qla4xxx: cleanup qla4xxx_initialize_ddb_list()
[SCSI] ses: add subenclosure support
[SCSI] bnx2fc: Bump version to 1.0.1
[SCSI] bnx2fc: Remove unnecessary module state checks
[SCSI] bnx2fc: Fix MTU issue by using static MTU
...
Diffstat (limited to 'drivers/scsi/sd.c')
-rw-r--r-- | drivers/scsi/sd.c | 63 |
1 files changed, 16 insertions, 47 deletions
diff --git a/drivers/scsi/sd.c b/drivers/scsi/sd.c index 7ff61d76b4c5..b61ebec6bca7 100644 --- a/drivers/scsi/sd.c +++ b/drivers/scsi/sd.c | |||
@@ -2027,14 +2027,10 @@ sd_read_cache_type(struct scsi_disk *sdkp, unsigned char *buffer) | |||
2027 | int old_rcd = sdkp->RCD; | 2027 | int old_rcd = sdkp->RCD; |
2028 | int old_dpofua = sdkp->DPOFUA; | 2028 | int old_dpofua = sdkp->DPOFUA; |
2029 | 2029 | ||
2030 | if (sdp->skip_ms_page_8) { | 2030 | if (sdp->skip_ms_page_8) |
2031 | if (sdp->type == TYPE_RBC) | 2031 | goto defaults; |
2032 | goto defaults; | 2032 | |
2033 | else { | 2033 | if (sdp->type == TYPE_RBC) { |
2034 | modepage = 0x3F; | ||
2035 | dbd = 0; | ||
2036 | } | ||
2037 | } else if (sdp->type == TYPE_RBC) { | ||
2038 | modepage = 6; | 2034 | modepage = 6; |
2039 | dbd = 8; | 2035 | dbd = 8; |
2040 | } else { | 2036 | } else { |
@@ -2062,11 +2058,13 @@ sd_read_cache_type(struct scsi_disk *sdkp, unsigned char *buffer) | |||
2062 | */ | 2058 | */ |
2063 | if (len < 3) | 2059 | if (len < 3) |
2064 | goto bad_sense; | 2060 | goto bad_sense; |
2065 | else if (len > SD_BUF_SIZE) { | 2061 | if (len > 20) |
2066 | sd_printk(KERN_NOTICE, sdkp, "Truncating mode parameter " | 2062 | len = 20; |
2067 | "data from %d to %d bytes\n", len, SD_BUF_SIZE); | 2063 | |
2068 | len = SD_BUF_SIZE; | 2064 | /* Take headers and block descriptors into account */ |
2069 | } | 2065 | len += data.header_length + data.block_descriptor_length; |
2066 | if (len > SD_BUF_SIZE) | ||
2067 | goto bad_sense; | ||
2070 | 2068 | ||
2071 | /* Get the data */ | 2069 | /* Get the data */ |
2072 | res = sd_do_mode_sense(sdp, dbd, modepage, buffer, len, &data, &sshdr); | 2070 | res = sd_do_mode_sense(sdp, dbd, modepage, buffer, len, &data, &sshdr); |
@@ -2074,45 +2072,16 @@ sd_read_cache_type(struct scsi_disk *sdkp, unsigned char *buffer) | |||
2074 | if (scsi_status_is_good(res)) { | 2072 | if (scsi_status_is_good(res)) { |
2075 | int offset = data.header_length + data.block_descriptor_length; | 2073 | int offset = data.header_length + data.block_descriptor_length; |
2076 | 2074 | ||
2077 | while (offset < len) { | 2075 | if (offset >= SD_BUF_SIZE - 2) { |
2078 | u8 page_code = buffer[offset] & 0x3F; | 2076 | sd_printk(KERN_ERR, sdkp, "Malformed MODE SENSE response\n"); |
2079 | u8 spf = buffer[offset] & 0x40; | 2077 | goto defaults; |
2080 | |||
2081 | if (page_code == 8 || page_code == 6) { | ||
2082 | /* We're interested only in the first 3 bytes. | ||
2083 | */ | ||
2084 | if (len - offset <= 2) { | ||
2085 | sd_printk(KERN_ERR, sdkp, "Incomplete " | ||
2086 | "mode parameter data\n"); | ||
2087 | goto defaults; | ||
2088 | } else { | ||
2089 | modepage = page_code; | ||
2090 | goto Page_found; | ||
2091 | } | ||
2092 | } else { | ||
2093 | /* Go to the next page */ | ||
2094 | if (spf && len - offset > 3) | ||
2095 | offset += 4 + (buffer[offset+2] << 8) + | ||
2096 | buffer[offset+3]; | ||
2097 | else if (!spf && len - offset > 1) | ||
2098 | offset += 2 + buffer[offset+1]; | ||
2099 | else { | ||
2100 | sd_printk(KERN_ERR, sdkp, "Incomplete " | ||
2101 | "mode parameter data\n"); | ||
2102 | goto defaults; | ||
2103 | } | ||
2104 | } | ||
2105 | } | 2078 | } |
2106 | 2079 | ||
2107 | if (modepage == 0x3F) { | 2080 | if ((buffer[offset] & 0x3f) != modepage) { |
2108 | sd_printk(KERN_ERR, sdkp, "No Caching mode page " | ||
2109 | "present\n"); | ||
2110 | goto defaults; | ||
2111 | } else if ((buffer[offset] & 0x3f) != modepage) { | ||
2112 | sd_printk(KERN_ERR, sdkp, "Got wrong page\n"); | 2081 | sd_printk(KERN_ERR, sdkp, "Got wrong page\n"); |
2113 | goto defaults; | 2082 | goto defaults; |
2114 | } | 2083 | } |
2115 | Page_found: | 2084 | |
2116 | if (modepage == 8) { | 2085 | if (modepage == 8) { |
2117 | sdkp->WCE = ((buffer[offset + 2] & 0x04) != 0); | 2086 | sdkp->WCE = ((buffer[offset + 2] & 0x04) != 0); |
2118 | sdkp->RCD = ((buffer[offset + 2] & 0x01) != 0); | 2087 | sdkp->RCD = ((buffer[offset + 2] & 0x01) != 0); |