1 /*- 2 * BSD LICENSE 3 * 4 * Copyright (C) 2008-2012 Daisuke Aoyama <aoyama@peach.ne.jp>. 5 * Copyright (c) Intel Corporation. 6 * All rights reserved. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions 10 * are met: 11 * 12 * * Redistributions of source code must retain the above copyright 13 * notice, this list of conditions and the following disclaimer. 14 * * Redistributions in binary form must reproduce the above copyright 15 * notice, this list of conditions and the following disclaimer in 16 * the documentation and/or other materials provided with the 17 * distribution. 18 * * Neither the name of Intel Corporation nor the names of its 19 * contributors may be used to endorse or promote products derived 20 * from this software without specific prior written permission. 21 * 22 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 23 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 24 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 25 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 26 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 27 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 28 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 29 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 30 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 31 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 32 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 33 */ 34 35 #include "spdk/stdinc.h" 36 37 #include "spdk/base64.h" 38 #include "spdk/crc32.h" 39 #include "spdk/endian.h" 40 #include "spdk/env.h" 41 #include "spdk/likely.h" 42 #include "spdk/trace.h" 43 #include "spdk/string.h" 44 #include "spdk/queue.h" 45 #include "spdk/net.h" 46 47 #include "iscsi/md5.h" 48 #include "iscsi/iscsi.h" 49 #include "iscsi/param.h" 50 #include "iscsi/tgt_node.h" 51 #include "iscsi/task.h" 52 #include "iscsi/conn.h" 53 #include "spdk/scsi.h" 54 #include "spdk/bdev.h" 55 #include "iscsi/portal_grp.h" 56 57 #include "spdk_internal/log.h" 58 59 #define MAX_TMPBUF 1024 60 61 #define SPDK_CRC32C_INITIAL 0xffffffffUL 62 #define SPDK_CRC32C_XOR 0xffffffffUL 63 64 #ifdef __FreeBSD__ 65 #define HAVE_SRANDOMDEV 1 66 #define HAVE_ARC4RANDOM 1 67 #endif 68 69 struct spdk_iscsi_globals g_spdk_iscsi = { 70 .mutex = PTHREAD_MUTEX_INITIALIZER, 71 .portal_head = TAILQ_HEAD_INITIALIZER(g_spdk_iscsi.portal_head), 72 .pg_head = TAILQ_HEAD_INITIALIZER(g_spdk_iscsi.pg_head), 73 .ig_head = TAILQ_HEAD_INITIALIZER(g_spdk_iscsi.ig_head), 74 .target_head = TAILQ_HEAD_INITIALIZER(g_spdk_iscsi.target_head), 75 .auth_group_head = TAILQ_HEAD_INITIALIZER(g_spdk_iscsi.auth_group_head), 76 .poll_group_head = TAILQ_HEAD_INITIALIZER(g_spdk_iscsi.poll_group_head), 77 }; 78 79 #define DMIN32(A,B) ((uint32_t) ((uint32_t)(A) > (uint32_t)(B) ? (uint32_t)(B) : (uint32_t)(A))) 80 #define DMIN64(A,B) ((uint64_t) ((A) > (B) ? (B) : (A))) 81 82 #define MATCH_DIGEST_WORD(BUF, CRC32C) \ 83 ( ((((uint32_t) *((uint8_t *)(BUF)+0)) << 0) \ 84 | (((uint32_t) *((uint8_t *)(BUF)+1)) << 8) \ 85 | (((uint32_t) *((uint8_t *)(BUF)+2)) << 16) \ 86 | (((uint32_t) *((uint8_t *)(BUF)+3)) << 24)) \ 87 == (CRC32C)) 88 89 #if 0 90 static int 91 match_digest_word(const uint8_t *buf, uint32_t crc32c) 92 { 93 uint32_t l; 94 95 l = (buf[0] & 0xffU) << 0; 96 l |= (buf[1] & 0xffU) << 8; 97 l |= (buf[2] & 0xffU) << 16; 98 l |= (buf[3] & 0xffU) << 24; 99 return (l == crc32c); 100 } 101 102 static uint8_t * 103 make_digest_word(uint8_t *buf, size_t len, uint32_t crc32c) 104 { 105 if (len < ISCSI_DIGEST_LEN) { 106 return NULL; 107 } 108 109 buf[0] = (crc32c >> 0) & 0xffU; 110 buf[1] = (crc32c >> 8) & 0xffU; 111 buf[2] = (crc32c >> 16) & 0xffU; 112 buf[3] = (crc32c >> 24) & 0xffU; 113 return buf; 114 } 115 #endif 116 117 #ifndef HAVE_SRANDOMDEV 118 static void 119 srandomdev(void) 120 { 121 unsigned long seed; 122 time_t now; 123 pid_t pid; 124 125 pid = getpid(); 126 now = time(NULL); 127 seed = pid ^ now; 128 srandom(seed); 129 } 130 #endif /* HAVE_SRANDOMDEV */ 131 132 #ifndef HAVE_ARC4RANDOM 133 static int g_arc4random_initialized = 0; 134 135 static uint32_t 136 arc4random(void) 137 { 138 uint32_t r; 139 uint32_t r1, r2; 140 141 if (!g_arc4random_initialized) { 142 srandomdev(); 143 g_arc4random_initialized = 1; 144 } 145 r1 = (uint32_t)(random() & 0xffff); 146 r2 = (uint32_t)(random() & 0xffff); 147 r = (r1 << 16) | r2; 148 return r; 149 } 150 #endif /* HAVE_ARC4RANDOM */ 151 152 static void 153 gen_random(uint8_t *buf, size_t len) 154 { 155 uint32_t r; 156 size_t idx; 157 158 for (idx = 0; idx < len; idx++) { 159 r = arc4random(); 160 buf[idx] = (uint8_t) r; 161 } 162 } 163 164 static uint64_t 165 iscsi_get_isid(const uint8_t isid[6]) 166 { 167 return (uint64_t)isid[0] << 40 | 168 (uint64_t)isid[1] << 32 | 169 (uint64_t)isid[2] << 24 | 170 (uint64_t)isid[3] << 16 | 171 (uint64_t)isid[4] << 8 | 172 (uint64_t)isid[5]; 173 } 174 175 static int 176 bin2hex(char *buf, size_t len, const uint8_t *data, size_t data_len) 177 { 178 const char *digits = "0123456789ABCDEF"; 179 size_t total = 0; 180 size_t idx; 181 182 if (len < 3) { 183 return -1; 184 } 185 buf[total] = '0'; 186 total++; 187 buf[total] = 'x'; 188 total++; 189 buf[total] = '\0'; 190 191 for (idx = 0; idx < data_len; idx++) { 192 if (total + 3 > len) { 193 buf[total] = '\0'; 194 return - 1; 195 } 196 buf[total] = digits[(data[idx] >> 4) & 0x0fU]; 197 total++; 198 buf[total] = digits[data[idx] & 0x0fU]; 199 total++; 200 } 201 buf[total] = '\0'; 202 return total; 203 } 204 205 static int 206 hex2bin(uint8_t *data, size_t data_len, const char *str) 207 { 208 const char *digits = "0123456789ABCDEF"; 209 const char *dp; 210 const char *p; 211 size_t total = 0; 212 int n0, n1; 213 214 p = str; 215 if (p[0] != '0' && (p[1] != 'x' && p[1] != 'X')) { 216 return -1; 217 } 218 p += 2; 219 220 while (p[0] != '\0' && p[1] != '\0') { 221 if (total >= data_len) { 222 return -1; 223 } 224 dp = strchr(digits, toupper((int) p[0])); 225 if (dp == NULL) { 226 return -1; 227 } 228 n0 = (int)(dp - digits); 229 dp = strchr(digits, toupper((int) p[1])); 230 if (dp == NULL) { 231 return -1; 232 } 233 n1 = (int)(dp - digits); 234 235 data[total] = (uint8_t)(((n0 & 0x0fU) << 4) | (n1 & 0x0fU)); 236 total++; 237 p += 2; 238 } 239 return total; 240 } 241 242 static int 243 iscsi_reject(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu, 244 int reason) 245 { 246 struct spdk_iscsi_pdu *rsp_pdu; 247 struct iscsi_bhs_reject *rsph; 248 uint8_t *data; 249 int total_ahs_len; 250 int data_len; 251 int alloc_len; 252 253 pdu->is_rejected = true; 254 255 total_ahs_len = pdu->bhs.total_ahs_len; 256 data_len = 0; 257 alloc_len = ISCSI_BHS_LEN + (4 * total_ahs_len); 258 259 if (conn->header_digest) { 260 alloc_len += ISCSI_DIGEST_LEN; 261 } 262 263 data = calloc(1, alloc_len); 264 if (!data) { 265 SPDK_ERRLOG("calloc() failed for data segment\n"); 266 return -ENOMEM; 267 } 268 269 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Reject PDU reason=%d\n", reason); 270 271 if (conn->sess != NULL) { 272 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, 273 "StatSN=%u, ExpCmdSN=%u, MaxCmdSN=%u\n", 274 conn->StatSN, conn->sess->ExpCmdSN, 275 conn->sess->MaxCmdSN); 276 } else { 277 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "StatSN=%u\n", conn->StatSN); 278 } 279 280 memcpy(data, &pdu->bhs, ISCSI_BHS_LEN); 281 data_len += ISCSI_BHS_LEN; 282 283 if (total_ahs_len != 0) { 284 total_ahs_len = spdk_min((4 * total_ahs_len), ISCSI_AHS_LEN); 285 memcpy(data + data_len, pdu->ahs, total_ahs_len); 286 data_len += total_ahs_len; 287 } 288 289 if (conn->header_digest) { 290 memcpy(data + data_len, pdu->header_digest, ISCSI_DIGEST_LEN); 291 data_len += ISCSI_DIGEST_LEN; 292 } 293 294 rsp_pdu = spdk_get_pdu(); 295 if (rsp_pdu == NULL) { 296 free(data); 297 return -ENOMEM; 298 } 299 300 rsph = (struct iscsi_bhs_reject *)&rsp_pdu->bhs; 301 rsp_pdu->data = data; 302 rsph->opcode = ISCSI_OP_REJECT; 303 rsph->flags |= 0x80; /* bit 0 is default to 1 */ 304 rsph->reason = reason; 305 DSET24(rsph->data_segment_len, data_len); 306 307 rsph->ffffffff = 0xffffffffU; 308 to_be32(&rsph->stat_sn, conn->StatSN); 309 conn->StatSN++; 310 311 if (conn->sess != NULL) { 312 to_be32(&rsph->exp_cmd_sn, conn->sess->ExpCmdSN); 313 to_be32(&rsph->max_cmd_sn, conn->sess->MaxCmdSN); 314 } else { 315 to_be32(&rsph->exp_cmd_sn, 1); 316 to_be32(&rsph->max_cmd_sn, 1); 317 } 318 319 SPDK_LOGDUMP(SPDK_LOG_ISCSI, "PDU", (void *)&rsp_pdu->bhs, ISCSI_BHS_LEN); 320 321 spdk_iscsi_conn_write_pdu(conn, rsp_pdu); 322 323 return 0; 324 } 325 326 uint32_t 327 spdk_iscsi_pdu_calc_header_digest(struct spdk_iscsi_pdu *pdu) 328 { 329 uint32_t crc32c; 330 uint32_t ahs_len_bytes = pdu->bhs.total_ahs_len * 4; 331 332 crc32c = SPDK_CRC32C_INITIAL; 333 crc32c = spdk_crc32c_update(&pdu->bhs, ISCSI_BHS_LEN, crc32c); 334 335 if (ahs_len_bytes) { 336 crc32c = spdk_crc32c_update(pdu->ahs, ahs_len_bytes, crc32c); 337 } 338 339 /* BHS and AHS are always 4-byte multiples in length, so no padding is necessary. */ 340 crc32c = crc32c ^ SPDK_CRC32C_XOR; 341 return crc32c; 342 } 343 344 uint32_t 345 spdk_iscsi_pdu_calc_data_digest(struct spdk_iscsi_pdu *pdu) 346 { 347 uint32_t data_len = DGET24(pdu->bhs.data_segment_len); 348 uint32_t crc32c; 349 uint32_t mod; 350 struct iovec iov; 351 uint32_t num_blocks; 352 353 crc32c = SPDK_CRC32C_INITIAL; 354 if (spdk_likely(!pdu->dif_insert_or_strip)) { 355 crc32c = spdk_crc32c_update(pdu->data, data_len, crc32c); 356 } else { 357 iov.iov_base = pdu->data_buf; 358 iov.iov_len = pdu->data_buf_len; 359 num_blocks = pdu->data_buf_len / pdu->dif_ctx.block_size; 360 361 spdk_dif_update_crc32c(&iov, 1, num_blocks, &crc32c, &pdu->dif_ctx); 362 } 363 364 mod = data_len % ISCSI_ALIGNMENT; 365 if (mod != 0) { 366 uint32_t pad_length = ISCSI_ALIGNMENT - mod; 367 uint8_t pad[3] = {0, 0, 0}; 368 369 assert(pad_length > 0); 370 assert(pad_length <= sizeof(pad)); 371 crc32c = spdk_crc32c_update(pad, pad_length, crc32c); 372 } 373 374 crc32c = crc32c ^ SPDK_CRC32C_XOR; 375 return crc32c; 376 } 377 378 static int 379 iscsi_conn_read_data_segment(struct spdk_iscsi_conn *conn, 380 struct spdk_iscsi_pdu *pdu, 381 uint32_t segment_len) 382 { 383 struct iovec buf_iov, iovs[32]; 384 int rc, _rc; 385 386 if (spdk_likely(!pdu->dif_insert_or_strip)) { 387 return spdk_iscsi_conn_read_data(conn, 388 segment_len - pdu->data_valid_bytes, 389 pdu->data_buf + pdu->data_valid_bytes); 390 } else { 391 buf_iov.iov_base = pdu->data_buf; 392 buf_iov.iov_len = pdu->data_buf_len; 393 rc = spdk_dif_set_md_interleave_iovs(iovs, 32, &buf_iov, 1, 394 pdu->data_valid_bytes, 395 segment_len - pdu->data_valid_bytes, NULL, 396 &pdu->dif_ctx); 397 if (rc > 0) { 398 rc = spdk_iscsi_conn_readv_data(conn, iovs, rc); 399 if (rc > 0) { 400 _rc = spdk_dif_generate_stream(&buf_iov, 1, 401 pdu->data_valid_bytes, rc, 402 &pdu->dif_ctx); 403 if (_rc != 0) { 404 SPDK_ERRLOG("DIF generate failed\n"); 405 rc = _rc; 406 } 407 } 408 } else { 409 SPDK_ERRLOG("Setup iovs for interleaved metadata failed\n"); 410 } 411 return rc; 412 } 413 } 414 415 struct _iscsi_sgl { 416 struct iovec *iov; 417 int iovcnt; 418 uint32_t iov_offset; 419 uint32_t total_size; 420 }; 421 422 static inline void 423 _iscsi_sgl_init(struct _iscsi_sgl *s, struct iovec *iovs, int iovcnt, 424 uint32_t iov_offset) 425 { 426 s->iov = iovs; 427 s->iovcnt = iovcnt; 428 s->iov_offset = iov_offset; 429 s->total_size = 0; 430 } 431 432 static inline bool 433 _iscsi_sgl_append(struct _iscsi_sgl *s, uint8_t *data, uint32_t data_len) 434 { 435 if (s->iov_offset >= data_len) { 436 s->iov_offset -= data_len; 437 } else { 438 assert(s->iovcnt > 0); 439 s->iov->iov_base = data + s->iov_offset; 440 s->iov->iov_len = data_len - s->iov_offset; 441 s->total_size += data_len - s->iov_offset; 442 s->iov_offset = 0; 443 s->iov++; 444 s->iovcnt--; 445 if (s->iovcnt == 0) { 446 return false; 447 } 448 } 449 450 return true; 451 } 452 453 /* Build iovec array to leave metadata space for every data block 454 * when reading data segment from socket. 455 */ 456 static inline bool 457 _iscsi_sgl_append_with_md(struct _iscsi_sgl *s, 458 void *buf, uint32_t buf_len, uint32_t data_len, 459 struct spdk_dif_ctx *dif_ctx) 460 { 461 int rc; 462 uint32_t total_size = 0; 463 struct iovec buf_iov; 464 465 if (s->iov_offset >= data_len) { 466 s->iov_offset -= data_len; 467 } else { 468 buf_iov.iov_base = buf; 469 buf_iov.iov_len = buf_len; 470 rc = spdk_dif_set_md_interleave_iovs(s->iov, s->iovcnt, &buf_iov, 1, 471 s->iov_offset, data_len - s->iov_offset, 472 &total_size, dif_ctx); 473 if (rc < 0) { 474 SPDK_ERRLOG("Failed to setup iovs for DIF strip\n"); 475 return false; 476 } 477 478 s->total_size += total_size; 479 s->iov_offset = 0; 480 assert(s->iovcnt >= rc); 481 s->iovcnt -= rc; 482 s->iov += rc; 483 484 if (s->iovcnt == 0) { 485 return false; 486 } 487 } 488 489 return true; 490 } 491 492 int 493 spdk_iscsi_build_iovs(struct spdk_iscsi_conn *conn, struct iovec *iovs, int iovcnt, 494 struct spdk_iscsi_pdu *pdu, uint32_t *_mapped_length) 495 { 496 struct _iscsi_sgl sgl; 497 int enable_digest; 498 uint32_t total_ahs_len; 499 uint32_t data_len; 500 501 if (iovcnt == 0) { 502 return 0; 503 } 504 505 total_ahs_len = pdu->bhs.total_ahs_len; 506 data_len = DGET24(pdu->bhs.data_segment_len); 507 data_len = ISCSI_ALIGN(data_len); 508 509 enable_digest = 1; 510 if (pdu->bhs.opcode == ISCSI_OP_LOGIN_RSP) { 511 /* this PDU should be sent without digest */ 512 enable_digest = 0; 513 } 514 515 _iscsi_sgl_init(&sgl, iovs, iovcnt, pdu->writev_offset); 516 517 /* BHS */ 518 if (!_iscsi_sgl_append(&sgl, (uint8_t *)&pdu->bhs, ISCSI_BHS_LEN)) { 519 goto end; 520 } 521 /* AHS */ 522 if (total_ahs_len > 0) { 523 if (!_iscsi_sgl_append(&sgl, pdu->ahs, 4 * total_ahs_len)) { 524 goto end; 525 } 526 } 527 528 /* Header Digest */ 529 if (enable_digest && conn->header_digest) { 530 if (!_iscsi_sgl_append(&sgl, pdu->header_digest, ISCSI_DIGEST_LEN)) { 531 goto end; 532 } 533 } 534 535 /* Data Segment */ 536 if (data_len > 0) { 537 if (!pdu->dif_insert_or_strip) { 538 if (!_iscsi_sgl_append(&sgl, pdu->data, data_len)) { 539 goto end; 540 } 541 } else { 542 if (!_iscsi_sgl_append_with_md(&sgl, pdu->data, pdu->data_buf_len, 543 data_len, &pdu->dif_ctx)) { 544 goto end; 545 } 546 } 547 } 548 549 /* Data Digest */ 550 if (enable_digest && conn->data_digest && data_len != 0) { 551 _iscsi_sgl_append(&sgl, pdu->data_digest, ISCSI_DIGEST_LEN); 552 } 553 554 end: 555 if (_mapped_length != NULL) { 556 *_mapped_length = sgl.total_size; 557 } 558 559 return iovcnt - sgl.iovcnt; 560 } 561 562 void spdk_free_sess(struct spdk_iscsi_sess *sess) 563 { 564 if (sess == NULL) { 565 return; 566 } 567 568 sess->tag = 0; 569 sess->target = NULL; 570 sess->session_type = SESSION_TYPE_INVALID; 571 spdk_iscsi_param_free(sess->params); 572 free(sess->conns); 573 spdk_scsi_port_free(&sess->initiator_port); 574 spdk_mempool_put(g_spdk_iscsi.session_pool, (void *)sess); 575 } 576 577 static int 578 create_iscsi_sess(struct spdk_iscsi_conn *conn, 579 struct spdk_iscsi_tgt_node *target, 580 enum session_type session_type) 581 { 582 struct spdk_iscsi_sess *sess; 583 int rc; 584 585 sess = spdk_mempool_get(g_spdk_iscsi.session_pool); 586 if (!sess) { 587 SPDK_ERRLOG("Unable to get session object\n"); 588 SPDK_ERRLOG("MaxSessions set to %d\n", g_spdk_iscsi.MaxSessions); 589 return -ENOMEM; 590 } 591 592 /* configuration values */ 593 pthread_mutex_lock(&g_spdk_iscsi.mutex); 594 595 sess->MaxConnections = g_spdk_iscsi.MaxConnectionsPerSession; 596 sess->MaxOutstandingR2T = DEFAULT_MAXOUTSTANDINGR2T; 597 598 sess->DefaultTime2Wait = g_spdk_iscsi.DefaultTime2Wait; 599 sess->DefaultTime2Retain = g_spdk_iscsi.DefaultTime2Retain; 600 sess->FirstBurstLength = g_spdk_iscsi.FirstBurstLength; 601 sess->MaxBurstLength = SPDK_ISCSI_MAX_BURST_LENGTH; 602 sess->InitialR2T = DEFAULT_INITIALR2T; 603 sess->ImmediateData = g_spdk_iscsi.ImmediateData; 604 sess->DataPDUInOrder = DEFAULT_DATAPDUINORDER; 605 sess->DataSequenceInOrder = DEFAULT_DATASEQUENCEINORDER; 606 sess->ErrorRecoveryLevel = g_spdk_iscsi.ErrorRecoveryLevel; 607 608 pthread_mutex_unlock(&g_spdk_iscsi.mutex); 609 610 sess->tag = conn->pg_tag; 611 612 sess->conns = calloc(sess->MaxConnections, sizeof(*sess->conns)); 613 if (!sess->conns) { 614 SPDK_ERRLOG("calloc() failed for connection array\n"); 615 return -ENOMEM; 616 } 617 618 sess->connections = 0; 619 620 sess->conns[sess->connections] = conn; 621 sess->connections++; 622 623 sess->params = NULL; 624 sess->target = target; 625 sess->isid = 0; 626 sess->session_type = session_type; 627 sess->current_text_itt = 0xffffffffU; 628 629 /* set default params */ 630 rc = spdk_iscsi_sess_params_init(&sess->params); 631 if (rc < 0) { 632 SPDK_ERRLOG("iscsi_sess_params_init() failed\n"); 633 goto error_return; 634 } 635 /* replace with config value */ 636 rc = spdk_iscsi_param_set_int(sess->params, "MaxConnections", 637 sess->MaxConnections); 638 if (rc < 0) { 639 SPDK_ERRLOG("iscsi_param_set_int() failed\n"); 640 goto error_return; 641 } 642 643 rc = spdk_iscsi_param_set_int(sess->params, "MaxOutstandingR2T", 644 sess->MaxOutstandingR2T); 645 if (rc < 0) { 646 SPDK_ERRLOG("iscsi_param_set_int() failed\n"); 647 goto error_return; 648 } 649 650 rc = spdk_iscsi_param_set_int(sess->params, "DefaultTime2Wait", 651 sess->DefaultTime2Wait); 652 if (rc < 0) { 653 SPDK_ERRLOG("iscsi_param_set_int() failed\n"); 654 goto error_return; 655 } 656 657 rc = spdk_iscsi_param_set_int(sess->params, "DefaultTime2Retain", 658 sess->DefaultTime2Retain); 659 if (rc < 0) { 660 SPDK_ERRLOG("iscsi_param_set_int() failed\n"); 661 goto error_return; 662 } 663 664 rc = spdk_iscsi_param_set_int(sess->params, "FirstBurstLength", 665 sess->FirstBurstLength); 666 if (rc < 0) { 667 SPDK_ERRLOG("iscsi_param_set_int() failed\n"); 668 goto error_return; 669 } 670 671 rc = spdk_iscsi_param_set_int(sess->params, "MaxBurstLength", 672 sess->MaxBurstLength); 673 if (rc < 0) { 674 SPDK_ERRLOG("iscsi_param_set_int() failed\n"); 675 goto error_return; 676 } 677 678 rc = spdk_iscsi_param_set(sess->params, "InitialR2T", 679 sess->InitialR2T ? "Yes" : "No"); 680 if (rc < 0) { 681 SPDK_ERRLOG("iscsi_param_set() failed\n"); 682 goto error_return; 683 } 684 685 rc = spdk_iscsi_param_set(sess->params, "ImmediateData", 686 sess->ImmediateData ? "Yes" : "No"); 687 if (rc < 0) { 688 SPDK_ERRLOG("iscsi_param_set() failed\n"); 689 goto error_return; 690 } 691 692 rc = spdk_iscsi_param_set(sess->params, "DataPDUInOrder", 693 sess->DataPDUInOrder ? "Yes" : "No"); 694 if (rc < 0) { 695 SPDK_ERRLOG("iscsi_param_set() failed\n"); 696 goto error_return; 697 } 698 699 rc = spdk_iscsi_param_set(sess->params, "DataSequenceInOrder", 700 sess->DataSequenceInOrder ? "Yes" : "No"); 701 if (rc < 0) { 702 SPDK_ERRLOG("iscsi_param_set() failed\n"); 703 goto error_return; 704 } 705 706 rc = spdk_iscsi_param_set_int(sess->params, "ErrorRecoveryLevel", 707 sess->ErrorRecoveryLevel); 708 if (rc < 0) { 709 SPDK_ERRLOG("iscsi_param_set_int() failed\n"); 710 goto error_return; 711 } 712 713 /* realloc buffer */ 714 rc = spdk_iscsi_param_set_int(conn->params, "MaxRecvDataSegmentLength", 715 conn->MaxRecvDataSegmentLength); 716 if (rc < 0) { 717 SPDK_ERRLOG("iscsi_param_set_int() failed\n"); 718 goto error_return; 719 } 720 721 /* sess for first connection of session */ 722 conn->sess = sess; 723 return 0; 724 725 error_return: 726 spdk_free_sess(sess); 727 conn->sess = NULL; 728 return -1; 729 } 730 731 static struct spdk_iscsi_sess * 732 get_iscsi_sess_by_tsih(uint16_t tsih) 733 { 734 struct spdk_iscsi_sess *session; 735 736 if (tsih == 0 || tsih > g_spdk_iscsi.MaxSessions) { 737 return NULL; 738 } 739 740 session = g_spdk_iscsi.session[tsih - 1]; 741 assert(tsih == session->tsih); 742 743 return session; 744 } 745 746 static uint8_t 747 append_iscsi_sess(struct spdk_iscsi_conn *conn, 748 const char *initiator_port_name, uint16_t tsih, uint16_t cid) 749 { 750 struct spdk_iscsi_sess *sess; 751 752 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "append session: init port name=%s, tsih=%u, cid=%u\n", 753 initiator_port_name, tsih, cid); 754 755 sess = get_iscsi_sess_by_tsih(tsih); 756 if (sess == NULL) { 757 SPDK_ERRLOG("spdk_get_iscsi_sess_by_tsih failed\n"); 758 return ISCSI_LOGIN_CONN_ADD_FAIL; 759 } 760 if ((conn->pg_tag != sess->tag) || 761 (strcasecmp(initiator_port_name, spdk_scsi_port_get_name(sess->initiator_port)) != 0) || 762 (conn->target != sess->target)) { 763 /* no match */ 764 SPDK_ERRLOG("no MCS session for init port name=%s, tsih=%d, cid=%d\n", 765 initiator_port_name, tsih, cid); 766 return ISCSI_LOGIN_CONN_ADD_FAIL; 767 } 768 769 if (sess->connections >= sess->MaxConnections) { 770 /* no slot for connection */ 771 SPDK_ERRLOG("too many connections for init port name=%s, tsih=%d, cid=%d\n", 772 initiator_port_name, tsih, cid); 773 return ISCSI_LOGIN_TOO_MANY_CONNECTIONS; 774 } 775 776 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Connections (tsih %d): %d\n", sess->tsih, sess->connections); 777 conn->sess = sess; 778 779 /* 780 * TODO: need a mutex or other sync mechanism to protect the session's 781 * connection list. 782 */ 783 sess->conns[sess->connections] = conn; 784 sess->connections++; 785 786 return 0; 787 } 788 789 static int 790 iscsi_append_text(struct spdk_iscsi_conn *conn __attribute__((__unused__)), 791 const char *key, const char *val, uint8_t *data, 792 int alloc_len, int data_len) 793 { 794 int total; 795 int len; 796 797 total = data_len; 798 if (alloc_len < 1) { 799 return 0; 800 } 801 if (total > alloc_len) { 802 total = alloc_len; 803 data[total - 1] = '\0'; 804 return total; 805 } 806 807 if (alloc_len - total < 1) { 808 SPDK_ERRLOG("data space small %d\n", alloc_len); 809 return total; 810 } 811 len = snprintf((char *) data + total, alloc_len - total, "%s=%s", key, val); 812 total += len + 1; 813 814 return total; 815 } 816 817 static int 818 iscsi_append_param(struct spdk_iscsi_conn *conn, const char *key, 819 uint8_t *data, int alloc_len, int data_len) 820 { 821 struct iscsi_param *param; 822 int rc; 823 824 param = spdk_iscsi_param_find(conn->params, key); 825 if (param == NULL) { 826 param = spdk_iscsi_param_find(conn->sess->params, key); 827 if (param == NULL) { 828 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "no key %.64s\n", key); 829 return data_len; 830 } 831 } 832 rc = iscsi_append_text(conn, param->key, param->val, data, 833 alloc_len, data_len); 834 return rc; 835 } 836 837 static int 838 iscsi_auth_params(struct spdk_iscsi_conn *conn, 839 struct iscsi_param *params, const char *method, uint8_t *data, 840 int alloc_len, int data_len) 841 { 842 char *in_val; 843 char *in_next; 844 char *new_val; 845 const char *algorithm; 846 const char *name; 847 const char *response; 848 const char *identifier; 849 const char *challenge; 850 int total; 851 int rc; 852 853 if (conn == NULL || params == NULL || method == NULL) { 854 return -1; 855 } 856 if (strcasecmp(method, "CHAP") == 0) { 857 /* method OK */ 858 } else { 859 SPDK_ERRLOG("unsupported AuthMethod %.64s\n", method); 860 return -1; 861 } 862 863 total = data_len; 864 if (alloc_len < 1) { 865 return 0; 866 } 867 if (total > alloc_len) { 868 total = alloc_len; 869 data[total - 1] = '\0'; 870 return total; 871 } 872 873 /* for temporary store */ 874 in_val = malloc(ISCSI_TEXT_MAX_VAL_LEN + 1); 875 if (!in_val) { 876 SPDK_ERRLOG("malloc() failed for temporary store\n"); 877 return -ENOMEM; 878 } 879 880 /* CHAP method (RFC1994) */ 881 if ((algorithm = spdk_iscsi_param_get_val(params, "CHAP_A")) != NULL) { 882 if (conn->auth.chap_phase != ISCSI_CHAP_PHASE_WAIT_A) { 883 SPDK_ERRLOG("CHAP sequence error\n"); 884 goto error_return; 885 } 886 887 /* CHAP_A is LIST type */ 888 snprintf(in_val, ISCSI_TEXT_MAX_VAL_LEN + 1, "%s", algorithm); 889 in_next = in_val; 890 while ((new_val = spdk_strsepq(&in_next, ",")) != NULL) { 891 if (strcasecmp(new_val, "5") == 0) { 892 /* CHAP with MD5 */ 893 break; 894 } 895 } 896 if (new_val == NULL) { 897 snprintf(in_val, ISCSI_TEXT_MAX_VAL_LEN + 1, "%s", "Reject"); 898 new_val = in_val; 899 iscsi_append_text(conn, "CHAP_A", new_val, 900 data, alloc_len, total); 901 goto error_return; 902 } 903 /* selected algorithm is 5 (MD5) */ 904 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "got CHAP_A=%s\n", new_val); 905 total = iscsi_append_text(conn, "CHAP_A", new_val, 906 data, alloc_len, total); 907 908 /* Identifier is one octet */ 909 gen_random(conn->auth.chap_id, 1); 910 snprintf(in_val, ISCSI_TEXT_MAX_VAL_LEN, "%d", 911 (int) conn->auth.chap_id[0]); 912 total = iscsi_append_text(conn, "CHAP_I", in_val, 913 data, alloc_len, total); 914 915 /* Challenge Value is a variable stream of octets */ 916 /* (binary length MUST not exceed 1024 bytes) */ 917 conn->auth.chap_challenge_len = ISCSI_CHAP_CHALLENGE_LEN; 918 gen_random(conn->auth.chap_challenge, conn->auth.chap_challenge_len); 919 bin2hex(in_val, ISCSI_TEXT_MAX_VAL_LEN, 920 conn->auth.chap_challenge, conn->auth.chap_challenge_len); 921 total = iscsi_append_text(conn, "CHAP_C", in_val, 922 data, alloc_len, total); 923 924 conn->auth.chap_phase = ISCSI_CHAP_PHASE_WAIT_NR; 925 } else if ((name = spdk_iscsi_param_get_val(params, "CHAP_N")) != NULL) { 926 uint8_t resmd5[SPDK_MD5DIGEST_LEN]; 927 uint8_t tgtmd5[SPDK_MD5DIGEST_LEN]; 928 struct spdk_md5ctx md5ctx; 929 size_t decoded_len = 0; 930 931 if (conn->auth.chap_phase != ISCSI_CHAP_PHASE_WAIT_NR) { 932 SPDK_ERRLOG("CHAP sequence error\n"); 933 goto error_return; 934 } 935 936 response = spdk_iscsi_param_get_val(params, "CHAP_R"); 937 if (response == NULL) { 938 SPDK_ERRLOG("no response\n"); 939 goto error_return; 940 } 941 if (response[0] == '0' && 942 (response[1] == 'x' || response[1] == 'X')) { 943 rc = hex2bin(resmd5, SPDK_MD5DIGEST_LEN, response); 944 if (rc < 0 || rc != SPDK_MD5DIGEST_LEN) { 945 SPDK_ERRLOG("response format error\n"); 946 goto error_return; 947 } 948 } else if (response[0] == '0' && 949 (response[1] == 'b' || response[1] == 'B')) { 950 response += 2; 951 rc = spdk_base64_decode(resmd5, &decoded_len, response); 952 if (rc < 0 || decoded_len != SPDK_MD5DIGEST_LEN) { 953 SPDK_ERRLOG("response format error\n"); 954 goto error_return; 955 } 956 } else { 957 SPDK_ERRLOG("response format error\n"); 958 goto error_return; 959 } 960 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "got CHAP_N/CHAP_R\n"); 961 962 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "ag_tag=%d\n", conn->chap_group); 963 964 rc = spdk_iscsi_chap_get_authinfo(&conn->auth, name, conn->chap_group); 965 if (rc < 0) { 966 /* SPDK_ERRLOG("auth user or secret is missing\n"); */ 967 SPDK_ERRLOG("spdk_iscsi_chap_get_authinfo() failed\n"); 968 goto error_return; 969 } 970 if (conn->auth.user[0] == '\0' || conn->auth.secret[0] == '\0') { 971 /* SPDK_ERRLOG("auth user or secret is missing\n"); */ 972 SPDK_ERRLOG("auth failed (name %.64s)\n", name); 973 goto error_return; 974 } 975 976 spdk_md5init(&md5ctx); 977 /* Identifier */ 978 spdk_md5update(&md5ctx, conn->auth.chap_id, 1); 979 /* followed by secret */ 980 spdk_md5update(&md5ctx, conn->auth.secret, 981 strlen(conn->auth.secret)); 982 /* followed by Challenge Value */ 983 spdk_md5update(&md5ctx, conn->auth.chap_challenge, 984 conn->auth.chap_challenge_len); 985 /* tgtmd5 is expecting Response Value */ 986 spdk_md5final(tgtmd5, &md5ctx); 987 988 bin2hex(in_val, ISCSI_TEXT_MAX_VAL_LEN, tgtmd5, SPDK_MD5DIGEST_LEN); 989 990 #if 0 991 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "tgtmd5=%s, resmd5=%s\n", in_val, response); 992 spdk_dump("tgtmd5", tgtmd5, SPDK_MD5DIGEST_LEN); 993 spdk_dump("resmd5", resmd5, SPDK_MD5DIGEST_LEN); 994 #endif 995 996 /* compare MD5 digest */ 997 if (memcmp(tgtmd5, resmd5, SPDK_MD5DIGEST_LEN) != 0) { 998 /* not match */ 999 /* SPDK_ERRLOG("auth user or secret is missing\n"); */ 1000 SPDK_ERRLOG("auth failed (name %.64s)\n", name); 1001 goto error_return; 1002 } 1003 /* OK initiator's secret */ 1004 conn->authenticated = true; 1005 1006 /* mutual CHAP? */ 1007 identifier = spdk_iscsi_param_get_val(params, "CHAP_I"); 1008 if (identifier != NULL) { 1009 conn->auth.chap_mid[0] = (uint8_t) strtol(identifier, NULL, 10); 1010 challenge = spdk_iscsi_param_get_val(params, "CHAP_C"); 1011 if (challenge == NULL) { 1012 SPDK_ERRLOG("CHAP sequence error\n"); 1013 goto error_return; 1014 } 1015 if (challenge[0] == '0' && 1016 (challenge[1] == 'x' || challenge[1] == 'X')) { 1017 rc = hex2bin(conn->auth.chap_mchallenge, 1018 ISCSI_CHAP_CHALLENGE_LEN, challenge); 1019 if (rc < 0) { 1020 SPDK_ERRLOG("challenge format error\n"); 1021 goto error_return; 1022 } 1023 conn->auth.chap_mchallenge_len = rc; 1024 } else if (challenge[0] == '0' && 1025 (challenge[1] == 'b' || challenge[1] == 'B')) { 1026 challenge += 2; 1027 rc = spdk_base64_decode(conn->auth.chap_mchallenge, 1028 &decoded_len, challenge); 1029 if (rc < 0) { 1030 SPDK_ERRLOG("challenge format error\n"); 1031 goto error_return; 1032 } 1033 conn->auth.chap_mchallenge_len = decoded_len; 1034 } else { 1035 SPDK_ERRLOG("challenge format error\n"); 1036 goto error_return; 1037 } 1038 #if 0 1039 spdk_dump("MChallenge", conn->auth.chap_mchallenge, 1040 conn->auth.chap_mchallenge_len); 1041 #endif 1042 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "got CHAP_I/CHAP_C\n"); 1043 1044 if (conn->auth.muser[0] == '\0' || conn->auth.msecret[0] == '\0') { 1045 /* SPDK_ERRLOG("mutual auth user or secret is missing\n"); */ 1046 SPDK_ERRLOG("auth failed (name %.64s)\n", name); 1047 goto error_return; 1048 } 1049 1050 spdk_md5init(&md5ctx); 1051 /* Identifier */ 1052 spdk_md5update(&md5ctx, conn->auth.chap_mid, 1); 1053 /* followed by secret */ 1054 spdk_md5update(&md5ctx, conn->auth.msecret, 1055 strlen(conn->auth.msecret)); 1056 /* followed by Challenge Value */ 1057 spdk_md5update(&md5ctx, conn->auth.chap_mchallenge, 1058 conn->auth.chap_mchallenge_len); 1059 /* tgtmd5 is Response Value */ 1060 spdk_md5final(tgtmd5, &md5ctx); 1061 1062 bin2hex(in_val, ISCSI_TEXT_MAX_VAL_LEN, tgtmd5, SPDK_MD5DIGEST_LEN); 1063 1064 total = iscsi_append_text(conn, "CHAP_N", 1065 conn->auth.muser, data, alloc_len, total); 1066 total = iscsi_append_text(conn, "CHAP_R", 1067 in_val, data, alloc_len, total); 1068 } else { 1069 /* not mutual */ 1070 if (conn->mutual_chap) { 1071 SPDK_ERRLOG("required mutual CHAP\n"); 1072 goto error_return; 1073 } 1074 } 1075 1076 conn->auth.chap_phase = ISCSI_CHAP_PHASE_END; 1077 } else { 1078 /* not found CHAP keys */ 1079 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "start CHAP\n"); 1080 conn->auth.chap_phase = ISCSI_CHAP_PHASE_WAIT_A; 1081 } 1082 1083 free(in_val); 1084 return total; 1085 1086 error_return: 1087 conn->auth.chap_phase = ISCSI_CHAP_PHASE_WAIT_A; 1088 free(in_val); 1089 return -1; 1090 } 1091 1092 static int 1093 iscsi_check_values(struct spdk_iscsi_conn *conn) 1094 { 1095 if (conn->sess->FirstBurstLength > conn->sess->MaxBurstLength) { 1096 SPDK_ERRLOG("FirstBurstLength(%d) > MaxBurstLength(%d)\n", 1097 conn->sess->FirstBurstLength, 1098 conn->sess->MaxBurstLength); 1099 return -1; 1100 } 1101 if (conn->sess->FirstBurstLength > g_spdk_iscsi.FirstBurstLength) { 1102 SPDK_ERRLOG("FirstBurstLength(%d) > iSCSI target restriction(%d)\n", 1103 conn->sess->FirstBurstLength, g_spdk_iscsi.FirstBurstLength); 1104 return -1; 1105 } 1106 if (conn->sess->MaxBurstLength > 0x00ffffff) { 1107 SPDK_ERRLOG("MaxBurstLength(%d) > 0x00ffffff\n", 1108 conn->sess->MaxBurstLength); 1109 return -1; 1110 } 1111 1112 if (conn->MaxRecvDataSegmentLength < 512) { 1113 SPDK_ERRLOG("MaxRecvDataSegmentLength(%d) < 512\n", 1114 conn->MaxRecvDataSegmentLength); 1115 return -1; 1116 } 1117 if (conn->MaxRecvDataSegmentLength > 0x00ffffff) { 1118 SPDK_ERRLOG("MaxRecvDataSegmentLength(%d) > 0x00ffffff\n", 1119 conn->MaxRecvDataSegmentLength); 1120 return -1; 1121 } 1122 return 0; 1123 } 1124 1125 /* 1126 * The response function of spdk_iscsi_op_login 1127 * return: 1128 * 0:success; 1129 * -1:error; 1130 */ 1131 static int 1132 iscsi_op_login_response(struct spdk_iscsi_conn *conn, 1133 struct spdk_iscsi_pdu *rsp_pdu, struct iscsi_param *params) 1134 { 1135 struct iscsi_bhs_login_rsp *rsph; 1136 int rc; 1137 1138 rsph = (struct iscsi_bhs_login_rsp *)&rsp_pdu->bhs; 1139 rsph->version_max = ISCSI_VERSION; 1140 rsph->version_act = ISCSI_VERSION; 1141 DSET24(rsph->data_segment_len, rsp_pdu->data_segment_len); 1142 1143 to_be32(&rsph->stat_sn, conn->StatSN); 1144 conn->StatSN++; 1145 1146 if (conn->sess != NULL) { 1147 to_be32(&rsph->exp_cmd_sn, conn->sess->ExpCmdSN); 1148 to_be32(&rsph->max_cmd_sn, conn->sess->MaxCmdSN); 1149 } else { 1150 to_be32(&rsph->exp_cmd_sn, rsp_pdu->cmd_sn); 1151 to_be32(&rsph->max_cmd_sn, rsp_pdu->cmd_sn); 1152 } 1153 1154 SPDK_LOGDUMP(SPDK_LOG_ISCSI, "PDU", (uint8_t *)rsph, ISCSI_BHS_LEN); 1155 SPDK_LOGDUMP(SPDK_LOG_ISCSI, "DATA", rsp_pdu->data, rsp_pdu->data_segment_len); 1156 1157 /* Set T/CSG/NSG to reserved if login error. */ 1158 if (rsph->status_class != 0) { 1159 rsph->flags &= ~ISCSI_LOGIN_TRANSIT; 1160 rsph->flags &= ~ISCSI_LOGIN_CURRENT_STAGE_MASK; 1161 rsph->flags &= ~ISCSI_LOGIN_NEXT_STAGE_MASK; 1162 } 1163 spdk_iscsi_conn_write_pdu(conn, rsp_pdu); 1164 1165 /* after send PDU digest on/off */ 1166 if (conn->full_feature) { 1167 /* update internal variables */ 1168 rc = spdk_iscsi_copy_param2var(conn); 1169 if (rc < 0) { 1170 SPDK_ERRLOG("spdk_iscsi_copy_param2var() failed\n"); 1171 spdk_iscsi_param_free(params); 1172 return -1; 1173 } 1174 /* check value */ 1175 rc = iscsi_check_values(conn); 1176 if (rc < 0) { 1177 SPDK_ERRLOG("iscsi_check_values() failed\n"); 1178 spdk_iscsi_param_free(params); 1179 return -1; 1180 } 1181 } 1182 1183 spdk_iscsi_param_free(params); 1184 return 0; 1185 } 1186 1187 /* 1188 * This function is used to del the original param and update it with new 1189 * value 1190 * return: 1191 * 0: success 1192 * otherwise: error 1193 */ 1194 static int 1195 iscsi_op_login_update_param(struct spdk_iscsi_conn *conn, 1196 const char *key, const char *value, 1197 const char *list) 1198 { 1199 int rc = 0; 1200 struct iscsi_param *new_param, *orig_param; 1201 int index; 1202 1203 orig_param = spdk_iscsi_param_find(conn->params, key); 1204 if (orig_param == NULL) { 1205 SPDK_ERRLOG("orig_param %s not found\n", key); 1206 return SPDK_ISCSI_LOGIN_ERROR_PARAMETER; 1207 } 1208 1209 index = orig_param->state_index; 1210 rc = spdk_iscsi_param_del(&conn->params, key); 1211 if (rc < 0) { 1212 SPDK_ERRLOG("iscsi_param_del(%s) failed\n", key); 1213 return SPDK_ISCSI_LOGIN_ERROR_PARAMETER; 1214 } 1215 rc = spdk_iscsi_param_add(&conn->params, key, value, list, ISPT_LIST); 1216 if (rc < 0) { 1217 SPDK_ERRLOG("iscsi_param_add() failed\n"); 1218 return SPDK_ISCSI_LOGIN_ERROR_PARAMETER; 1219 } 1220 new_param = spdk_iscsi_param_find(conn->params, key); 1221 if (new_param == NULL) { 1222 SPDK_ERRLOG("spdk_iscsi_param_find() failed\n"); 1223 return SPDK_ISCSI_LOGIN_ERROR_PARAMETER; 1224 } 1225 new_param->state_index = index; 1226 return rc; 1227 } 1228 1229 static int 1230 iscsi_negotiate_chap_param(struct spdk_iscsi_conn *conn) 1231 { 1232 int rc = 0; 1233 1234 if (conn->disable_chap) { 1235 rc = iscsi_op_login_update_param(conn, "AuthMethod", "None", "None"); 1236 } else if (conn->require_chap) { 1237 rc = iscsi_op_login_update_param(conn, "AuthMethod", "CHAP", "CHAP"); 1238 } 1239 1240 return rc; 1241 } 1242 1243 /* 1244 * The function which is used to handle the part of session discovery 1245 * return: 1246 * 0, success; 1247 * otherwise: error; 1248 */ 1249 static int 1250 iscsi_op_login_session_discovery_chap(struct spdk_iscsi_conn *conn) 1251 { 1252 return iscsi_negotiate_chap_param(conn); 1253 } 1254 1255 /* 1256 * This function is used to update the param related with chap 1257 * return: 1258 * 0: success 1259 * otherwise: error 1260 */ 1261 static int 1262 iscsi_op_login_negotiate_chap_param(struct spdk_iscsi_conn *conn, 1263 struct spdk_iscsi_tgt_node *target) 1264 { 1265 conn->disable_chap = target->disable_chap; 1266 conn->require_chap = target->require_chap; 1267 conn->mutual_chap = target->mutual_chap; 1268 conn->chap_group = target->chap_group; 1269 1270 return iscsi_negotiate_chap_param(conn); 1271 } 1272 1273 static int 1274 iscsi_op_login_negotiate_digest_param(struct spdk_iscsi_conn *conn, 1275 struct spdk_iscsi_tgt_node *target) 1276 { 1277 int rc; 1278 1279 if (target->header_digest) { 1280 /* 1281 * User specified header digests, so update the list of 1282 * HeaderDigest values to remove "None" so that only 1283 * initiators who support CRC32C can connect. 1284 */ 1285 rc = iscsi_op_login_update_param(conn, "HeaderDigest", "CRC32C", "CRC32C"); 1286 if (rc < 0) { 1287 return rc; 1288 } 1289 } 1290 1291 if (target->data_digest) { 1292 /* 1293 * User specified data digests, so update the list of 1294 * DataDigest values to remove "None" so that only 1295 * initiators who support CRC32C can connect. 1296 */ 1297 rc = iscsi_op_login_update_param(conn, "DataDigest", "CRC32C", "CRC32C"); 1298 if (rc < 0) { 1299 return rc; 1300 } 1301 } 1302 1303 return 0; 1304 } 1305 1306 /* 1307 * This function use to check the session 1308 * return: 1309 * 0, success 1310 * otherwise: error 1311 */ 1312 static int 1313 iscsi_op_login_check_session(struct spdk_iscsi_conn *conn, 1314 struct spdk_iscsi_pdu *rsp_pdu, 1315 char *initiator_port_name, int cid) 1316 1317 { 1318 int rc = 0; 1319 struct iscsi_bhs_login_rsp *rsph; 1320 1321 rsph = (struct iscsi_bhs_login_rsp *)&rsp_pdu->bhs; 1322 /* check existing session */ 1323 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "isid=%"PRIx64", tsih=%u, cid=%u\n", 1324 iscsi_get_isid(rsph->isid), from_be16(&rsph->tsih), cid); 1325 if (rsph->tsih != 0) { 1326 /* multiple connections */ 1327 rc = append_iscsi_sess(conn, initiator_port_name, 1328 from_be16(&rsph->tsih), cid); 1329 if (rc != 0) { 1330 SPDK_ERRLOG("isid=%"PRIx64", tsih=%u, cid=%u:" 1331 "spdk_append_iscsi_sess() failed\n", 1332 iscsi_get_isid(rsph->isid), from_be16(&rsph->tsih), 1333 cid); 1334 /* Can't include in session */ 1335 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1336 rsph->status_detail = rc; 1337 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1338 } 1339 } else if (!g_spdk_iscsi.AllowDuplicateIsid) { 1340 /* new session, drop old sess by the initiator */ 1341 spdk_iscsi_drop_conns(conn, initiator_port_name, 0 /* drop old */); 1342 } 1343 1344 return rc; 1345 } 1346 1347 /* 1348 * This function is used to check the target info 1349 * return: 1350 * 0: success 1351 * otherwise: error 1352 */ 1353 static int 1354 iscsi_op_login_check_target(struct spdk_iscsi_conn *conn, 1355 struct spdk_iscsi_pdu *rsp_pdu, 1356 const char *target_name, 1357 struct spdk_iscsi_tgt_node **target) 1358 { 1359 bool result; 1360 struct iscsi_bhs_login_rsp *rsph; 1361 1362 rsph = (struct iscsi_bhs_login_rsp *)&rsp_pdu->bhs; 1363 *target = spdk_iscsi_find_tgt_node(target_name); 1364 if (*target == NULL) { 1365 SPDK_WARNLOG("target %s not found\n", target_name); 1366 /* Not found */ 1367 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1368 rsph->status_detail = ISCSI_LOGIN_TARGET_NOT_FOUND; 1369 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1370 } 1371 if (spdk_iscsi_tgt_node_is_destructed(*target)) { 1372 SPDK_ERRLOG("target %s is removed\n", target_name); 1373 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1374 rsph->status_detail = ISCSI_LOGIN_TARGET_REMOVED; 1375 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1376 } 1377 result = spdk_iscsi_tgt_node_access(conn, *target, 1378 conn->initiator_name, 1379 conn->initiator_addr); 1380 if (!result) { 1381 SPDK_ERRLOG("access denied\n"); 1382 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1383 rsph->status_detail = ISCSI_LOGIN_AUTHORIZATION_FAIL; 1384 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1385 } 1386 1387 return 0; 1388 } 1389 1390 /* 1391 * The function which is used to handle the part of normal login session 1392 * return: 1393 * 0, success; 1394 * SPDK_ISCSI_LOGIN_ERROR_PARAMETER, parameter error; 1395 */ 1396 static int 1397 iscsi_op_login_session_normal(struct spdk_iscsi_conn *conn, 1398 struct spdk_iscsi_pdu *rsp_pdu, 1399 char *initiator_port_name, 1400 struct iscsi_param *params, 1401 int cid) 1402 { 1403 struct spdk_iscsi_tgt_node *target = NULL; 1404 const char *target_name; 1405 const char *target_short_name; 1406 struct iscsi_bhs_login_rsp *rsph; 1407 int rc = 0; 1408 1409 rsph = (struct iscsi_bhs_login_rsp *)&rsp_pdu->bhs; 1410 target_name = spdk_iscsi_param_get_val(params, "TargetName"); 1411 1412 if (target_name == NULL) { 1413 SPDK_ERRLOG("TargetName is empty\n"); 1414 /* Missing parameter */ 1415 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1416 rsph->status_detail = ISCSI_LOGIN_MISSING_PARMS; 1417 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1418 } 1419 1420 memset(conn->target_short_name, 0, MAX_TARGET_NAME); 1421 target_short_name = strstr(target_name, ":"); 1422 if (target_short_name != NULL) { 1423 target_short_name++; /* Advance past the ':' */ 1424 if (strlen(target_short_name) >= MAX_TARGET_NAME) { 1425 SPDK_ERRLOG("Target Short Name (%s) is more than %u characters\n", 1426 target_short_name, MAX_TARGET_NAME); 1427 /* Invalid request */ 1428 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1429 rsph->status_detail = ISCSI_LOGIN_INVALID_LOGIN_REQUEST; 1430 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1431 } 1432 snprintf(conn->target_short_name, MAX_TARGET_NAME, "%s", 1433 target_short_name); 1434 } 1435 1436 pthread_mutex_lock(&g_spdk_iscsi.mutex); 1437 rc = iscsi_op_login_check_target(conn, rsp_pdu, target_name, &target); 1438 pthread_mutex_unlock(&g_spdk_iscsi.mutex); 1439 1440 if (rc < 0) { 1441 return rc; 1442 } 1443 1444 conn->target = target; 1445 conn->dev = target->dev; 1446 conn->target_port = spdk_scsi_dev_find_port_by_id(target->dev, 1447 conn->pg_tag); 1448 1449 rc = iscsi_op_login_check_session(conn, rsp_pdu, 1450 initiator_port_name, cid); 1451 if (rc < 0) { 1452 return rc; 1453 } 1454 1455 /* force target flags */ 1456 pthread_mutex_lock(&target->mutex); 1457 rc = iscsi_op_login_negotiate_chap_param(conn, target); 1458 pthread_mutex_unlock(&target->mutex); 1459 1460 if (rc == 0) { 1461 rc = iscsi_op_login_negotiate_digest_param(conn, target); 1462 } 1463 1464 if (rc != 0) { 1465 /* Invalid request */ 1466 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1467 rsph->status_detail = ISCSI_LOGIN_INVALID_LOGIN_REQUEST; 1468 } 1469 1470 return rc; 1471 } 1472 1473 /* 1474 * This function is used to judge the session type 1475 * return 1476 * 0: success 1477 * otherwise, error 1478 */ 1479 static int 1480 iscsi_op_login_session_type(struct spdk_iscsi_conn *conn, 1481 struct spdk_iscsi_pdu *rsp_pdu, 1482 enum session_type *session_type, 1483 struct iscsi_param *params) 1484 { 1485 const char *session_type_str; 1486 struct iscsi_bhs_login_rsp *rsph; 1487 1488 rsph = (struct iscsi_bhs_login_rsp *)&rsp_pdu->bhs; 1489 session_type_str = spdk_iscsi_param_get_val(params, "SessionType"); 1490 if (session_type_str == NULL) { 1491 if (rsph->tsih != 0) { 1492 *session_type = SESSION_TYPE_NORMAL; 1493 } else { 1494 SPDK_ERRLOG("SessionType is empty\n"); 1495 /* Missing parameter */ 1496 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1497 rsph->status_detail = ISCSI_LOGIN_MISSING_PARMS; 1498 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1499 } 1500 } else { 1501 if (strcasecmp(session_type_str, "Discovery") == 0) { 1502 *session_type = SESSION_TYPE_DISCOVERY; 1503 } else if (strcasecmp(session_type_str, "Normal") == 0) { 1504 *session_type = SESSION_TYPE_NORMAL; 1505 } else { 1506 *session_type = SESSION_TYPE_INVALID; 1507 SPDK_ERRLOG("SessionType is invalid\n"); 1508 /* Missing parameter */ 1509 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1510 rsph->status_detail = ISCSI_LOGIN_MISSING_PARMS; 1511 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1512 } 1513 } 1514 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Session Type: %s\n", session_type_str); 1515 1516 return 0; 1517 } 1518 /* 1519 * This function is used to initialize the port info 1520 * return 1521 * 0: success 1522 * otherwise: error 1523 */ 1524 static int 1525 iscsi_op_login_initialize_port(struct spdk_iscsi_conn *conn, 1526 struct spdk_iscsi_pdu *rsp_pdu, 1527 char *initiator_port_name, 1528 uint32_t name_length, 1529 struct iscsi_param *params) 1530 { 1531 const char *val; 1532 struct iscsi_bhs_login_rsp *rsph; 1533 rsph = (struct iscsi_bhs_login_rsp *)&rsp_pdu->bhs; 1534 1535 /* Initiator Name and Port */ 1536 val = spdk_iscsi_param_get_val(params, "InitiatorName"); 1537 if (val == NULL) { 1538 SPDK_ERRLOG("InitiatorName is empty\n"); 1539 /* Missing parameter */ 1540 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1541 rsph->status_detail = ISCSI_LOGIN_MISSING_PARMS; 1542 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1543 } 1544 snprintf(conn->initiator_name, sizeof(conn->initiator_name), "%s", val); 1545 snprintf(initiator_port_name, name_length, 1546 "%s,i,0x%12.12" PRIx64, val, iscsi_get_isid(rsph->isid)); 1547 spdk_strlwr(conn->initiator_name); 1548 spdk_strlwr(initiator_port_name); 1549 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Initiator name: %s\n", conn->initiator_name); 1550 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Initiator port: %s\n", initiator_port_name); 1551 1552 return 0; 1553 } 1554 1555 /* 1556 * This function is used to set the info in the connection data structure 1557 * return 1558 * 0: success 1559 * otherwise: error 1560 */ 1561 static int 1562 iscsi_op_login_set_conn_info(struct spdk_iscsi_conn *conn, 1563 struct spdk_iscsi_pdu *rsp_pdu, 1564 char *initiator_port_name, 1565 enum session_type session_type, int cid) 1566 { 1567 int rc = 0; 1568 struct spdk_iscsi_tgt_node *target; 1569 struct iscsi_bhs_login_rsp *rsph; 1570 struct spdk_scsi_port *initiator_port; 1571 1572 target = conn->target; 1573 1574 rsph = (struct iscsi_bhs_login_rsp *)&rsp_pdu->bhs; 1575 conn->authenticated = false; 1576 conn->auth.chap_phase = ISCSI_CHAP_PHASE_WAIT_A; 1577 conn->cid = cid; 1578 1579 if (conn->sess == NULL) { 1580 /* create initiator port */ 1581 initiator_port = spdk_scsi_port_create(iscsi_get_isid(rsph->isid), 0, initiator_port_name); 1582 if (initiator_port == NULL) { 1583 SPDK_ERRLOG("create_port() failed\n"); 1584 rsph->status_class = ISCSI_CLASS_TARGET_ERROR; 1585 rsph->status_detail = ISCSI_LOGIN_STATUS_NO_RESOURCES; 1586 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1587 } 1588 1589 /* new session */ 1590 rc = create_iscsi_sess(conn, target, session_type); 1591 if (rc < 0) { 1592 spdk_scsi_port_free(&initiator_port); 1593 SPDK_ERRLOG("create_sess() failed\n"); 1594 rsph->status_class = ISCSI_CLASS_TARGET_ERROR; 1595 rsph->status_detail = ISCSI_LOGIN_STATUS_NO_RESOURCES; 1596 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1597 } 1598 /* initialize parameters */ 1599 conn->sess->initiator_port = initiator_port; 1600 conn->StatSN = from_be32(&rsph->stat_sn); 1601 conn->sess->isid = iscsi_get_isid(rsph->isid); 1602 1603 /* Initiator port TransportID */ 1604 spdk_scsi_port_set_iscsi_transport_id(conn->sess->initiator_port, 1605 conn->initiator_name, 1606 conn->sess->isid); 1607 1608 /* Discovery sessions will not have a target. */ 1609 if (target != NULL) { 1610 conn->sess->queue_depth = target->queue_depth; 1611 } else { 1612 /* 1613 * Assume discovery sessions have an effective command 1614 * windows size of 1. 1615 */ 1616 conn->sess->queue_depth = 1; 1617 } 1618 conn->sess->ExpCmdSN = rsp_pdu->cmd_sn; 1619 conn->sess->MaxCmdSN = rsp_pdu->cmd_sn + conn->sess->queue_depth - 1; 1620 } 1621 1622 conn->initiator_port = conn->sess->initiator_port; 1623 1624 return 0; 1625 } 1626 1627 /* 1628 * This function is used to set the target info 1629 * return 1630 * 0: success 1631 * otherwise: error 1632 */ 1633 static int 1634 iscsi_op_login_set_target_info(struct spdk_iscsi_conn *conn, 1635 struct spdk_iscsi_pdu *rsp_pdu, 1636 enum session_type session_type) 1637 { 1638 char buf[MAX_TMPBUF]; 1639 const char *val; 1640 int rc = 0; 1641 struct spdk_iscsi_tgt_node *target = conn->target; 1642 1643 /* declarative parameters */ 1644 if (target != NULL) { 1645 pthread_mutex_lock(&target->mutex); 1646 if (target->alias[0] != '\0') { 1647 snprintf(buf, sizeof buf, "%s", target->alias); 1648 } else { 1649 snprintf(buf, sizeof buf, "%s", ""); 1650 } 1651 pthread_mutex_unlock(&target->mutex); 1652 rc = spdk_iscsi_param_set(conn->sess->params, "TargetAlias", buf); 1653 if (rc < 0) { 1654 SPDK_ERRLOG("iscsi_param_set() failed\n"); 1655 return SPDK_ISCSI_LOGIN_ERROR_PARAMETER; 1656 } 1657 } 1658 snprintf(buf, sizeof buf, "%s:%s,%d", conn->portal_host, conn->portal_port, 1659 conn->pg_tag); 1660 rc = spdk_iscsi_param_set(conn->sess->params, "TargetAddress", buf); 1661 if (rc < 0) { 1662 SPDK_ERRLOG("iscsi_param_set() failed\n"); 1663 return SPDK_ISCSI_LOGIN_ERROR_PARAMETER; 1664 } 1665 snprintf(buf, sizeof buf, "%d", conn->pg_tag); 1666 rc = spdk_iscsi_param_set(conn->sess->params, "TargetPortalGroupTag", buf); 1667 if (rc < 0) { 1668 SPDK_ERRLOG("iscsi_param_set() failed\n"); 1669 return SPDK_ISCSI_LOGIN_ERROR_PARAMETER; 1670 } 1671 1672 /* write in response */ 1673 if (target != NULL) { 1674 val = spdk_iscsi_param_get_val(conn->sess->params, "TargetAlias"); 1675 if (val != NULL && strlen(val) != 0) { 1676 rsp_pdu->data_segment_len = iscsi_append_param(conn, 1677 "TargetAlias", 1678 rsp_pdu->data, 1679 rsp_pdu->data_buf_len, 1680 rsp_pdu->data_segment_len); 1681 } 1682 if (session_type == SESSION_TYPE_DISCOVERY) { 1683 rsp_pdu->data_segment_len = iscsi_append_param(conn, 1684 "TargetAddress", 1685 rsp_pdu->data, 1686 rsp_pdu->data_buf_len, 1687 rsp_pdu->data_segment_len); 1688 } 1689 rsp_pdu->data_segment_len = iscsi_append_param(conn, 1690 "TargetPortalGroupTag", 1691 rsp_pdu->data, 1692 rsp_pdu->data_buf_len, 1693 rsp_pdu->data_segment_len); 1694 } 1695 1696 return rc; 1697 } 1698 1699 /* 1700 * This function is used to handle the login of iscsi initiator when there is 1701 * no session 1702 * return: 1703 * 0, success; 1704 * SPDK_ISCSI_LOGIN_ERROR_PARAMETER, parameter error; 1705 * SPDK_ISCSI_LOGIN_ERROR_RESPONSE, used to notify the login fail. 1706 */ 1707 static int 1708 iscsi_op_login_phase_none(struct spdk_iscsi_conn *conn, 1709 struct spdk_iscsi_pdu *rsp_pdu, 1710 struct iscsi_param *params, int cid) 1711 { 1712 enum session_type session_type; 1713 char initiator_port_name[MAX_INITIATOR_PORT_NAME]; 1714 struct iscsi_bhs_login_rsp *rsph; 1715 int rc = 0; 1716 rsph = (struct iscsi_bhs_login_rsp *)&rsp_pdu->bhs; 1717 1718 conn->target = NULL; 1719 conn->dev = NULL; 1720 1721 rc = iscsi_op_login_initialize_port(conn, rsp_pdu, initiator_port_name, 1722 MAX_INITIATOR_PORT_NAME, params); 1723 if (rc < 0) { 1724 return rc; 1725 } 1726 1727 rc = iscsi_op_login_session_type(conn, rsp_pdu, &session_type, params); 1728 if (rc < 0) { 1729 return rc; 1730 } 1731 1732 /* Target Name and Port */ 1733 if (session_type == SESSION_TYPE_NORMAL) { 1734 rc = iscsi_op_login_session_normal(conn, rsp_pdu, 1735 initiator_port_name, 1736 params, cid); 1737 if (rc < 0) { 1738 return rc; 1739 } 1740 1741 } else if (session_type == SESSION_TYPE_DISCOVERY) { 1742 rsph->tsih = 0; 1743 1744 /* force target flags */ 1745 pthread_mutex_lock(&g_spdk_iscsi.mutex); 1746 rc = iscsi_op_login_session_discovery_chap(conn); 1747 pthread_mutex_unlock(&g_spdk_iscsi.mutex); 1748 if (rc < 0) { 1749 return rc; 1750 } 1751 } else { 1752 SPDK_ERRLOG("unknown session type\n"); 1753 /* Missing parameter */ 1754 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1755 rsph->status_detail = ISCSI_LOGIN_MISSING_PARMS; 1756 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1757 } 1758 1759 rc = iscsi_op_login_set_conn_info(conn, rsp_pdu, initiator_port_name, 1760 session_type, cid); 1761 if (rc < 0) { 1762 return rc; 1763 } 1764 1765 /* limit conns on discovery session */ 1766 if (session_type == SESSION_TYPE_DISCOVERY) { 1767 conn->sess->MaxConnections = 1; 1768 rc = spdk_iscsi_param_set_int(conn->sess->params, 1769 "MaxConnections", 1770 conn->sess->MaxConnections); 1771 if (rc < 0) { 1772 SPDK_ERRLOG("iscsi_param_set_int() failed\n"); 1773 return SPDK_ISCSI_LOGIN_ERROR_PARAMETER; 1774 } 1775 } 1776 1777 return iscsi_op_login_set_target_info(conn, rsp_pdu, session_type); 1778 } 1779 1780 /* 1781 * The function which is used to initialize the internal response data 1782 * structure of iscsi login function. 1783 * return: 1784 * 0, success; 1785 * otherwise, error; 1786 */ 1787 static int 1788 iscsi_op_login_rsp_init(struct spdk_iscsi_conn *conn, 1789 struct spdk_iscsi_pdu *pdu, struct spdk_iscsi_pdu *rsp_pdu) 1790 { 1791 struct iscsi_bhs_login_req *reqh; 1792 struct iscsi_bhs_login_rsp *rsph; 1793 uint32_t alloc_len; 1794 1795 rsph = (struct iscsi_bhs_login_rsp *)&rsp_pdu->bhs; 1796 rsph->opcode = ISCSI_OP_LOGIN_RSP; 1797 rsph->status_class = ISCSI_CLASS_SUCCESS; 1798 rsph->status_detail = ISCSI_LOGIN_ACCEPT; 1799 rsp_pdu->data_segment_len = 0; 1800 1801 /* Default MaxRecvDataSegmentLength - RFC3720(12.12) */ 1802 if (conn->MaxRecvDataSegmentLength < 8192) { 1803 alloc_len = 8192; 1804 } else { 1805 alloc_len = conn->MaxRecvDataSegmentLength; 1806 } 1807 1808 rsp_pdu->data = calloc(1, alloc_len); 1809 if (!rsp_pdu->data) { 1810 SPDK_ERRLOG("calloc() failed for data segment\n"); 1811 rsph->status_class = ISCSI_CLASS_TARGET_ERROR; 1812 rsph->status_detail = ISCSI_LOGIN_STATUS_NO_RESOURCES; 1813 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1814 } 1815 rsp_pdu->data_buf_len = alloc_len; 1816 1817 reqh = (struct iscsi_bhs_login_req *)&pdu->bhs; 1818 rsph->flags |= (reqh->flags & ISCSI_LOGIN_TRANSIT); 1819 rsph->flags |= (reqh->flags & ISCSI_LOGIN_CONTINUE); 1820 rsph->flags |= (reqh->flags & ISCSI_LOGIN_CURRENT_STAGE_MASK); 1821 if (ISCSI_BHS_LOGIN_GET_TBIT(rsph->flags)) { 1822 rsph->flags |= (reqh->flags & ISCSI_LOGIN_NEXT_STAGE_MASK); 1823 } 1824 1825 /* We don't need to convert from network byte order. Just store it */ 1826 memcpy(&rsph->isid, reqh->isid, 6); 1827 rsph->tsih = reqh->tsih; 1828 rsph->itt = reqh->itt; 1829 rsp_pdu->cmd_sn = from_be32(&reqh->cmd_sn); 1830 1831 if (rsph->tsih) { 1832 rsph->stat_sn = reqh->exp_stat_sn; 1833 } 1834 1835 SPDK_LOGDUMP(SPDK_LOG_ISCSI, "PDU", (uint8_t *)&pdu->bhs, ISCSI_BHS_LEN); 1836 1837 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, 1838 "T=%d, C=%d, CSG=%d, NSG=%d, Min=%d, Max=%d, ITT=%x\n", 1839 ISCSI_BHS_LOGIN_GET_TBIT(rsph->flags), 1840 ISCSI_BHS_LOGIN_GET_CBIT(rsph->flags), 1841 ISCSI_BHS_LOGIN_GET_CSG(rsph->flags), 1842 ISCSI_BHS_LOGIN_GET_NSG(rsph->flags), 1843 reqh->version_min, reqh->version_max, from_be32(&rsph->itt)); 1844 1845 if (conn->sess != NULL) { 1846 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, 1847 "CmdSN=%u, ExpStatSN=%u, StatSN=%u, ExpCmdSN=%u," 1848 "MaxCmdSN=%u\n", rsp_pdu->cmd_sn, 1849 from_be32(&rsph->stat_sn), conn->StatSN, 1850 conn->sess->ExpCmdSN, 1851 conn->sess->MaxCmdSN); 1852 } else { 1853 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, 1854 "CmdSN=%u, ExpStatSN=%u, StatSN=%u\n", 1855 rsp_pdu->cmd_sn, from_be32(&rsph->stat_sn), 1856 conn->StatSN); 1857 } 1858 1859 if (ISCSI_BHS_LOGIN_GET_TBIT(rsph->flags) && 1860 ISCSI_BHS_LOGIN_GET_CBIT(rsph->flags)) { 1861 SPDK_ERRLOG("transit error\n"); 1862 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1863 rsph->status_detail = ISCSI_LOGIN_INITIATOR_ERROR; 1864 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1865 } 1866 /* make sure reqh->version_max < ISCSI_VERSION */ 1867 if (reqh->version_min > ISCSI_VERSION) { 1868 SPDK_ERRLOG("unsupported version min %d/max %d, expecting %d\n", reqh->version_min, 1869 reqh->version_max, ISCSI_VERSION); 1870 /* Unsupported version */ 1871 /* set all reserved flag to zero */ 1872 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1873 rsph->status_detail = ISCSI_LOGIN_UNSUPPORTED_VERSION; 1874 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1875 } 1876 1877 if ((ISCSI_BHS_LOGIN_GET_NSG(rsph->flags) == ISCSI_NSG_RESERVED_CODE) && 1878 ISCSI_BHS_LOGIN_GET_TBIT(rsph->flags)) { 1879 /* set NSG to zero */ 1880 rsph->flags &= ~ISCSI_LOGIN_NEXT_STAGE_MASK; 1881 /* also set other bits to zero */ 1882 rsph->flags &= ~ISCSI_LOGIN_TRANSIT; 1883 rsph->flags &= ~ISCSI_LOGIN_CURRENT_STAGE_MASK; 1884 SPDK_ERRLOG("Received reserved NSG code: %d\n", ISCSI_NSG_RESERVED_CODE); 1885 /* Initiator error */ 1886 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1887 rsph->status_detail = ISCSI_LOGIN_INITIATOR_ERROR; 1888 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1889 } 1890 1891 return 0; 1892 } 1893 1894 static int 1895 iscsi_op_login_store_incoming_params(struct spdk_iscsi_conn *conn, 1896 struct spdk_iscsi_pdu *pdu, struct spdk_iscsi_pdu *rsp_pdu, 1897 struct iscsi_param **params) 1898 { 1899 struct iscsi_bhs_login_req *reqh; 1900 struct iscsi_bhs_login_rsp *rsph; 1901 int rc; 1902 1903 reqh = (struct iscsi_bhs_login_req *)&pdu->bhs; 1904 rsph = (struct iscsi_bhs_login_rsp *)&rsp_pdu->bhs; 1905 1906 rc = spdk_iscsi_parse_params(params, pdu->data, 1907 pdu->data_segment_len, ISCSI_BHS_LOGIN_GET_CBIT(reqh->flags), 1908 &conn->partial_text_parameter); 1909 if (rc < 0) { 1910 SPDK_ERRLOG("iscsi_parse_params() failed\n"); 1911 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1912 rsph->status_detail = ISCSI_LOGIN_INITIATOR_ERROR; 1913 return SPDK_ISCSI_LOGIN_ERROR_PARAMETER; 1914 } 1915 1916 return 0; 1917 } 1918 1919 /* 1920 * This function is used to set the csg bit case in rsp 1921 * return: 1922 * 0, success 1923 * otherwise: error 1924 */ 1925 static int 1926 iscsi_op_login_rsp_handle_csg_bit(struct spdk_iscsi_conn *conn, 1927 struct spdk_iscsi_pdu *rsp_pdu, 1928 struct iscsi_param *params) 1929 { 1930 const char *auth_method; 1931 int rc; 1932 struct iscsi_bhs_login_rsp *rsph; 1933 rsph = (struct iscsi_bhs_login_rsp *)&rsp_pdu->bhs; 1934 1935 switch (ISCSI_BHS_LOGIN_GET_CSG(rsph->flags)) { 1936 case ISCSI_SECURITY_NEGOTIATION_PHASE: 1937 /* SecurityNegotiation */ 1938 auth_method = spdk_iscsi_param_get_val(conn->params, "AuthMethod"); 1939 if (auth_method == NULL) { 1940 SPDK_ERRLOG("AuthMethod is empty\n"); 1941 /* Missing parameter */ 1942 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1943 rsph->status_detail = ISCSI_LOGIN_MISSING_PARMS; 1944 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1945 } 1946 if (strcasecmp(auth_method, "None") == 0) { 1947 conn->authenticated = true; 1948 } else { 1949 rc = iscsi_auth_params(conn, params, auth_method, 1950 rsp_pdu->data, rsp_pdu->data_buf_len, 1951 rsp_pdu->data_segment_len); 1952 if (rc < 0) { 1953 SPDK_ERRLOG("iscsi_auth_params() failed\n"); 1954 /* Authentication failure */ 1955 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1956 rsph->status_detail = ISCSI_LOGIN_AUTHENT_FAIL; 1957 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1958 } 1959 rsp_pdu->data_segment_len = rc; 1960 if (!conn->authenticated) { 1961 /* not complete */ 1962 rsph->flags &= ~ISCSI_LOGIN_TRANSIT; 1963 } else { 1964 if (conn->auth.chap_phase != ISCSI_CHAP_PHASE_END) { 1965 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "CHAP phase not complete"); 1966 } 1967 } 1968 1969 SPDK_LOGDUMP(SPDK_LOG_ISCSI, "Negotiated Auth Params", 1970 rsp_pdu->data, rsp_pdu->data_segment_len); 1971 } 1972 break; 1973 1974 case ISCSI_OPERATIONAL_NEGOTIATION_PHASE: 1975 /* LoginOperationalNegotiation */ 1976 if (conn->state == ISCSI_CONN_STATE_INVALID) { 1977 if (conn->require_chap) { 1978 /* Authentication failure */ 1979 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1980 rsph->status_detail = ISCSI_LOGIN_AUTHENT_FAIL; 1981 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1982 } else { 1983 /* AuthMethod=None */ 1984 conn->authenticated = true; 1985 } 1986 } 1987 if (!conn->authenticated) { 1988 SPDK_ERRLOG("authentication error\n"); 1989 /* Authentication failure */ 1990 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 1991 rsph->status_detail = ISCSI_LOGIN_AUTHENT_FAIL; 1992 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 1993 } 1994 break; 1995 1996 case ISCSI_FULL_FEATURE_PHASE: 1997 /* FullFeaturePhase */ 1998 SPDK_ERRLOG("XXX Login in FullFeaturePhase\n"); 1999 /* Initiator error */ 2000 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 2001 rsph->status_detail = ISCSI_LOGIN_INITIATOR_ERROR; 2002 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 2003 2004 default: 2005 SPDK_ERRLOG("unknown stage\n"); 2006 /* Initiator error */ 2007 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 2008 rsph->status_detail = ISCSI_LOGIN_INITIATOR_ERROR; 2009 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 2010 } 2011 2012 return 0; 2013 } 2014 2015 /* This function is used to notify the session info 2016 * return 2017 * 0: success 2018 * otherwise: error 2019 */ 2020 static int 2021 iscsi_op_login_notify_session_info(struct spdk_iscsi_conn *conn, 2022 struct spdk_iscsi_pdu *rsp_pdu) 2023 { 2024 struct iscsi_bhs_login_rsp *rsph; 2025 2026 rsph = (struct iscsi_bhs_login_rsp *)&rsp_pdu->bhs; 2027 if (conn->sess->session_type == SESSION_TYPE_NORMAL) { 2028 /* normal session */ 2029 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Login from %s (%s) on %s tgt_node%d" 2030 " (%s:%s,%d), ISID=%"PRIx64", TSIH=%u," 2031 " CID=%u, HeaderDigest=%s, DataDigest=%s\n", 2032 conn->initiator_name, conn->initiator_addr, 2033 conn->target->name, conn->target->num, 2034 conn->portal_host, conn->portal_port, conn->pg_tag, 2035 conn->sess->isid, conn->sess->tsih, conn->cid, 2036 (spdk_iscsi_param_eq_val(conn->params, "HeaderDigest", "CRC32C") 2037 ? "on" : "off"), 2038 (spdk_iscsi_param_eq_val(conn->params, "DataDigest", "CRC32C") 2039 ? "on" : "off")); 2040 } else if (conn->sess->session_type == SESSION_TYPE_DISCOVERY) { 2041 /* discovery session */ 2042 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Login(discovery) from %s (%s) on" 2043 " (%s:%s,%d), ISID=%"PRIx64", TSIH=%u," 2044 " CID=%u, HeaderDigest=%s, DataDigest=%s\n", 2045 conn->initiator_name, conn->initiator_addr, 2046 conn->portal_host, conn->portal_port, conn->pg_tag, 2047 conn->sess->isid, conn->sess->tsih, conn->cid, 2048 (spdk_iscsi_param_eq_val(conn->params, "HeaderDigest", "CRC32C") 2049 ? "on" : "off"), 2050 (spdk_iscsi_param_eq_val(conn->params, "DataDigest", "CRC32C") 2051 ? "on" : "off")); 2052 } else { 2053 SPDK_ERRLOG("unknown session type\n"); 2054 /* Initiator error */ 2055 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 2056 rsph->status_detail = ISCSI_LOGIN_INITIATOR_ERROR; 2057 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 2058 } 2059 2060 return 0; 2061 } 2062 2063 /* 2064 * This function is to handle the tbit cases 2065 * return 2066 * 0: success 2067 * otherwise error 2068 */ 2069 static int 2070 iscsi_op_login_rsp_handle_t_bit(struct spdk_iscsi_conn *conn, 2071 struct spdk_iscsi_pdu *rsp_pdu) 2072 { 2073 int rc; 2074 struct iscsi_bhs_login_rsp *rsph; 2075 rsph = (struct iscsi_bhs_login_rsp *)&rsp_pdu->bhs; 2076 2077 switch (ISCSI_BHS_LOGIN_GET_NSG(rsph->flags)) { 2078 case ISCSI_SECURITY_NEGOTIATION_PHASE: 2079 /* SecurityNegotiation */ 2080 conn->login_phase = ISCSI_SECURITY_NEGOTIATION_PHASE; 2081 break; 2082 2083 case ISCSI_OPERATIONAL_NEGOTIATION_PHASE: 2084 /* LoginOperationalNegotiation */ 2085 conn->login_phase = ISCSI_OPERATIONAL_NEGOTIATION_PHASE; 2086 break; 2087 2088 case ISCSI_FULL_FEATURE_PHASE: 2089 /* FullFeaturePhase */ 2090 conn->login_phase = ISCSI_FULL_FEATURE_PHASE; 2091 to_be16(&rsph->tsih, conn->sess->tsih); 2092 2093 rc = iscsi_op_login_notify_session_info(conn, rsp_pdu); 2094 if (rc < 0) { 2095 return rc; 2096 } 2097 2098 conn->full_feature = 1; 2099 break; 2100 2101 default: 2102 SPDK_ERRLOG("unknown stage\n"); 2103 /* Initiator error */ 2104 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 2105 rsph->status_detail = ISCSI_LOGIN_INITIATOR_ERROR; 2106 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 2107 } 2108 2109 return 0; 2110 } 2111 2112 /* 2113 * This function is used to set the values of the internal data structure used 2114 * by spdk_iscsi_op_login function 2115 * return: 2116 * 0, used to notify the a successful login 2117 * SPDK_ISCSI_LOGIN_ERROR_RESPONSE, used to notify a failure login. 2118 */ 2119 static int 2120 iscsi_op_login_rsp_handle(struct spdk_iscsi_conn *conn, 2121 struct spdk_iscsi_pdu *rsp_pdu, struct iscsi_param **params) 2122 { 2123 int rc; 2124 struct iscsi_bhs_login_rsp *rsph; 2125 rsph = (struct iscsi_bhs_login_rsp *)&rsp_pdu->bhs; 2126 2127 /* negotiate parameters */ 2128 rc = spdk_iscsi_negotiate_params(conn, params, rsp_pdu->data, 2129 rsp_pdu->data_buf_len, 2130 rsp_pdu->data_segment_len); 2131 if (rc < 0) { 2132 /* 2133 * spdk_iscsi_negotiate_params just returns -1 on failure, 2134 * so translate this into meaningful response codes and 2135 * return values. 2136 */ 2137 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 2138 rsph->status_detail = ISCSI_LOGIN_INITIATOR_ERROR; 2139 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 2140 } 2141 2142 rsp_pdu->data_segment_len = rc; 2143 SPDK_LOGDUMP(SPDK_LOG_ISCSI, "Negotiated Params", rsp_pdu->data, rc); 2144 2145 /* handle the CSG bit case */ 2146 rc = iscsi_op_login_rsp_handle_csg_bit(conn, rsp_pdu, *params); 2147 if (rc < 0) { 2148 return rc; 2149 } 2150 2151 /* handle the T bit case */ 2152 if (ISCSI_BHS_LOGIN_GET_TBIT(rsph->flags)) { 2153 rc = iscsi_op_login_rsp_handle_t_bit(conn, rsp_pdu); 2154 } 2155 2156 return rc; 2157 } 2158 2159 static int 2160 iscsi_pdu_hdr_op_login(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 2161 { 2162 int rc; 2163 struct iscsi_bhs_login_req *reqh; 2164 struct spdk_iscsi_pdu *rsp_pdu; 2165 2166 if (conn->full_feature && conn->sess != NULL && 2167 conn->sess->session_type == SESSION_TYPE_DISCOVERY) { 2168 return SPDK_ISCSI_CONNECTION_FATAL; 2169 } 2170 2171 reqh = (struct iscsi_bhs_login_req *)&pdu->bhs; 2172 pdu->cmd_sn = from_be32(&reqh->cmd_sn); 2173 2174 /* During login processing, use the 8KB default FirstBurstLength as 2175 * our maximum data segment length value. 2176 */ 2177 if (pdu->data_segment_len > SPDK_ISCSI_FIRST_BURST_LENGTH) { 2178 return iscsi_reject(conn, pdu, ISCSI_REASON_PROTOCOL_ERROR); 2179 } 2180 2181 rsp_pdu = spdk_get_pdu(); 2182 if (rsp_pdu == NULL) { 2183 return SPDK_ISCSI_CONNECTION_FATAL; 2184 } 2185 rc = iscsi_op_login_rsp_init(conn, pdu, rsp_pdu); 2186 if (rc < 0) { 2187 iscsi_op_login_response(conn, rsp_pdu, NULL); 2188 return rc; 2189 } 2190 2191 conn->login_rsp_pdu = rsp_pdu; 2192 return 0; 2193 } 2194 2195 static int 2196 iscsi_pdu_payload_op_login(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 2197 { 2198 int rc; 2199 struct iscsi_bhs_login_req *reqh; 2200 struct spdk_iscsi_pdu *rsp_pdu; 2201 struct iscsi_param *params = NULL; 2202 int cid; 2203 2204 if (conn->login_rsp_pdu == NULL) { 2205 return 0; 2206 } 2207 2208 rsp_pdu = conn->login_rsp_pdu; 2209 2210 reqh = (struct iscsi_bhs_login_req *)&pdu->bhs; 2211 cid = from_be16(&reqh->cid); 2212 2213 rc = iscsi_op_login_store_incoming_params(conn, pdu, rsp_pdu, ¶ms); 2214 if (rc < 0) { 2215 iscsi_op_login_response(conn, rsp_pdu, NULL); 2216 return rc; 2217 } 2218 2219 if (conn->state == ISCSI_CONN_STATE_INVALID) { 2220 rc = iscsi_op_login_phase_none(conn, rsp_pdu, params, cid); 2221 if (rc == SPDK_ISCSI_LOGIN_ERROR_RESPONSE || rc == SPDK_ISCSI_LOGIN_ERROR_PARAMETER) { 2222 iscsi_op_login_response(conn, rsp_pdu, params); 2223 return rc; 2224 } 2225 } 2226 2227 rc = iscsi_op_login_rsp_handle(conn, rsp_pdu, ¶ms); 2228 if (rc == SPDK_ISCSI_LOGIN_ERROR_RESPONSE) { 2229 iscsi_op_login_response(conn, rsp_pdu, params); 2230 return rc; 2231 } 2232 2233 rc = iscsi_op_login_response(conn, rsp_pdu, params); 2234 if (rc == 0) { 2235 conn->state = ISCSI_CONN_STATE_RUNNING; 2236 if (conn->full_feature != 0) { 2237 spdk_iscsi_conn_schedule(conn); 2238 } 2239 } else { 2240 SPDK_ERRLOG("login error - connection will be destroyed\n"); 2241 } 2242 2243 return rc; 2244 } 2245 2246 static int 2247 iscsi_pdu_hdr_op_text(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 2248 { 2249 uint32_t task_tag; 2250 uint32_t ExpStatSN; 2251 int F_bit, C_bit; 2252 struct iscsi_bhs_text_req *reqh; 2253 2254 if (pdu->data_segment_len > spdk_get_max_immediate_data_size()) { 2255 SPDK_ERRLOG("data segment len(=%zu) > immediate data len(=%"PRIu32")\n", 2256 pdu->data_segment_len, spdk_get_max_immediate_data_size()); 2257 return iscsi_reject(conn, pdu, ISCSI_REASON_PROTOCOL_ERROR); 2258 } 2259 2260 reqh = (struct iscsi_bhs_text_req *)&pdu->bhs; 2261 2262 F_bit = !!(reqh->flags & ISCSI_FLAG_FINAL); 2263 C_bit = !!(reqh->flags & ISCSI_TEXT_CONTINUE); 2264 task_tag = from_be32(&reqh->itt); 2265 ExpStatSN = from_be32(&reqh->exp_stat_sn); 2266 2267 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "I=%d, F=%d, C=%d, ITT=%x, TTT=%x\n", 2268 reqh->immediate, F_bit, C_bit, task_tag, from_be32(&reqh->ttt)); 2269 2270 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, 2271 "CmdSN=%u, ExpStatSN=%u, StatSN=%u, ExpCmdSN=%u, MaxCmdSN=%u\n", 2272 pdu->cmd_sn, ExpStatSN, conn->StatSN, conn->sess->ExpCmdSN, 2273 conn->sess->MaxCmdSN); 2274 2275 if (ExpStatSN != conn->StatSN) { 2276 #if 0 2277 SPDK_ERRLOG("StatSN(%u) error\n", ExpStatSN); 2278 return -1; 2279 #else 2280 /* StarPort have a bug */ 2281 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "StatSN(%u) rewound\n", ExpStatSN); 2282 conn->StatSN = ExpStatSN; 2283 #endif 2284 } 2285 2286 if (F_bit && C_bit) { 2287 SPDK_ERRLOG("final and continue\n"); 2288 return -1; 2289 } 2290 2291 /* 2292 * If this is the first text op in a sequence, save the ITT so we can 2293 * compare it against the ITT for subsequent ops in the same sequence. 2294 * If a subsequent text op in same sequence has a different ITT, reject 2295 * that PDU. 2296 */ 2297 if (conn->sess->current_text_itt == 0xffffffffU) { 2298 conn->sess->current_text_itt = task_tag; 2299 } else if (conn->sess->current_text_itt != task_tag) { 2300 SPDK_ERRLOG("The correct itt is %u, and the current itt is %u...\n", 2301 conn->sess->current_text_itt, task_tag); 2302 return iscsi_reject(conn, pdu, ISCSI_REASON_PROTOCOL_ERROR); 2303 } 2304 2305 return 0; 2306 } 2307 2308 static int 2309 iscsi_pdu_payload_op_text(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 2310 { 2311 struct iscsi_param *params = NULL; 2312 struct spdk_iscsi_pdu *rsp_pdu; 2313 uint8_t *data; 2314 uint64_t lun; 2315 uint32_t task_tag; 2316 const char *val; 2317 int F_bit, C_bit; 2318 int data_len; 2319 int alloc_len; 2320 int rc; 2321 struct iscsi_bhs_text_req *reqh; 2322 struct iscsi_bhs_text_resp *rsph; 2323 2324 data_len = 0; 2325 alloc_len = conn->MaxRecvDataSegmentLength; 2326 2327 reqh = (struct iscsi_bhs_text_req *)&pdu->bhs; 2328 2329 F_bit = !!(reqh->flags & ISCSI_FLAG_FINAL); 2330 C_bit = !!(reqh->flags & ISCSI_TEXT_CONTINUE); 2331 lun = from_be64(&reqh->lun); 2332 task_tag = from_be32(&reqh->itt); 2333 2334 /* store incoming parameters */ 2335 rc = spdk_iscsi_parse_params(¶ms, pdu->data, pdu->data_segment_len, 2336 C_bit, &conn->partial_text_parameter); 2337 if (rc < 0) { 2338 SPDK_ERRLOG("iscsi_parse_params() failed\n"); 2339 spdk_iscsi_param_free(params); 2340 return -1; 2341 } 2342 2343 data = calloc(1, alloc_len); 2344 if (!data) { 2345 SPDK_ERRLOG("calloc() failed for data segment\n"); 2346 spdk_iscsi_param_free(params); 2347 return -ENOMEM; 2348 } 2349 2350 /* negotiate parameters */ 2351 data_len = spdk_iscsi_negotiate_params(conn, ¶ms, 2352 data, alloc_len, data_len); 2353 if (data_len < 0) { 2354 SPDK_ERRLOG("spdk_iscsi_negotiate_params() failed\n"); 2355 spdk_iscsi_param_free(params); 2356 free(data); 2357 return -1; 2358 } 2359 2360 /* sendtargets is special case */ 2361 val = spdk_iscsi_param_get_val(params, "SendTargets"); 2362 if (val != NULL) { 2363 if (spdk_iscsi_param_eq_val(conn->sess->params, 2364 "SessionType", "Discovery")) { 2365 if (strcasecmp(val, "") == 0) { 2366 val = "ALL"; 2367 } 2368 2369 data_len = spdk_iscsi_send_tgts(conn, 2370 conn->initiator_name, 2371 conn->initiator_addr, 2372 val, data, alloc_len, 2373 data_len); 2374 } else { 2375 if (strcasecmp(val, "") == 0) { 2376 val = conn->target->name; 2377 } 2378 2379 if (strcasecmp(val, "ALL") == 0) { 2380 /* not in discovery session */ 2381 data_len = iscsi_append_text(conn, 2382 "SendTargets", 2383 "Reject", data, 2384 alloc_len, data_len); 2385 } else { 2386 data_len = spdk_iscsi_send_tgts(conn, 2387 conn->initiator_name, 2388 conn->initiator_addr, 2389 val, data, alloc_len, 2390 data_len); 2391 } 2392 } 2393 } else { 2394 if (spdk_iscsi_param_eq_val(conn->sess->params, "SessionType", "Discovery")) { 2395 spdk_iscsi_param_free(params); 2396 free(data); 2397 return SPDK_ISCSI_CONNECTION_FATAL; 2398 } 2399 } 2400 2401 SPDK_LOGDUMP(SPDK_LOG_ISCSI, "Negotiated Params", data, data_len); 2402 2403 /* response PDU */ 2404 rsp_pdu = spdk_get_pdu(); 2405 if (rsp_pdu == NULL) { 2406 spdk_iscsi_param_free(params); 2407 free(data); 2408 return SPDK_ISCSI_CONNECTION_FATAL; 2409 } 2410 rsph = (struct iscsi_bhs_text_resp *)&rsp_pdu->bhs; 2411 2412 rsp_pdu->data = data; 2413 rsph->opcode = ISCSI_OP_TEXT_RSP; 2414 2415 if (F_bit) { 2416 rsph->flags |= ISCSI_FLAG_FINAL; 2417 } 2418 2419 if (C_bit) { 2420 rsph->flags |= ISCSI_TEXT_CONTINUE; 2421 } 2422 2423 DSET24(rsph->data_segment_len, data_len); 2424 to_be64(&rsph->lun, lun); 2425 to_be32(&rsph->itt, task_tag); 2426 2427 if (F_bit) { 2428 rsph->ttt = 0xffffffffU; 2429 conn->sess->current_text_itt = 0xffffffffU; 2430 } else { 2431 to_be32(&rsph->ttt, 1 + conn->id); 2432 } 2433 2434 to_be32(&rsph->stat_sn, conn->StatSN); 2435 conn->StatSN++; 2436 2437 if (reqh->immediate == 0) { 2438 conn->sess->MaxCmdSN++; 2439 } 2440 2441 to_be32(&rsph->exp_cmd_sn, conn->sess->ExpCmdSN); 2442 to_be32(&rsph->max_cmd_sn, conn->sess->MaxCmdSN); 2443 2444 spdk_iscsi_conn_write_pdu(conn, rsp_pdu); 2445 2446 /* update internal variables */ 2447 rc = spdk_iscsi_copy_param2var(conn); 2448 if (rc < 0) { 2449 SPDK_ERRLOG("spdk_iscsi_copy_param2var() failed\n"); 2450 spdk_iscsi_param_free(params); 2451 return -1; 2452 } 2453 2454 /* check value */ 2455 rc = iscsi_check_values(conn); 2456 if (rc < 0) { 2457 SPDK_ERRLOG("iscsi_check_values() failed\n"); 2458 spdk_iscsi_param_free(params); 2459 return -1; 2460 } 2461 2462 spdk_iscsi_param_free(params); 2463 return 0; 2464 } 2465 2466 static int 2467 iscsi_pdu_hdr_op_logout(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 2468 { 2469 struct spdk_iscsi_pdu *rsp_pdu; 2470 uint32_t task_tag; 2471 uint32_t ExpStatSN; 2472 int response; 2473 struct iscsi_bhs_logout_req *reqh; 2474 struct iscsi_bhs_logout_resp *rsph; 2475 uint16_t cid; 2476 2477 reqh = (struct iscsi_bhs_logout_req *)&pdu->bhs; 2478 2479 cid = from_be16(&reqh->cid); 2480 task_tag = from_be32(&reqh->itt); 2481 ExpStatSN = from_be32(&reqh->exp_stat_sn); 2482 2483 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "reason=%d, ITT=%x, cid=%d\n", 2484 reqh->reason, task_tag, cid); 2485 2486 if (reqh->reason != 0 && conn->sess->session_type == SESSION_TYPE_DISCOVERY) { 2487 SPDK_ERRLOG("only logout with close the session reason can be in discovery session"); 2488 return SPDK_ISCSI_CONNECTION_FATAL; 2489 } 2490 2491 if (conn->sess != NULL) { 2492 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, 2493 "CmdSN=%u, ExpStatSN=%u, StatSN=%u, ExpCmdSN=%u, MaxCmdSN=%u\n", 2494 pdu->cmd_sn, ExpStatSN, conn->StatSN, 2495 conn->sess->ExpCmdSN, conn->sess->MaxCmdSN); 2496 2497 if (pdu->cmd_sn != conn->sess->ExpCmdSN) { 2498 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "CmdSN(%u) might have dropped\n", pdu->cmd_sn); 2499 /* ignore error */ 2500 } 2501 } else { 2502 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "CmdSN=%u, ExpStatSN=%u, StatSN=%u\n", 2503 pdu->cmd_sn, ExpStatSN, conn->StatSN); 2504 } 2505 2506 if (ExpStatSN != conn->StatSN) { 2507 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "StatSN(%u/%u) might have dropped\n", 2508 ExpStatSN, conn->StatSN); 2509 /* ignore error */ 2510 } 2511 2512 if (conn->id == cid) { 2513 /* connection or session closed successfully */ 2514 response = 0; 2515 spdk_iscsi_conn_logout(conn); 2516 } else { 2517 response = 1; 2518 } 2519 2520 /* response PDU */ 2521 rsp_pdu = spdk_get_pdu(); 2522 if (rsp_pdu == NULL) { 2523 return SPDK_ISCSI_CONNECTION_FATAL; 2524 } 2525 rsph = (struct iscsi_bhs_logout_resp *)&rsp_pdu->bhs; 2526 rsp_pdu->data = NULL; 2527 rsph->opcode = ISCSI_OP_LOGOUT_RSP; 2528 rsph->flags |= 0x80; /* bit 0 must be 1 */ 2529 rsph->response = response; 2530 DSET24(rsph->data_segment_len, 0); 2531 to_be32(&rsph->itt, task_tag); 2532 2533 if (conn->sess != NULL) { 2534 to_be32(&rsph->stat_sn, conn->StatSN); 2535 conn->StatSN++; 2536 2537 if (conn->sess->connections == 1) { 2538 conn->sess->MaxCmdSN++; 2539 } 2540 2541 to_be32(&rsph->exp_cmd_sn, conn->sess->ExpCmdSN); 2542 to_be32(&rsph->max_cmd_sn, conn->sess->MaxCmdSN); 2543 } else { 2544 to_be32(&rsph->stat_sn, conn->StatSN); 2545 conn->StatSN++; 2546 to_be32(&rsph->exp_cmd_sn, pdu->cmd_sn); 2547 to_be32(&rsph->max_cmd_sn, pdu->cmd_sn); 2548 } 2549 2550 rsph->time_2_wait = 0; 2551 rsph->time_2_retain = 0; 2552 2553 spdk_iscsi_conn_write_pdu(conn, rsp_pdu); 2554 2555 if (conn->sess == NULL) { 2556 /* 2557 * login failed but initiator still sent a logout rather than 2558 * just closing the TCP connection. 2559 */ 2560 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Logout(login failed) from %s (%s) on" 2561 " (%s:%s,%d)\n", 2562 conn->initiator_name, conn->initiator_addr, 2563 conn->portal_host, conn->portal_port, conn->pg_tag); 2564 } else if (spdk_iscsi_param_eq_val(conn->sess->params, "SessionType", "Normal")) { 2565 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Logout from %s (%s) on %s tgt_node%d" 2566 " (%s:%s,%d), ISID=%"PRIx64", TSIH=%u," 2567 " CID=%u, HeaderDigest=%s, DataDigest=%s\n", 2568 conn->initiator_name, conn->initiator_addr, 2569 conn->target->name, conn->target->num, 2570 conn->portal_host, conn->portal_port, conn->pg_tag, 2571 conn->sess->isid, conn->sess->tsih, conn->cid, 2572 (spdk_iscsi_param_eq_val(conn->params, "HeaderDigest", "CRC32C") 2573 ? "on" : "off"), 2574 (spdk_iscsi_param_eq_val(conn->params, "DataDigest", "CRC32C") 2575 ? "on" : "off")); 2576 } else { 2577 /* discovery session */ 2578 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Logout(discovery) from %s (%s) on" 2579 " (%s:%s,%d), ISID=%"PRIx64", TSIH=%u," 2580 " CID=%u, HeaderDigest=%s, DataDigest=%s\n", 2581 conn->initiator_name, conn->initiator_addr, 2582 conn->portal_host, conn->portal_port, conn->pg_tag, 2583 conn->sess->isid, conn->sess->tsih, conn->cid, 2584 (spdk_iscsi_param_eq_val(conn->params, "HeaderDigest", "CRC32C") 2585 ? "on" : "off"), 2586 (spdk_iscsi_param_eq_val(conn->params, "DataDigest", "CRC32C") 2587 ? "on" : "off")); 2588 } 2589 2590 return 0; 2591 } 2592 2593 static int 2594 iscsi_send_r2t(struct spdk_iscsi_conn *conn, 2595 struct spdk_iscsi_task *task, int offset, 2596 int len, uint32_t transfer_tag, uint32_t *R2TSN) 2597 { 2598 struct spdk_iscsi_pdu *rsp_pdu; 2599 struct iscsi_bhs_r2t *rsph; 2600 uint64_t fmt_lun; 2601 2602 /* R2T PDU */ 2603 rsp_pdu = spdk_get_pdu(); 2604 if (rsp_pdu == NULL) { 2605 return SPDK_ISCSI_CONNECTION_FATAL; 2606 } 2607 rsph = (struct iscsi_bhs_r2t *)&rsp_pdu->bhs; 2608 rsp_pdu->data = NULL; 2609 rsph->opcode = ISCSI_OP_R2T; 2610 rsph->flags |= 0x80; /* bit 0 is default to 1 */ 2611 fmt_lun = spdk_scsi_lun_id_int_to_fmt(task->lun_id); 2612 to_be64(&rsph->lun, fmt_lun); 2613 to_be32(&rsph->itt, task->tag); 2614 to_be32(&rsph->ttt, transfer_tag); 2615 2616 to_be32(&rsph->stat_sn, conn->StatSN); 2617 to_be32(&rsph->exp_cmd_sn, conn->sess->ExpCmdSN); 2618 to_be32(&rsph->max_cmd_sn, conn->sess->MaxCmdSN); 2619 2620 to_be32(&rsph->r2t_sn, *R2TSN); 2621 *R2TSN += 1; 2622 2623 task->r2t_datasn = 0; /* next expected datasn to ack */ 2624 2625 to_be32(&rsph->buffer_offset, (uint32_t)offset); 2626 to_be32(&rsph->desired_xfer_len, (uint32_t)len); 2627 task->desired_data_transfer_length = (size_t)len; 2628 2629 /* we need to hold onto this task/cmd because until the PDU has been 2630 * written out */ 2631 rsp_pdu->task = task; 2632 task->scsi.ref++; 2633 2634 spdk_iscsi_conn_write_pdu(conn, rsp_pdu); 2635 2636 return 0; 2637 } 2638 2639 /* This function is used to remove the r2t pdu from snack_pdu_list by < task, r2t_sn> info */ 2640 static struct spdk_iscsi_pdu * 2641 iscsi_remove_r2t_pdu_from_snack_list(struct spdk_iscsi_conn *conn, 2642 struct spdk_iscsi_task *task, 2643 uint32_t r2t_sn) 2644 { 2645 struct spdk_iscsi_pdu *pdu; 2646 struct iscsi_bhs_r2t *r2t_header; 2647 2648 TAILQ_FOREACH(pdu, &conn->snack_pdu_list, tailq) { 2649 if (pdu->bhs.opcode == ISCSI_OP_R2T) { 2650 r2t_header = (struct iscsi_bhs_r2t *)&pdu->bhs; 2651 if (pdu->task == task && 2652 from_be32(&r2t_header->r2t_sn) == r2t_sn) { 2653 TAILQ_REMOVE(&conn->snack_pdu_list, pdu, tailq); 2654 return pdu; 2655 } 2656 } 2657 } 2658 2659 return NULL; 2660 } 2661 2662 /* This function is used re-send the r2t packet */ 2663 static int 2664 iscsi_send_r2t_recovery(struct spdk_iscsi_conn *conn, 2665 struct spdk_iscsi_task *task, uint32_t r2t_sn, 2666 bool send_new_r2tsn) 2667 { 2668 struct spdk_iscsi_pdu *pdu; 2669 struct iscsi_bhs_r2t *rsph; 2670 uint32_t transfer_len; 2671 uint32_t len; 2672 int rc; 2673 2674 /* remove the r2t pdu from the snack_list */ 2675 pdu = iscsi_remove_r2t_pdu_from_snack_list(conn, task, r2t_sn); 2676 if (!pdu) { 2677 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "No pdu is found\n"); 2678 return -1; 2679 } 2680 2681 /* flag 2682 * false: only need to re-send the old r2t with changing statsn 2683 * true: we send a r2t with new r2tsn 2684 */ 2685 if (!send_new_r2tsn) { 2686 to_be32(&pdu->bhs.stat_sn, conn->StatSN); 2687 spdk_iscsi_conn_write_pdu(conn, pdu); 2688 } else { 2689 rsph = (struct iscsi_bhs_r2t *)&pdu->bhs; 2690 transfer_len = from_be32(&rsph->desired_xfer_len); 2691 2692 /* still need to increase the acked r2tsn */ 2693 task->acked_r2tsn++; 2694 len = DMIN32(conn->sess->MaxBurstLength, (transfer_len - 2695 task->next_expected_r2t_offset)); 2696 2697 /* remove the old_r2t_pdu */ 2698 if (pdu->task) { 2699 spdk_iscsi_task_put(pdu->task); 2700 } 2701 spdk_put_pdu(pdu); 2702 2703 /* re-send a new r2t pdu */ 2704 rc = iscsi_send_r2t(conn, task, task->next_expected_r2t_offset, 2705 len, task->ttt, &task->R2TSN); 2706 if (rc < 0) { 2707 return SPDK_ISCSI_CONNECTION_FATAL; 2708 } 2709 } 2710 2711 return 0; 2712 } 2713 2714 static int 2715 add_transfer_task(struct spdk_iscsi_conn *conn, struct spdk_iscsi_task *task) 2716 { 2717 uint32_t transfer_len; 2718 size_t max_burst_len; 2719 size_t segment_len; 2720 size_t data_len; 2721 int len; 2722 int idx; 2723 int rc; 2724 int data_out_req; 2725 2726 transfer_len = task->scsi.transfer_len; 2727 data_len = spdk_iscsi_task_get_pdu(task)->data_segment_len; 2728 max_burst_len = conn->sess->MaxBurstLength; 2729 segment_len = SPDK_ISCSI_MAX_RECV_DATA_SEGMENT_LENGTH; 2730 data_out_req = 1 + (transfer_len - data_len - 1) / segment_len; 2731 task->data_out_cnt = data_out_req; 2732 2733 /* 2734 * If we already have too many tasks using R2T, then queue this task 2735 * and start sending R2T for it after some of the tasks using R2T/data 2736 * out buffers complete. 2737 */ 2738 if (conn->pending_r2t >= DEFAULT_MAXR2T) { 2739 TAILQ_INSERT_TAIL(&conn->queued_r2t_tasks, task, link); 2740 return 0; 2741 } 2742 2743 conn->data_out_cnt += data_out_req; 2744 idx = conn->pending_r2t++; 2745 2746 conn->outstanding_r2t_tasks[idx] = task; 2747 task->next_expected_r2t_offset = data_len; 2748 task->current_r2t_length = 0; 2749 task->R2TSN = 0; 2750 /* According to RFC3720 10.8.5, 0xffffffff is 2751 * reserved for TTT in R2T. 2752 */ 2753 if (++conn->ttt == 0xffffffffu) { 2754 conn->ttt = 0; 2755 } 2756 task->ttt = conn->ttt; 2757 2758 while (data_len != transfer_len) { 2759 len = DMIN32(max_burst_len, (transfer_len - data_len)); 2760 rc = iscsi_send_r2t(conn, task, data_len, len, 2761 task->ttt, &task->R2TSN); 2762 if (rc < 0) { 2763 SPDK_ERRLOG("iscsi_send_r2t() failed\n"); 2764 return rc; 2765 } 2766 data_len += len; 2767 task->next_r2t_offset = data_len; 2768 task->outstanding_r2t++; 2769 if (conn->sess->MaxOutstandingR2T == task->outstanding_r2t) { 2770 break; 2771 } 2772 } 2773 2774 TAILQ_INSERT_TAIL(&conn->active_r2t_tasks, task, link); 2775 return 0; 2776 } 2777 2778 /* If there are additional large writes queued for R2Ts, start them now. 2779 * This is called when a large write is just completed or when multiple LUNs 2780 * are attached and large write tasks for the specific LUN are cleared. 2781 */ 2782 static void 2783 start_queued_transfer_tasks(struct spdk_iscsi_conn *conn) 2784 { 2785 struct spdk_iscsi_task *task, *tmp; 2786 2787 TAILQ_FOREACH_SAFE(task, &conn->queued_r2t_tasks, link, tmp) { 2788 if (conn->pending_r2t < DEFAULT_MAXR2T) { 2789 TAILQ_REMOVE(&conn->queued_r2t_tasks, task, link); 2790 add_transfer_task(conn, task); 2791 } else { 2792 break; 2793 } 2794 } 2795 } 2796 2797 void spdk_del_transfer_task(struct spdk_iscsi_conn *conn, uint32_t task_tag) 2798 { 2799 struct spdk_iscsi_task *task; 2800 int i; 2801 2802 for (i = 0; i < conn->pending_r2t; i++) { 2803 if (conn->outstanding_r2t_tasks[i]->tag == task_tag) { 2804 task = conn->outstanding_r2t_tasks[i]; 2805 conn->data_out_cnt -= task->data_out_cnt; 2806 2807 conn->pending_r2t--; 2808 for (; i < conn->pending_r2t; i++) { 2809 conn->outstanding_r2t_tasks[i] = conn->outstanding_r2t_tasks[i + 1]; 2810 } 2811 conn->outstanding_r2t_tasks[conn->pending_r2t] = NULL; 2812 break; 2813 } 2814 } 2815 2816 start_queued_transfer_tasks(conn); 2817 } 2818 2819 static void 2820 del_connection_queued_task(struct spdk_iscsi_conn *conn, void *tailq, 2821 struct spdk_scsi_lun *lun, 2822 struct spdk_iscsi_pdu *pdu) 2823 { 2824 struct spdk_iscsi_task *task, *task_tmp; 2825 struct spdk_iscsi_pdu *pdu_tmp; 2826 2827 /* 2828 * Temporary used to index spdk_scsi_task related 2829 * queues of the connection. 2830 */ 2831 TAILQ_HEAD(queued_tasks, spdk_iscsi_task) *head; 2832 head = (struct queued_tasks *)tailq; 2833 2834 TAILQ_FOREACH_SAFE(task, head, link, task_tmp) { 2835 pdu_tmp = spdk_iscsi_task_get_pdu(task); 2836 if ((lun == NULL || lun == task->scsi.lun) && 2837 (pdu == NULL || SN32_LT(pdu_tmp->cmd_sn, pdu->cmd_sn))) { 2838 TAILQ_REMOVE(head, task, link); 2839 if (lun != NULL && spdk_scsi_lun_is_removing(lun)) { 2840 spdk_scsi_task_process_null_lun(&task->scsi); 2841 spdk_iscsi_task_response(conn, task); 2842 } 2843 spdk_iscsi_task_put(task); 2844 } 2845 } 2846 } 2847 2848 void spdk_clear_all_transfer_task(struct spdk_iscsi_conn *conn, 2849 struct spdk_scsi_lun *lun, 2850 struct spdk_iscsi_pdu *pdu) 2851 { 2852 int i, j, pending_r2t; 2853 struct spdk_iscsi_task *task; 2854 struct spdk_iscsi_pdu *pdu_tmp; 2855 2856 pending_r2t = conn->pending_r2t; 2857 for (i = 0; i < pending_r2t; i++) { 2858 task = conn->outstanding_r2t_tasks[i]; 2859 pdu_tmp = spdk_iscsi_task_get_pdu(task); 2860 if ((lun == NULL || lun == task->scsi.lun) && 2861 (pdu == NULL || SN32_LT(pdu_tmp->cmd_sn, pdu->cmd_sn))) { 2862 conn->outstanding_r2t_tasks[i] = NULL; 2863 task->outstanding_r2t = 0; 2864 task->next_r2t_offset = 0; 2865 task->next_expected_r2t_offset = 0; 2866 conn->data_out_cnt -= task->data_out_cnt; 2867 conn->pending_r2t--; 2868 } 2869 } 2870 2871 for (i = 0; i < pending_r2t; i++) { 2872 if (conn->outstanding_r2t_tasks[i] != NULL) { 2873 continue; 2874 } 2875 for (j = i + 1; j < pending_r2t; j++) { 2876 if (conn->outstanding_r2t_tasks[j] != NULL) { 2877 conn->outstanding_r2t_tasks[i] = conn->outstanding_r2t_tasks[j]; 2878 conn->outstanding_r2t_tasks[j] = NULL; 2879 break; 2880 } 2881 } 2882 } 2883 2884 del_connection_queued_task(conn, &conn->active_r2t_tasks, lun, pdu); 2885 del_connection_queued_task(conn, &conn->queued_r2t_tasks, lun, pdu); 2886 2887 start_queued_transfer_tasks(conn); 2888 } 2889 2890 static struct spdk_iscsi_task * 2891 get_transfer_task(struct spdk_iscsi_conn *conn, uint32_t transfer_tag) 2892 { 2893 int i; 2894 2895 for (i = 0; i < conn->pending_r2t; i++) { 2896 if (conn->outstanding_r2t_tasks[i]->ttt == transfer_tag) { 2897 return (conn->outstanding_r2t_tasks[i]); 2898 } 2899 } 2900 2901 return NULL; 2902 } 2903 2904 static int 2905 iscsi_send_datain(struct spdk_iscsi_conn *conn, 2906 struct spdk_iscsi_task *task, int datain_flag, 2907 int residual_len, int offset, int DataSN, int len) 2908 { 2909 struct spdk_iscsi_pdu *rsp_pdu; 2910 struct iscsi_bhs_data_in *rsph; 2911 uint32_t task_tag; 2912 uint32_t transfer_tag; 2913 int F_bit, U_bit, O_bit, S_bit; 2914 struct spdk_iscsi_task *primary; 2915 2916 primary = spdk_iscsi_task_get_primary(task); 2917 2918 /* DATA PDU */ 2919 rsp_pdu = spdk_get_pdu(); 2920 rsph = (struct iscsi_bhs_data_in *)&rsp_pdu->bhs; 2921 rsp_pdu->data = task->scsi.iovs[0].iov_base + offset; 2922 rsp_pdu->data_buf_len = task->scsi.iovs[0].iov_len - offset; 2923 rsp_pdu->data_from_mempool = true; 2924 2925 task_tag = task->tag; 2926 transfer_tag = 0xffffffffU; 2927 2928 F_bit = datain_flag & ISCSI_FLAG_FINAL; 2929 O_bit = datain_flag & ISCSI_DATAIN_OVERFLOW; 2930 U_bit = datain_flag & ISCSI_DATAIN_UNDERFLOW; 2931 S_bit = datain_flag & ISCSI_DATAIN_STATUS; 2932 2933 /* 2934 * we need to hold onto this task/cmd because until the 2935 * PDU has been written out 2936 */ 2937 rsp_pdu->task = task; 2938 task->scsi.ref++; 2939 2940 rsph->opcode = ISCSI_OP_SCSI_DATAIN; 2941 2942 if (F_bit) { 2943 rsph->flags |= ISCSI_FLAG_FINAL; 2944 } 2945 2946 /* we leave the A_bit clear */ 2947 2948 if (F_bit && S_bit) { 2949 if (O_bit) { 2950 rsph->flags |= ISCSI_DATAIN_OVERFLOW; 2951 } 2952 2953 if (U_bit) { 2954 rsph->flags |= ISCSI_DATAIN_UNDERFLOW; 2955 } 2956 } 2957 2958 if (S_bit) { 2959 rsph->flags |= ISCSI_DATAIN_STATUS; 2960 rsph->status = task->scsi.status; 2961 } 2962 2963 DSET24(rsph->data_segment_len, len); 2964 2965 to_be32(&rsph->itt, task_tag); 2966 to_be32(&rsph->ttt, transfer_tag); 2967 2968 if (S_bit) { 2969 to_be32(&rsph->stat_sn, conn->StatSN); 2970 conn->StatSN++; 2971 } 2972 2973 if (F_bit && S_bit && !spdk_iscsi_task_is_immediate(primary)) { 2974 conn->sess->MaxCmdSN++; 2975 } 2976 2977 to_be32(&rsph->exp_cmd_sn, conn->sess->ExpCmdSN); 2978 to_be32(&rsph->max_cmd_sn, conn->sess->MaxCmdSN); 2979 2980 to_be32(&rsph->data_sn, DataSN); 2981 2982 if (conn->sess->ErrorRecoveryLevel >= 1) { 2983 primary->datain_datasn = DataSN; 2984 } 2985 DataSN++; 2986 2987 if (task->parent) { 2988 offset += primary->scsi.data_transferred; 2989 } 2990 to_be32(&rsph->buffer_offset, (uint32_t)offset); 2991 2992 if (F_bit && S_bit) { 2993 to_be32(&rsph->res_cnt, residual_len); 2994 } 2995 2996 spdk_iscsi_conn_write_pdu(conn, rsp_pdu); 2997 2998 return DataSN; 2999 } 3000 3001 static int 3002 iscsi_transfer_in(struct spdk_iscsi_conn *conn, struct spdk_iscsi_task *task) 3003 { 3004 uint32_t DataSN; 3005 int transfer_len; 3006 int data_len; 3007 int segment_len; 3008 int offset; 3009 int residual_len = 0; 3010 int sent_status; 3011 int len; 3012 int datain_flag = 0; 3013 int datain_seq_cnt; 3014 int i; 3015 int sequence_end; 3016 struct spdk_iscsi_task *primary; 3017 3018 primary = spdk_iscsi_task_get_primary(task); 3019 segment_len = conn->MaxRecvDataSegmentLength; 3020 data_len = task->scsi.data_transferred; 3021 transfer_len = task->scsi.length; 3022 3023 if (task->scsi.status != SPDK_SCSI_STATUS_GOOD) { 3024 if (task != primary) { 3025 conn->data_in_cnt--; 3026 /* Handle the case when primary task return success but the subtask failed */ 3027 if (primary->bytes_completed == primary->scsi.transfer_len && 3028 primary->scsi.status == SPDK_SCSI_STATUS_GOOD) { 3029 conn->data_in_cnt--; 3030 } 3031 } else { 3032 /* handle the case that it is a primary task which has subtasks */ 3033 if (primary->scsi.transfer_len != primary->scsi.length) { 3034 conn->data_in_cnt--; 3035 } 3036 } 3037 3038 return 0; 3039 } 3040 3041 if (data_len < transfer_len) { 3042 /* underflow */ 3043 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Underflow %u/%u\n", data_len, transfer_len); 3044 residual_len = transfer_len - data_len; 3045 transfer_len = data_len; 3046 datain_flag |= ISCSI_DATAIN_UNDERFLOW; 3047 } else if (data_len > transfer_len) { 3048 /* overflow */ 3049 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Overflow %u/%u\n", data_len, transfer_len); 3050 residual_len = data_len - transfer_len; 3051 datain_flag |= ISCSI_DATAIN_OVERFLOW; 3052 } else { 3053 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Transfer %u\n", transfer_len); 3054 residual_len = 0; 3055 } 3056 3057 DataSN = primary->datain_datasn; 3058 sent_status = 0; 3059 3060 /* calculate the number of sequences for all data-in pdus */ 3061 datain_seq_cnt = 1 + ((transfer_len - 1) / (int)conn->sess->MaxBurstLength); 3062 for (i = 0; i < datain_seq_cnt; i++) { 3063 offset = i * conn->sess->MaxBurstLength; 3064 sequence_end = DMIN32(((i + 1) * conn->sess->MaxBurstLength), 3065 transfer_len); 3066 3067 /* send data splitted by segment_len */ 3068 for (; offset < sequence_end; offset += segment_len) { 3069 len = DMIN32(segment_len, (sequence_end - offset)); 3070 3071 datain_flag &= ~ISCSI_FLAG_FINAL; 3072 datain_flag &= ~ISCSI_DATAIN_STATUS; 3073 3074 if (offset + len == sequence_end) { 3075 /* last PDU in a sequence */ 3076 datain_flag |= ISCSI_FLAG_FINAL; 3077 if (task->scsi.sense_data_len == 0) { 3078 /* The last pdu in all data-in pdus */ 3079 if ((offset + len) == transfer_len && 3080 (primary->bytes_completed == primary->scsi.transfer_len)) { 3081 datain_flag |= ISCSI_DATAIN_STATUS; 3082 sent_status = 1; 3083 } 3084 } 3085 } 3086 3087 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Transfer=%d, Offset=%d, Len=%d\n", 3088 sequence_end, offset, len); 3089 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "StatSN=%u, DataSN=%u, Offset=%u, Len=%d\n", 3090 conn->StatSN, DataSN, offset, len); 3091 3092 DataSN = iscsi_send_datain(conn, task, datain_flag, residual_len, 3093 offset, DataSN, len); 3094 } 3095 } 3096 3097 if (task != primary) { 3098 primary->scsi.data_transferred += task->scsi.data_transferred; 3099 } 3100 primary->datain_datasn = DataSN; 3101 3102 return sent_status; 3103 } 3104 3105 void spdk_iscsi_task_response(struct spdk_iscsi_conn *conn, 3106 struct spdk_iscsi_task *task) 3107 { 3108 struct spdk_iscsi_pdu *rsp_pdu; 3109 struct iscsi_bhs_scsi_resp *rsph; 3110 uint32_t task_tag; 3111 uint32_t transfer_len; 3112 size_t residual_len; 3113 size_t data_len; 3114 int O_bit, U_bit; 3115 int rc; 3116 struct spdk_iscsi_task *primary; 3117 3118 primary = spdk_iscsi_task_get_primary(task); 3119 3120 transfer_len = primary->scsi.transfer_len; 3121 task_tag = task->tag; 3122 3123 /* transfer data from logical unit */ 3124 /* (direction is view of initiator side) */ 3125 if (spdk_iscsi_task_is_read(primary)) { 3126 rc = iscsi_transfer_in(conn, task); 3127 if (rc > 0) { 3128 /* sent status by last DATAIN PDU */ 3129 return; 3130 } 3131 3132 if (primary->bytes_completed != primary->scsi.transfer_len) { 3133 return; 3134 } 3135 } 3136 3137 O_bit = U_bit = 0; 3138 residual_len = 0; 3139 data_len = primary->scsi.data_transferred; 3140 3141 if ((transfer_len != 0) && 3142 (task->scsi.status == SPDK_SCSI_STATUS_GOOD)) { 3143 if (data_len < transfer_len) { 3144 /* underflow */ 3145 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Underflow %zu/%u\n", data_len, transfer_len); 3146 residual_len = transfer_len - data_len; 3147 U_bit = 1; 3148 } else if (data_len > transfer_len) { 3149 /* overflow */ 3150 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Overflow %zu/%u\n", data_len, transfer_len); 3151 residual_len = data_len - transfer_len; 3152 O_bit = 1; 3153 } else { 3154 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Transfer %u\n", transfer_len); 3155 } 3156 } 3157 3158 /* response PDU */ 3159 rsp_pdu = spdk_get_pdu(); 3160 assert(rsp_pdu != NULL); 3161 rsph = (struct iscsi_bhs_scsi_resp *)&rsp_pdu->bhs; 3162 assert(task->scsi.sense_data_len <= sizeof(rsp_pdu->sense.data)); 3163 memcpy(rsp_pdu->sense.data, task->scsi.sense_data, task->scsi.sense_data_len); 3164 to_be16(&rsp_pdu->sense.length, task->scsi.sense_data_len); 3165 rsp_pdu->data = (uint8_t *)&rsp_pdu->sense; 3166 rsp_pdu->data_from_mempool = true; 3167 3168 /* 3169 * we need to hold onto this task/cmd because until the 3170 * PDU has been written out 3171 */ 3172 rsp_pdu->task = task; 3173 task->scsi.ref++; 3174 3175 rsph->opcode = ISCSI_OP_SCSI_RSP; 3176 rsph->flags |= 0x80; /* bit 0 is default to 1 */ 3177 3178 if (O_bit) { 3179 rsph->flags |= ISCSI_SCSI_OVERFLOW; 3180 } 3181 3182 if (U_bit) { 3183 rsph->flags |= ISCSI_SCSI_UNDERFLOW; 3184 } 3185 3186 rsph->status = task->scsi.status; 3187 if (task->scsi.sense_data_len) { 3188 /* SenseLength (2 bytes) + SenseData */ 3189 DSET24(rsph->data_segment_len, 2 + task->scsi.sense_data_len); 3190 } 3191 to_be32(&rsph->itt, task_tag); 3192 3193 to_be32(&rsph->stat_sn, conn->StatSN); 3194 conn->StatSN++; 3195 3196 if (!spdk_iscsi_task_is_immediate(primary)) { 3197 conn->sess->MaxCmdSN++; 3198 } 3199 3200 to_be32(&rsph->exp_cmd_sn, conn->sess->ExpCmdSN); 3201 to_be32(&rsph->max_cmd_sn, conn->sess->MaxCmdSN); 3202 3203 to_be32(&rsph->bi_read_res_cnt, 0); 3204 to_be32(&rsph->res_cnt, residual_len); 3205 3206 spdk_iscsi_conn_write_pdu(conn, rsp_pdu); 3207 } 3208 3209 /* 3210 * This function compare the input pdu's bhs with the pdu's bhs associated by 3211 * active_r2t_tasks and queued_r2t_tasks in a connection 3212 */ 3213 static bool 3214 iscsi_compare_pdu_bhs_within_existed_r2t_tasks(struct spdk_iscsi_conn *conn, 3215 struct spdk_iscsi_pdu *pdu) 3216 { 3217 struct spdk_iscsi_task *task; 3218 3219 TAILQ_FOREACH(task, &conn->active_r2t_tasks, link) { 3220 if (!memcmp(&pdu->bhs, spdk_iscsi_task_get_bhs(task), ISCSI_BHS_LEN)) { 3221 return true; 3222 } 3223 } 3224 3225 TAILQ_FOREACH(task, &conn->queued_r2t_tasks, link) { 3226 if (!memcmp(&pdu->bhs, spdk_iscsi_task_get_bhs(task), ISCSI_BHS_LEN)) { 3227 return true; 3228 } 3229 } 3230 3231 return false; 3232 } 3233 3234 static void 3235 iscsi_queue_task(struct spdk_iscsi_conn *conn, struct spdk_iscsi_task *task) 3236 { 3237 spdk_trace_record(TRACE_ISCSI_TASK_QUEUE, conn->id, task->scsi.length, 3238 (uintptr_t)task, (uintptr_t)task->pdu); 3239 task->is_queued = true; 3240 spdk_scsi_dev_queue_task(conn->dev, &task->scsi); 3241 } 3242 3243 int spdk_iscsi_conn_handle_queued_datain_tasks(struct spdk_iscsi_conn *conn) 3244 { 3245 struct spdk_iscsi_task *task; 3246 3247 while (!TAILQ_EMPTY(&conn->queued_datain_tasks) && 3248 conn->data_in_cnt < MAX_LARGE_DATAIN_PER_CONNECTION) { 3249 task = TAILQ_FIRST(&conn->queued_datain_tasks); 3250 assert(task->current_datain_offset <= task->scsi.transfer_len); 3251 3252 if (task->current_datain_offset == 0) { 3253 task->scsi.lun = spdk_scsi_dev_get_lun(conn->dev, task->lun_id); 3254 if (task->scsi.lun == NULL) { 3255 TAILQ_REMOVE(&conn->queued_datain_tasks, task, link); 3256 spdk_scsi_task_process_null_lun(&task->scsi); 3257 spdk_iscsi_task_cpl(&task->scsi); 3258 return 0; 3259 } 3260 task->current_datain_offset = task->scsi.length; 3261 conn->data_in_cnt++; 3262 iscsi_queue_task(conn, task); 3263 continue; 3264 } 3265 if (task->current_datain_offset < task->scsi.transfer_len) { 3266 struct spdk_iscsi_task *subtask; 3267 uint32_t remaining_size = 0; 3268 3269 remaining_size = task->scsi.transfer_len - task->current_datain_offset; 3270 subtask = spdk_iscsi_task_get(conn, task, spdk_iscsi_task_cpl); 3271 assert(subtask != NULL); 3272 subtask->scsi.offset = task->current_datain_offset; 3273 subtask->scsi.length = DMIN32(SPDK_BDEV_LARGE_BUF_MAX_SIZE, remaining_size); 3274 spdk_scsi_task_set_data(&subtask->scsi, NULL, 0); 3275 task->current_datain_offset += subtask->scsi.length; 3276 conn->data_in_cnt++; 3277 3278 task->scsi.lun = spdk_scsi_dev_get_lun(conn->dev, task->lun_id); 3279 if (task->scsi.lun == NULL) { 3280 /* Remove the primary task from the list if this is the last subtask */ 3281 if (task->current_datain_offset == task->scsi.transfer_len) { 3282 TAILQ_REMOVE(&conn->queued_datain_tasks, task, link); 3283 } 3284 subtask->scsi.transfer_len = subtask->scsi.length; 3285 spdk_scsi_task_process_null_lun(&subtask->scsi); 3286 spdk_iscsi_task_cpl(&subtask->scsi); 3287 return 0; 3288 } 3289 3290 iscsi_queue_task(conn, subtask); 3291 } 3292 if (task->current_datain_offset == task->scsi.transfer_len) { 3293 TAILQ_REMOVE(&conn->queued_datain_tasks, task, link); 3294 } 3295 } 3296 return 0; 3297 } 3298 3299 static int 3300 iscsi_pdu_payload_op_scsi_read(struct spdk_iscsi_conn *conn, struct spdk_iscsi_task *task) 3301 { 3302 int32_t remaining_size; 3303 3304 TAILQ_INIT(&task->subtask_list); 3305 task->parent = NULL; 3306 task->scsi.offset = 0; 3307 task->scsi.length = DMIN32(SPDK_BDEV_LARGE_BUF_MAX_SIZE, task->scsi.transfer_len); 3308 spdk_scsi_task_set_data(&task->scsi, NULL, 0); 3309 3310 remaining_size = task->scsi.transfer_len - task->scsi.length; 3311 task->current_datain_offset = 0; 3312 3313 if (remaining_size == 0) { 3314 iscsi_queue_task(conn, task); 3315 return 0; 3316 } 3317 3318 TAILQ_INSERT_TAIL(&conn->queued_datain_tasks, task, link); 3319 3320 return spdk_iscsi_conn_handle_queued_datain_tasks(conn); 3321 } 3322 3323 static int 3324 iscsi_pdu_payload_op_scsi_write(struct spdk_iscsi_conn *conn, struct spdk_iscsi_task *task) 3325 { 3326 struct spdk_iscsi_pdu *pdu; 3327 struct iscsi_bhs_scsi_req *reqh; 3328 uint32_t transfer_len; 3329 uint32_t scsi_data_len; 3330 int rc; 3331 3332 pdu = spdk_iscsi_task_get_pdu(task); 3333 reqh = (struct iscsi_bhs_scsi_req *)&pdu->bhs; 3334 3335 transfer_len = task->scsi.transfer_len; 3336 3337 if (spdk_likely(!pdu->dif_insert_or_strip)) { 3338 scsi_data_len = pdu->data_segment_len; 3339 } else { 3340 scsi_data_len = pdu->data_buf_len; 3341 } 3342 3343 if (reqh->final_bit && 3344 pdu->data_segment_len < transfer_len) { 3345 /* needs R2T */ 3346 rc = add_transfer_task(conn, task); 3347 if (rc < 0) { 3348 SPDK_ERRLOG("add_transfer_task() failed\n"); 3349 spdk_iscsi_task_put(task); 3350 return SPDK_ISCSI_CONNECTION_FATAL; 3351 } 3352 3353 /* Non-immediate writes */ 3354 if (pdu->data_segment_len == 0) { 3355 return 0; 3356 } else { 3357 /* we are doing the first partial write task */ 3358 task->scsi.ref++; 3359 spdk_scsi_task_set_data(&task->scsi, pdu->data, scsi_data_len); 3360 task->scsi.length = pdu->data_segment_len; 3361 } 3362 } 3363 3364 if (pdu->data_segment_len == transfer_len) { 3365 /* we are doing small writes with no R2T */ 3366 spdk_scsi_task_set_data(&task->scsi, pdu->data, scsi_data_len); 3367 task->scsi.length = transfer_len; 3368 } 3369 3370 iscsi_queue_task(conn, task); 3371 return 0; 3372 } 3373 3374 static int 3375 iscsi_pdu_hdr_op_scsi(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 3376 { 3377 struct spdk_iscsi_task *task; 3378 struct spdk_scsi_dev *dev; 3379 uint8_t *cdb; 3380 uint64_t lun; 3381 uint32_t task_tag; 3382 uint32_t data_len; 3383 uint32_t transfer_len; 3384 int R_bit, W_bit; 3385 int lun_i; 3386 struct iscsi_bhs_scsi_req *reqh; 3387 3388 if (conn->sess->session_type != SESSION_TYPE_NORMAL) { 3389 SPDK_ERRLOG("ISCSI_OP_SCSI not allowed in discovery and invalid session\n"); 3390 return SPDK_ISCSI_CONNECTION_FATAL; 3391 } 3392 3393 reqh = (struct iscsi_bhs_scsi_req *)&pdu->bhs; 3394 3395 R_bit = reqh->read_bit; 3396 W_bit = reqh->write_bit; 3397 lun = from_be64(&reqh->lun); 3398 task_tag = from_be32(&reqh->itt); 3399 data_len = pdu->data_segment_len; 3400 transfer_len = from_be32(&reqh->expected_data_xfer_len); 3401 cdb = reqh->cdb; 3402 3403 SPDK_LOGDUMP(SPDK_LOG_ISCSI, "CDB", cdb, 16); 3404 3405 task = spdk_iscsi_task_get(conn, NULL, spdk_iscsi_task_cpl); 3406 if (!task) { 3407 SPDK_ERRLOG("Unable to acquire task\n"); 3408 return SPDK_ISCSI_CONNECTION_FATAL; 3409 } 3410 3411 spdk_iscsi_task_associate_pdu(task, pdu); 3412 lun_i = spdk_scsi_lun_id_fmt_to_int(lun); 3413 task->lun_id = lun_i; 3414 dev = conn->dev; 3415 task->scsi.lun = spdk_scsi_dev_get_lun(dev, lun_i); 3416 3417 if ((R_bit != 0) && (W_bit != 0)) { 3418 SPDK_ERRLOG("Bidirectional CDB is not supported\n"); 3419 spdk_iscsi_task_put(task); 3420 return SPDK_ISCSI_CONNECTION_FATAL; 3421 } 3422 3423 task->scsi.cdb = cdb; 3424 task->tag = task_tag; 3425 task->scsi.transfer_len = transfer_len; 3426 task->scsi.target_port = conn->target_port; 3427 task->scsi.initiator_port = conn->initiator_port; 3428 task->parent = NULL; 3429 task->rsp_scsi_status = SPDK_SCSI_STATUS_GOOD; 3430 3431 if (task->scsi.lun == NULL) { 3432 spdk_scsi_task_process_null_lun(&task->scsi); 3433 spdk_iscsi_task_cpl(&task->scsi); 3434 return 0; 3435 } 3436 3437 /* no bi-directional support */ 3438 if (R_bit) { 3439 task->scsi.dxfer_dir = SPDK_SCSI_DIR_FROM_DEV; 3440 } else if (W_bit) { 3441 task->scsi.dxfer_dir = SPDK_SCSI_DIR_TO_DEV; 3442 3443 if ((conn->sess->ErrorRecoveryLevel >= 1) && 3444 (iscsi_compare_pdu_bhs_within_existed_r2t_tasks(conn, pdu))) { 3445 spdk_iscsi_task_response(conn, task); 3446 spdk_iscsi_task_put(task); 3447 return 0; 3448 } 3449 3450 if (pdu->data_segment_len > spdk_get_max_immediate_data_size()) { 3451 SPDK_ERRLOG("data segment len(=%zu) > immediate data len(=%"PRIu32")\n", 3452 pdu->data_segment_len, spdk_get_max_immediate_data_size()); 3453 spdk_iscsi_task_put(task); 3454 return iscsi_reject(conn, pdu, ISCSI_REASON_PROTOCOL_ERROR); 3455 } 3456 3457 if (pdu->data_segment_len > transfer_len) { 3458 SPDK_ERRLOG("data segment len(=%zu) > task transfer len(=%d)\n", 3459 pdu->data_segment_len, transfer_len); 3460 spdk_iscsi_task_put(task); 3461 return iscsi_reject(conn, pdu, ISCSI_REASON_PROTOCOL_ERROR); 3462 } 3463 3464 /* check the ImmediateData and also pdu->data_segment_len */ 3465 if ((!conn->sess->ImmediateData && (data_len > 0)) || 3466 (data_len > conn->sess->FirstBurstLength)) { 3467 spdk_iscsi_task_put(task); 3468 return iscsi_reject(conn, pdu, ISCSI_REASON_PROTOCOL_ERROR); 3469 } 3470 } else { 3471 /* neither R nor W bit set */ 3472 task->scsi.dxfer_dir = SPDK_SCSI_DIR_NONE; 3473 if (transfer_len > 0) { 3474 spdk_iscsi_task_put(task); 3475 SPDK_ERRLOG("Reject scsi cmd with EDTL > 0 but (R | W) == 0\n"); 3476 return iscsi_reject(conn, pdu, ISCSI_REASON_INVALID_PDU_FIELD); 3477 } 3478 } 3479 3480 pdu->task = task; 3481 return 0; 3482 } 3483 3484 static int 3485 iscsi_pdu_payload_op_scsi(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 3486 { 3487 struct spdk_iscsi_task *task; 3488 3489 if (pdu->task == NULL) { 3490 return 0; 3491 } 3492 3493 task = pdu->task; 3494 3495 if (spdk_scsi_dev_get_lun(conn->dev, task->lun_id) == NULL) { 3496 spdk_scsi_task_process_null_lun(&task->scsi); 3497 spdk_iscsi_task_cpl(&task->scsi); 3498 return 0; 3499 } 3500 3501 switch (task->scsi.dxfer_dir) { 3502 case SPDK_SCSI_DIR_FROM_DEV: 3503 return iscsi_pdu_payload_op_scsi_read(conn, task); 3504 case SPDK_SCSI_DIR_TO_DEV: 3505 return iscsi_pdu_payload_op_scsi_write(conn, task); 3506 case SPDK_SCSI_DIR_NONE: 3507 iscsi_queue_task(conn, task); 3508 return 0; 3509 default: 3510 assert(false); 3511 spdk_iscsi_task_put(task); 3512 break; 3513 } 3514 3515 return SPDK_ISCSI_CONNECTION_FATAL; 3516 } 3517 3518 static void 3519 abort_transfer_task_in_task_mgmt_resp(struct spdk_iscsi_conn *conn, 3520 struct spdk_iscsi_task *task) 3521 { 3522 struct spdk_iscsi_pdu *pdu; 3523 3524 pdu = spdk_iscsi_task_get_pdu(task); 3525 3526 switch (task->scsi.function) { 3527 /* abort task identified by Reference Task Tag field */ 3528 case ISCSI_TASK_FUNC_ABORT_TASK: 3529 spdk_del_transfer_task(conn, task->scsi.abort_id); 3530 break; 3531 3532 /* abort all tasks issued via this session on the LUN */ 3533 case ISCSI_TASK_FUNC_ABORT_TASK_SET: 3534 spdk_clear_all_transfer_task(conn, task->scsi.lun, pdu); 3535 break; 3536 3537 case ISCSI_TASK_FUNC_LOGICAL_UNIT_RESET: 3538 spdk_clear_all_transfer_task(conn, task->scsi.lun, pdu); 3539 break; 3540 } 3541 } 3542 3543 void 3544 spdk_iscsi_task_mgmt_response(struct spdk_iscsi_conn *conn, 3545 struct spdk_iscsi_task *task) 3546 { 3547 struct spdk_iscsi_pdu *rsp_pdu; 3548 struct iscsi_bhs_task_req *reqh; 3549 struct iscsi_bhs_task_resp *rsph; 3550 3551 if (task->pdu == NULL) { 3552 /* 3553 * This was an internally generated task management command, 3554 * usually from LUN cleanup when a connection closes. 3555 */ 3556 return; 3557 } 3558 3559 reqh = (struct iscsi_bhs_task_req *)&task->pdu->bhs; 3560 /* response PDU */ 3561 rsp_pdu = spdk_get_pdu(); 3562 rsph = (struct iscsi_bhs_task_resp *)&rsp_pdu->bhs; 3563 rsph->opcode = ISCSI_OP_TASK_RSP; 3564 rsph->flags |= 0x80; /* bit 0 default to 1 */ 3565 switch (task->scsi.response) { 3566 case SPDK_SCSI_TASK_MGMT_RESP_COMPLETE: 3567 abort_transfer_task_in_task_mgmt_resp(conn, task); 3568 rsph->response = ISCSI_TASK_FUNC_RESP_COMPLETE; 3569 break; 3570 case SPDK_SCSI_TASK_MGMT_RESP_SUCCESS: 3571 abort_transfer_task_in_task_mgmt_resp(conn, task); 3572 rsph->response = ISCSI_TASK_FUNC_RESP_COMPLETE; 3573 break; 3574 case SPDK_SCSI_TASK_MGMT_RESP_REJECT: 3575 rsph->response = ISCSI_TASK_FUNC_REJECTED; 3576 break; 3577 case SPDK_SCSI_TASK_MGMT_RESP_INVALID_LUN: 3578 rsph->response = ISCSI_TASK_FUNC_RESP_LUN_NOT_EXIST; 3579 break; 3580 case SPDK_SCSI_TASK_MGMT_RESP_TARGET_FAILURE: 3581 rsph->response = ISCSI_TASK_FUNC_REJECTED; 3582 break; 3583 case SPDK_SCSI_TASK_MGMT_RESP_REJECT_FUNC_NOT_SUPPORTED: 3584 rsph->response = ISCSI_TASK_FUNC_RESP_FUNC_NOT_SUPPORTED; 3585 break; 3586 } 3587 rsph->itt = reqh->itt; 3588 3589 to_be32(&rsph->stat_sn, conn->StatSN); 3590 conn->StatSN++; 3591 3592 if (reqh->immediate == 0) { 3593 conn->sess->MaxCmdSN++; 3594 } 3595 3596 to_be32(&rsph->exp_cmd_sn, conn->sess->ExpCmdSN); 3597 to_be32(&rsph->max_cmd_sn, conn->sess->MaxCmdSN); 3598 3599 spdk_iscsi_conn_write_pdu(conn, rsp_pdu); 3600 } 3601 3602 static int 3603 _iscsi_conn_abort_queued_datain_task(struct spdk_iscsi_conn *conn, 3604 struct spdk_iscsi_task *task) 3605 { 3606 struct spdk_iscsi_task *subtask; 3607 uint32_t remaining_size; 3608 3609 while (conn->data_in_cnt < MAX_LARGE_DATAIN_PER_CONNECTION) { 3610 assert(task->current_datain_offset <= task->scsi.transfer_len); 3611 3612 /* If no IO is submitted yet, just abort the primary task. */ 3613 if (task->current_datain_offset == 0) { 3614 TAILQ_REMOVE(&conn->queued_datain_tasks, task, link); 3615 spdk_scsi_task_process_abort(&task->scsi); 3616 spdk_iscsi_task_cpl(&task->scsi); 3617 return 0; 3618 } 3619 3620 /* If any IO is submitted already, abort all subtasks by repetition. */ 3621 if (task->current_datain_offset < task->scsi.transfer_len) { 3622 remaining_size = task->scsi.transfer_len - task->current_datain_offset; 3623 subtask = spdk_iscsi_task_get(conn, task, spdk_iscsi_task_cpl); 3624 assert(subtask != NULL); 3625 subtask->scsi.offset = task->current_datain_offset; 3626 subtask->scsi.length = DMIN32(SPDK_BDEV_LARGE_BUF_MAX_SIZE, remaining_size); 3627 spdk_scsi_task_set_data(&subtask->scsi, NULL, 0); 3628 task->current_datain_offset += subtask->scsi.length; 3629 conn->data_in_cnt++; 3630 3631 subtask->scsi.transfer_len = subtask->scsi.length; 3632 spdk_scsi_task_process_abort(&subtask->scsi); 3633 spdk_iscsi_task_cpl(&subtask->scsi); 3634 } 3635 3636 /* Remove the primary task from the list if this is the last subtask */ 3637 if (task->current_datain_offset == task->scsi.transfer_len) { 3638 TAILQ_REMOVE(&conn->queued_datain_tasks, task, link); 3639 return 0; 3640 } 3641 } 3642 3643 return -1; 3644 } 3645 3646 static int 3647 iscsi_conn_abort_queued_datain_task(struct spdk_iscsi_conn *conn, 3648 uint32_t ref_task_tag) 3649 { 3650 struct spdk_iscsi_task *task; 3651 3652 TAILQ_FOREACH(task, &conn->queued_datain_tasks, link) { 3653 if (task->tag == ref_task_tag) { 3654 return _iscsi_conn_abort_queued_datain_task(conn, task); 3655 } 3656 } 3657 3658 return 0; 3659 } 3660 3661 static int 3662 iscsi_conn_abort_queued_datain_tasks(struct spdk_iscsi_conn *conn, 3663 struct spdk_scsi_lun *lun, 3664 struct spdk_iscsi_pdu *pdu) 3665 { 3666 struct spdk_iscsi_task *task, *task_tmp; 3667 struct spdk_iscsi_pdu *pdu_tmp; 3668 int rc; 3669 3670 TAILQ_FOREACH_SAFE(task, &conn->queued_datain_tasks, link, task_tmp) { 3671 pdu_tmp = spdk_iscsi_task_get_pdu(task); 3672 if ((lun == NULL || lun == task->scsi.lun) && 3673 (pdu == NULL || (SN32_LT(pdu_tmp->cmd_sn, pdu->cmd_sn)))) { 3674 rc = _iscsi_conn_abort_queued_datain_task(conn, task); 3675 if (rc != 0) { 3676 return rc; 3677 } 3678 } 3679 } 3680 3681 return 0; 3682 } 3683 3684 static void 3685 iscsi_queue_mgmt_task(struct spdk_iscsi_conn *conn, struct spdk_iscsi_task *task) 3686 { 3687 struct spdk_scsi_lun *lun; 3688 3689 lun = spdk_scsi_dev_get_lun(conn->dev, task->lun_id); 3690 if (lun == NULL) { 3691 task->scsi.response = SPDK_SCSI_TASK_MGMT_RESP_INVALID_LUN; 3692 spdk_iscsi_task_mgmt_response(conn, task); 3693 spdk_iscsi_task_put(task); 3694 return; 3695 } 3696 3697 spdk_scsi_dev_queue_mgmt_task(conn->dev, &task->scsi); 3698 } 3699 3700 static int 3701 _iscsi_op_abort_task(void *arg) 3702 { 3703 struct spdk_iscsi_task *task = arg; 3704 int rc; 3705 3706 rc = iscsi_conn_abort_queued_datain_task(task->conn, task->scsi.abort_id); 3707 if (rc != 0) { 3708 return 1; 3709 } 3710 3711 spdk_poller_unregister(&task->mgmt_poller); 3712 iscsi_queue_mgmt_task(task->conn, task); 3713 return 1; 3714 } 3715 3716 static void 3717 iscsi_op_abort_task(struct spdk_iscsi_task *task, uint32_t ref_task_tag) 3718 { 3719 task->scsi.abort_id = ref_task_tag; 3720 task->scsi.function = SPDK_SCSI_TASK_FUNC_ABORT_TASK; 3721 task->mgmt_poller = spdk_poller_register(_iscsi_op_abort_task, task, 10); 3722 } 3723 3724 static int 3725 _iscsi_op_abort_task_set(void *arg) 3726 { 3727 struct spdk_iscsi_task *task = arg; 3728 int rc; 3729 3730 rc = iscsi_conn_abort_queued_datain_tasks(task->conn, task->scsi.lun, 3731 task->pdu); 3732 if (rc != 0) { 3733 return 1; 3734 } 3735 3736 spdk_poller_unregister(&task->mgmt_poller); 3737 iscsi_queue_mgmt_task(task->conn, task); 3738 return 1; 3739 } 3740 3741 void 3742 spdk_iscsi_op_abort_task_set(struct spdk_iscsi_task *task, uint8_t function) 3743 { 3744 task->scsi.function = function; 3745 task->mgmt_poller = spdk_poller_register(_iscsi_op_abort_task_set, task, 10); 3746 } 3747 3748 static int 3749 iscsi_pdu_hdr_op_task(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 3750 { 3751 struct iscsi_bhs_task_req *reqh; 3752 uint64_t lun; 3753 uint32_t task_tag; 3754 uint32_t ref_task_tag; 3755 uint8_t function; 3756 int lun_i; 3757 struct spdk_iscsi_task *task; 3758 struct spdk_scsi_dev *dev; 3759 3760 if (conn->sess->session_type != SESSION_TYPE_NORMAL) { 3761 SPDK_ERRLOG("ISCSI_OP_TASK not allowed in discovery and invalid session\n"); 3762 return SPDK_ISCSI_CONNECTION_FATAL; 3763 } 3764 3765 reqh = (struct iscsi_bhs_task_req *)&pdu->bhs; 3766 function = reqh->flags & ISCSI_TASK_FUNCTION_MASK; 3767 lun = from_be64(&reqh->lun); 3768 task_tag = from_be32(&reqh->itt); 3769 ref_task_tag = from_be32(&reqh->ref_task_tag); 3770 3771 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "I=%d, func=%d, ITT=%x, ref TT=%x, LUN=0x%16.16"PRIx64"\n", 3772 reqh->immediate, function, task_tag, ref_task_tag, lun); 3773 3774 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "StatSN=%u, ExpCmdSN=%u, MaxCmdSN=%u\n", 3775 conn->StatSN, conn->sess->ExpCmdSN, conn->sess->MaxCmdSN); 3776 3777 lun_i = spdk_scsi_lun_id_fmt_to_int(lun); 3778 dev = conn->dev; 3779 3780 task = spdk_iscsi_task_get(conn, NULL, spdk_iscsi_task_mgmt_cpl); 3781 if (!task) { 3782 SPDK_ERRLOG("Unable to acquire task\n"); 3783 return SPDK_ISCSI_CONNECTION_FATAL; 3784 } 3785 3786 spdk_iscsi_task_associate_pdu(task, pdu); 3787 task->scsi.target_port = conn->target_port; 3788 task->scsi.initiator_port = conn->initiator_port; 3789 task->tag = task_tag; 3790 task->scsi.lun = spdk_scsi_dev_get_lun(dev, lun_i); 3791 task->lun_id = lun_i; 3792 3793 if (task->scsi.lun == NULL) { 3794 task->scsi.response = SPDK_SCSI_TASK_MGMT_RESP_INVALID_LUN; 3795 spdk_iscsi_task_mgmt_response(conn, task); 3796 spdk_iscsi_task_put(task); 3797 return 0; 3798 } 3799 3800 switch (function) { 3801 /* abort task identified by Referenced Task Tag field */ 3802 case ISCSI_TASK_FUNC_ABORT_TASK: 3803 SPDK_NOTICELOG("ABORT_TASK\n"); 3804 3805 iscsi_op_abort_task(task, ref_task_tag); 3806 return 0; 3807 3808 /* abort all tasks issued via this session on the LUN */ 3809 case ISCSI_TASK_FUNC_ABORT_TASK_SET: 3810 SPDK_NOTICELOG("ABORT_TASK_SET\n"); 3811 3812 spdk_iscsi_op_abort_task_set(task, SPDK_SCSI_TASK_FUNC_ABORT_TASK_SET); 3813 return 0; 3814 3815 case ISCSI_TASK_FUNC_CLEAR_TASK_SET: 3816 task->scsi.response = SPDK_SCSI_TASK_MGMT_RESP_REJECT_FUNC_NOT_SUPPORTED; 3817 SPDK_NOTICELOG("CLEAR_TASK_SET (Unsupported)\n"); 3818 break; 3819 3820 case ISCSI_TASK_FUNC_CLEAR_ACA: 3821 task->scsi.response = SPDK_SCSI_TASK_MGMT_RESP_REJECT_FUNC_NOT_SUPPORTED; 3822 SPDK_NOTICELOG("CLEAR_ACA (Unsupported)\n"); 3823 break; 3824 3825 case ISCSI_TASK_FUNC_LOGICAL_UNIT_RESET: 3826 SPDK_NOTICELOG("LOGICAL_UNIT_RESET\n"); 3827 3828 spdk_iscsi_op_abort_task_set(task, SPDK_SCSI_TASK_FUNC_LUN_RESET); 3829 return 0; 3830 3831 case ISCSI_TASK_FUNC_TARGET_WARM_RESET: 3832 SPDK_NOTICELOG("TARGET_WARM_RESET (Unsupported)\n"); 3833 3834 #if 0 3835 spdk_iscsi_drop_conns(conn, conn->initiator_name, 1 /* drop all */); 3836 rc = spdk_iscsi_tgt_node_reset(conn->sess->target, lun); 3837 if (rc < 0) { 3838 SPDK_ERRLOG("tgt_node reset failed\n"); 3839 } 3840 #else 3841 task->scsi.response = SPDK_SCSI_TASK_MGMT_RESP_REJECT_FUNC_NOT_SUPPORTED; 3842 #endif 3843 break; 3844 3845 case ISCSI_TASK_FUNC_TARGET_COLD_RESET: 3846 SPDK_NOTICELOG("TARGET_COLD_RESET\n"); 3847 3848 #if 0 3849 spdk_iscsi_drop_conns(conn, conn->initiator_name, 1 /* drop all */); 3850 3851 rc = spdk_iscsi_tgt_node_reset(conn->sess->target, lun); 3852 if (rc < 0) { 3853 SPDK_ERRLOG("tgt_node reset failed\n"); 3854 } 3855 3856 conn->state = ISCSI_CONN_STATE_EXITING; 3857 #else 3858 task->scsi.response = SPDK_SCSI_TASK_MGMT_RESP_REJECT_FUNC_NOT_SUPPORTED; 3859 #endif 3860 break; 3861 3862 case ISCSI_TASK_FUNC_TASK_REASSIGN: 3863 SPDK_NOTICELOG("TASK_REASSIGN (Unsupported)\n"); 3864 task->scsi.response = SPDK_SCSI_TASK_MGMT_RESP_REJECT_FUNC_NOT_SUPPORTED; 3865 break; 3866 3867 default: 3868 SPDK_ERRLOG("unsupported function %d\n", function); 3869 task->scsi.response = SPDK_SCSI_TASK_MGMT_RESP_REJECT; 3870 break; 3871 } 3872 3873 spdk_iscsi_task_mgmt_response(conn, task); 3874 spdk_iscsi_task_put(task); 3875 return 0; 3876 } 3877 3878 void spdk_iscsi_send_nopin(struct spdk_iscsi_conn *conn) 3879 { 3880 struct spdk_iscsi_pdu *rsp_pdu; 3881 struct iscsi_bhs_nop_in *rsp; 3882 3883 /* Only send nopin if we have logged in and are in a normal session. */ 3884 if (conn->sess == NULL || 3885 !conn->full_feature || 3886 !spdk_iscsi_param_eq_val(conn->sess->params, "SessionType", "Normal")) { 3887 return; 3888 } 3889 3890 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "send NOPIN isid=%"PRIx64", tsih=%u, cid=%u\n", 3891 conn->sess->isid, conn->sess->tsih, conn->cid); 3892 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "StatSN=%u, ExpCmdSN=%u, MaxCmdSN=%u\n", 3893 conn->StatSN, conn->sess->ExpCmdSN, 3894 conn->sess->MaxCmdSN); 3895 3896 rsp_pdu = spdk_get_pdu(); 3897 rsp = (struct iscsi_bhs_nop_in *) &rsp_pdu->bhs; 3898 rsp_pdu->data = NULL; 3899 3900 /* 3901 * spdk_get_pdu() memset's the PDU for us, so only fill out the needed 3902 * fields. 3903 */ 3904 rsp->opcode = ISCSI_OP_NOPIN; 3905 rsp->flags = 0x80; 3906 /* 3907 * Technically the to_be32() is not needed here, since 3908 * to_be32(0xFFFFFFFU) returns 0xFFFFFFFFU. 3909 */ 3910 to_be32(&rsp->itt, 0xFFFFFFFFU); 3911 to_be32(&rsp->ttt, conn->id); 3912 to_be32(&rsp->stat_sn, conn->StatSN); 3913 to_be32(&rsp->exp_cmd_sn, conn->sess->ExpCmdSN); 3914 to_be32(&rsp->max_cmd_sn, conn->sess->MaxCmdSN); 3915 3916 spdk_iscsi_conn_write_pdu(conn, rsp_pdu); 3917 conn->last_nopin = spdk_get_ticks(); 3918 conn->nop_outstanding = true; 3919 } 3920 3921 static int 3922 iscsi_pdu_hdr_op_nopout(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 3923 { 3924 struct iscsi_bhs_nop_out *reqh; 3925 uint32_t task_tag; 3926 uint32_t transfer_tag; 3927 int I_bit; 3928 3929 if (conn->sess->session_type == SESSION_TYPE_DISCOVERY) { 3930 SPDK_ERRLOG("ISCSI_OP_NOPOUT not allowed in discovery session\n"); 3931 return SPDK_ISCSI_CONNECTION_FATAL; 3932 } 3933 3934 reqh = (struct iscsi_bhs_nop_out *)&pdu->bhs; 3935 I_bit = reqh->immediate; 3936 3937 if (pdu->data_segment_len > SPDK_ISCSI_MAX_RECV_DATA_SEGMENT_LENGTH) { 3938 return iscsi_reject(conn, pdu, ISCSI_REASON_PROTOCOL_ERROR); 3939 } 3940 3941 task_tag = from_be32(&reqh->itt); 3942 transfer_tag = from_be32(&reqh->ttt); 3943 3944 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "I=%d, ITT=%x, TTT=%x\n", 3945 I_bit, task_tag, transfer_tag); 3946 3947 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "CmdSN=%u, StatSN=%u, ExpCmdSN=%u, MaxCmdSN=%u\n", 3948 pdu->cmd_sn, conn->StatSN, conn->sess->ExpCmdSN, 3949 conn->sess->MaxCmdSN); 3950 3951 if (transfer_tag != 0xFFFFFFFF && transfer_tag != (uint32_t)conn->id) { 3952 SPDK_ERRLOG("invalid transfer tag 0x%x\n", transfer_tag); 3953 /* 3954 * Technically we should probably fail the connection here, but for now 3955 * just print the error message and continue. 3956 */ 3957 } 3958 3959 if (task_tag == 0xffffffffU && I_bit == 0) { 3960 SPDK_ERRLOG("got NOPOUT ITT=0xffffffff, I=0\n"); 3961 return SPDK_ISCSI_CONNECTION_FATAL; 3962 } 3963 3964 return 0; 3965 } 3966 3967 static int 3968 iscsi_pdu_payload_op_nopout(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 3969 { 3970 struct spdk_iscsi_pdu *rsp_pdu; 3971 struct iscsi_bhs_nop_out *reqh; 3972 struct iscsi_bhs_nop_in *rsph; 3973 uint8_t *data; 3974 uint64_t lun; 3975 uint32_t task_tag; 3976 int I_bit; 3977 int data_len; 3978 3979 reqh = (struct iscsi_bhs_nop_out *)&pdu->bhs; 3980 I_bit = reqh->immediate; 3981 3982 data_len = pdu->data_segment_len; 3983 if (data_len > conn->MaxRecvDataSegmentLength) { 3984 data_len = conn->MaxRecvDataSegmentLength; 3985 } 3986 3987 lun = from_be64(&reqh->lun); 3988 task_tag = from_be32(&reqh->itt); 3989 3990 /* 3991 * We don't actually check to see if this is a response to the NOP-In 3992 * that we sent. Our goal is to just verify that the initiator is 3993 * alive and responding to commands, not to verify that it tags 3994 * NOP-Outs correctly 3995 */ 3996 conn->nop_outstanding = false; 3997 3998 if (task_tag == 0xffffffffU) { 3999 assert(I_bit == 1); 4000 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "got NOPOUT ITT=0xffffffff\n"); 4001 return 0; 4002 } 4003 4004 data = calloc(1, data_len); 4005 if (!data) { 4006 SPDK_ERRLOG("calloc() failed for ping data\n"); 4007 return SPDK_ISCSI_CONNECTION_FATAL; 4008 } 4009 4010 /* response of NOPOUT */ 4011 if (data_len > 0) { 4012 /* copy ping data */ 4013 memcpy(data, pdu->data, data_len); 4014 } 4015 4016 /* response PDU */ 4017 rsp_pdu = spdk_get_pdu(); 4018 if (rsp_pdu == NULL) { 4019 free(data); 4020 return SPDK_ISCSI_CONNECTION_FATAL; 4021 } 4022 rsph = (struct iscsi_bhs_nop_in *)&rsp_pdu->bhs; 4023 rsp_pdu->data = data; 4024 rsph->opcode = ISCSI_OP_NOPIN; 4025 rsph->flags |= 0x80; /* bit 0 default to 1 */ 4026 DSET24(rsph->data_segment_len, data_len); 4027 to_be64(&rsph->lun, lun); 4028 to_be32(&rsph->itt, task_tag); 4029 to_be32(&rsph->ttt, 0xffffffffU); 4030 4031 to_be32(&rsph->stat_sn, conn->StatSN); 4032 conn->StatSN++; 4033 4034 if (I_bit == 0) { 4035 conn->sess->MaxCmdSN++; 4036 } 4037 4038 to_be32(&rsph->exp_cmd_sn, conn->sess->ExpCmdSN); 4039 to_be32(&rsph->max_cmd_sn, conn->sess->MaxCmdSN); 4040 4041 spdk_iscsi_conn_write_pdu(conn, rsp_pdu); 4042 conn->last_nopin = spdk_get_ticks(); 4043 4044 return 0; 4045 } 4046 4047 /* This function returns the spdk_scsi_task by searching the snack list via 4048 * task transfertag and the pdu's opcode 4049 */ 4050 static struct spdk_iscsi_task * 4051 get_scsi_task_from_ttt(struct spdk_iscsi_conn *conn, uint32_t transfer_tag) 4052 { 4053 struct spdk_iscsi_pdu *pdu; 4054 struct iscsi_bhs_data_in *datain_bhs; 4055 4056 TAILQ_FOREACH(pdu, &conn->snack_pdu_list, tailq) { 4057 if (pdu->bhs.opcode == ISCSI_OP_SCSI_DATAIN) { 4058 datain_bhs = (struct iscsi_bhs_data_in *)&pdu->bhs; 4059 if (from_be32(&datain_bhs->ttt) == transfer_tag) { 4060 return pdu->task; 4061 } 4062 } 4063 } 4064 4065 return NULL; 4066 } 4067 4068 /* This function returns the spdk_scsi_task by searching the snack list via 4069 * initiator task tag and the pdu's opcode 4070 */ 4071 static struct spdk_iscsi_task * 4072 get_scsi_task_from_itt(struct spdk_iscsi_conn *conn, 4073 uint32_t task_tag, enum iscsi_op opcode) 4074 { 4075 struct spdk_iscsi_pdu *pdu; 4076 4077 TAILQ_FOREACH(pdu, &conn->snack_pdu_list, tailq) { 4078 if (pdu->bhs.opcode == opcode && 4079 pdu->task != NULL && 4080 pdu->task->tag == task_tag) { 4081 return pdu->task; 4082 } 4083 } 4084 4085 return NULL; 4086 } 4087 4088 /* This function is used to handle the r2t snack */ 4089 static int 4090 iscsi_handle_r2t_snack(struct spdk_iscsi_conn *conn, 4091 struct spdk_iscsi_task *task, 4092 struct spdk_iscsi_pdu *pdu, uint32_t beg_run, 4093 uint32_t run_length, int32_t task_tag) 4094 { 4095 int32_t last_r2tsn; 4096 int i; 4097 4098 if (beg_run < task->acked_r2tsn) { 4099 SPDK_ERRLOG("ITT: 0x%08x, R2T SNACK requests retransmission of" 4100 "R2TSN: from 0x%08x to 0x%08x. But it has already" 4101 "ack to R2TSN:0x%08x, protocol error.\n", 4102 task_tag, beg_run, (beg_run + run_length), 4103 (task->acked_r2tsn - 1)); 4104 return iscsi_reject(conn, pdu, ISCSI_REASON_PROTOCOL_ERROR); 4105 } 4106 4107 if (run_length) { 4108 if ((beg_run + run_length) > task->R2TSN) { 4109 SPDK_ERRLOG("ITT: 0x%08x, received R2T SNACK with" 4110 "BegRun: 0x%08x, RunLength: 0x%08x, exceeds" 4111 "current R2TSN: 0x%08x, protocol error.\n", 4112 task_tag, beg_run, run_length, 4113 task->R2TSN); 4114 4115 return iscsi_reject(conn, pdu, ISCSI_REASON_INVALID_PDU_FIELD); 4116 } 4117 last_r2tsn = (beg_run + run_length); 4118 } else { 4119 last_r2tsn = task->R2TSN; 4120 } 4121 4122 for (i = beg_run; i < last_r2tsn; i++) { 4123 if (iscsi_send_r2t_recovery(conn, task, i, false) < 0) { 4124 SPDK_ERRLOG("The r2t_sn=%d of r2t_task=%p is not sent\n", i, task); 4125 } 4126 } 4127 return 0; 4128 } 4129 4130 /* This function is used to recover the data in packet */ 4131 static int 4132 iscsi_handle_recovery_datain(struct spdk_iscsi_conn *conn, 4133 struct spdk_iscsi_task *task, 4134 struct spdk_iscsi_pdu *pdu, uint32_t beg_run, 4135 uint32_t run_length, uint32_t task_tag) 4136 { 4137 struct spdk_iscsi_pdu *old_pdu, *pdu_temp; 4138 uint32_t i; 4139 struct iscsi_bhs_data_in *datain_header; 4140 uint32_t last_statsn; 4141 4142 task = spdk_iscsi_task_get_primary(task); 4143 4144 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "iscsi_handle_recovery_datain\n"); 4145 4146 if (beg_run < task->acked_data_sn) { 4147 SPDK_ERRLOG("ITT: 0x%08x, DATA IN SNACK requests retransmission of" 4148 "DATASN: from 0x%08x to 0x%08x but already acked to " 4149 "DATASN: 0x%08x protocol error\n", 4150 task_tag, beg_run, 4151 (beg_run + run_length), (task->acked_data_sn - 1)); 4152 4153 return iscsi_reject(conn, pdu, ISCSI_REASON_PROTOCOL_ERROR); 4154 } 4155 4156 if (run_length == 0) { 4157 /* as the DataSN begins at 0 */ 4158 run_length = task->datain_datasn + 1; 4159 } 4160 4161 if ((beg_run + run_length - 1) > task->datain_datasn) { 4162 SPDK_ERRLOG("Initiator requests BegRun: 0x%08x, RunLength:" 4163 "0x%08x greater than maximum DataSN: 0x%08x.\n", 4164 beg_run, run_length, task->datain_datasn); 4165 4166 return -1; 4167 } else { 4168 last_statsn = beg_run + run_length - 1; 4169 } 4170 4171 for (i = beg_run; i <= last_statsn; i++) { 4172 TAILQ_FOREACH_SAFE(old_pdu, &conn->snack_pdu_list, tailq, pdu_temp) { 4173 if (old_pdu->bhs.opcode == ISCSI_OP_SCSI_DATAIN) { 4174 datain_header = (struct iscsi_bhs_data_in *)&old_pdu->bhs; 4175 if (from_be32(&datain_header->itt) == task_tag && 4176 from_be32(&datain_header->data_sn) == i) { 4177 TAILQ_REMOVE(&conn->snack_pdu_list, old_pdu, tailq); 4178 spdk_iscsi_conn_write_pdu(conn, old_pdu); 4179 break; 4180 } 4181 } 4182 } 4183 } 4184 return 0; 4185 } 4186 4187 /* This function is used to handle the status snack */ 4188 static int 4189 iscsi_handle_status_snack(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 4190 { 4191 uint32_t beg_run; 4192 uint32_t run_length; 4193 struct iscsi_bhs_snack_req *reqh; 4194 uint32_t i; 4195 uint32_t last_statsn; 4196 bool found_pdu; 4197 struct spdk_iscsi_pdu *old_pdu; 4198 4199 reqh = (struct iscsi_bhs_snack_req *)&pdu->bhs; 4200 beg_run = from_be32(&reqh->beg_run); 4201 run_length = from_be32(&reqh->run_len); 4202 4203 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "beg_run=%d, run_length=%d, conn->StatSN=" 4204 "%d, conn->exp_statsn=%d\n", beg_run, run_length, 4205 conn->StatSN, conn->exp_statsn); 4206 4207 if (!beg_run) { 4208 beg_run = conn->exp_statsn; 4209 } else if (beg_run < conn->exp_statsn) { 4210 SPDK_ERRLOG("Got Status SNACK Begrun: 0x%08x, RunLength: 0x%08x " 4211 "but already got ExpStatSN: 0x%08x on CID:%hu.\n", 4212 beg_run, run_length, conn->StatSN, conn->cid); 4213 4214 return iscsi_reject(conn, pdu, ISCSI_REASON_INVALID_PDU_FIELD); 4215 } 4216 4217 last_statsn = (!run_length) ? conn->StatSN : (beg_run + run_length); 4218 4219 for (i = beg_run; i < last_statsn; i++) { 4220 found_pdu = false; 4221 TAILQ_FOREACH(old_pdu, &conn->snack_pdu_list, tailq) { 4222 if (from_be32(&old_pdu->bhs.stat_sn) == i) { 4223 found_pdu = true; 4224 break; 4225 } 4226 } 4227 4228 if (!found_pdu) { 4229 SPDK_ERRLOG("Unable to find StatSN: 0x%08x. For a Status" 4230 "SNACK, assuming this is a proactive SNACK " 4231 "for an untransmitted StatSN, ignoring.\n", 4232 beg_run); 4233 } else { 4234 TAILQ_REMOVE(&conn->snack_pdu_list, old_pdu, tailq); 4235 spdk_iscsi_conn_write_pdu(conn, old_pdu); 4236 } 4237 } 4238 4239 return 0; 4240 } 4241 4242 /* This function is used to handle the data ack snack */ 4243 static int 4244 iscsi_handle_data_ack(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 4245 { 4246 uint32_t transfer_tag; 4247 uint32_t beg_run; 4248 uint32_t run_length; 4249 struct spdk_iscsi_pdu *old_pdu; 4250 uint32_t old_datasn; 4251 struct iscsi_bhs_snack_req *reqh; 4252 struct spdk_iscsi_task *task; 4253 struct iscsi_bhs_data_in *datain_header; 4254 struct spdk_iscsi_task *primary; 4255 4256 reqh = (struct iscsi_bhs_snack_req *)&pdu->bhs; 4257 transfer_tag = from_be32(&reqh->ttt); 4258 beg_run = from_be32(&reqh->beg_run); 4259 run_length = from_be32(&reqh->run_len); 4260 task = NULL; 4261 datain_header = NULL; 4262 4263 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "beg_run=%d,transfer_tag=%d,run_len=%d\n", 4264 beg_run, transfer_tag, run_length); 4265 4266 task = get_scsi_task_from_ttt(conn, transfer_tag); 4267 if (!task) { 4268 SPDK_ERRLOG("Data ACK SNACK for TTT: 0x%08x is invalid.\n", 4269 transfer_tag); 4270 goto reject_return; 4271 } 4272 4273 primary = spdk_iscsi_task_get_primary(task); 4274 if ((run_length != 0) || (beg_run < primary->acked_data_sn)) { 4275 SPDK_ERRLOG("TTT: 0x%08x Data ACK SNACK BegRUN: %d is less than " 4276 "the next expected acked DataSN: %d\n", 4277 transfer_tag, beg_run, primary->acked_data_sn); 4278 goto reject_return; 4279 } 4280 4281 primary->acked_data_sn = beg_run; 4282 4283 /* To free the pdu */ 4284 TAILQ_FOREACH(old_pdu, &conn->snack_pdu_list, tailq) { 4285 if (old_pdu->bhs.opcode == ISCSI_OP_SCSI_DATAIN) { 4286 datain_header = (struct iscsi_bhs_data_in *) &old_pdu->bhs; 4287 old_datasn = from_be32(&datain_header->data_sn); 4288 if ((from_be32(&datain_header->ttt) == transfer_tag) && 4289 (old_datasn == beg_run - 1)) { 4290 TAILQ_REMOVE(&conn->snack_pdu_list, old_pdu, tailq); 4291 if (old_pdu->task) { 4292 spdk_iscsi_task_put(old_pdu->task); 4293 } 4294 spdk_put_pdu(old_pdu); 4295 break; 4296 } 4297 } 4298 } 4299 4300 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Received Data ACK SNACK for TTT: 0x%08x," 4301 " updated acked DataSN to 0x%08x.\n", transfer_tag, 4302 (task->acked_data_sn - 1)); 4303 4304 return 0; 4305 4306 reject_return: 4307 return iscsi_reject(conn, pdu, ISCSI_REASON_INVALID_SNACK); 4308 } 4309 4310 /* This function is used to handle the snack request from the initiator */ 4311 static int 4312 iscsi_pdu_hdr_op_snack(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 4313 { 4314 struct iscsi_bhs_snack_req *reqh; 4315 struct spdk_iscsi_task *task; 4316 int type; 4317 uint32_t task_tag; 4318 uint32_t beg_run; 4319 uint32_t run_length; 4320 int rc; 4321 4322 if (conn->sess->session_type == SESSION_TYPE_DISCOVERY) { 4323 SPDK_ERRLOG("ISCSI_OP_SNACK not allowed in discovery session\n"); 4324 return SPDK_ISCSI_CONNECTION_FATAL; 4325 } 4326 4327 reqh = (struct iscsi_bhs_snack_req *)&pdu->bhs; 4328 if (!conn->sess->ErrorRecoveryLevel) { 4329 SPDK_ERRLOG("Got a SNACK request in ErrorRecoveryLevel=0\n"); 4330 return iscsi_reject(conn, pdu, ISCSI_REASON_PROTOCOL_ERROR); 4331 } 4332 4333 type = reqh->flags & ISCSI_FLAG_SNACK_TYPE_MASK; 4334 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "The value of type is %d\n", type); 4335 4336 switch (type) { 4337 case 0: 4338 reqh = (struct iscsi_bhs_snack_req *)&pdu->bhs; 4339 task_tag = from_be32(&reqh->itt); 4340 beg_run = from_be32(&reqh->beg_run); 4341 run_length = from_be32(&reqh->run_len); 4342 4343 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "beg_run=%d, run_length=%d, " 4344 "task_tag=%x, transfer_tag=%u\n", beg_run, 4345 run_length, task_tag, from_be32(&reqh->ttt)); 4346 4347 task = get_scsi_task_from_itt(conn, task_tag, 4348 ISCSI_OP_SCSI_DATAIN); 4349 if (task) { 4350 return iscsi_handle_recovery_datain(conn, task, pdu, 4351 beg_run, run_length, task_tag); 4352 } 4353 task = get_scsi_task_from_itt(conn, task_tag, ISCSI_OP_R2T); 4354 if (task) { 4355 return iscsi_handle_r2t_snack(conn, task, pdu, beg_run, 4356 run_length, task_tag); 4357 } 4358 SPDK_ERRLOG("It is Neither datain nor r2t recovery request\n"); 4359 rc = -1; 4360 break; 4361 case ISCSI_FLAG_SNACK_TYPE_STATUS: 4362 rc = iscsi_handle_status_snack(conn, pdu); 4363 break; 4364 case ISCSI_FLAG_SNACK_TYPE_DATA_ACK: 4365 rc = iscsi_handle_data_ack(conn, pdu); 4366 break; 4367 case ISCSI_FLAG_SNACK_TYPE_RDATA: 4368 SPDK_ERRLOG("R-Data SNACK is Not Supported int spdk\n"); 4369 rc = iscsi_reject(conn, pdu, ISCSI_REASON_PROTOCOL_ERROR); 4370 break; 4371 default: 4372 SPDK_ERRLOG("Unknown SNACK type %d, protocol error\n", type); 4373 rc = iscsi_reject(conn, pdu, ISCSI_REASON_PROTOCOL_ERROR); 4374 break; 4375 } 4376 4377 return rc; 4378 } 4379 4380 static int 4381 iscsi_pdu_hdr_op_data(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 4382 { 4383 struct spdk_iscsi_task *task, *subtask; 4384 struct iscsi_bhs_data_out *reqh; 4385 struct spdk_scsi_lun *lun_dev; 4386 uint32_t transfer_tag; 4387 uint32_t task_tag; 4388 uint32_t transfer_len; 4389 uint32_t DataSN; 4390 uint32_t buffer_offset; 4391 uint32_t len; 4392 int F_bit; 4393 int rc; 4394 int reject_reason = ISCSI_REASON_INVALID_PDU_FIELD; 4395 4396 if (conn->sess->session_type == SESSION_TYPE_DISCOVERY) { 4397 SPDK_ERRLOG("ISCSI_OP_SCSI_DATAOUT not allowed in discovery session\n"); 4398 return SPDK_ISCSI_CONNECTION_FATAL; 4399 } 4400 4401 reqh = (struct iscsi_bhs_data_out *)&pdu->bhs; 4402 F_bit = !!(reqh->flags & ISCSI_FLAG_FINAL); 4403 transfer_tag = from_be32(&reqh->ttt); 4404 task_tag = from_be32(&reqh->itt); 4405 DataSN = from_be32(&reqh->data_sn); 4406 buffer_offset = from_be32(&reqh->buffer_offset); 4407 4408 if (pdu->data_segment_len > SPDK_ISCSI_MAX_RECV_DATA_SEGMENT_LENGTH) { 4409 reject_reason = ISCSI_REASON_PROTOCOL_ERROR; 4410 goto reject_return; 4411 } 4412 4413 task = get_transfer_task(conn, transfer_tag); 4414 if (task == NULL) { 4415 SPDK_ERRLOG("Not found task for transfer_tag=%x\n", transfer_tag); 4416 goto reject_return; 4417 } 4418 4419 lun_dev = spdk_scsi_dev_get_lun(conn->dev, task->lun_id); 4420 4421 if (pdu->data_segment_len > task->desired_data_transfer_length) { 4422 SPDK_ERRLOG("the dataout pdu data length is larger than the value sent by R2T PDU\n"); 4423 return SPDK_ISCSI_CONNECTION_FATAL; 4424 } 4425 4426 if (task->tag != task_tag) { 4427 SPDK_ERRLOG("The r2t task tag is %u, and the dataout task tag is %u\n", 4428 task->tag, task_tag); 4429 goto reject_return; 4430 } 4431 4432 if (DataSN != task->r2t_datasn) { 4433 SPDK_ERRLOG("DataSN(%u) exp=%d error\n", DataSN, task->r2t_datasn); 4434 if (conn->sess->ErrorRecoveryLevel >= 1) { 4435 goto send_r2t_recovery_return; 4436 } else { 4437 reject_reason = ISCSI_REASON_PROTOCOL_ERROR; 4438 goto reject_return; 4439 } 4440 } 4441 4442 if (buffer_offset != task->next_expected_r2t_offset) { 4443 SPDK_ERRLOG("offset(%u) error\n", buffer_offset); 4444 return SPDK_ISCSI_CONNECTION_FATAL; 4445 } 4446 4447 transfer_len = task->scsi.transfer_len; 4448 task->current_r2t_length += pdu->data_segment_len; 4449 task->next_expected_r2t_offset += pdu->data_segment_len; 4450 task->r2t_datasn++; 4451 4452 if (task->current_r2t_length > conn->sess->MaxBurstLength) { 4453 SPDK_ERRLOG("R2T burst(%u) > MaxBurstLength(%u)\n", 4454 task->current_r2t_length, 4455 conn->sess->MaxBurstLength); 4456 return SPDK_ISCSI_CONNECTION_FATAL; 4457 } 4458 4459 if (F_bit) { 4460 /* 4461 * This R2T burst is done. Clear the length before we 4462 * receive a PDU for the next R2t burst. 4463 */ 4464 task->current_r2t_length = 0; 4465 } 4466 4467 subtask = spdk_iscsi_task_get(conn, task, spdk_iscsi_task_cpl); 4468 if (subtask == NULL) { 4469 SPDK_ERRLOG("Unable to acquire subtask\n"); 4470 return SPDK_ISCSI_CONNECTION_FATAL; 4471 } 4472 subtask->scsi.offset = buffer_offset; 4473 subtask->scsi.length = pdu->data_segment_len; 4474 spdk_iscsi_task_associate_pdu(subtask, pdu); 4475 4476 if (task->next_expected_r2t_offset == transfer_len) { 4477 task->acked_r2tsn++; 4478 } else if (F_bit && (task->next_r2t_offset < transfer_len)) { 4479 task->acked_r2tsn++; 4480 len = DMIN32(conn->sess->MaxBurstLength, (transfer_len - 4481 task->next_r2t_offset)); 4482 rc = iscsi_send_r2t(conn, task, task->next_r2t_offset, len, 4483 task->ttt, &task->R2TSN); 4484 if (rc < 0) { 4485 SPDK_ERRLOG("iscsi_send_r2t() failed\n"); 4486 } 4487 task->next_r2t_offset += len; 4488 } 4489 4490 if (lun_dev == NULL) { 4491 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "LUN %d is removed, complete the task immediately\n", 4492 task->lun_id); 4493 subtask->scsi.transfer_len = subtask->scsi.length; 4494 spdk_scsi_task_process_null_lun(&subtask->scsi); 4495 spdk_iscsi_task_cpl(&subtask->scsi); 4496 return 0; 4497 } 4498 4499 pdu->task = subtask; 4500 return 0; 4501 4502 send_r2t_recovery_return: 4503 rc = iscsi_send_r2t_recovery(conn, task, task->acked_r2tsn, true); 4504 if (rc == 0) { 4505 return 0; 4506 } 4507 4508 reject_return: 4509 return iscsi_reject(conn, pdu, reject_reason); 4510 } 4511 4512 static int 4513 iscsi_pdu_payload_op_data(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 4514 { 4515 struct spdk_iscsi_task *subtask; 4516 4517 if (pdu->task == NULL) { 4518 return 0; 4519 } 4520 4521 subtask = pdu->task; 4522 4523 if (spdk_likely(!pdu->dif_insert_or_strip)) { 4524 spdk_scsi_task_set_data(&subtask->scsi, pdu->data, pdu->data_segment_len); 4525 } else { 4526 spdk_scsi_task_set_data(&subtask->scsi, pdu->data, pdu->data_buf_len); 4527 } 4528 4529 if (spdk_scsi_dev_get_lun(conn->dev, subtask->lun_id) == NULL) { 4530 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "LUN %d is removed, complete the task immediately\n", 4531 subtask->lun_id); 4532 subtask->scsi.transfer_len = subtask->scsi.length; 4533 spdk_scsi_task_process_null_lun(&subtask->scsi); 4534 spdk_iscsi_task_cpl(&subtask->scsi); 4535 return 0; 4536 } 4537 4538 iscsi_queue_task(conn, subtask); 4539 return 0; 4540 } 4541 4542 static void 4543 init_login_reject_response(struct spdk_iscsi_pdu *pdu, struct spdk_iscsi_pdu *rsp_pdu) 4544 { 4545 struct iscsi_bhs_login_rsp *rsph; 4546 4547 memset(rsp_pdu, 0, sizeof(struct spdk_iscsi_pdu)); 4548 rsph = (struct iscsi_bhs_login_rsp *)&rsp_pdu->bhs; 4549 rsph->version_max = ISCSI_VERSION; 4550 rsph->version_act = ISCSI_VERSION; 4551 rsph->opcode = ISCSI_OP_LOGIN_RSP; 4552 rsph->status_class = ISCSI_CLASS_INITIATOR_ERROR; 4553 rsph->status_detail = ISCSI_LOGIN_INVALID_LOGIN_REQUEST; 4554 rsph->itt = pdu->bhs.itt; 4555 } 4556 4557 static void 4558 iscsi_pdu_dump(struct spdk_iscsi_pdu *pdu) 4559 { 4560 SPDK_ERRLOGDUMP("PDU", (uint8_t *)&pdu->bhs, ISCSI_BHS_LEN); 4561 } 4562 4563 /* This function is used to refree the pdu when it is acknowledged */ 4564 static void 4565 remove_acked_pdu(struct spdk_iscsi_conn *conn, uint32_t ExpStatSN) 4566 { 4567 struct spdk_iscsi_pdu *pdu, *pdu_temp; 4568 uint32_t stat_sn; 4569 4570 conn->exp_statsn = DMIN32(ExpStatSN, conn->StatSN); 4571 TAILQ_FOREACH_SAFE(pdu, &conn->snack_pdu_list, tailq, pdu_temp) { 4572 stat_sn = from_be32(&pdu->bhs.stat_sn); 4573 if (SN32_LT(stat_sn, conn->exp_statsn)) { 4574 TAILQ_REMOVE(&conn->snack_pdu_list, pdu, tailq); 4575 spdk_iscsi_conn_free_pdu(conn, pdu); 4576 } 4577 } 4578 } 4579 4580 static int 4581 iscsi_update_cmdsn(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 4582 { 4583 int opcode; 4584 uint32_t ExpStatSN; 4585 int I_bit; 4586 struct spdk_iscsi_sess *sess; 4587 struct iscsi_bhs_scsi_req *reqh; 4588 4589 sess = conn->sess; 4590 if (!sess) { 4591 SPDK_ERRLOG("Connection has no associated session!\n"); 4592 return SPDK_ISCSI_CONNECTION_FATAL; 4593 } 4594 4595 opcode = pdu->bhs.opcode; 4596 reqh = (struct iscsi_bhs_scsi_req *)&pdu->bhs; 4597 4598 pdu->cmd_sn = from_be32(&reqh->cmd_sn); 4599 4600 I_bit = reqh->immediate; 4601 if (I_bit == 0) { 4602 if (SN32_LT(pdu->cmd_sn, sess->ExpCmdSN) || 4603 SN32_GT(pdu->cmd_sn, sess->MaxCmdSN)) { 4604 if (sess->session_type == SESSION_TYPE_NORMAL && 4605 opcode != ISCSI_OP_SCSI_DATAOUT) { 4606 SPDK_ERRLOG("CmdSN(%u) ignore (ExpCmdSN=%u, MaxCmdSN=%u)\n", 4607 pdu->cmd_sn, sess->ExpCmdSN, sess->MaxCmdSN); 4608 4609 if (sess->ErrorRecoveryLevel >= 1) { 4610 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Skip the error in ERL 1 and 2\n"); 4611 } else { 4612 return SPDK_PDU_FATAL; 4613 } 4614 } 4615 } 4616 } else if (pdu->cmd_sn != sess->ExpCmdSN) { 4617 SPDK_ERRLOG("CmdSN(%u) error ExpCmdSN=%u\n", pdu->cmd_sn, sess->ExpCmdSN); 4618 4619 if (sess->ErrorRecoveryLevel >= 1) { 4620 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "Skip the error in ERL 1 and 2\n"); 4621 } else if (opcode != ISCSI_OP_NOPOUT) { 4622 /* 4623 * The Linux initiator does not send valid CmdSNs for 4624 * nopout under heavy load, so do not close the 4625 * connection in that case. 4626 */ 4627 return SPDK_ISCSI_CONNECTION_FATAL; 4628 } 4629 } 4630 4631 ExpStatSN = from_be32(&reqh->exp_stat_sn); 4632 if (SN32_GT(ExpStatSN, conn->StatSN)) { 4633 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "StatSN(%u) advanced\n", ExpStatSN); 4634 ExpStatSN = conn->StatSN; 4635 } 4636 4637 if (sess->ErrorRecoveryLevel >= 1) { 4638 remove_acked_pdu(conn, ExpStatSN); 4639 } 4640 4641 if (!I_bit && opcode != ISCSI_OP_SCSI_DATAOUT) { 4642 sess->ExpCmdSN++; 4643 } 4644 4645 return 0; 4646 } 4647 4648 static int 4649 iscsi_pdu_hdr_handle(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 4650 { 4651 int opcode; 4652 int rc; 4653 struct spdk_iscsi_pdu *rsp_pdu = NULL; 4654 4655 if (pdu == NULL) { 4656 return -1; 4657 } 4658 4659 opcode = pdu->bhs.opcode; 4660 4661 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "opcode %x\n", opcode); 4662 4663 if (opcode == ISCSI_OP_LOGIN) { 4664 return iscsi_pdu_hdr_op_login(conn, pdu); 4665 } 4666 4667 /* connection in login phase but receive non-login opcode 4668 * return response code 0x020b to initiator. 4669 * */ 4670 if (!conn->full_feature && conn->state == ISCSI_CONN_STATE_RUNNING) { 4671 rsp_pdu = spdk_get_pdu(); 4672 if (rsp_pdu == NULL) { 4673 return SPDK_ISCSI_CONNECTION_FATAL; 4674 } 4675 init_login_reject_response(pdu, rsp_pdu); 4676 spdk_iscsi_conn_write_pdu(conn, rsp_pdu); 4677 SPDK_ERRLOG("Received opcode %d in login phase\n", opcode); 4678 return SPDK_ISCSI_LOGIN_ERROR_RESPONSE; 4679 } else if (conn->state == ISCSI_CONN_STATE_INVALID) { 4680 SPDK_ERRLOG("before Full Feature\n"); 4681 iscsi_pdu_dump(pdu); 4682 return SPDK_ISCSI_CONNECTION_FATAL; 4683 } 4684 4685 rc = iscsi_update_cmdsn(conn, pdu); 4686 if (rc != 0) { 4687 return rc; 4688 } 4689 4690 switch (opcode) { 4691 case ISCSI_OP_NOPOUT: 4692 rc = iscsi_pdu_hdr_op_nopout(conn, pdu); 4693 break; 4694 4695 case ISCSI_OP_SCSI: 4696 rc = iscsi_pdu_hdr_op_scsi(conn, pdu); 4697 break; 4698 case ISCSI_OP_TASK: 4699 rc = iscsi_pdu_hdr_op_task(conn, pdu); 4700 break; 4701 4702 case ISCSI_OP_TEXT: 4703 rc = iscsi_pdu_hdr_op_text(conn, pdu); 4704 break; 4705 4706 case ISCSI_OP_LOGOUT: 4707 rc = iscsi_pdu_hdr_op_logout(conn, pdu); 4708 break; 4709 4710 case ISCSI_OP_SCSI_DATAOUT: 4711 rc = iscsi_pdu_hdr_op_data(conn, pdu); 4712 break; 4713 4714 case ISCSI_OP_SNACK: 4715 rc = iscsi_pdu_hdr_op_snack(conn, pdu); 4716 break; 4717 4718 default: 4719 SPDK_ERRLOG("unsupported opcode %x\n", opcode); 4720 return iscsi_reject(conn, pdu, ISCSI_REASON_PROTOCOL_ERROR); 4721 } 4722 4723 if (rc < 0) { 4724 SPDK_ERRLOG("processing PDU header (opcode=%x) failed on %s(%s)\n", 4725 opcode, 4726 conn->target_port != NULL ? spdk_scsi_port_get_name(conn->target_port) : "NULL", 4727 conn->initiator_port != NULL ? spdk_scsi_port_get_name(conn->initiator_port) : "NULL"); 4728 } 4729 4730 return rc; 4731 } 4732 4733 static int 4734 iscsi_pdu_payload_handle(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu) 4735 { 4736 int opcode; 4737 int rc = 0; 4738 4739 opcode = pdu->bhs.opcode; 4740 4741 SPDK_DEBUGLOG(SPDK_LOG_ISCSI, "opcode %x\n", opcode); 4742 4743 switch (opcode) { 4744 case ISCSI_OP_LOGIN: 4745 rc = iscsi_pdu_payload_op_login(conn, pdu); 4746 break; 4747 case ISCSI_OP_NOPOUT: 4748 rc = iscsi_pdu_payload_op_nopout(conn, pdu); 4749 break; 4750 case ISCSI_OP_SCSI: 4751 rc = iscsi_pdu_payload_op_scsi(conn, pdu); 4752 break; 4753 case ISCSI_OP_TASK: 4754 break; 4755 case ISCSI_OP_TEXT: 4756 rc = iscsi_pdu_payload_op_text(conn, pdu); 4757 break; 4758 case ISCSI_OP_LOGOUT: 4759 break; 4760 case ISCSI_OP_SCSI_DATAOUT: 4761 rc = iscsi_pdu_payload_op_data(conn, pdu); 4762 break; 4763 case ISCSI_OP_SNACK: 4764 break; 4765 default: 4766 SPDK_ERRLOG("unsupported opcode %x\n", opcode); 4767 return iscsi_reject(conn, pdu, ISCSI_REASON_PROTOCOL_ERROR); 4768 } 4769 4770 if (rc < 0) { 4771 SPDK_ERRLOG("processing PDU payload (opcode=%x) failed on %s(%s)\n", 4772 opcode, 4773 conn->target_port != NULL ? spdk_scsi_port_get_name(conn->target_port) : "NULL", 4774 conn->initiator_port != NULL ? spdk_scsi_port_get_name(conn->initiator_port) : "NULL"); 4775 } 4776 4777 return rc; 4778 } 4779 4780 static int 4781 iscsi_read_pdu(struct spdk_iscsi_conn *conn) 4782 { 4783 enum iscsi_pdu_recv_state prev_state; 4784 struct spdk_iscsi_pdu *pdu; 4785 struct spdk_mempool *pool; 4786 uint32_t crc32c; 4787 int ahs_len; 4788 uint32_t data_len; 4789 int rc; 4790 4791 do { 4792 prev_state = conn->pdu_recv_state; 4793 pdu = conn->pdu_in_progress; 4794 4795 switch (conn->pdu_recv_state) { 4796 case ISCSI_PDU_RECV_STATE_AWAIT_PDU_READY: 4797 assert(conn->pdu_in_progress == NULL); 4798 4799 conn->pdu_in_progress = spdk_get_pdu(); 4800 if (conn->pdu_in_progress == NULL) { 4801 return SPDK_ISCSI_CONNECTION_FATAL; 4802 } 4803 conn->pdu_recv_state = ISCSI_PDU_RECV_STATE_AWAIT_PDU_HDR; 4804 break; 4805 case ISCSI_PDU_RECV_STATE_AWAIT_PDU_HDR: 4806 if (pdu->bhs_valid_bytes < ISCSI_BHS_LEN) { 4807 rc = spdk_iscsi_conn_read_data(conn, 4808 ISCSI_BHS_LEN - pdu->bhs_valid_bytes, 4809 (uint8_t *)&pdu->bhs + pdu->bhs_valid_bytes); 4810 if (rc < 0) { 4811 conn->pdu_recv_state = ISCSI_PDU_RECV_STATE_ERROR; 4812 break; 4813 } 4814 pdu->bhs_valid_bytes += rc; 4815 if (pdu->bhs_valid_bytes < ISCSI_BHS_LEN) { 4816 return 0; 4817 } 4818 } 4819 4820 pdu->data_segment_len = ISCSI_ALIGN(DGET24(pdu->bhs.data_segment_len)); 4821 4822 /* AHS */ 4823 ahs_len = pdu->bhs.total_ahs_len * 4; 4824 assert(ahs_len <= ISCSI_AHS_LEN); 4825 if (pdu->ahs_valid_bytes < ahs_len) { 4826 rc = spdk_iscsi_conn_read_data(conn, 4827 ahs_len - pdu->ahs_valid_bytes, 4828 pdu->ahs + pdu->ahs_valid_bytes); 4829 if (rc < 0) { 4830 conn->pdu_recv_state = ISCSI_PDU_RECV_STATE_ERROR; 4831 break; 4832 } 4833 4834 pdu->ahs_valid_bytes += rc; 4835 if (pdu->ahs_valid_bytes < ahs_len) { 4836 return 0; 4837 } 4838 } 4839 4840 /* Header Digest */ 4841 if (conn->header_digest && 4842 pdu->hdigest_valid_bytes < ISCSI_DIGEST_LEN) { 4843 rc = spdk_iscsi_conn_read_data(conn, 4844 ISCSI_DIGEST_LEN - pdu->hdigest_valid_bytes, 4845 pdu->header_digest + pdu->hdigest_valid_bytes); 4846 if (rc < 0) { 4847 conn->pdu_recv_state = ISCSI_PDU_RECV_STATE_ERROR; 4848 break; 4849 } 4850 4851 pdu->hdigest_valid_bytes += rc; 4852 if (pdu->hdigest_valid_bytes < ISCSI_DIGEST_LEN) { 4853 return 0; 4854 } 4855 } 4856 4857 if (conn->header_digest) { 4858 crc32c = spdk_iscsi_pdu_calc_header_digest(pdu); 4859 rc = MATCH_DIGEST_WORD(pdu->header_digest, crc32c); 4860 if (rc == 0) { 4861 SPDK_ERRLOG("header digest error (%s)\n", conn->initiator_name); 4862 conn->pdu_recv_state = ISCSI_PDU_RECV_STATE_ERROR; 4863 break; 4864 } 4865 } 4866 4867 rc = iscsi_pdu_hdr_handle(conn, pdu); 4868 if (rc < 0) { 4869 SPDK_ERRLOG("Critical error is detected. Close the connection\n"); 4870 conn->pdu_recv_state = ISCSI_PDU_RECV_STATE_ERROR; 4871 break; 4872 } 4873 4874 conn->pdu_recv_state = ISCSI_PDU_RECV_STATE_AWAIT_PDU_PAYLOAD; 4875 break; 4876 case ISCSI_PDU_RECV_STATE_AWAIT_PDU_PAYLOAD: 4877 data_len = pdu->data_segment_len; 4878 4879 if (data_len != 0 && pdu->data_buf == NULL) { 4880 if (data_len <= spdk_get_max_immediate_data_size()) { 4881 pool = g_spdk_iscsi.pdu_immediate_data_pool; 4882 pdu->data_buf_len = SPDK_BDEV_BUF_SIZE_WITH_MD(spdk_get_max_immediate_data_size()); 4883 } else if (data_len <= SPDK_ISCSI_MAX_RECV_DATA_SEGMENT_LENGTH) { 4884 pool = g_spdk_iscsi.pdu_data_out_pool; 4885 pdu->data_buf_len = SPDK_BDEV_BUF_SIZE_WITH_MD(SPDK_ISCSI_MAX_RECV_DATA_SEGMENT_LENGTH); 4886 } else { 4887 SPDK_ERRLOG("Data(%d) > MaxSegment(%d)\n", 4888 data_len, SPDK_ISCSI_MAX_RECV_DATA_SEGMENT_LENGTH); 4889 conn->pdu_recv_state = ISCSI_PDU_RECV_STATE_ERROR; 4890 break; 4891 } 4892 pdu->mobj = spdk_mempool_get(pool); 4893 if (pdu->mobj == NULL) { 4894 return 0; 4895 } 4896 pdu->data_buf = pdu->mobj->buf; 4897 pdu->data = pdu->mobj->buf; 4898 pdu->data_from_mempool = true; 4899 4900 if (spdk_unlikely(spdk_iscsi_get_dif_ctx(conn, pdu, &pdu->dif_ctx))) { 4901 pdu->dif_insert_or_strip = true; 4902 } 4903 } 4904 4905 /* copy the actual data into local buffer */ 4906 if (pdu->data_valid_bytes < data_len) { 4907 rc = iscsi_conn_read_data_segment(conn, pdu, data_len); 4908 if (rc < 0) { 4909 conn->pdu_recv_state = ISCSI_PDU_RECV_STATE_ERROR; 4910 break; 4911 } 4912 4913 pdu->data_valid_bytes += rc; 4914 if (pdu->data_valid_bytes < data_len) { 4915 return 0; 4916 } 4917 } 4918 4919 /* copy out the data digest */ 4920 if (conn->data_digest && data_len != 0 && 4921 pdu->ddigest_valid_bytes < ISCSI_DIGEST_LEN) { 4922 rc = spdk_iscsi_conn_read_data(conn, 4923 ISCSI_DIGEST_LEN - pdu->ddigest_valid_bytes, 4924 pdu->data_digest + pdu->ddigest_valid_bytes); 4925 if (rc < 0) { 4926 conn->pdu_recv_state = ISCSI_PDU_RECV_STATE_ERROR; 4927 break; 4928 } 4929 4930 pdu->ddigest_valid_bytes += rc; 4931 if (pdu->ddigest_valid_bytes < ISCSI_DIGEST_LEN) { 4932 return 0; 4933 } 4934 } 4935 4936 /* All data for this PDU has now been read from the socket. */ 4937 spdk_trace_record(TRACE_ISCSI_READ_PDU, conn->id, pdu->data_valid_bytes, 4938 (uintptr_t)pdu, pdu->bhs.opcode); 4939 4940 /* check data digest */ 4941 if (conn->data_digest && data_len != 0) { 4942 crc32c = spdk_iscsi_pdu_calc_data_digest(pdu); 4943 rc = MATCH_DIGEST_WORD(pdu->data_digest, crc32c); 4944 if (rc == 0) { 4945 SPDK_ERRLOG("data digest error (%s)\n", conn->initiator_name); 4946 conn->pdu_recv_state = ISCSI_PDU_RECV_STATE_ERROR; 4947 break; 4948 } 4949 } 4950 4951 if (conn->is_logged_out) { 4952 SPDK_ERRLOG("pdu received after logout\n"); 4953 conn->pdu_recv_state = ISCSI_PDU_RECV_STATE_ERROR; 4954 break; 4955 } 4956 4957 if (!pdu->is_rejected) { 4958 rc = iscsi_pdu_payload_handle(conn, pdu); 4959 } else { 4960 rc = 0; 4961 } 4962 if (rc == 0) { 4963 spdk_trace_record(TRACE_ISCSI_TASK_EXECUTED, 0, 0, (uintptr_t)pdu, 0); 4964 spdk_put_pdu(pdu); 4965 conn->pdu_in_progress = NULL; 4966 conn->pdu_recv_state = ISCSI_PDU_RECV_STATE_AWAIT_PDU_READY; 4967 return 1; 4968 } else { 4969 conn->pdu_recv_state = ISCSI_PDU_RECV_STATE_ERROR; 4970 } 4971 break; 4972 case ISCSI_PDU_RECV_STATE_ERROR: 4973 return SPDK_ISCSI_CONNECTION_FATAL; 4974 default: 4975 assert(false); 4976 SPDK_ERRLOG("code should not come here\n"); 4977 break; 4978 } 4979 } while (prev_state != conn->pdu_recv_state); 4980 4981 return 0; 4982 } 4983 4984 #define GET_PDU_LOOP_COUNT 16 4985 4986 int 4987 spdk_iscsi_handle_incoming_pdus(struct spdk_iscsi_conn *conn) 4988 { 4989 int i, rc; 4990 4991 /* Read new PDUs from network */ 4992 for (i = 0; i < GET_PDU_LOOP_COUNT; i++) { 4993 rc = iscsi_read_pdu(conn); 4994 if (rc == 0) { 4995 break; 4996 } else if (rc < 0) { 4997 return rc; 4998 } 4999 5000 if (conn->is_stopped) { 5001 break; 5002 } 5003 } 5004 5005 return i; 5006 } 5007 5008 bool 5009 spdk_iscsi_get_dif_ctx(struct spdk_iscsi_conn *conn, struct spdk_iscsi_pdu *pdu, 5010 struct spdk_dif_ctx *dif_ctx) 5011 { 5012 struct iscsi_bhs *bhs; 5013 uint32_t data_offset = 0; 5014 uint8_t *cdb = NULL; 5015 uint64_t lun; 5016 int lun_id = 0; 5017 struct spdk_scsi_lun *lun_dev; 5018 5019 /* connection is not in full feature phase but non-login opcode 5020 * was received. 5021 */ 5022 if ((!conn->full_feature && conn->state == ISCSI_CONN_STATE_RUNNING) || 5023 conn->state == ISCSI_CONN_STATE_INVALID) { 5024 return false; 5025 } 5026 5027 /* SCSI Command is allowed only in normal session */ 5028 if (conn->sess == NULL || 5029 conn->sess->session_type != SESSION_TYPE_NORMAL) { 5030 return false; 5031 } 5032 5033 bhs = &pdu->bhs; 5034 5035 switch (bhs->opcode) { 5036 case ISCSI_OP_SCSI: { 5037 struct iscsi_bhs_scsi_req *sbhs; 5038 5039 sbhs = (struct iscsi_bhs_scsi_req *)bhs; 5040 data_offset = 0; 5041 cdb = sbhs->cdb; 5042 lun = from_be64(&sbhs->lun); 5043 lun_id = spdk_scsi_lun_id_fmt_to_int(lun); 5044 break; 5045 } 5046 case ISCSI_OP_SCSI_DATAOUT: { 5047 struct iscsi_bhs_data_out *dbhs; 5048 struct spdk_iscsi_task *task; 5049 int transfer_tag; 5050 5051 dbhs = (struct iscsi_bhs_data_out *)bhs; 5052 data_offset = from_be32(&dbhs->buffer_offset); 5053 transfer_tag = from_be32(&dbhs->ttt); 5054 task = get_transfer_task(conn, transfer_tag); 5055 if (task == NULL) { 5056 return false; 5057 } 5058 cdb = task->scsi.cdb; 5059 lun_id = task->lun_id; 5060 break; 5061 } 5062 case ISCSI_OP_SCSI_DATAIN: { 5063 struct iscsi_bhs_data_in *dbhs; 5064 struct spdk_iscsi_task *task; 5065 5066 dbhs = (struct iscsi_bhs_data_in *)bhs; 5067 data_offset = from_be32(&dbhs->buffer_offset); 5068 task = pdu->task; 5069 assert(task != NULL); 5070 cdb = task->scsi.cdb; 5071 lun_id = task->lun_id; 5072 break; 5073 } 5074 default: 5075 return false; 5076 } 5077 5078 lun_dev = spdk_scsi_dev_get_lun(conn->dev, lun_id); 5079 if (lun_dev == NULL) { 5080 return false; 5081 } 5082 5083 return spdk_scsi_lun_get_dif_ctx(lun_dev, cdb, data_offset, dif_ctx); 5084 } 5085 5086 bool spdk_iscsi_is_deferred_free_pdu(struct spdk_iscsi_pdu *pdu) 5087 { 5088 if (pdu == NULL) { 5089 return false; 5090 } 5091 5092 if (pdu->bhs.opcode == ISCSI_OP_R2T || 5093 pdu->bhs.opcode == ISCSI_OP_SCSI_DATAIN) { 5094 return true; 5095 } 5096 5097 return false; 5098 } 5099