Package org.jscsi.target.connection.stage.fullfeature

Source Code of org.jscsi.target.connection.stage.fullfeature.RequestSenseStage

package org.jscsi.target.connection.stage.fullfeature;


import java.io.IOException;
import java.security.DigestException;

import org.jscsi.exception.InternetSCSIException;
import org.jscsi.parser.BasicHeaderSegment;
import org.jscsi.parser.ProtocolDataUnit;
import org.jscsi.parser.scsi.SCSICommandParser;
import org.jscsi.parser.scsi.SCSIResponseParser;
import org.jscsi.parser.scsi.SCSIStatus;
import org.jscsi.target.connection.TargetPduFactory;
import org.jscsi.target.connection.phase.TargetFullFeaturePhase;
import org.jscsi.target.scsi.ScsiResponseDataSegment;
import org.jscsi.target.scsi.cdb.RequestSenseCdb;
import org.jscsi.target.scsi.sense.AdditionalSenseBytes;
import org.jscsi.target.scsi.sense.AdditionalSenseCodeAndQualifier;
import org.jscsi.target.scsi.sense.DescriptorFormatSenseData;
import org.jscsi.target.scsi.sense.ErrorType;
import org.jscsi.target.scsi.sense.FixedFormatSenseData;
import org.jscsi.target.scsi.sense.SenseData;
import org.jscsi.target.scsi.sense.SenseKey;
import org.jscsi.target.scsi.sense.information.FourByteInformation;
import org.jscsi.target.scsi.sense.senseDataDescriptor.SenseDataDescriptor;
import org.jscsi.target.scsi.sense.senseDataDescriptor.senseKeySpecific.FieldPointerSenseKeySpecificData;
import org.jscsi.target.settings.SettingsException;


/**
* A stage for processing <code>REQUEST SENSE</code> SCSI commands.
* <p>
* The <code>REQUEST SENSE</code> command requests that the device server transfer {@link SenseData} to the application
* client.
*
* @author Andreas Ergenzinger
*/
public class RequestSenseStage extends TargetFullFeatureStage {

    public RequestSenseStage (TargetFullFeaturePhase targetFullFeaturePhase) {
        super(targetFullFeaturePhase);
    }

    @Override
    public void execute (ProtocolDataUnit pdu) throws IOException , InterruptedException , InternetSCSIException , DigestException , SettingsException {

        final BasicHeaderSegment bhs = pdu.getBasicHeaderSegment();
        final SCSICommandParser parser = (SCSICommandParser) bhs.getParser();

        ProtocolDataUnit responsePDU = null;// the response PDU

        // get command details in CDB
        final RequestSenseCdb cdb = new RequestSenseCdb(parser.getCDB());
        final FieldPointerSenseKeySpecificData[] illegalFieldPointers = cdb.getIllegalFieldPointers();

        if (illegalFieldPointers != null) {
            // an illegal request has been made

            SenseData senseData;

            if (cdb.getDescriptorFormat()) {
                // descriptor format sense data has been requested

                senseData = new DescriptorFormatSenseData(ErrorType.CURRENT,// errorType
                SenseKey.ILLEGAL_REQUEST,// sense key
                AdditionalSenseCodeAndQualifier.INVALID_FIELD_IN_CDB,// additional
                                                                     // sense
                                                                     // code
                                                                     // and
                                                                     // qualifier
                new SenseDataDescriptor[0]);// sense data descriptors

            } else {
                // fixed format sense data has been requested

                senseData = new FixedFormatSenseData(false,// valid
                ErrorType.CURRENT,// error type
                false,// file mark
                false,// end of medium
                false,// incorrect length indicator
                SenseKey.ILLEGAL_REQUEST,// sense key
                new FourByteInformation(),// information
                new FourByteInformation(),// command specific
                                          // information
                AdditionalSenseCodeAndQualifier.INVALID_FIELD_IN_CDB,// additional
                                                                     // sense
                                                                     // code
                                                                     // and
                                                                     // qualifier
                (byte) 0,// field replaceable unit code
                illegalFieldPointers[0],// sense key specific data, only
                                        // report first problem
                new AdditionalSenseBytes());// additional sense bytes
            }

            responsePDU = TargetPduFactory.createSCSIResponsePdu(false,// bidirectionalReadResidualOverflow
                    false,// bidirectionalReadResidualUnderflow
                    false,// residualOverflow
                    false,// residualUnderflow,
                    SCSIResponseParser.ServiceResponse.TARGET_FAILURE,// response,
                    SCSIStatus.CHECK_CONDITION,// status,
                    bhs.getInitiatorTaskTag(),// initiatorTaskTag,
                    0,// snackTag
                    0,// expectedDataSequenceNumber
                    0,// bidirectionalReadResidualCount
                    0,// residualCount
                    new ScsiResponseDataSegment(senseData, parser.getExpectedDataTransferLength()));// data
                                                                                                    // segment

        } else {
            /*
             * PDU is okay carry out command Sense data shall be available and cleared under the conditions defined in
             * SAM-3. If the device server has no other sense data available to return, it shall return the sense key
             * set to NO SENSE and the additional sense code set to NO ADDITIONAL SENSE INFORMATION. This will always be
             * the case with the jSCSI Target.
             */

            SenseData senseData;

            final SenseKey senseKey = SenseKey.NO_SENSE;
            final AdditionalSenseCodeAndQualifier additionalSense = AdditionalSenseCodeAndQualifier.NO_ADDITIONAL_SENSE_INFORMATION;

            if (cdb.getDescriptorFormat()) {
                // descriptor format sense data has been requested

                senseData = new DescriptorFormatSenseData(ErrorType.CURRENT,// errorType
                senseKey,// sense key
                additionalSense,// additional sense code and qualifier
                new SenseDataDescriptor[0]);// sense data descriptors

            } else {
                // fixed format sense data has been requested

                senseData = new FixedFormatSenseData(false,// valid
                ErrorType.CURRENT,// error type
                false,// file mark
                false,// end of medium
                false,// incorrect length indicator
                senseKey,// sense key
                new FourByteInformation(),// information
                new FourByteInformation(),// command specific
                                          // information
                additionalSense,// additional sense code and qualifier
                (byte) 0,// field replaceable unit code
                null,// sense key specific data, only report first
                     // problem
                null);// additional sense bytes
            }

            responsePDU = TargetPduFactory.createSCSIResponsePdu(false,// bidirectionalReadResidualOverflow
                    false,// bidirectionalReadResidualUnderflow
                    false,// residualOverflow
                    false,// residualUnderflow,
                    SCSIResponseParser.ServiceResponse.COMMAND_COMPLETED_AT_TARGET,// response,
                    SCSIStatus.GOOD,// status,
                    bhs.getInitiatorTaskTag(),// initiatorTaskTag,
                    0,// snackTag
                    0,// expectedDataSequenceNumber
                    0,// bidirectionalReadResidualCount
                    0,// residualCount
                    new ScsiResponseDataSegment(senseData, parser.getExpectedDataTransferLength()));// data
                                                                                                    // segment
        }

        // send response
        connection.sendPdu(responsePDU);
    }

}
TOP

Related Classes of org.jscsi.target.connection.stage.fullfeature.RequestSenseStage

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.