diff options
author | Christoph Hellwig <hch@infradead.org> | 2012-05-20 11:59:15 -0400 |
---|---|---|
committer | Nicholas Bellinger <nab@linux-iscsi.org> | 2012-07-16 20:27:45 -0400 |
commit | 1fd032ee10d2816c947f5d5b9abda95e728f0a8f (patch) | |
tree | 2a76ad6b466160127dd41ba1d2f6fdb54f412bf2 /drivers/target/target_core_pscsi.c | |
parent | d6e0175cf3f9737a760482d185bb73566bcc9331 (diff) |
target: move code for CDB emulation
Move the existing code in target_core_cdb.c into the files for the command
sets that the emulations implement.
(roland + nab: Squash patch: Fix range calculation in WRITE SAME emulation
when num blocks == 0s)
Signed-off-by: Christoph Hellwig <hch@lst.de>
Signed-off-by: Nicholas Bellinger <nab@linux-iscsi.org>
Diffstat (limited to 'drivers/target/target_core_pscsi.c')
-rw-r--r-- | drivers/target/target_core_pscsi.c | 465 |
1 files changed, 24 insertions, 441 deletions
diff --git a/drivers/target/target_core_pscsi.c b/drivers/target/target_core_pscsi.c index 378da242d84..099c59d31b1 100644 --- a/drivers/target/target_core_pscsi.c +++ b/drivers/target/target_core_pscsi.c | |||
@@ -1022,470 +1022,53 @@ fail: | |||
1022 | return -ENOMEM; | 1022 | return -ENOMEM; |
1023 | } | 1023 | } |
1024 | 1024 | ||
1025 | static inline u32 pscsi_get_sectors_6( | 1025 | static int pscsi_parse_cdb(struct se_cmd *cmd) |
1026 | unsigned char *cdb, | ||
1027 | struct se_cmd *cmd, | ||
1028 | int *ret) | ||
1029 | { | 1026 | { |
1030 | struct se_device *dev = cmd->se_dev; | 1027 | unsigned char *cdb = cmd->t_task_cdb; |
1031 | 1028 | unsigned int dummy_size; | |
1032 | /* | 1029 | int ret; |
1033 | * Assume TYPE_DISK for non struct se_device objects. | ||
1034 | * Use 8-bit sector value. | ||
1035 | */ | ||
1036 | if (!dev) | ||
1037 | goto type_disk; | ||
1038 | |||
1039 | /* | ||
1040 | * Use 24-bit allocation length for TYPE_TAPE. | ||
1041 | */ | ||
1042 | if (dev->transport->get_device_type(dev) == TYPE_TAPE) | ||
1043 | return (u32)(cdb[2] << 16) + (cdb[3] << 8) + cdb[4]; | ||
1044 | |||
1045 | /* | ||
1046 | * Everything else assume TYPE_DISK Sector CDB location. | ||
1047 | * Use 8-bit sector value. SBC-3 says: | ||
1048 | * | ||
1049 | * A TRANSFER LENGTH field set to zero specifies that 256 | ||
1050 | * logical blocks shall be written. Any other value | ||
1051 | * specifies the number of logical blocks that shall be | ||
1052 | * written. | ||
1053 | */ | ||
1054 | type_disk: | ||
1055 | return cdb[4] ? : 256; | ||
1056 | } | ||
1057 | |||
1058 | static inline u32 pscsi_get_sectors_10( | ||
1059 | unsigned char *cdb, | ||
1060 | struct se_cmd *cmd, | ||
1061 | int *ret) | ||
1062 | { | ||
1063 | struct se_device *dev = cmd->se_dev; | ||
1064 | |||
1065 | /* | ||
1066 | * Assume TYPE_DISK for non struct se_device objects. | ||
1067 | * Use 16-bit sector value. | ||
1068 | */ | ||
1069 | if (!dev) | ||
1070 | goto type_disk; | ||
1071 | |||
1072 | /* | ||
1073 | * XXX_10 is not defined in SSC, throw an exception | ||
1074 | */ | ||
1075 | if (dev->transport->get_device_type(dev) == TYPE_TAPE) { | ||
1076 | *ret = -EINVAL; | ||
1077 | return 0; | ||
1078 | } | ||
1079 | |||
1080 | /* | ||
1081 | * Everything else assume TYPE_DISK Sector CDB location. | ||
1082 | * Use 16-bit sector value. | ||
1083 | */ | ||
1084 | type_disk: | ||
1085 | return (u32)(cdb[7] << 8) + cdb[8]; | ||
1086 | } | ||
1087 | |||
1088 | static inline u32 pscsi_get_sectors_12( | ||
1089 | unsigned char *cdb, | ||
1090 | struct se_cmd *cmd, | ||
1091 | int *ret) | ||
1092 | { | ||
1093 | struct se_device *dev = cmd->se_dev; | ||
1094 | |||
1095 | /* | ||
1096 | * Assume TYPE_DISK for non struct se_device objects. | ||
1097 | * Use 32-bit sector value. | ||
1098 | */ | ||
1099 | if (!dev) | ||
1100 | goto type_disk; | ||
1101 | 1030 | ||
1102 | /* | 1031 | if (cmd->se_cmd_flags & SCF_BIDI) { |
1103 | * XXX_12 is not defined in SSC, throw an exception | 1032 | cmd->se_cmd_flags |= SCF_SCSI_CDB_EXCEPTION; |
1104 | */ | 1033 | cmd->scsi_sense_reason = TCM_UNSUPPORTED_SCSI_OPCODE; |
1105 | if (dev->transport->get_device_type(dev) == TYPE_TAPE) { | 1034 | return -EINVAL; |
1106 | *ret = -EINVAL; | ||
1107 | return 0; | ||
1108 | } | 1035 | } |
1109 | 1036 | ||
1110 | /* | 1037 | /* |
1111 | * Everything else assume TYPE_DISK Sector CDB location. | 1038 | * For REPORT LUNS we always need to emulate the respone, and for everything |
1112 | * Use 32-bit sector value. | 1039 | * related to persistent reservations and ALUA we might optionally use our |
1040 | * handlers before passing on the command to the physical hardware. | ||
1113 | */ | 1041 | */ |
1114 | type_disk: | ||
1115 | return (u32)(cdb[6] << 24) + (cdb[7] << 16) + (cdb[8] << 8) + cdb[9]; | ||
1116 | } | ||
1117 | |||
1118 | static inline u32 pscsi_get_sectors_16( | ||
1119 | unsigned char *cdb, | ||
1120 | struct se_cmd *cmd, | ||
1121 | int *ret) | ||
1122 | { | ||
1123 | struct se_device *dev = cmd->se_dev; | ||
1124 | |||
1125 | /* | ||
1126 | * Assume TYPE_DISK for non struct se_device objects. | ||
1127 | * Use 32-bit sector value. | ||
1128 | */ | ||
1129 | if (!dev) | ||
1130 | goto type_disk; | ||
1131 | |||
1132 | /* | ||
1133 | * Use 24-bit allocation length for TYPE_TAPE. | ||
1134 | */ | ||
1135 | if (dev->transport->get_device_type(dev) == TYPE_TAPE) | ||
1136 | return (u32)(cdb[12] << 16) + (cdb[13] << 8) + cdb[14]; | ||
1137 | |||
1138 | type_disk: | ||
1139 | return (u32)(cdb[10] << 24) + (cdb[11] << 16) + | ||
1140 | (cdb[12] << 8) + cdb[13]; | ||
1141 | } | ||
1142 | |||
1143 | /* | ||
1144 | * Used for VARIABLE_LENGTH_CDB WRITE_32 and READ_32 variants | ||
1145 | */ | ||
1146 | static inline u32 pscsi_get_sectors_32( | ||
1147 | unsigned char *cdb, | ||
1148 | struct se_cmd *cmd, | ||
1149 | int *ret) | ||
1150 | { | ||
1151 | /* | ||
1152 | * Assume TYPE_DISK for non struct se_device objects. | ||
1153 | * Use 32-bit sector value. | ||
1154 | */ | ||
1155 | return (u32)(cdb[28] << 24) + (cdb[29] << 16) + | ||
1156 | (cdb[30] << 8) + cdb[31]; | ||
1157 | |||
1158 | } | ||
1159 | |||
1160 | static inline u32 pscsi_get_lba_21(unsigned char *cdb) | ||
1161 | { | ||
1162 | return ((cdb[1] & 0x1f) << 16) | (cdb[2] << 8) | cdb[3]; | ||
1163 | } | ||
1164 | |||
1165 | static inline u32 pscsi_get_lba_32(unsigned char *cdb) | ||
1166 | { | ||
1167 | return (cdb[2] << 24) | (cdb[3] << 16) | (cdb[4] << 8) | cdb[5]; | ||
1168 | } | ||
1169 | |||
1170 | static inline unsigned long long pscsi_get_lba_64(unsigned char *cdb) | ||
1171 | { | ||
1172 | unsigned int __v1, __v2; | ||
1173 | |||
1174 | __v1 = (cdb[2] << 24) | (cdb[3] << 16) | (cdb[4] << 8) | cdb[5]; | ||
1175 | __v2 = (cdb[6] << 24) | (cdb[7] << 16) | (cdb[8] << 8) | cdb[9]; | ||
1176 | |||
1177 | return ((unsigned long long)__v2) | (unsigned long long)__v1 << 32; | ||
1178 | } | ||
1179 | |||
1180 | /* | ||
1181 | * For VARIABLE_LENGTH_CDB w/ 32 byte extended CDBs | ||
1182 | */ | ||
1183 | static inline unsigned long long pscsi_get_lba_64_ext(unsigned char *cdb) | ||
1184 | { | ||
1185 | unsigned int __v1, __v2; | ||
1186 | |||
1187 | __v1 = (cdb[12] << 24) | (cdb[13] << 16) | (cdb[14] << 8) | cdb[15]; | ||
1188 | __v2 = (cdb[16] << 24) | (cdb[17] << 16) | (cdb[18] << 8) | cdb[19]; | ||
1189 | |||
1190 | return ((unsigned long long)__v2) | (unsigned long long)__v1 << 32; | ||
1191 | } | ||
1192 | |||
1193 | |||
1194 | static inline u32 pscsi_get_size( | ||
1195 | u32 sectors, | ||
1196 | unsigned char *cdb, | ||
1197 | struct se_cmd *cmd) | ||
1198 | { | ||
1199 | struct se_device *dev = cmd->se_dev; | ||
1200 | |||
1201 | if (dev->transport->get_device_type(dev) == TYPE_TAPE) { | ||
1202 | if (cdb[1] & 1) { /* sectors */ | ||
1203 | return dev->se_sub_dev->se_dev_attrib.block_size * sectors; | ||
1204 | } else /* bytes */ | ||
1205 | return sectors; | ||
1206 | } | ||
1207 | |||
1208 | pr_debug("Returning block_size: %u, sectors: %u == %u for" | ||
1209 | " %s object\n", dev->se_sub_dev->se_dev_attrib.block_size, | ||
1210 | sectors, dev->se_sub_dev->se_dev_attrib.block_size * sectors, | ||
1211 | dev->transport->name); | ||
1212 | |||
1213 | return dev->se_sub_dev->se_dev_attrib.block_size * sectors; | ||
1214 | } | ||
1215 | |||
1216 | static int pscsi_parse_cdb(struct se_cmd *cmd, unsigned int *size) | ||
1217 | { | ||
1218 | struct se_device *dev = cmd->se_dev; | ||
1219 | struct se_subsystem_dev *su_dev = dev->se_sub_dev; | ||
1220 | unsigned char *cdb = cmd->t_task_cdb; | ||
1221 | int sector_ret = 0; | ||
1222 | u32 sectors = 0; | ||
1223 | u16 service_action; | ||
1224 | int ret; | ||
1225 | |||
1226 | if (cmd->se_cmd_flags & SCF_BIDI) | ||
1227 | goto out_unsupported_cdb; | ||
1228 | |||
1229 | switch (cdb[0]) { | 1042 | switch (cdb[0]) { |
1230 | case READ_6: | 1043 | case REPORT_LUNS: |
1231 | sectors = pscsi_get_sectors_6(cdb, cmd, §or_ret); | 1044 | case PERSISTENT_RESERVE_IN: |
1232 | if (sector_ret) | 1045 | case PERSISTENT_RESERVE_OUT: |
1233 | goto out_unsupported_cdb; | 1046 | case RELEASE: |
1234 | *size = pscsi_get_size(sectors, cdb, cmd); | 1047 | case RELEASE_10: |
1235 | cmd->t_task_lba = pscsi_get_lba_21(cdb); | 1048 | case RESERVE: |
1236 | cmd->se_cmd_flags |= SCF_SCSI_DATA_CDB; | 1049 | case RESERVE_10: |
1050 | ret = spc_parse_cdb(cmd, &dummy_size); | ||
1051 | if (ret) | ||
1052 | return ret; | ||
1237 | break; | 1053 | break; |
1054 | case READ_6: | ||
1238 | case READ_10: | 1055 | case READ_10: |
1239 | sectors = pscsi_get_sectors_10(cdb, cmd, §or_ret); | ||
1240 | if (sector_ret) | ||
1241 | goto out_unsupported_cdb; | ||
1242 | *size = pscsi_get_size(sectors, cdb, cmd); | ||
1243 | cmd->t_task_lba = pscsi_get_lba_32(cdb); | ||
1244 | cmd->se_cmd_flags |= SCF_SCSI_DATA_CDB; | ||
1245 | break; | ||
1246 | case READ_12: | 1056 | case READ_12: |
1247 | sectors = pscsi_get_sectors_12(cdb, cmd, §or_ret); | ||
1248 | if (sector_ret) | ||
1249 | goto out_unsupported_cdb; | ||
1250 | *size = pscsi_get_size(sectors, cdb, cmd); | ||
1251 | cmd->t_task_lba = pscsi_get_lba_32(cdb); | ||
1252 | cmd->se_cmd_flags |= SCF_SCSI_DATA_CDB; | ||
1253 | break; | ||
1254 | case READ_16: | 1057 | case READ_16: |
1255 | sectors = pscsi_get_sectors_16(cdb, cmd, §or_ret); | ||
1256 | if (sector_ret) | ||
1257 | goto out_unsupported_cdb; | ||
1258 | *size = pscsi_get_size(sectors, cdb, cmd); | ||
1259 | cmd->t_task_lba = pscsi_get_lba_64(cdb); | ||
1260 | cmd->se_cmd_flags |= SCF_SCSI_DATA_CDB; | ||
1261 | break; | ||
1262 | case WRITE_6: | 1058 | case WRITE_6: |
1263 | sectors = pscsi_get_sectors_6(cdb, cmd, §or_ret); | ||
1264 | if (sector_ret) | ||
1265 | goto out_unsupported_cdb; | ||
1266 | *size = pscsi_get_size(sectors, cdb, cmd); | ||
1267 | cmd->t_task_lba = pscsi_get_lba_21(cdb); | ||
1268 | cmd->se_cmd_flags |= SCF_SCSI_DATA_CDB; | ||
1269 | break; | ||
1270 | case WRITE_10: | 1059 | case WRITE_10: |
1271 | case WRITE_VERIFY: | ||
1272 | sectors = pscsi_get_sectors_10(cdb, cmd, §or_ret); | ||
1273 | if (sector_ret) | ||
1274 | goto out_unsupported_cdb; | ||
1275 | *size = pscsi_get_size(sectors, cdb, cmd); | ||
1276 | cmd->t_task_lba = pscsi_get_lba_32(cdb); | ||
1277 | if (cdb[1] & 0x8) | ||
1278 | cmd->se_cmd_flags |= SCF_FUA; | ||
1279 | cmd->se_cmd_flags |= SCF_SCSI_DATA_CDB; | ||
1280 | break; | ||
1281 | case WRITE_12: | 1060 | case WRITE_12: |
1282 | sectors = pscsi_get_sectors_12(cdb, cmd, §or_ret); | ||
1283 | if (sector_ret) | ||
1284 | goto out_unsupported_cdb; | ||
1285 | *size = pscsi_get_size(sectors, cdb, cmd); | ||
1286 | cmd->t_task_lba = pscsi_get_lba_32(cdb); | ||
1287 | if (cdb[1] & 0x8) | ||
1288 | cmd->se_cmd_flags |= SCF_FUA; | ||
1289 | cmd->se_cmd_flags |= SCF_SCSI_DATA_CDB; | ||
1290 | break; | ||
1291 | case WRITE_16: | 1061 | case WRITE_16: |
1292 | sectors = pscsi_get_sectors_16(cdb, cmd, §or_ret); | 1062 | case WRITE_VERIFY: |
1293 | if (sector_ret) | ||
1294 | goto out_unsupported_cdb; | ||
1295 | *size = pscsi_get_size(sectors, cdb, cmd); | ||
1296 | cmd->t_task_lba = pscsi_get_lba_64(cdb); | ||
1297 | if (cdb[1] & 0x8) | ||
1298 | cmd->se_cmd_flags |= SCF_FUA; | ||
1299 | cmd->se_cmd_flags |= SCF_SCSI_DATA_CDB; | 1063 | cmd->se_cmd_flags |= SCF_SCSI_DATA_CDB; |
1300 | break; | 1064 | break; |
1301 | case VARIABLE_LENGTH_CMD: | ||
1302 | service_action = get_unaligned_be16(&cdb[8]); | ||
1303 | switch (service_action) { | ||
1304 | case WRITE_SAME_32: | ||
1305 | sectors = pscsi_get_sectors_32(cdb, cmd, §or_ret); | ||
1306 | if (sector_ret) | ||
1307 | goto out_unsupported_cdb; | ||
1308 | |||
1309 | if (!sectors) { | ||
1310 | pr_err("WSNZ=1, WRITE_SAME w/sectors=0 not" | ||
1311 | " supported\n"); | ||
1312 | goto out_invalid_cdb_field; | ||
1313 | } | ||
1314 | |||
1315 | *size = pscsi_get_size(1, cdb, cmd); | ||
1316 | cmd->t_task_lba = get_unaligned_be64(&cdb[12]); | ||
1317 | break; | ||
1318 | default: | ||
1319 | pr_err("VARIABLE_LENGTH_CMD service action" | ||
1320 | " 0x%04x not supported\n", service_action); | ||
1321 | goto out_unsupported_cdb; | ||
1322 | } | ||
1323 | break; | ||
1324 | case GPCMD_READ_BUFFER_CAPACITY: | ||
1325 | case GPCMD_SEND_OPC: | ||
1326 | *size = (cdb[7] << 8) + cdb[8]; | ||
1327 | break; | ||
1328 | case READ_BLOCK_LIMITS: | ||
1329 | *size = READ_BLOCK_LEN; | ||
1330 | break; | ||
1331 | case GPCMD_GET_CONFIGURATION: | ||
1332 | case GPCMD_READ_FORMAT_CAPACITIES: | ||
1333 | case GPCMD_READ_DISC_INFO: | ||
1334 | case GPCMD_READ_TRACK_RZONE_INFO: | ||
1335 | *size = (cdb[7] << 8) + cdb[8]; | ||
1336 | break; | ||
1337 | case GPCMD_MECHANISM_STATUS: | ||
1338 | case GPCMD_READ_DVD_STRUCTURE: | ||
1339 | *size = (cdb[8] << 8) + cdb[9]; | ||
1340 | break; | ||
1341 | case READ_POSITION: | ||
1342 | *size = READ_POSITION_LEN; | ||
1343 | break; | ||
1344 | case READ_BUFFER: | ||
1345 | *size = (cdb[6] << 16) + (cdb[7] << 8) + cdb[8]; | ||
1346 | break; | ||
1347 | case READ_CAPACITY: | ||
1348 | *size = READ_CAP_LEN; | ||
1349 | break; | ||
1350 | case READ_MEDIA_SERIAL_NUMBER: | ||
1351 | case SERVICE_ACTION_IN: | ||
1352 | case ACCESS_CONTROL_IN: | ||
1353 | case ACCESS_CONTROL_OUT: | ||
1354 | *size = (cdb[10] << 24) | (cdb[11] << 16) | | ||
1355 | (cdb[12] << 8) | cdb[13]; | ||
1356 | break; | ||
1357 | case READ_TOC: | ||
1358 | *size = cdb[8]; | ||
1359 | break; | ||
1360 | case READ_ELEMENT_STATUS: | ||
1361 | *size = 65536 * cdb[7] + 256 * cdb[8] + cdb[9]; | ||
1362 | break; | ||
1363 | case SYNCHRONIZE_CACHE: | ||
1364 | case SYNCHRONIZE_CACHE_16: | ||
1365 | /* | ||
1366 | * Extract LBA and range to be flushed for emulated SYNCHRONIZE_CACHE | ||
1367 | */ | ||
1368 | if (cdb[0] == SYNCHRONIZE_CACHE) { | ||
1369 | sectors = pscsi_get_sectors_10(cdb, cmd, §or_ret); | ||
1370 | cmd->t_task_lba = pscsi_get_lba_32(cdb); | ||
1371 | } else { | ||
1372 | sectors = pscsi_get_sectors_16(cdb, cmd, §or_ret); | ||
1373 | cmd->t_task_lba = pscsi_get_lba_64(cdb); | ||
1374 | } | ||
1375 | if (sector_ret) | ||
1376 | goto out_unsupported_cdb; | ||
1377 | |||
1378 | *size = pscsi_get_size(sectors, cdb, cmd); | ||
1379 | break; | ||
1380 | case UNMAP: | ||
1381 | *size = get_unaligned_be16(&cdb[7]); | ||
1382 | break; | ||
1383 | case WRITE_SAME_16: | ||
1384 | sectors = pscsi_get_sectors_16(cdb, cmd, §or_ret); | ||
1385 | if (sector_ret) | ||
1386 | goto out_unsupported_cdb; | ||
1387 | |||
1388 | if (!sectors) { | ||
1389 | pr_err("WSNZ=1, WRITE_SAME w/sectors=0 not supported\n"); | ||
1390 | goto out_invalid_cdb_field; | ||
1391 | } | ||
1392 | |||
1393 | *size = pscsi_get_size(1, cdb, cmd); | ||
1394 | cmd->t_task_lba = get_unaligned_be64(&cdb[2]); | ||
1395 | break; | ||
1396 | case WRITE_SAME: | ||
1397 | sectors = pscsi_get_sectors_10(cdb, cmd, §or_ret); | ||
1398 | if (sector_ret) | ||
1399 | goto out_unsupported_cdb; | ||
1400 | |||
1401 | if (!sectors) { | ||
1402 | pr_err("WSNZ=1, WRITE_SAME w/sectors=0 not supported\n"); | ||
1403 | goto out_invalid_cdb_field; | ||
1404 | } | ||
1405 | |||
1406 | *size = pscsi_get_size(1, cdb, cmd); | ||
1407 | cmd->t_task_lba = get_unaligned_be32(&cdb[2]); | ||
1408 | break; | ||
1409 | case ALLOW_MEDIUM_REMOVAL: | ||
1410 | case ERASE: | ||
1411 | case REZERO_UNIT: | ||
1412 | case SEEK_10: | ||
1413 | case SPACE: | ||
1414 | case START_STOP: | ||
1415 | case VERIFY: | ||
1416 | case WRITE_FILEMARKS: | ||
1417 | case GPCMD_CLOSE_TRACK: | ||
1418 | case INITIALIZE_ELEMENT_STATUS: | ||
1419 | case GPCMD_LOAD_UNLOAD: | ||
1420 | case GPCMD_SET_SPEED: | ||
1421 | case MOVE_MEDIUM: | ||
1422 | *size = 0; | ||
1423 | break; | ||
1424 | case GET_EVENT_STATUS_NOTIFICATION: | ||
1425 | *size = (cdb[7] << 8) | cdb[8]; | ||
1426 | break; | ||
1427 | case ATA_16: | ||
1428 | switch (cdb[2] & 0x3) { /* T_LENGTH */ | ||
1429 | case 0x0: | ||
1430 | sectors = 0; | ||
1431 | break; | ||
1432 | case 0x1: | ||
1433 | sectors = (((cdb[1] & 0x1) ? cdb[3] : 0) << 8) | cdb[4]; | ||
1434 | break; | ||
1435 | case 0x2: | ||
1436 | sectors = (((cdb[1] & 0x1) ? cdb[5] : 0) << 8) | cdb[6]; | ||
1437 | break; | ||
1438 | case 0x3: | ||
1439 | pr_err("T_LENGTH=0x3 not supported for ATA_16\n"); | ||
1440 | goto out_invalid_cdb_field; | ||
1441 | } | ||
1442 | |||
1443 | /* BYTE_BLOCK */ | ||
1444 | if (cdb[2] & 0x4) { | ||
1445 | /* BLOCK T_TYPE: 512 or sector */ | ||
1446 | *size = sectors * ((cdb[2] & 0x10) ? | ||
1447 | dev->se_sub_dev->se_dev_attrib.block_size : 512); | ||
1448 | } else { | ||
1449 | /* BYTE */ | ||
1450 | *size = sectors; | ||
1451 | } | ||
1452 | break; | ||
1453 | default: | 1065 | default: |
1454 | ret = spc_parse_cdb(cmd, size, true); | 1066 | break; |
1455 | if (ret) | ||
1456 | return ret; | ||
1457 | } | ||
1458 | |||
1459 | if (cmd->se_cmd_flags & SCF_SCSI_DATA_CDB) { | ||
1460 | if (sectors > su_dev->se_dev_attrib.fabric_max_sectors) { | ||
1461 | printk_ratelimited(KERN_ERR "SCSI OP %02xh with too" | ||
1462 | " big sectors %u exceeds fabric_max_sectors:" | ||
1463 | " %u\n", cdb[0], sectors, | ||
1464 | su_dev->se_dev_attrib.fabric_max_sectors); | ||
1465 | goto out_invalid_cdb_field; | ||
1466 | } | ||
1467 | if (sectors > su_dev->se_dev_attrib.hw_max_sectors) { | ||
1468 | printk_ratelimited(KERN_ERR "SCSI OP %02xh with too" | ||
1469 | " big sectors %u exceeds backend hw_max_sectors:" | ||
1470 | " %u\n", cdb[0], sectors, | ||
1471 | su_dev->se_dev_attrib.hw_max_sectors); | ||
1472 | goto out_invalid_cdb_field; | ||
1473 | } | ||
1474 | } | 1067 | } |
1475 | 1068 | ||
1476 | return 0; | 1069 | return 0; |
1477 | |||
1478 | out_unsupported_cdb: | ||
1479 | cmd->se_cmd_flags |= SCF_SCSI_CDB_EXCEPTION; | ||
1480 | cmd->scsi_sense_reason = TCM_UNSUPPORTED_SCSI_OPCODE; | ||
1481 | return -EINVAL; | ||
1482 | out_invalid_cdb_field: | ||
1483 | cmd->se_cmd_flags |= SCF_SCSI_CDB_EXCEPTION; | ||
1484 | cmd->scsi_sense_reason = TCM_INVALID_CDB_FIELD; | ||
1485 | return -EINVAL; | ||
1486 | } | 1070 | } |
1487 | 1071 | ||
1488 | |||
1489 | static int pscsi_execute_cmd(struct se_cmd *cmd, struct scatterlist *sgl, | 1072 | static int pscsi_execute_cmd(struct se_cmd *cmd, struct scatterlist *sgl, |
1490 | u32 sgl_nents, enum dma_data_direction data_direction) | 1073 | u32 sgl_nents, enum dma_data_direction data_direction) |
1491 | { | 1074 | { |