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