Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

iSCSI.iSCSIResiduals.WriteVerify10Residuals test #370

Open
Ser01x opened this issue Mar 1, 2022 · 1 comment
Open

iSCSI.iSCSIResiduals.WriteVerify10Residuals test #370

Ser01x opened this issue Mar 1, 2022 · 1 comment

Comments

@Ser01x
Copy link
Contributor

Ser01x commented Mar 1, 2022

I look into iSCSI.iSCSIResiduals.WriteVerify10Residuals test with Linux TCM target. And there is we have the following errors:

    1. test_writeverify10_residuals.c:134  - CU_ASSERT_EQUAL(task->status,SCSI_STATUS_GOOD)
    2. test_writeverify10_residuals.c:227  - CU_ASSERT_EQUAL(task->status,SCSI_STATUS_GOOD)
    3. test_writeverify10_residuals.c:281  - CU_ASSERT_EQUAL(task->status,SCSI_STATUS_GOOD)
    4. test_writeverify10_residuals.c:308  - CU_FAIL("Block was not written correctly")
    5. test_writeverify10_residuals.c:354  - CU_ASSERT_EQUAL(task->status,SCSI_STATUS_GOOD)
    6. test_writeverify10_residuals.c:381  - CU_FAIL("Block was not written correctly")    Send PRIN/READ_KEYS

Why do we expect to receive the SCSI_STATUS_GOOD status for WriteVerify request if the iSCSI(PDU)->ExpectedDataTransferLength != CDB->TransferLength?

I have explored iSCSI RFC (RFC 3720, section 10.3) and SAM3 (4.6 The service delivery subsystem), but did not find the exact answer to what to do in this case (iSCSI(PDU)->ExpectedDataTransferLength != CDB->TransferLength). The Linux rejects such requests: https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/tree/drivers/target/target_core_transport.c?h=v5.16.11#n1389

Is it correct to check the answer in the WriteVerify test like here: https://github.com/sahlberg/libiscsi/blob/master/test-tool/test_writeverify10_residuals.c#L173 ?

ok = task->status == SCSI_STATUS_GOOD ||
        (task->status == SCSI_STATUS_CHECK_CONDITION &&
         task->sense.key == SCSI_SENSE_ILLEGAL_REQUEST &&
         task->sense.ascq == SCSI_SENSE_ASCQ_INVALID_FIELD_IN_INFORMATION_UNIT);
CU_ASSERT(ok);
@bvanassche
Copy link
Collaborator

The Linux kernel SCSI target code (drivers/target/*) is not the best reference to look up information about how SCSI commands should behave. A better reference are the ANSI T10 standards in combination with the SCSI transport standards. The best description of the behavior in case the expected data transfer length (EDTL) does not match the data buffer length is the description from RFC 3720. From that RFC (section 11.4.5):

The Residual Count field MUST be valid in the case where either the U bit or the O bit is set. If neither bit is set, the Residual Count field MUST be ignored on reception and SHOULD be set to 0 when sending. Targets may set the residual count, and initiators may use it when the response code is Command Completed at Target (even if the status returned is not GOOD). If the O bit is set, the Residual Count indicates the number of bytes that were not transferred because the initiator's Expected Data Transfer Length was not sufficient. If the U bit is set, the Residual Count indicates the number of bytes that were not transferred out of the number of bytes expected to be transferred.

A slightly more clear description is available in the SRP specification:

A data-in under (DIUNDER) bit set to one, indicates that the DATA-IN RESIDUAL COUNT field is valid and contains the count of data bytes that were expected to be transferred to the data-in buffer that were not transferred. The application client should examine the DATA-IN RESIDUAL COUNT field in the context of the command to determine whether or not an error condition occurred.

A data-in over (DIOVER) bit set to one indicates that the DATA-IN RESIDUAL COUNT field is valid and contains the count of data bytes that were not able to be transferred to the data-in buffer as a result of the length of the data-in buffer not being sufficient. The application client should examine the DATA-IN RESIDUAL COUNT field in the context of the command to determine whether or not an error condition occurred.

A data-out under (DOUNDER) bit set to one indicates that the DATA-OUT RESIDUAL COUNT field is valid and contains the count of data bytes that were expected to be transferred from the data-out buffer that were not transferred. The application client should examine the DATA-OUT RESIDUAL COUNT field in the context of the command to determine whether or not an error condition occurred.

A data-out over (DOOVER) bit set to one indicates that the DATA-OUT RESIDUAL COUNT field is valid and contains the count of data bytes that were not able to be transferred from the data-out buffer as a result of the length of the data-out buffer not being sufficient. The application client should examine the DATA-OUT RESIDUAL COUNT
field in the context of the command to determine whether or not an error condition occurred.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants