1// SPDX-License-Identifier: GPL-2.0-or-later
2/*******************************************************************************
3 * This file contains main functions related to iSCSI DataSequenceInOrder=No
4 * and DataPDUInOrder=No.
5 *
6 * (c) Copyright 2007-2013 Datera, Inc.
7 *
8 * Author: Nicholas A. Bellinger <nab@linux-iscsi.org>
9 *
10 ******************************************************************************/
11
12#include <linux/slab.h>
13#include <linux/random.h>
14
15#include <target/iscsi/iscsi_target_core.h>
16#include "iscsi_target_util.h"
17#include "iscsi_target_tpg.h"
18#include "iscsi_target_seq_pdu_list.h"
19
20#ifdef DEBUG
21static void iscsit_dump_seq_list(struct iscsit_cmd *cmd)
22{
23	int i;
24	struct iscsi_seq *seq;
25
26	pr_debug("Dumping Sequence List for ITT: 0x%08x:\n",
27			cmd->init_task_tag);
28
29	for (i = 0; i < cmd->seq_count; i++) {
30		seq = &cmd->seq_list[i];
31		pr_debug("i: %d, pdu_start: %d, pdu_count: %d,"
32			" offset: %d, xfer_len: %d, seq_send_order: %d,"
33			" seq_no: %d\n", i, seq->pdu_start, seq->pdu_count,
34			seq->offset, seq->xfer_len, seq->seq_send_order,
35			seq->seq_no);
36	}
37}
38
39static void iscsit_dump_pdu_list(struct iscsit_cmd *cmd)
40{
41	int i;
42	struct iscsi_pdu *pdu;
43
44	pr_debug("Dumping PDU List for ITT: 0x%08x:\n",
45			cmd->init_task_tag);
46
47	for (i = 0; i < cmd->pdu_count; i++) {
48		pdu = &cmd->pdu_list[i];
49		pr_debug("i: %d, offset: %d, length: %d,"
50			" pdu_send_order: %d, seq_no: %d\n", i, pdu->offset,
51			pdu->length, pdu->pdu_send_order, pdu->seq_no);
52	}
53}
54#else
55static void iscsit_dump_seq_list(struct iscsit_cmd *cmd) {}
56static void iscsit_dump_pdu_list(struct iscsit_cmd *cmd) {}
57#endif
58
59static void iscsit_ordered_seq_lists(
60	struct iscsit_cmd *cmd,
61	u8 type)
62{
63	u32 i, seq_count = 0;
64
65	for (i = 0; i < cmd->seq_count; i++) {
66		if (cmd->seq_list[i].type != SEQTYPE_NORMAL)
67			continue;
68		cmd->seq_list[i].seq_send_order = seq_count++;
69	}
70}
71
72static void iscsit_ordered_pdu_lists(
73	struct iscsit_cmd *cmd,
74	u8 type)
75{
76	u32 i, pdu_send_order = 0, seq_no = 0;
77
78	for (i = 0; i < cmd->pdu_count; i++) {
79redo:
80		if (cmd->pdu_list[i].seq_no == seq_no) {
81			cmd->pdu_list[i].pdu_send_order = pdu_send_order++;
82			continue;
83		}
84		seq_no++;
85		pdu_send_order = 0;
86		goto redo;
87	}
88}
89
90/*
91 *	Generate count random values into array.
92 *	Use 0x80000000 to mark generates valued in array[].
93 */
94static void iscsit_create_random_array(u32 *array, u32 count)
95{
96	int i, j, k;
97
98	if (count == 1) {
99		array[0] = 0;
100		return;
101	}
102
103	for (i = 0; i < count; i++) {
104redo:
105		get_random_bytes(&j, sizeof(u32));
106		j = (1 + (int) (9999 + 1) - j) % count;
107		for (k = 0; k < i + 1; k++) {
108			j |= 0x80000000;
109			if ((array[k] & 0x80000000) && (array[k] == j))
110				goto redo;
111		}
112		array[i] = j;
113	}
114
115	for (i = 0; i < count; i++)
116		array[i] &= ~0x80000000;
117}
118
119static int iscsit_randomize_pdu_lists(
120	struct iscsit_cmd *cmd,
121	u8 type)
122{
123	int i = 0;
124	u32 *array, pdu_count, seq_count = 0, seq_no = 0, seq_offset = 0;
125
126	for (pdu_count = 0; pdu_count < cmd->pdu_count; pdu_count++) {
127redo:
128		if (cmd->pdu_list[pdu_count].seq_no == seq_no) {
129			seq_count++;
130			continue;
131		}
132		array = kcalloc(seq_count, sizeof(u32), GFP_KERNEL);
133		if (!array) {
134			pr_err("Unable to allocate memory"
135				" for random array.\n");
136			return -ENOMEM;
137		}
138		iscsit_create_random_array(array, seq_count);
139
140		for (i = 0; i < seq_count; i++)
141			cmd->pdu_list[seq_offset+i].pdu_send_order = array[i];
142
143		kfree(array);
144
145		seq_offset += seq_count;
146		seq_count = 0;
147		seq_no++;
148		goto redo;
149	}
150
151	if (seq_count) {
152		array = kcalloc(seq_count, sizeof(u32), GFP_KERNEL);
153		if (!array) {
154			pr_err("Unable to allocate memory for"
155				" random array.\n");
156			return -ENOMEM;
157		}
158		iscsit_create_random_array(array, seq_count);
159
160		for (i = 0; i < seq_count; i++)
161			cmd->pdu_list[seq_offset+i].pdu_send_order = array[i];
162
163		kfree(array);
164	}
165
166	return 0;
167}
168
169static int iscsit_randomize_seq_lists(
170	struct iscsit_cmd *cmd,
171	u8 type)
172{
173	int i, j = 0;
174	u32 *array, seq_count = cmd->seq_count;
175
176	if ((type == PDULIST_IMMEDIATE) || (type == PDULIST_UNSOLICITED))
177		seq_count--;
178	else if (type == PDULIST_IMMEDIATE_AND_UNSOLICITED)
179		seq_count -= 2;
180
181	if (!seq_count)
182		return 0;
183
184	array = kcalloc(seq_count, sizeof(u32), GFP_KERNEL);
185	if (!array) {
186		pr_err("Unable to allocate memory for random array.\n");
187		return -ENOMEM;
188	}
189	iscsit_create_random_array(array, seq_count);
190
191	for (i = 0; i < cmd->seq_count; i++) {
192		if (cmd->seq_list[i].type != SEQTYPE_NORMAL)
193			continue;
194		cmd->seq_list[i].seq_send_order = array[j++];
195	}
196
197	kfree(array);
198	return 0;
199}
200
201static void iscsit_determine_counts_for_list(
202	struct iscsit_cmd *cmd,
203	struct iscsi_build_list *bl,
204	u32 *seq_count,
205	u32 *pdu_count)
206{
207	int check_immediate = 0;
208	u32 burstlength = 0, offset = 0;
209	u32 unsolicited_data_length = 0;
210	u32 mdsl;
211	struct iscsit_conn *conn = cmd->conn;
212
213	if (cmd->se_cmd.data_direction == DMA_TO_DEVICE)
214		mdsl = cmd->conn->conn_ops->MaxXmitDataSegmentLength;
215	else
216		mdsl = cmd->conn->conn_ops->MaxRecvDataSegmentLength;
217
218	if ((bl->type == PDULIST_IMMEDIATE) ||
219	    (bl->type == PDULIST_IMMEDIATE_AND_UNSOLICITED))
220		check_immediate = 1;
221
222	if ((bl->type == PDULIST_UNSOLICITED) ||
223	    (bl->type == PDULIST_IMMEDIATE_AND_UNSOLICITED))
224		unsolicited_data_length = min(cmd->se_cmd.data_length,
225			conn->sess->sess_ops->FirstBurstLength);
226
227	while (offset < cmd->se_cmd.data_length) {
228		*pdu_count += 1;
229
230		if (check_immediate) {
231			check_immediate = 0;
232			offset += bl->immediate_data_length;
233			*seq_count += 1;
234			if (unsolicited_data_length)
235				unsolicited_data_length -=
236					bl->immediate_data_length;
237			continue;
238		}
239		if (unsolicited_data_length > 0) {
240			if ((offset + mdsl) >= cmd->se_cmd.data_length) {
241				unsolicited_data_length -=
242					(cmd->se_cmd.data_length - offset);
243				offset += (cmd->se_cmd.data_length - offset);
244				continue;
245			}
246			if ((offset + mdsl)
247					>= conn->sess->sess_ops->FirstBurstLength) {
248				unsolicited_data_length -=
249					(conn->sess->sess_ops->FirstBurstLength -
250					offset);
251				offset += (conn->sess->sess_ops->FirstBurstLength -
252					offset);
253				burstlength = 0;
254				*seq_count += 1;
255				continue;
256			}
257
258			offset += mdsl;
259			unsolicited_data_length -= mdsl;
260			continue;
261		}
262		if ((offset + mdsl) >= cmd->se_cmd.data_length) {
263			offset += (cmd->se_cmd.data_length - offset);
264			continue;
265		}
266		if ((burstlength + mdsl) >=
267		     conn->sess->sess_ops->MaxBurstLength) {
268			offset += (conn->sess->sess_ops->MaxBurstLength -
269					burstlength);
270			burstlength = 0;
271			*seq_count += 1;
272			continue;
273		}
274
275		burstlength += mdsl;
276		offset += mdsl;
277	}
278}
279
280
281/*
282 *	Builds PDU and/or Sequence list, called while DataSequenceInOrder=No
283 *	or DataPDUInOrder=No.
284 */
285static int iscsit_do_build_pdu_and_seq_lists(
286	struct iscsit_cmd *cmd,
287	struct iscsi_build_list *bl)
288{
289	int check_immediate = 0, datapduinorder, datasequenceinorder;
290	u32 burstlength = 0, offset = 0, i = 0, mdsl;
291	u32 pdu_count = 0, seq_no = 0, unsolicited_data_length = 0;
292	struct iscsit_conn *conn = cmd->conn;
293	struct iscsi_pdu *pdu = cmd->pdu_list;
294	struct iscsi_seq *seq = cmd->seq_list;
295
296	if (cmd->se_cmd.data_direction == DMA_TO_DEVICE)
297		mdsl = cmd->conn->conn_ops->MaxXmitDataSegmentLength;
298	else
299		mdsl = cmd->conn->conn_ops->MaxRecvDataSegmentLength;
300
301	datapduinorder = conn->sess->sess_ops->DataPDUInOrder;
302	datasequenceinorder = conn->sess->sess_ops->DataSequenceInOrder;
303
304	if ((bl->type == PDULIST_IMMEDIATE) ||
305	    (bl->type == PDULIST_IMMEDIATE_AND_UNSOLICITED))
306		check_immediate = 1;
307
308	if ((bl->type == PDULIST_UNSOLICITED) ||
309	    (bl->type == PDULIST_IMMEDIATE_AND_UNSOLICITED))
310		unsolicited_data_length = min(cmd->se_cmd.data_length,
311			conn->sess->sess_ops->FirstBurstLength);
312
313	while (offset < cmd->se_cmd.data_length) {
314		pdu_count++;
315		if (!datapduinorder) {
316			pdu[i].offset = offset;
317			pdu[i].seq_no = seq_no;
318		}
319		if (!datasequenceinorder && (pdu_count == 1)) {
320			seq[seq_no].pdu_start = i;
321			seq[seq_no].seq_no = seq_no;
322			seq[seq_no].offset = offset;
323			seq[seq_no].orig_offset = offset;
324		}
325
326		if (check_immediate) {
327			check_immediate = 0;
328			if (!datapduinorder) {
329				pdu[i].type = PDUTYPE_IMMEDIATE;
330				pdu[i++].length = bl->immediate_data_length;
331			}
332			if (!datasequenceinorder) {
333				seq[seq_no].type = SEQTYPE_IMMEDIATE;
334				seq[seq_no].pdu_count = 1;
335				seq[seq_no].xfer_len =
336					bl->immediate_data_length;
337			}
338			offset += bl->immediate_data_length;
339			pdu_count = 0;
340			seq_no++;
341			if (unsolicited_data_length)
342				unsolicited_data_length -=
343					bl->immediate_data_length;
344			continue;
345		}
346		if (unsolicited_data_length > 0) {
347			if ((offset + mdsl) >= cmd->se_cmd.data_length) {
348				if (!datapduinorder) {
349					pdu[i].type = PDUTYPE_UNSOLICITED;
350					pdu[i].length =
351						(cmd->se_cmd.data_length - offset);
352				}
353				if (!datasequenceinorder) {
354					seq[seq_no].type = SEQTYPE_UNSOLICITED;
355					seq[seq_no].pdu_count = pdu_count;
356					seq[seq_no].xfer_len = (burstlength +
357						(cmd->se_cmd.data_length - offset));
358				}
359				unsolicited_data_length -=
360						(cmd->se_cmd.data_length - offset);
361				offset += (cmd->se_cmd.data_length - offset);
362				continue;
363			}
364			if ((offset + mdsl) >=
365					conn->sess->sess_ops->FirstBurstLength) {
366				if (!datapduinorder) {
367					pdu[i].type = PDUTYPE_UNSOLICITED;
368					pdu[i++].length =
369					   (conn->sess->sess_ops->FirstBurstLength -
370						offset);
371				}
372				if (!datasequenceinorder) {
373					seq[seq_no].type = SEQTYPE_UNSOLICITED;
374					seq[seq_no].pdu_count = pdu_count;
375					seq[seq_no].xfer_len = (burstlength +
376					   (conn->sess->sess_ops->FirstBurstLength -
377						offset));
378				}
379				unsolicited_data_length -=
380					(conn->sess->sess_ops->FirstBurstLength -
381						offset);
382				offset += (conn->sess->sess_ops->FirstBurstLength -
383						offset);
384				burstlength = 0;
385				pdu_count = 0;
386				seq_no++;
387				continue;
388			}
389
390			if (!datapduinorder) {
391				pdu[i].type = PDUTYPE_UNSOLICITED;
392				pdu[i++].length = mdsl;
393			}
394			burstlength += mdsl;
395			offset += mdsl;
396			unsolicited_data_length -= mdsl;
397			continue;
398		}
399		if ((offset + mdsl) >= cmd->se_cmd.data_length) {
400			if (!datapduinorder) {
401				pdu[i].type = PDUTYPE_NORMAL;
402				pdu[i].length = (cmd->se_cmd.data_length - offset);
403			}
404			if (!datasequenceinorder) {
405				seq[seq_no].type = SEQTYPE_NORMAL;
406				seq[seq_no].pdu_count = pdu_count;
407				seq[seq_no].xfer_len = (burstlength +
408					(cmd->se_cmd.data_length - offset));
409			}
410			offset += (cmd->se_cmd.data_length - offset);
411			continue;
412		}
413		if ((burstlength + mdsl) >=
414		     conn->sess->sess_ops->MaxBurstLength) {
415			if (!datapduinorder) {
416				pdu[i].type = PDUTYPE_NORMAL;
417				pdu[i++].length =
418					(conn->sess->sess_ops->MaxBurstLength -
419						burstlength);
420			}
421			if (!datasequenceinorder) {
422				seq[seq_no].type = SEQTYPE_NORMAL;
423				seq[seq_no].pdu_count = pdu_count;
424				seq[seq_no].xfer_len = (burstlength +
425					(conn->sess->sess_ops->MaxBurstLength -
426					burstlength));
427			}
428			offset += (conn->sess->sess_ops->MaxBurstLength -
429					burstlength);
430			burstlength = 0;
431			pdu_count = 0;
432			seq_no++;
433			continue;
434		}
435
436		if (!datapduinorder) {
437			pdu[i].type = PDUTYPE_NORMAL;
438			pdu[i++].length = mdsl;
439		}
440		burstlength += mdsl;
441		offset += mdsl;
442	}
443
444	if (!datasequenceinorder) {
445		if (bl->data_direction & ISCSI_PDU_WRITE) {
446			if (bl->randomize & RANDOM_R2T_OFFSETS) {
447				if (iscsit_randomize_seq_lists(cmd, bl->type)
448						< 0)
449					return -1;
450			} else
451				iscsit_ordered_seq_lists(cmd, bl->type);
452		} else if (bl->data_direction & ISCSI_PDU_READ) {
453			if (bl->randomize & RANDOM_DATAIN_SEQ_OFFSETS) {
454				if (iscsit_randomize_seq_lists(cmd, bl->type)
455						< 0)
456					return -1;
457			} else
458				iscsit_ordered_seq_lists(cmd, bl->type);
459		}
460
461		iscsit_dump_seq_list(cmd);
462	}
463	if (!datapduinorder) {
464		if (bl->data_direction & ISCSI_PDU_WRITE) {
465			if (bl->randomize & RANDOM_DATAOUT_PDU_OFFSETS) {
466				if (iscsit_randomize_pdu_lists(cmd, bl->type)
467						< 0)
468					return -1;
469			} else
470				iscsit_ordered_pdu_lists(cmd, bl->type);
471		} else if (bl->data_direction & ISCSI_PDU_READ) {
472			if (bl->randomize & RANDOM_DATAIN_PDU_OFFSETS) {
473				if (iscsit_randomize_pdu_lists(cmd, bl->type)
474						< 0)
475					return -1;
476			} else
477				iscsit_ordered_pdu_lists(cmd, bl->type);
478		}
479
480		iscsit_dump_pdu_list(cmd);
481	}
482
483	return 0;
484}
485
486int iscsit_build_pdu_and_seq_lists(
487	struct iscsit_cmd *cmd,
488	u32 immediate_data_length)
489{
490	struct iscsi_build_list bl;
491	u32 pdu_count = 0, seq_count = 1;
492	struct iscsit_conn *conn = cmd->conn;
493	struct iscsi_pdu *pdu = NULL;
494	struct iscsi_seq *seq = NULL;
495
496	struct iscsit_session *sess = conn->sess;
497	struct iscsi_node_attrib *na;
498
499	/*
500	 * Do nothing if no OOO shenanigans
501	 */
502	if (sess->sess_ops->DataSequenceInOrder &&
503	    sess->sess_ops->DataPDUInOrder)
504		return 0;
505
506	if (cmd->data_direction == DMA_NONE)
507		return 0;
508
509	na = iscsit_tpg_get_node_attrib(sess);
510	memset(&bl, 0, sizeof(struct iscsi_build_list));
511
512	if (cmd->data_direction == DMA_FROM_DEVICE) {
513		bl.data_direction = ISCSI_PDU_READ;
514		bl.type = PDULIST_NORMAL;
515		if (na->random_datain_pdu_offsets)
516			bl.randomize |= RANDOM_DATAIN_PDU_OFFSETS;
517		if (na->random_datain_seq_offsets)
518			bl.randomize |= RANDOM_DATAIN_SEQ_OFFSETS;
519	} else {
520		bl.data_direction = ISCSI_PDU_WRITE;
521		bl.immediate_data_length = immediate_data_length;
522		if (na->random_r2t_offsets)
523			bl.randomize |= RANDOM_R2T_OFFSETS;
524
525		if (!cmd->immediate_data && !cmd->unsolicited_data)
526			bl.type = PDULIST_NORMAL;
527		else if (cmd->immediate_data && !cmd->unsolicited_data)
528			bl.type = PDULIST_IMMEDIATE;
529		else if (!cmd->immediate_data && cmd->unsolicited_data)
530			bl.type = PDULIST_UNSOLICITED;
531		else if (cmd->immediate_data && cmd->unsolicited_data)
532			bl.type = PDULIST_IMMEDIATE_AND_UNSOLICITED;
533	}
534
535	iscsit_determine_counts_for_list(cmd, &bl, &seq_count, &pdu_count);
536
537	if (!conn->sess->sess_ops->DataSequenceInOrder) {
538		seq = kcalloc(seq_count, sizeof(struct iscsi_seq), GFP_ATOMIC);
539		if (!seq) {
540			pr_err("Unable to allocate struct iscsi_seq list\n");
541			return -ENOMEM;
542		}
543		cmd->seq_list = seq;
544		cmd->seq_count = seq_count;
545	}
546
547	if (!conn->sess->sess_ops->DataPDUInOrder) {
548		pdu = kcalloc(pdu_count, sizeof(struct iscsi_pdu), GFP_ATOMIC);
549		if (!pdu) {
550			pr_err("Unable to allocate struct iscsi_pdu list.\n");
551			kfree(seq);
552			return -ENOMEM;
553		}
554		cmd->pdu_list = pdu;
555		cmd->pdu_count = pdu_count;
556	}
557
558	return iscsit_do_build_pdu_and_seq_lists(cmd, &bl);
559}
560
561struct iscsi_pdu *iscsit_get_pdu_holder(
562	struct iscsit_cmd *cmd,
563	u32 offset,
564	u32 length)
565{
566	u32 i;
567	struct iscsi_pdu *pdu = NULL;
568
569	if (!cmd->pdu_list) {
570		pr_err("struct iscsit_cmd->pdu_list is NULL!\n");
571		return NULL;
572	}
573
574	pdu = &cmd->pdu_list[0];
575
576	for (i = 0; i < cmd->pdu_count; i++)
577		if ((pdu[i].offset == offset) && (pdu[i].length == length))
578			return &pdu[i];
579
580	pr_err("Unable to locate PDU holder for ITT: 0x%08x, Offset:"
581		" %u, Length: %u\n", cmd->init_task_tag, offset, length);
582	return NULL;
583}
584
585struct iscsi_pdu *iscsit_get_pdu_holder_for_seq(
586	struct iscsit_cmd *cmd,
587	struct iscsi_seq *seq)
588{
589	u32 i;
590	struct iscsit_conn *conn = cmd->conn;
591	struct iscsi_pdu *pdu = NULL;
592
593	if (!cmd->pdu_list) {
594		pr_err("struct iscsit_cmd->pdu_list is NULL!\n");
595		return NULL;
596	}
597
598	if (conn->sess->sess_ops->DataSequenceInOrder) {
599redo:
600		pdu = &cmd->pdu_list[cmd->pdu_start];
601
602		for (i = 0; pdu[i].seq_no != cmd->seq_no; i++) {
603			pr_debug("pdu[i].seq_no: %d, pdu[i].pdu"
604				"_send_order: %d, pdu[i].offset: %d,"
605				" pdu[i].length: %d\n", pdu[i].seq_no,
606				pdu[i].pdu_send_order, pdu[i].offset,
607				pdu[i].length);
608
609			if (pdu[i].pdu_send_order == cmd->pdu_send_order) {
610				cmd->pdu_send_order++;
611				return &pdu[i];
612			}
613		}
614
615		cmd->pdu_start += cmd->pdu_send_order;
616		cmd->pdu_send_order = 0;
617		cmd->seq_no++;
618
619		if (cmd->pdu_start < cmd->pdu_count)
620			goto redo;
621
622		pr_err("Command ITT: 0x%08x unable to locate"
623			" struct iscsi_pdu for cmd->pdu_send_order: %u.\n",
624			cmd->init_task_tag, cmd->pdu_send_order);
625		return NULL;
626	} else {
627		if (!seq) {
628			pr_err("struct iscsi_seq is NULL!\n");
629			return NULL;
630		}
631
632		pr_debug("seq->pdu_start: %d, seq->pdu_count: %d,"
633			" seq->seq_no: %d\n", seq->pdu_start, seq->pdu_count,
634			seq->seq_no);
635
636		pdu = &cmd->pdu_list[seq->pdu_start];
637
638		if (seq->pdu_send_order == seq->pdu_count) {
639			pr_err("Command ITT: 0x%08x seq->pdu_send"
640				"_order: %u equals seq->pdu_count: %u\n",
641				cmd->init_task_tag, seq->pdu_send_order,
642				seq->pdu_count);
643			return NULL;
644		}
645
646		for (i = 0; i < seq->pdu_count; i++) {
647			if (pdu[i].pdu_send_order == seq->pdu_send_order) {
648				seq->pdu_send_order++;
649				return &pdu[i];
650			}
651		}
652
653		pr_err("Command ITT: 0x%08x unable to locate iscsi"
654			"_pdu_t for seq->pdu_send_order: %u.\n",
655			cmd->init_task_tag, seq->pdu_send_order);
656		return NULL;
657	}
658
659	return NULL;
660}
661
662struct iscsi_seq *iscsit_get_seq_holder(
663	struct iscsit_cmd *cmd,
664	u32 offset,
665	u32 length)
666{
667	u32 i;
668
669	if (!cmd->seq_list) {
670		pr_err("struct iscsit_cmd->seq_list is NULL!\n");
671		return NULL;
672	}
673
674	for (i = 0; i < cmd->seq_count; i++) {
675		pr_debug("seq_list[i].orig_offset: %d, seq_list[i]."
676			"xfer_len: %d, seq_list[i].seq_no %u\n",
677			cmd->seq_list[i].orig_offset, cmd->seq_list[i].xfer_len,
678			cmd->seq_list[i].seq_no);
679
680		if ((cmd->seq_list[i].orig_offset +
681				cmd->seq_list[i].xfer_len) >=
682				(offset + length))
683			return &cmd->seq_list[i];
684	}
685
686	pr_err("Unable to locate Sequence holder for ITT: 0x%08x,"
687		" Offset: %u, Length: %u\n", cmd->init_task_tag, offset,
688		length);
689	return NULL;
690}
691