Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit ba159914 authored by Nicholas Bellinger's avatar Nicholas Bellinger
Browse files

iscsi-target: Fix iscsit_add_reject* usage for iser



This patch changes iscsit_add_reject() + iscsit_add_reject_from_cmd()
usage to not sleep on iscsi_cmd->reject_comp to address a free-after-use
usage bug in v3.10 with iser-target code.

It saves ->reject_reason for use within iscsit_build_reject() so the
correct value for both transport cases.  It also drops the legacy
fail_conn parameter usage throughput iscsi-target code and adds
two iscsit_add_reject_cmd() and iscsit_reject_cmd helper functions,
along with various small cleanups.

(v2: Re-enable target_put_sess_cmd() to be called from
     iscsit_add_reject_from_cmd() for rejects invoked after
     target_get_sess_cmd() has been called)

Cc: Or Gerlitz <ogerlitz@mellanox.com>
Cc: Mike Christie <michaelc@cs.wisc.edu>
Cc: stable@vger.kernel.org  # 3.10+
Signed-off-by: default avatarNicholas Bellinger <nab@linux-iscsi.org>
parent 3df8f68a
Loading
Loading
Loading
Loading
+0 −5
Original line number Diff line number Diff line
@@ -939,11 +939,6 @@ isert_handle_scsi_cmd(struct isert_conn *isert_conn,
	if (!rc && dump_payload == false && unsol_data)
		iscsit_set_unsoliticed_dataout(cmd);

	if (rc == CMDSN_ERROR_CANNOT_RECOVER)
		return iscsit_add_reject_from_cmd(
			   ISCSI_REASON_PROTOCOL_ERROR,
			   1, 0, (unsigned char *)hdr, cmd);

	return 0;
}

+103 −152

File changed.

Preview size limit exceeded, changes collapsed.

+1 −1
Original line number Diff line number Diff line
@@ -15,7 +15,7 @@ extern struct iscsi_np *iscsit_add_np(struct __kernel_sockaddr_storage *,
extern int iscsit_reset_np_thread(struct iscsi_np *, struct iscsi_tpg_np *,
				struct iscsi_portal_group *);
extern int iscsit_del_np(struct iscsi_np *);
extern int iscsit_add_reject_from_cmd(u8, int, int, unsigned char *, struct iscsi_cmd *);
extern int iscsit_reject_cmd(struct iscsi_cmd *cmd, u8, unsigned char *);
extern void iscsit_set_unsoliticed_dataout(struct iscsi_cmd *);
extern int iscsit_logout_closesession(struct iscsi_cmd *, struct iscsi_conn *);
extern int iscsit_logout_closeconnection(struct iscsi_cmd *, struct iscsi_conn *);
+4 −4
Original line number Diff line number Diff line
@@ -132,9 +132,8 @@ enum cmd_flags_table {
	ICF_CONTIG_MEMORY			= 0x00000020,
	ICF_ATTACHED_TO_RQUEUE			= 0x00000040,
	ICF_OOO_CMDSN				= 0x00000080,
	ICF_REJECT_FAIL_CONN			= 0x00000100,
	IFC_SENDTARGETS_ALL			= 0x00000200,
	IFC_SENDTARGETS_SINGLE			= 0x00000400,
	IFC_SENDTARGETS_ALL			= 0x00000100,
	IFC_SENDTARGETS_SINGLE			= 0x00000200,
};

/* struct iscsi_cmd->i_state */
@@ -368,6 +367,8 @@ struct iscsi_cmd {
	u8			maxcmdsn_inc;
	/* Immediate Unsolicited Dataout */
	u8			unsolicited_data;
	/* Reject reason code */
	u8			reject_reason;
	/* CID contained in logout PDU when opcode == ISCSI_INIT_LOGOUT_CMND */
	u16			logout_cid;
	/* Command flags */
@@ -450,7 +451,6 @@ struct iscsi_cmd {
	struct list_head	datain_list;
	/* R2T List */
	struct list_head	cmd_r2t_list;
	struct completion	reject_comp;
	/* Timer for DataOUT */
	struct timer_list	dataout_timer;
	/* Iovecs for SCSI data payload RX/TX w/ kernel level sockets */
+3 −4
Original line number Diff line number Diff line
@@ -746,13 +746,12 @@ int iscsit_check_post_dataout(
		if (!conn->sess->sess_ops->ErrorRecoveryLevel) {
			pr_err("Unable to recover from DataOUT CRC"
				" failure while ERL=0, closing session.\n");
			iscsit_add_reject_from_cmd(ISCSI_REASON_DATA_DIGEST_ERROR,
					1, 0, buf, cmd);
			iscsit_reject_cmd(cmd, ISCSI_REASON_DATA_DIGEST_ERROR,
					  buf);
			return DATAOUT_CANNOT_RECOVER;
		}

		iscsit_add_reject_from_cmd(ISCSI_REASON_DATA_DIGEST_ERROR,
				0, 0, buf, cmd);
		iscsit_reject_cmd(cmd, ISCSI_REASON_DATA_DIGEST_ERROR, buf);
		return iscsit_dataout_post_crc_failed(cmd, buf);
	}
}
Loading