1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9 * or http://www.opensolaris.org/os/licensing. 10 * See the License for the specific language governing permissions 11 * and limitations under the License. 12 * 13 * When distributing Covered Code, include this CDDL HEADER in each 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 */ 21 22 /* 23 * Copyright (c) 2008, 2010, Oracle and/or its affiliates. All rights reserved. 24 * Copyright 2016 Nexenta Systems, Inc. 25 */ 26 27 #include <sys/cpuvar.h> 28 #include <sys/types.h> 29 #include <sys/conf.h> 30 #include <sys/file.h> 31 #include <sys/ddi.h> 32 #include <sys/sunddi.h> 33 #include <sys/modctl.h> 34 #include <sys/scsi/generic/persist.h> 35 #include <sys/scsi/scsi_names.h> 36 37 #include <sys/socket.h> 38 #include <sys/strsubr.h> 39 #include <sys/sysmacros.h> 40 #include <sys/note.h> 41 #include <sys/sdt.h> 42 #include <sys/errno.h> 43 44 #include <sys/stmf.h> 45 #include <sys/stmf_ioctl.h> 46 #include <sys/portif.h> 47 #include <sys/idm/idm.h> 48 #include <sys/idm/idm_text.h> 49 #include <sys/idm/idm_so.h> 50 51 #define ISCSIT_LOGIN_SM_STRINGS 52 #include "iscsit.h" 53 #include "iscsit_auth.h" 54 55 typedef struct { 56 list_node_t le_ctx_node; 57 iscsit_login_event_t le_ctx_event; 58 idm_pdu_t *le_pdu; 59 } login_event_ctx_t; 60 61 #ifndef TRUE 62 #define TRUE B_TRUE 63 #endif 64 65 #ifndef FALSE 66 #define FALSE B_FALSE 67 #endif 68 69 #define DEFAULT_RADIUS_PORT 1812 70 71 static void 72 login_sm_complete(void *ict_void); 73 74 static void 75 login_sm_event_dispatch(iscsit_conn_login_t *lsm, iscsit_conn_t *ict, 76 login_event_ctx_t *ctx); 77 78 static void 79 login_sm_init(iscsit_conn_t *ict, login_event_ctx_t *ctx); 80 81 static void 82 login_sm_waiting(iscsit_conn_t *ict, login_event_ctx_t *ctx); 83 84 static void 85 login_sm_processing(iscsit_conn_t *ict, login_event_ctx_t *ctx); 86 87 static void 88 login_sm_responding(iscsit_conn_t *ict, login_event_ctx_t *ctx); 89 90 static void 91 login_sm_responded(iscsit_conn_t *ict, login_event_ctx_t *ctx); 92 93 static void 94 login_sm_ffp(iscsit_conn_t *ict, login_event_ctx_t *ctx); 95 96 static void 97 login_sm_done(iscsit_conn_t *ict, login_event_ctx_t *ctx); 98 99 static void 100 login_sm_error(iscsit_conn_t *ict, login_event_ctx_t *ctx); 101 102 static void 103 login_sm_new_state(iscsit_conn_t *ict, login_event_ctx_t *ctx, 104 iscsit_login_state_t new_state); 105 106 static void 107 login_sm_send_ack(iscsit_conn_t *ict, idm_pdu_t *pdu); 108 109 static idm_status_t 110 login_sm_validate_ack(iscsit_conn_t *ict, idm_pdu_t *pdu); 111 112 static boolean_t 113 login_sm_is_last_response(idm_pdu_t *pdu); 114 115 static void 116 login_sm_handle_initial_login(iscsit_conn_t *ict, idm_pdu_t *pdu); 117 118 static void 119 login_sm_send_next_response(iscsit_conn_t *ict, idm_pdu_t *pdu); 120 121 static void 122 login_sm_process_request(iscsit_conn_t *ict); 123 124 static idm_status_t 125 login_sm_req_pdu_check(iscsit_conn_t *ict, idm_pdu_t *pdu); 126 127 static idm_status_t 128 login_sm_process_nvlist(iscsit_conn_t *ict); 129 130 static idm_status_t 131 login_sm_check_security(iscsit_conn_t *ict); 132 133 static idm_pdu_t * 134 login_sm_build_login_response(iscsit_conn_t *ict); 135 136 static void 137 login_sm_ffp_actions(iscsit_conn_t *ict); 138 139 static idm_status_t 140 login_sm_validate_initial_parameters(iscsit_conn_t *ict); 141 142 static idm_status_t 143 login_sm_session_bind(iscsit_conn_t *ict); 144 145 static idm_status_t 146 login_sm_set_auth(iscsit_conn_t *ict); 147 148 static idm_status_t 149 login_sm_session_register(iscsit_conn_t *ict); 150 151 static kv_status_t 152 iscsit_handle_key(iscsit_conn_t *ict, nvpair_t *nvp, char *nvp_name); 153 154 static kv_status_t 155 iscsit_handle_common_key(iscsit_conn_t *ict, nvpair_t *nvp, 156 const idm_kv_xlate_t *ikvx); 157 158 static kv_status_t 159 iscsit_handle_security_key(iscsit_conn_t *ict, nvpair_t *nvp, 160 const idm_kv_xlate_t *ikvx); 161 162 static kv_status_t 163 iscsit_reply_security_key(iscsit_conn_t *ict); 164 165 static kv_status_t 166 iscsit_handle_operational_key(iscsit_conn_t *ict, nvpair_t *nvp, 167 const idm_kv_xlate_t *ikvx); 168 169 static kv_status_t 170 iscsit_reply_numerical(iscsit_conn_t *ict, 171 const char *nvp_name, const uint64_t value); 172 173 static kv_status_t 174 iscsit_reply_string(iscsit_conn_t *ict, 175 const char *nvp_name, const char *text); 176 177 static kv_status_t 178 iscsit_handle_digest(iscsit_conn_t *ict, nvpair_t *choices, 179 const idm_kv_xlate_t *ikvx); 180 181 static kv_status_t 182 iscsit_handle_boolean(iscsit_conn_t *ict, nvpair_t *nvp, boolean_t value, 183 const idm_kv_xlate_t *ikvx, boolean_t iscsit_value); 184 185 static kv_status_t 186 iscsit_handle_numerical(iscsit_conn_t *ict, nvpair_t *nvp, uint64_t value, 187 const idm_kv_xlate_t *ikvx, 188 uint64_t iscsi_min_value, uint64_t iscsi_max_value, 189 uint64_t iscsit_max_value); 190 191 static void 192 iscsit_process_negotiated_values(iscsit_conn_t *ict); 193 194 static void 195 login_resp_complete_cb(idm_pdu_t *pdu, idm_status_t status); 196 197 static idm_status_t 198 iscsit_add_declarative_keys(iscsit_conn_t *ict); 199 200 static char * 201 iscsit_fold_name(char *name, size_t *buflen); 202 203 uint64_t max_dataseglen_target = ISCSIT_MAX_RECV_DATA_SEGMENT_LENGTH; 204 205 /* 206 * global mutex defined in iscsit.c to enforce 207 * login_sm_session_bind as a critical section 208 */ 209 extern kmutex_t login_sm_session_mutex; 210 211 idm_status_t 212 iscsit_login_sm_init(iscsit_conn_t *ict) 213 { 214 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 215 216 bzero(lsm, sizeof (iscsit_conn_login_t)); 217 218 (void) nvlist_alloc(&lsm->icl_negotiated_values, NV_UNIQUE_NAME, 219 KM_SLEEP); 220 221 /* 222 * Hold connection until the login state machine completes 223 */ 224 iscsit_conn_hold(ict); 225 226 /* 227 * Pre-allocating a login response PDU means we will always be 228 * able to respond to a login request -- even if we can't allocate 229 * a data buffer to hold the text responses we can at least send 230 * a login failure. 231 */ 232 lsm->icl_login_resp_tmpl = kmem_zalloc(sizeof (iscsi_login_rsp_hdr_t), 233 KM_SLEEP); 234 235 idm_sm_audit_init(&lsm->icl_state_audit); 236 mutex_init(&lsm->icl_mutex, NULL, MUTEX_DEFAULT, NULL); 237 list_create(&lsm->icl_login_events, sizeof (login_event_ctx_t), 238 offsetof(login_event_ctx_t, le_ctx_node)); 239 list_create(&lsm->icl_pdu_list, sizeof (idm_pdu_t), 240 offsetof(idm_pdu_t, isp_client_lnd)); 241 242 lsm->icl_login_state = ILS_LOGIN_INIT; 243 lsm->icl_login_last_state = ILS_LOGIN_INIT; 244 245 /* 246 * Initialize operational parameters to default values. Anything 247 * we don't specifically negotiate stays at the default. 248 */ 249 ict->ict_op.op_discovery_session = B_FALSE; 250 ict->ict_op.op_initial_r2t = ISCSI_DEFAULT_INITIALR2T; 251 ict->ict_op.op_immed_data = ISCSI_DEFAULT_IMMEDIATE_DATA; 252 ict->ict_op.op_data_pdu_in_order = ISCSI_DEFAULT_DATA_PDU_IN_ORDER; 253 ict->ict_op.op_data_sequence_in_order = 254 ISCSI_DEFAULT_DATA_SEQUENCE_IN_ORDER; 255 ict->ict_op.op_max_connections = ISCSI_DEFAULT_MAX_CONNECTIONS; 256 ict->ict_op.op_max_recv_data_segment_length = 257 ISCSI_DEFAULT_MAX_RECV_SEG_LEN; 258 ict->ict_op.op_max_burst_length = ISCSI_DEFAULT_MAX_BURST_LENGTH; 259 ict->ict_op.op_first_burst_length = ISCSI_DEFAULT_FIRST_BURST_LENGTH; 260 ict->ict_op.op_default_time_2_wait = ISCSI_DEFAULT_TIME_TO_WAIT; 261 ict->ict_op.op_default_time_2_retain = ISCSI_DEFAULT_TIME_TO_RETAIN; 262 ict->ict_op.op_max_outstanding_r2t = ISCSI_DEFAULT_MAX_OUT_R2T; 263 ict->ict_op.op_error_recovery_level = 264 ISCSI_DEFAULT_ERROR_RECOVERY_LEVEL; 265 266 return (IDM_STATUS_SUCCESS); 267 } 268 269 static void 270 login_resp_complete_cb(idm_pdu_t *pdu, idm_status_t status) 271 { 272 iscsit_conn_t *ict = pdu->isp_private; 273 274 /* 275 * Check that this is a login pdu 276 */ 277 ASSERT((pdu->isp_flags & IDM_PDU_LOGIN_TX) != 0); 278 idm_pdu_free(pdu); 279 280 if ((status != IDM_STATUS_SUCCESS) || 281 (ict->ict_login_sm.icl_login_resp_err_class != 0)) { 282 /* 283 * Transport or login error occurred. 284 */ 285 iscsit_login_sm_event(ict, ILE_LOGIN_ERROR, NULL); 286 } 287 iscsit_conn_rele(ict); 288 } 289 290 void 291 iscsit_login_sm_fini(iscsit_conn_t *ict) 292 { 293 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 294 295 mutex_enter(&lsm->icl_mutex); 296 list_destroy(&lsm->icl_pdu_list); 297 list_destroy(&lsm->icl_login_events); 298 299 kmem_free(lsm->icl_login_resp_tmpl, sizeof (iscsi_login_rsp_hdr_t)); 300 301 /* clean up the login response idm text buffer */ 302 if (lsm->icl_login_resp_itb != NULL) { 303 idm_itextbuf_free(lsm->icl_login_resp_itb); 304 lsm->icl_login_resp_itb = NULL; 305 } 306 307 nvlist_free(lsm->icl_negotiated_values); 308 mutex_destroy(&lsm->icl_mutex); 309 } 310 311 void 312 iscsit_login_sm_event(iscsit_conn_t *ict, iscsit_login_event_t event, 313 idm_pdu_t *pdu) 314 { 315 /* 316 * This is a bit ugly but if we're already in ILS_LOGIN_ERROR 317 * or ILS_LOGIN_DONE then just drop any additional events. They 318 * won't change the state and it's possible we've already called 319 * iscsit_login_sm_fini in which case the mutex is destroyed. 320 */ 321 if ((ict->ict_login_sm.icl_login_state == ILS_LOGIN_ERROR) || 322 (ict->ict_login_sm.icl_login_state == ILS_LOGIN_DONE)) 323 return; 324 325 mutex_enter(&ict->ict_login_sm.icl_mutex); 326 iscsit_login_sm_event_locked(ict, event, pdu); 327 mutex_exit(&ict->ict_login_sm.icl_mutex); 328 } 329 void 330 iscsit_login_sm_event_locked(iscsit_conn_t *ict, iscsit_login_event_t event, 331 idm_pdu_t *pdu) 332 { 333 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 334 login_event_ctx_t *ctx; 335 336 ASSERT(mutex_owned(&lsm->icl_mutex)); 337 ctx = kmem_zalloc(sizeof (*ctx), KM_SLEEP); 338 339 ctx->le_ctx_event = event; 340 ctx->le_pdu = pdu; 341 342 list_insert_tail(&lsm->icl_login_events, ctx); 343 344 /* 345 * Use the icl_busy flag to keep the state machine single threaded. 346 * This also serves as recursion avoidance since this flag will 347 * always be set if we call login_sm_event from within the 348 * state machine code. 349 */ 350 if (!lsm->icl_busy) { 351 lsm->icl_busy = B_TRUE; 352 while (!list_is_empty(&lsm->icl_login_events)) { 353 ctx = list_head(&lsm->icl_login_events); 354 list_remove(&lsm->icl_login_events, ctx); 355 idm_sm_audit_event(&lsm->icl_state_audit, 356 SAS_ISCSIT_LOGIN, (int)lsm->icl_login_state, 357 (int)ctx->le_ctx_event, (uintptr_t)pdu); 358 359 /* 360 * If the lsm is in a terminal state, just drain 361 * any remaining events. 362 */ 363 if ((lsm->icl_login_state == ILS_LOGIN_ERROR) || 364 (lsm->icl_login_state == ILS_LOGIN_DONE)) { 365 kmem_free(ctx, sizeof (*ctx)); 366 continue; 367 } 368 mutex_exit(&lsm->icl_mutex); 369 login_sm_event_dispatch(lsm, ict, ctx); 370 mutex_enter(&lsm->icl_mutex); 371 } 372 lsm->icl_busy = B_FALSE; 373 374 /* 375 * When the state machine reaches ILS_LOGIN_DONE or 376 * ILS_LOGIN_ERROR state the login process has completed 377 * and it's time to cleanup. The state machine code will 378 * mark itself "complete" when this happens. 379 * 380 * To protect against spurious events (which shouldn't 381 * happen) set icl_busy again. 382 */ 383 if (lsm->icl_login_complete) { 384 lsm->icl_busy = B_TRUE; 385 if (taskq_dispatch(iscsit_global.global_dispatch_taskq, 386 login_sm_complete, ict, DDI_SLEEP) == 387 TASKQID_INVALID) { 388 cmn_err(CE_WARN, "iscsit_login_sm_event_locked:" 389 " Failed to dispatch task"); 390 } 391 } 392 } 393 } 394 395 static void 396 login_sm_complete(void *ict_void) 397 { 398 iscsit_conn_t *ict = ict_void; 399 400 /* 401 * State machine has run to completion, resources 402 * will be cleaned up when connection is destroyed. 403 */ 404 iscsit_conn_rele(ict); 405 } 406 407 static void 408 login_sm_event_dispatch(iscsit_conn_login_t *lsm, iscsit_conn_t *ict, 409 login_event_ctx_t *ctx) 410 { 411 idm_pdu_t *pdu = ctx->le_pdu; /* Only valid for some events */ 412 413 DTRACE_PROBE2(login__event, iscsit_conn_t *, ict, 414 login_event_ctx_t *, ctx); 415 416 IDM_SM_LOG(CE_NOTE, "login_sm_event_dispatch: ict %p event %s(%d)", 417 (void *)ict, 418 iscsit_ile_name[ctx->le_ctx_event], ctx->le_ctx_event); 419 420 /* State independent actions */ 421 switch (ctx->le_ctx_event) { 422 case ILE_LOGIN_RCV: 423 /* Perform basic sanity checks on the header */ 424 if (login_sm_req_pdu_check(ict, pdu) != IDM_STATUS_SUCCESS) { 425 idm_pdu_t *rpdu; 426 427 SET_LOGIN_ERROR(ict, ISCSI_STATUS_CLASS_INITIATOR_ERR, 428 ISCSI_LOGIN_STATUS_INVALID_REQUEST); 429 /* 430 * If we haven't processed any PDU's yet then use 431 * this one as a template for the response 432 */ 433 if (ict->ict_login_sm.icl_login_resp_tmpl->opcode == 0) 434 login_sm_handle_initial_login(ict, pdu); 435 rpdu = login_sm_build_login_response(ict); 436 login_sm_send_next_response(ict, rpdu); 437 idm_pdu_complete(pdu, IDM_STATUS_SUCCESS); 438 kmem_free(ctx, sizeof (*ctx)); 439 return; 440 } 441 break; 442 default: 443 break; 444 } 445 446 /* State dependent actions */ 447 switch (lsm->icl_login_state) { 448 case ILS_LOGIN_INIT: 449 login_sm_init(ict, ctx); 450 break; 451 case ILS_LOGIN_WAITING: 452 login_sm_waiting(ict, ctx); 453 break; 454 case ILS_LOGIN_PROCESSING: 455 login_sm_processing(ict, ctx); 456 break; 457 case ILS_LOGIN_RESPONDING: 458 login_sm_responding(ict, ctx); 459 break; 460 case ILS_LOGIN_RESPONDED: 461 login_sm_responded(ict, ctx); 462 break; 463 case ILS_LOGIN_FFP: 464 login_sm_ffp(ict, ctx); 465 break; 466 case ILS_LOGIN_DONE: 467 login_sm_done(ict, ctx); 468 break; 469 case ILS_LOGIN_ERROR: 470 login_sm_error(ict, ctx); 471 break; 472 } 473 474 kmem_free(ctx, sizeof (*ctx)); 475 } 476 477 static void 478 login_sm_init(iscsit_conn_t *ict, login_event_ctx_t *ctx) 479 { 480 idm_pdu_t *pdu; 481 482 switch (ctx->le_ctx_event) { 483 case ILE_LOGIN_RCV: 484 pdu = ctx->le_pdu; 485 486 /* 487 * This is the first login PDU we've received so use 488 * it to build the login response template and set our CSG. 489 */ 490 login_sm_handle_initial_login(ict, pdu); 491 492 /* 493 * Accumulate all the login PDU's that make up this 494 * request on a queue. 495 */ 496 mutex_enter(&ict->ict_login_sm.icl_mutex); 497 list_insert_tail(&ict->ict_login_sm.icl_pdu_list, pdu); 498 mutex_exit(&ict->ict_login_sm.icl_mutex); 499 500 if (pdu->isp_hdr->flags & ISCSI_FLAG_LOGIN_CONTINUE) { 501 login_sm_send_ack(ict, pdu); 502 login_sm_new_state(ict, ctx, ILS_LOGIN_WAITING); 503 } else { 504 login_sm_new_state(ict, ctx, ILS_LOGIN_PROCESSING); 505 } 506 break; 507 case ILE_LOGIN_CONN_ERROR: 508 case ILE_LOGIN_ERROR: 509 login_sm_new_state(ict, ctx, ILS_LOGIN_ERROR); 510 break; 511 default: 512 ASSERT(0); 513 } 514 } 515 516 static void 517 login_sm_waiting(iscsit_conn_t *ict, login_event_ctx_t *ctx) 518 { 519 idm_pdu_t *pdu; 520 521 switch (ctx->le_ctx_event) { 522 case ILE_LOGIN_RCV: 523 pdu = ctx->le_pdu; 524 mutex_enter(&ict->ict_login_sm.icl_mutex); 525 list_insert_tail(&ict->ict_login_sm.icl_pdu_list, pdu); 526 mutex_exit(&ict->ict_login_sm.icl_mutex); 527 if (!(pdu->isp_hdr->flags & ISCSI_FLAG_LOGIN_CONTINUE)) { 528 login_sm_new_state(ict, ctx, ILS_LOGIN_PROCESSING); 529 } else { 530 login_sm_send_ack(ict, pdu); 531 } 532 break; 533 case ILE_LOGIN_ERROR: 534 login_sm_new_state(ict, ctx, ILS_LOGIN_ERROR); 535 break; 536 case ILE_LOGIN_RESP_COMPLETE: 537 break; 538 default: 539 ASSERT(0); 540 } 541 } 542 543 static void 544 login_sm_processing(iscsit_conn_t *ict, login_event_ctx_t *ctx) 545 { 546 switch (ctx->le_ctx_event) { 547 case ILE_LOGIN_RESP_READY: 548 login_sm_new_state(ict, ctx, ILS_LOGIN_RESPONDING); 549 break; 550 case ILE_LOGIN_RCV: 551 idm_pdu_complete(ctx->le_pdu, IDM_STATUS_SUCCESS); 552 /*FALLTHROUGH*/ 553 case ILE_LOGIN_CONN_ERROR: 554 case ILE_LOGIN_ERROR: 555 login_sm_new_state(ict, ctx, ILS_LOGIN_ERROR); 556 break; 557 default: 558 ASSERT(0); 559 } 560 } 561 562 static void 563 login_sm_responding(iscsit_conn_t *ict, login_event_ctx_t *ctx) 564 { 565 idm_pdu_t *pdu, *rpdu; 566 567 switch (ctx->le_ctx_event) { 568 case ILE_LOGIN_RCV: 569 pdu = ctx->le_pdu; 570 /* 571 * We should only be in "responding" state if we have not 572 * sent the last PDU of a multi-PDU login response sequence. 573 * In that case we expect this received PDU to be an 574 * acknowledgement from the initiator (login PDU with C 575 * bit cleared and no data). If it's the acknowledgement 576 * we are expecting then we send the next PDU in the login 577 * response sequence. Otherwise it's a protocol error and 578 * the login fails. 579 */ 580 if (login_sm_validate_ack(ict, pdu) == IDM_STATUS_SUCCESS) { 581 rpdu = login_sm_build_login_response(ict); 582 login_sm_send_next_response(ict, rpdu); 583 } else { 584 login_sm_new_state(ict, ctx, ILS_LOGIN_ERROR); 585 } 586 idm_pdu_complete(pdu, IDM_STATUS_SUCCESS); 587 break; 588 case ILE_LOGIN_FFP: 589 login_sm_new_state(ict, ctx, ILS_LOGIN_FFP); 590 break; 591 case ILE_LOGIN_RESP_COMPLETE: 592 login_sm_new_state(ict, ctx, ILS_LOGIN_RESPONDED); 593 break; 594 case ILE_LOGIN_CONN_ERROR: 595 case ILE_LOGIN_ERROR: 596 login_sm_new_state(ict, ctx, ILS_LOGIN_ERROR); 597 break; 598 default: 599 ASSERT(0); 600 } 601 } 602 603 static void 604 login_sm_responded(iscsit_conn_t *ict, login_event_ctx_t *ctx) 605 { 606 idm_pdu_t *pdu; 607 iscsi_login_hdr_t *lh; 608 609 switch (ctx->le_ctx_event) { 610 case ILE_LOGIN_RCV: 611 pdu = ctx->le_pdu; 612 lh = (iscsi_login_hdr_t *)pdu->isp_hdr; 613 /* 614 * Set the CSG, NSG and Transit bits based on the this PDU. 615 * The CSG already validated in login_sm_req_pdu_check(). 616 * We'll clear the transit bit if we encounter any login 617 * parameters in the request that required an additional 618 * login transfer (i.e. no acceptable 619 * choices in range or we needed to change a boolean 620 * value from "Yes" to "No"). 621 */ 622 ict->ict_login_sm.icl_login_csg = 623 ISCSI_LOGIN_CURRENT_STAGE(lh->flags); 624 ict->ict_login_sm.icl_login_nsg = 625 ISCSI_LOGIN_NEXT_STAGE(lh->flags); 626 ict->ict_login_sm.icl_login_transit = 627 lh->flags & ISCSI_FLAG_LOGIN_TRANSIT; 628 mutex_enter(&ict->ict_login_sm.icl_mutex); 629 list_insert_tail(&ict->ict_login_sm.icl_pdu_list, pdu); 630 mutex_exit(&ict->ict_login_sm.icl_mutex); 631 if (pdu->isp_hdr->flags & ISCSI_FLAG_LOGIN_CONTINUE) { 632 login_sm_send_ack(ict, pdu); 633 login_sm_new_state(ict, ctx, ILS_LOGIN_WAITING); 634 } else { 635 login_sm_new_state(ict, ctx, ILS_LOGIN_PROCESSING); 636 } 637 break; 638 case ILE_LOGIN_CONN_ERROR: 639 case ILE_LOGIN_ERROR: 640 login_sm_new_state(ict, ctx, ILS_LOGIN_ERROR); 641 break; 642 default: 643 ASSERT(0); 644 } 645 } 646 647 static void 648 login_sm_ffp(iscsit_conn_t *ict, login_event_ctx_t *ctx) 649 { 650 switch (ctx->le_ctx_event) { 651 case ILE_LOGIN_RESP_COMPLETE: 652 login_sm_new_state(ict, ctx, ILS_LOGIN_DONE); 653 break; 654 case ILE_LOGIN_CONN_ERROR: 655 case ILE_LOGIN_ERROR: 656 login_sm_new_state(ict, ctx, ILS_LOGIN_ERROR); 657 break; 658 default: 659 ASSERT(0); 660 } 661 662 } 663 664 /*ARGSUSED*/ 665 static void 666 login_sm_done(iscsit_conn_t *ict, login_event_ctx_t *ctx) 667 { 668 /* Terminal state, we should get no events */ 669 switch (ctx->le_ctx_event) { 670 case ILE_LOGIN_RCV: 671 /* 672 * We've already processed everything we're going to 673 * process. Drop any additional login PDU's. 674 */ 675 idm_pdu_complete(ctx->le_pdu, IDM_STATUS_SUCCESS); 676 break; 677 case ILE_LOGIN_CONN_ERROR: 678 /* Don't care */ 679 break; 680 default: 681 ASSERT(0); 682 } 683 } 684 685 /*ARGSUSED*/ 686 static void 687 login_sm_error(iscsit_conn_t *ict, login_event_ctx_t *ctx) 688 { 689 switch (ctx->le_ctx_event) { 690 case ILE_LOGIN_RCV: 691 /* 692 * We've already processed everything we're going to 693 * process. Drop any additional login PDU's. 694 */ 695 idm_pdu_complete(ctx->le_pdu, IDM_STATUS_SUCCESS); 696 break; 697 case ILE_LOGIN_CONN_ERROR: 698 /* Don't care */ 699 break; 700 default: 701 ASSERT(0); 702 } 703 } 704 705 static void 706 login_sm_new_state(iscsit_conn_t *ict, login_event_ctx_t *ctx, 707 iscsit_login_state_t new_state) 708 { 709 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 710 idm_pdu_t *rpdu; 711 712 /* 713 * Validate new state 714 */ 715 ASSERT(new_state != ILS_UNDEFINED); 716 ASSERT3U(new_state, <, ILS_MAX_STATE); 717 718 new_state = (new_state < ILS_MAX_STATE) ? 719 new_state : ILS_UNDEFINED; 720 721 IDM_SM_LOG(CE_NOTE, "login_sm_new_state: conn %p " 722 "%s (%d) --> %s (%d)\n", (void *)ict->ict_ic, 723 iscsit_ils_name[lsm->icl_login_state], lsm->icl_login_state, 724 iscsit_ils_name[new_state], new_state); 725 726 DTRACE_PROBE3(login__state__change, 727 iscsit_conn_t *, ict, login_event_ctx_t *, ctx, 728 iscsit_login_state_t, new_state); 729 730 mutex_enter(&lsm->icl_mutex); 731 idm_sm_audit_state_change(&lsm->icl_state_audit, SAS_ISCSIT_LOGIN, 732 (int)lsm->icl_login_state, (int)new_state); 733 lsm->icl_login_last_state = lsm->icl_login_state; 734 lsm->icl_login_state = new_state; 735 mutex_exit(&lsm->icl_mutex); 736 737 /* 738 * Tale of caution here. The use of new_state instead of using 739 * lsm->icl_login_state is deliberate (which had been used originally). 740 * Since the icl_mutex is dropped under the right circumstances 741 * the login state changes between setting the state and examining 742 * the state to proceed. No big surprise since the lock was being 743 * used in the first place to prevent just that type of change. 744 * 745 * There has been a case where network errors occurred while a client 746 * was attempting to reinstate the connection causing multiple 747 * login packets to arrive into the state machine. Those multiple 748 * packets which were processed incorrectly caused the reference 749 * count on the connection to be one higher than it should be and 750 * from then on the connection can't close correctly causing a hang. 751 * 752 * Upon examination of the core it was found that the connection 753 * audit data had calls looking like: 754 * login_sm_event_dispatch 755 * login_sm_processing 756 * login_sm_new_state 757 * That call sequence means the new state was/is ILS_LOGIN_ERROR 758 * yet the audit trail continues with a call to 759 * login_sm_send_next_response 760 * which could only occur if icl_login_state had changed. Had the 761 * design of COMSTAR taken this into account the code would 762 * originally have held the icl_mutex across the processing of the 763 * state processing. Lock order and calls which sleep prevent that 764 * from being possible. The next best solution is to use the local 765 * variable which holds the state. 766 */ 767 switch (new_state) { 768 case ILS_LOGIN_WAITING: 769 /* Do nothing, waiting for more login PDU's */ 770 break; 771 case ILS_LOGIN_PROCESSING: 772 /* All login PDU's received, process login request */ 773 login_sm_process_request(ict); 774 break; 775 case ILS_LOGIN_RESPONDING: 776 rpdu = login_sm_build_login_response(ict); 777 login_sm_send_next_response(ict, rpdu); 778 break; 779 case ILS_LOGIN_RESPONDED: 780 /* clean up the login response idm text buffer */ 781 if (lsm->icl_login_resp_itb != NULL) { 782 idm_itextbuf_free(lsm->icl_login_resp_itb); 783 lsm->icl_login_resp_itb = NULL; 784 } 785 break; 786 case ILS_LOGIN_FFP: 787 login_sm_ffp_actions(ict); 788 break; 789 case ILS_LOGIN_DONE: 790 case ILS_LOGIN_ERROR: 791 /* 792 * Flag the terminal state for the dispatcher 793 */ 794 lsm->icl_login_complete = B_TRUE; 795 break; 796 case ILS_LOGIN_INIT: /* Initial state, can't return */ 797 default: 798 ASSERT(0); 799 /*NOTREACHED*/ 800 } 801 } 802 803 /*ARGSUSED*/ 804 static void 805 login_sm_send_ack(iscsit_conn_t *ict, idm_pdu_t *pdu) 806 { 807 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 808 idm_pdu_t *lack; 809 810 /* 811 * allocate the response pdu 812 */ 813 lack = idm_pdu_alloc(sizeof (iscsi_hdr_t), 0); 814 idm_pdu_init(lack, ict->ict_ic, ict, login_resp_complete_cb); 815 lack->isp_flags |= IDM_PDU_LOGIN_TX; 816 817 /* 818 * copy the response template into the response pdu 819 */ 820 bcopy(lsm->icl_login_resp_tmpl, lack->isp_hdr, sizeof (iscsi_hdr_t)); 821 822 iscsit_conn_hold(ict); 823 idm_pdu_tx(lack); 824 } 825 826 /*ARGSUSED*/ 827 static idm_status_t 828 login_sm_validate_ack(iscsit_conn_t *ict, idm_pdu_t *pdu) 829 { 830 iscsi_hdr_t *ihp = pdu->isp_hdr; 831 if (ihp->flags & ISCSI_FLAG_TEXT_CONTINUE) { 832 return (IDM_STATUS_FAIL); 833 } 834 if (ntoh24(ihp->dlength) != 0) { 835 return (IDM_STATUS_FAIL); 836 } 837 return (IDM_STATUS_SUCCESS); 838 } 839 840 static boolean_t 841 login_sm_is_last_response(idm_pdu_t *pdu) 842 { 843 844 if (pdu->isp_hdr->flags & ISCSI_FLAG_LOGIN_CONTINUE) { 845 return (B_FALSE); 846 } 847 return (B_TRUE); 848 } 849 850 851 static void 852 login_sm_handle_initial_login(iscsit_conn_t *ict, idm_pdu_t *pdu) 853 { 854 iscsi_login_hdr_t *lh_req = (iscsi_login_hdr_t *)pdu->isp_hdr; 855 iscsi_login_rsp_hdr_t *lh_resp = 856 ict->ict_login_sm.icl_login_resp_tmpl; 857 858 /* 859 * First login PDU, this connection should not have a sesssion 860 * associated. 861 */ 862 ASSERT(ict->ict_sess == NULL); 863 864 /* 865 * Save off TSIH and ISID for later use in finding a session 866 */ 867 ict->ict_login_sm.icl_cmdsn = ntohl(lh_req->cmdsn); 868 ict->ict_login_sm.icl_tsih = ntohs(lh_req->tsid); 869 bcopy(lh_req->isid, ict->ict_login_sm.icl_isid, ISCSI_ISID_LEN); 870 871 /* 872 * We'll need the CID as well 873 */ 874 ict->ict_cid = ntohs(lh_req->cid); 875 876 /* 877 * Set the CSG, NSG and Transit bits based on the first PDU 878 * in the login sequence. The CSG already validated in 879 * login_sm_req_pdu_check(). We'll clear the transit bit if 880 * we encounter any login parameters in the request that 881 * required an additional login transfer (i.e. no acceptable 882 * choices in range or we needed to change a boolean 883 * value from "Yes" to "No"). 884 */ 885 ict->ict_login_sm.icl_login_csg = 886 ISCSI_LOGIN_CURRENT_STAGE(lh_req->flags); 887 ict->ict_login_sm.icl_login_nsg = 888 ISCSI_LOGIN_NEXT_STAGE(lh_req->flags); 889 ict->ict_login_sm.icl_login_transit = 890 lh_req->flags & ISCSI_FLAG_LOGIN_TRANSIT; 891 892 /* 893 * Initialize header for login reject response. This will also 894 * be copied for use as a template for other login responses 895 */ 896 lh_resp->opcode = ISCSI_OP_LOGIN_RSP; 897 lh_resp->max_version = ISCSIT_MAX_VERSION; 898 899 /* 900 * We already validated that we can support one of the initiator's 901 * versions in login_sm_req_pdu_check(). 902 */ 903 #if (ISCSIT_MAX_VERSION > 0) 904 if (ISCSIT_MAX_VERSION >= lh_req->min_version) { 905 lh_resp->active_version = 906 MIN(lh_req->max_version, ISCSIT_MAX_VERSION); 907 } else { 908 ASSERT(ISCSIT_MAX_VERSION <= lh_req->max_version); 909 lh_resp->active_version = ISCSIT_MAX_VERSION; 910 } 911 #endif 912 913 lh_resp->hlength = 0; /* No AHS */ 914 bcopy(lh_req->isid, lh_resp->isid, ISCSI_ISID_LEN); 915 lh_resp->tsid = lh_req->tsid; 916 lh_resp->itt = lh_req->itt; 917 918 /* 919 * StatSn, ExpCmdSn and MaxCmdSn will be set immediately before 920 * transmission 921 */ 922 } 923 924 static void 925 login_sm_send_next_response(iscsit_conn_t *ict, idm_pdu_t *pdu) 926 { 927 iscsi_login_rsp_hdr_t *lh_resp = (iscsi_login_rsp_hdr_t *)pdu->isp_hdr; 928 929 /* Make sure this PDU is part of the login phase */ 930 ASSERT((pdu->isp_flags & IDM_PDU_LOGIN_TX) != 0); 931 932 /* 933 * Fill in header values 934 */ 935 hton24(lh_resp->dlength, pdu->isp_datalen); 936 937 /* 938 * If the login is successful, this login response will contain 939 * the next StatSN and advance the StatSN for the connection. 940 */ 941 if (lh_resp->status_class == ISCSI_STATUS_CLASS_SUCCESS) { 942 ASSERT(ict->ict_sess != NULL); 943 944 if ((lh_resp->flags & ISCSI_FLAG_LOGIN_TRANSIT) && 945 (ISCSI_LOGIN_NEXT_STAGE(lh_resp->flags) == 946 ISCSI_FULL_FEATURE_PHASE) && 947 !(lh_resp->flags & ISCSI_FLAG_LOGIN_CONTINUE)) { 948 iscsit_login_sm_event(ict, ILE_LOGIN_FFP, NULL); 949 } 950 if (login_sm_is_last_response(pdu) == B_TRUE) { 951 /* 952 * The last of a potentially mult-PDU response finished. 953 */ 954 iscsit_login_sm_event(ict, ILE_LOGIN_RESP_COMPLETE, 955 NULL); 956 } 957 958 iscsit_conn_hold(ict); 959 pdu->isp_flags |= IDM_PDU_SET_STATSN | IDM_PDU_ADVANCE_STATSN; 960 iscsit_pdu_tx(pdu); 961 } else { 962 /* 963 * If status_class != ISCSI_STATUS_CLASS_SUCCESS then 964 * StatSN is not valid and we can call idm_pdu_tx instead 965 * of iscsit_pdu_tx. This is very good thing since in 966 * some cases of login failure we may not have a session. 967 * Since iscsit_calc_rspsn grabs the session mutex while 968 * it is retrieving values for expcmdsn and maxcmdsn this 969 * would cause a panic. 970 * 971 * Since we still want a value for expcmdsn, fill in an 972 * appropriate value based on the login request before 973 * sending the response. Cmdsn/expcmdsn do not advance during 974 * login phase. 975 */ 976 lh_resp->expcmdsn = htonl(ict->ict_login_sm.icl_cmdsn); 977 lh_resp->maxcmdsn = htonl(ict->ict_login_sm.icl_cmdsn + 1); 978 979 iscsit_conn_hold(ict); 980 idm_pdu_tx(pdu); 981 } 982 983 } 984 985 static void 986 login_sm_process_request(iscsit_conn_t *ict) 987 { 988 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 989 uint8_t error_class = 0; 990 uint8_t error_detail = 0; 991 992 /* 993 * First walk all the PDU's that make up this login request 994 * and compile all the iSCSI key-value pairs into nvlist format. 995 */ 996 997 ASSERT(lsm->icl_request_nvlist == NULL); 998 /* create an nvlist for request key/value pairs */ 999 if (idm_pdu_list_to_nvlist(&lsm->icl_pdu_list, 1000 &lsm->icl_request_nvlist, &error_detail) != IDM_STATUS_SUCCESS) { 1001 error_class = ISCSI_STATUS_CLASS_TARGET_ERR; 1002 SET_LOGIN_ERROR(ict, error_class, error_detail); 1003 goto request_fail; 1004 } 1005 1006 /* Allocate a new nvlist for response key/value pairs */ 1007 ASSERT(lsm->icl_response_nvlist == NULL); 1008 if (nvlist_alloc(&lsm->icl_response_nvlist, NV_UNIQUE_NAME, 1009 KM_NOSLEEP) != 0) { 1010 error_class = ISCSI_STATUS_CLASS_TARGET_ERR; 1011 error_detail = ISCSI_LOGIN_STATUS_NO_RESOURCES; 1012 SET_LOGIN_ERROR(ict, error_class, error_detail); 1013 goto request_fail; 1014 } 1015 1016 /* 1017 * This would be a very good time to make sure we have 1018 * negotiated the required values for the login phase. For 1019 * example we definitely should have defined InitiatorName, 1020 * and Target name regardless of our current login phase. 1021 */ 1022 if (!ict->ict_op.op_initial_params_set) { 1023 if (login_sm_validate_initial_parameters(ict) != 1024 IDM_STATUS_SUCCESS) { 1025 goto request_fail; 1026 } 1027 1028 /* 1029 * Now setup our session association. This includes 1030 * create a new session or looking up an existing session, 1031 * and if this is not a discovery session then we will 1032 * also register this session with STMF. 1033 */ 1034 if (login_sm_session_bind(ict) != IDM_STATUS_SUCCESS) { 1035 goto request_fail; 1036 } 1037 1038 if (login_sm_set_auth(ict) != IDM_STATUS_SUCCESS) { 1039 goto request_fail; 1040 } 1041 1042 /* 1043 * Prepend TargetAlias and PortalGroupTag 1044 */ 1045 if (ict->ict_op.op_discovery_session == B_FALSE) { 1046 if ((lsm->icl_auth.ca_tgt_alias[0]) != '\0') { 1047 (void) iscsit_reply_string(ict, 1048 "TargetAlias", 1049 &lsm->icl_auth.ca_tgt_alias[0]); 1050 } 1051 (void) iscsit_reply_numerical(ict, 1052 "TargetPortalGroupTag", 1053 (uint64_t)lsm->icl_tpgt_tag); 1054 } 1055 1056 ict->ict_op.op_initial_params_set = B_TRUE; 1057 } 1058 1059 if (login_sm_process_nvlist(ict) != IDM_STATUS_SUCCESS) { 1060 goto request_fail; 1061 } 1062 1063 if (login_sm_check_security(ict) != IDM_STATUS_SUCCESS) { 1064 goto request_fail; 1065 } 1066 1067 /* clean up request_nvlist */ 1068 if (lsm->icl_request_nvlist != NULL) { 1069 nvlist_free(lsm->icl_request_nvlist); 1070 lsm->icl_request_nvlist = NULL; 1071 } 1072 1073 /* convert any responses to textbuf form */ 1074 ASSERT(lsm->icl_login_resp_itb == NULL); 1075 if (lsm->icl_response_nvlist) { 1076 lsm->icl_login_resp_itb = idm_nvlist_to_itextbuf( 1077 lsm->icl_response_nvlist); 1078 if (lsm->icl_login_resp_itb == NULL) { 1079 /* Still need to send the resp so continue */ 1080 SET_LOGIN_ERROR(ict, 1081 ISCSI_STATUS_CLASS_TARGET_ERR, 1082 ISCSI_LOGIN_STATUS_NO_RESOURCES); 1083 } 1084 /* clean up response_nvlist */ 1085 nvlist_free(lsm->icl_response_nvlist); 1086 lsm->icl_response_nvlist = NULL; 1087 } 1088 1089 /* tell the state machine to send the textbuf */ 1090 iscsit_login_sm_event(ict, ILE_LOGIN_RESP_READY, NULL); 1091 return; 1092 1093 request_fail: 1094 1095 /* clean up request_nvlist and response_nvlist */ 1096 if (lsm->icl_request_nvlist != NULL) { 1097 nvlist_free(lsm->icl_request_nvlist); 1098 lsm->icl_request_nvlist = NULL; 1099 } 1100 if (lsm->icl_response_nvlist != NULL) { 1101 nvlist_free(lsm->icl_response_nvlist); 1102 lsm->icl_response_nvlist = NULL; 1103 } 1104 /* Make sure we already set the login error */ 1105 if (ict->ict_login_sm.icl_login_resp_err_class == 1106 ISCSI_STATUS_CLASS_SUCCESS) { 1107 SET_LOGIN_ERROR(ict, 1108 ISCSI_STATUS_CLASS_TARGET_ERR, 1109 ISCSI_LOGIN_STATUS_TARGET_ERROR); 1110 } 1111 iscsit_login_sm_event(ict, ILE_LOGIN_RESP_READY, NULL); 1112 } 1113 1114 1115 static void 1116 login_sm_ffp_actions(iscsit_conn_t *ict) 1117 { 1118 iscsit_process_negotiated_values(ict); 1119 } 1120 1121 static idm_status_t 1122 login_sm_validate_initial_parameters(iscsit_conn_t *ict) 1123 { 1124 int nvrc; 1125 char *string_val; 1126 char *u8_iscsi_name; 1127 size_t u8_iscsi_name_len; 1128 uint8_t error_class = ISCSI_STATUS_CLASS_INITIATOR_ERR; 1129 uint8_t error_detail = ISCSI_LOGIN_STATUS_MISSING_FIELDS; 1130 idm_status_t status = IDM_STATUS_FAIL; 1131 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 1132 1133 /* 1134 * Make sure we received the required information from the initial 1135 * login. Add these declaratives to the negotiated list and 1136 * remove them from the request list as we go. If anything fails, 1137 * the caller will clean-up the nvlists. 1138 */ 1139 1140 /* 1141 * Initiator name 1142 */ 1143 if ((nvrc = nvlist_lookup_string(lsm->icl_request_nvlist, 1144 "InitiatorName", &string_val)) != 0) { 1145 goto initial_params_done; 1146 } 1147 1148 u8_iscsi_name = iscsit_fold_name(string_val, &u8_iscsi_name_len); 1149 if (u8_iscsi_name == NULL) 1150 goto initial_params_done; 1151 nvrc = nvlist_add_string(lsm->icl_negotiated_values, "InitiatorName", 1152 u8_iscsi_name); 1153 kmem_free(u8_iscsi_name, u8_iscsi_name_len); 1154 if (nvrc != 0) 1155 goto initial_params_done; 1156 1157 if ((nvrc = nvlist_lookup_string(lsm->icl_negotiated_values, 1158 "InitiatorName", &string_val)) != 0) { 1159 goto initial_params_done; 1160 } 1161 lsm->icl_initiator_name = string_val; 1162 idm_conn_set_initiator_name(ict->ict_ic, lsm->icl_initiator_name); 1163 if ((nvrc = nvlist_remove(lsm->icl_request_nvlist, 1164 "InitiatorName", DATA_TYPE_STRING)) != 0) { 1165 goto initial_params_done; 1166 } 1167 1168 /* 1169 * Session type 1170 */ 1171 ict->ict_op.op_discovery_session = B_FALSE; 1172 nvrc = nvlist_lookup_string(lsm->icl_request_nvlist, 1173 "SessionType", &string_val); 1174 if (nvrc != ENOENT && nvrc != 0) { 1175 goto initial_params_done; 1176 } 1177 if (nvrc == 0) { 1178 if (strcmp(string_val, "Discovery") == 0) { 1179 ict->ict_op.op_discovery_session = B_TRUE; 1180 } else if (strcmp(string_val, "Normal") != 0) { 1181 goto initial_params_done; 1182 } 1183 if ((nvrc = nvlist_add_string(lsm->icl_negotiated_values, 1184 "SessionType", string_val)) != 0) { 1185 goto initial_params_done; 1186 } 1187 if ((nvrc = nvlist_remove(lsm->icl_request_nvlist, 1188 "SessionType", DATA_TYPE_STRING)) != 0) { 1189 goto initial_params_done; 1190 } 1191 } 1192 1193 /* 1194 * Must have either TargetName or SessionType==Discovery 1195 */ 1196 lsm->icl_target_name = NULL; 1197 nvrc = nvlist_lookup_string(lsm->icl_request_nvlist, 1198 "TargetName", &string_val); 1199 if (nvrc != ENOENT && nvrc != 0) { 1200 goto initial_params_done; 1201 } 1202 if (nvrc == 0) { 1203 u8_iscsi_name = iscsit_fold_name(string_val, 1204 &u8_iscsi_name_len); 1205 if (u8_iscsi_name == NULL) 1206 goto initial_params_done; 1207 nvrc = nvlist_add_string(lsm->icl_negotiated_values, 1208 "TargetName", u8_iscsi_name); 1209 kmem_free(u8_iscsi_name, u8_iscsi_name_len); 1210 if (nvrc != 0) 1211 goto initial_params_done; 1212 if ((nvrc = nvlist_lookup_string(lsm->icl_negotiated_values, 1213 "TargetName", &string_val)) != 0) { 1214 goto initial_params_done; 1215 } 1216 lsm->icl_target_name = string_val; 1217 idm_conn_set_target_name(ict->ict_ic, lsm->icl_target_name); 1218 if ((nvrc = nvlist_remove(lsm->icl_request_nvlist, 1219 "TargetName", DATA_TYPE_STRING)) != 0) { 1220 goto initial_params_done; 1221 } 1222 } else if (ict->ict_op.op_discovery_session == B_FALSE) { 1223 /* 1224 * Missing target name 1225 */ 1226 goto initial_params_done; 1227 } 1228 1229 idm_conn_set_isid(ict->ict_ic, lsm->icl_isid); 1230 (void) snprintf(ict->ict_ic->ic_tsih, ISCSI_MAX_TSIH_LEN + 1, "0x%04x", 1231 lsm->icl_tsih); 1232 1233 IDM_SM_LOG(CE_NOTE, "conn %p: initiator=%s", (void *)ict->ict_ic, 1234 (lsm->icl_initiator_name == NULL) ? "N/A" : 1235 lsm->icl_initiator_name); 1236 IDM_SM_LOG(CE_NOTE, "conn %p: target=%s", (void *)ict->ict_ic, 1237 (lsm->icl_target_name == NULL) ? "N/A" : 1238 lsm->icl_target_name); 1239 IDM_SM_LOG(CE_NOTE, "conn %p: sessiontype=%s", (void *)ict->ict_ic, 1240 ict->ict_op.op_discovery_session ? "Discovery" : "Normal"); 1241 1242 /* Sucess */ 1243 status = IDM_STATUS_SUCCESS; 1244 error_class = ISCSI_STATUS_CLASS_SUCCESS; 1245 error_detail = ISCSI_LOGIN_STATUS_ACCEPT; 1246 1247 initial_params_done: 1248 SET_LOGIN_ERROR(ict, error_class, error_detail); 1249 return (status); 1250 } 1251 1252 1253 /* 1254 * login_sm_session_bind 1255 * 1256 * This function looks at the data from the initial login request 1257 * of a new connection and either looks up and existing session, 1258 * creates a new session, or returns an error. RFC3720 section 5.3.1 1259 * defines these rules: 1260 * 1261 * +------------------------------------------------------------------+ 1262 * |ISID | TSIH | CID | Target action | 1263 * +------------------------------------------------------------------+ 1264 * |new | non-zero | any | fail the login | 1265 * | | | | ("session does not exist") | 1266 * +------------------------------------------------------------------+ 1267 * |new | zero | any | instantiate a new session | 1268 * +------------------------------------------------------------------+ 1269 * |existing | zero | any | do session reinstatement | 1270 * | | | | (see section 5.3.5) | 1271 * +------------------------------------------------------------------+ 1272 * |existing | non-zero | new | add a new connection to | 1273 * | | existing | | the session | 1274 * +------------------------------------------------------------------+ 1275 * |existing | non-zero |existing| do connection reinstatement| 1276 * | | existing | | (see section 5.3.4) | 1277 * +------------------------------------------------------------------+ 1278 * |existing | non-zero | any | fail the login | 1279 * | | new | | ("session does not exist") | 1280 * +------------------------------------------------------------------+ 1281 * 1282 */ 1283 1284 /* 1285 * Map an <ipv6,port> address to an <ipv4,port> address if possible. 1286 * Returns: 1287 * 1 - success 1288 * 0 - address not mapable 1289 */ 1290 1291 int 1292 iscsit_is_v4_mapped(struct sockaddr_storage *sa, struct sockaddr_storage *v4sa) 1293 { 1294 struct sockaddr_in *sin; 1295 struct in_addr *in; 1296 struct sockaddr_in6 *sin6; 1297 struct in6_addr *in6; 1298 int ret = 0; 1299 1300 sin6 = (struct sockaddr_in6 *)sa; 1301 in6 = &sin6->sin6_addr; 1302 if ((sa->ss_family == AF_INET6) && 1303 (IN6_IS_ADDR_V4MAPPED(in6) || IN6_IS_ADDR_V4COMPAT(in6))) { 1304 sin = (struct sockaddr_in *)v4sa; 1305 in = &sin->sin_addr; 1306 v4sa->ss_family = AF_INET; 1307 sin->sin_port = sin6->sin6_port; 1308 IN6_V4MAPPED_TO_INADDR(in6, in); 1309 ret = 1; 1310 } 1311 return (ret); 1312 } 1313 1314 static idm_status_t 1315 login_sm_session_bind(iscsit_conn_t *ict) 1316 { 1317 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 1318 iscsit_tgt_t *tgt = NULL; 1319 iscsit_tpgt_t *tpgt = NULL; 1320 iscsit_portal_t *portal = NULL; 1321 iscsit_sess_t *existing_sess = NULL; 1322 iscsit_sess_t *new_sess = NULL; 1323 iscsit_conn_t *existing_ict = NULL; 1324 uint8_t error_class; 1325 uint8_t error_detail; 1326 1327 /* 1328 * The multi-threaded execution of binding login sessions to target 1329 * introduced race conditions in the session creation/binding and 1330 * allowed duplicate sessions to tbe created. The addition of the 1331 * global mutex login_sm_session_mutex makes this function single 1332 * threaded to avoid such race conditions. Although this causes 1333 * a small portion of the login to be serialized, it is unlikely 1334 * that there would be numerous simultaneous logins to become a 1335 * performance issue. 1336 */ 1337 mutex_enter(&login_sm_session_mutex); 1338 1339 /* 1340 * Look up target and then check if there are sessions or connections 1341 * that match this request (see below). Any holds taken on objects 1342 * must be released at the end of the function (let's keep things 1343 * simple). 1344 * 1345 * If target name is set then we should have a corresponding target 1346 * context configured. 1347 */ 1348 if (lsm->icl_target_name != NULL) { 1349 /* 1350 * iscsit_tgt_lookup implicitly takes a ref on the target 1351 */ 1352 ISCSIT_GLOBAL_LOCK(RW_READER); 1353 tgt = iscsit_tgt_lookup_locked(lsm->icl_target_name); 1354 if (tgt == NULL) { 1355 ISCSIT_GLOBAL_UNLOCK(); 1356 SET_LOGIN_ERROR(ict, ISCSI_STATUS_CLASS_INITIATOR_ERR, 1357 ISCSI_LOGIN_STATUS_TGT_NOT_FOUND); 1358 goto session_bind_error; 1359 } else { 1360 mutex_enter(&tgt->target_mutex); 1361 tpgt = avl_first(&tgt->target_tpgt_list); 1362 1363 if (IS_DEFAULT_TPGT(tpgt)) { 1364 lsm->icl_tpgt_tag = ISCSIT_DEFAULT_TPGT; 1365 } else { 1366 /* 1367 * Find the portal group tag for the 1368 * login response. 1369 */ 1370 struct sockaddr_storage v4sa, *sa; 1371 1372 sa = &ict->ict_ic->ic_laddr; 1373 portal = iscsit_tgt_lookup_portal(tgt, 1374 sa, &tpgt); 1375 if (portal == NULL && 1376 iscsit_is_v4_mapped(sa, &v4sa)) { 1377 /* 1378 * Try again if the local address 1379 * was v6 mappable to v4. 1380 */ 1381 portal = iscsit_tgt_lookup_portal(tgt, 1382 &v4sa, &tpgt); 1383 1384 } 1385 if (portal == NULL) { 1386 /* 1387 * Initiator came in on wrong address 1388 */ 1389 SET_LOGIN_ERROR(ict, 1390 ISCSI_STATUS_CLASS_INITIATOR_ERR, 1391 ISCSI_LOGIN_STATUS_TGT_NOT_FOUND); 1392 mutex_exit(&tgt->target_mutex); 1393 ISCSIT_GLOBAL_UNLOCK(); 1394 goto session_bind_error; 1395 } 1396 1397 /* 1398 * Need to release holds on the portal and 1399 * tpgt after processing is complete. 1400 */ 1401 lsm->icl_tpgt_tag = tpgt->tpgt_tag; 1402 iscsit_portal_rele(portal); 1403 iscsit_tpgt_rele(tpgt); 1404 } 1405 1406 mutex_enter(&iscsit_global.global_state_mutex); 1407 if ((tgt->target_state != TS_STMF_ONLINE) || 1408 ((iscsit_global.global_svc_state != ISE_ENABLED) && 1409 ((iscsit_global.global_svc_state != ISE_BUSY)))) { 1410 mutex_exit(&iscsit_global.global_state_mutex); 1411 SET_LOGIN_ERROR(ict, 1412 ISCSI_STATUS_CLASS_TARGET_ERR, 1413 ISCSI_LOGIN_STATUS_SVC_UNAVAILABLE); 1414 mutex_exit(&tgt->target_mutex); 1415 ISCSIT_GLOBAL_UNLOCK(); 1416 goto session_bind_error; 1417 } 1418 mutex_exit(&iscsit_global.global_state_mutex); 1419 mutex_exit(&tgt->target_mutex); 1420 ISCSIT_GLOBAL_UNLOCK(); 1421 } 1422 } 1423 1424 ASSERT((tgt != NULL) || (ict->ict_op.op_discovery_session == B_TRUE)); 1425 1426 /* 1427 * Check if there is an existing session matching this ISID. If 1428 * tgt == NULL then we'll look for the session on the global list 1429 * of discovery session. If we find a session then the ISID 1430 * exists. 1431 */ 1432 existing_sess = iscsit_tgt_lookup_sess(tgt, lsm->icl_initiator_name, 1433 lsm->icl_isid, lsm->icl_tsih, lsm->icl_tpgt_tag); 1434 if (existing_sess != NULL) { 1435 existing_ict = iscsit_sess_lookup_conn(existing_sess, 1436 ict->ict_cid); 1437 } 1438 1439 /* 1440 * If this is a discovery session, make sure it has appropriate 1441 * parameters. 1442 */ 1443 if ((ict->ict_op.op_discovery_session == B_TRUE) && 1444 ((lsm->icl_tsih != ISCSI_UNSPEC_TSIH) || (existing_sess != NULL))) { 1445 /* XXX Do we need to check for existing ISID (sess != NULL)? */ 1446 SET_LOGIN_ERROR(ict, ISCSI_STATUS_CLASS_INITIATOR_ERR, 1447 ISCSI_LOGIN_STATUS_INVALID_REQUEST); 1448 goto session_bind_error; 1449 } 1450 1451 /* 1452 * Check the two error conditions from the table. 1453 * 1454 * ISID=new, TSIH=non-zero 1455 */ 1456 if ((existing_sess == NULL) && (lsm->icl_tsih != ISCSI_UNSPEC_TSIH)) { 1457 /* fail the login */ 1458 SET_LOGIN_ERROR(ict, ISCSI_STATUS_CLASS_INITIATOR_ERR, 1459 ISCSI_LOGIN_STATUS_NO_SESSION); 1460 goto session_bind_error; 1461 } 1462 1463 /* ISID=existing, TSIH=non-zero new */ 1464 if ((existing_sess != NULL) && (lsm->icl_tsih != 0) && 1465 (existing_sess->ist_tsih != lsm->icl_tsih)) { 1466 /* fail the login */ 1467 SET_LOGIN_ERROR(ict, ISCSI_STATUS_CLASS_INITIATOR_ERR, 1468 ISCSI_LOGIN_STATUS_NO_SESSION); 1469 goto session_bind_error; 1470 } 1471 1472 /* 1473 * Handle the remaining table cases in order 1474 */ 1475 if (existing_sess == NULL) { 1476 /* Should have caught this above */ 1477 ASSERT(lsm->icl_tsih == ISCSI_UNSPEC_TSIH); 1478 /* 1479 * ISID=new, TSIH=zero --> instantiate a new session 1480 */ 1481 new_sess = iscsit_sess_create(tgt, ict, lsm->icl_cmdsn, 1482 lsm->icl_isid, lsm->icl_tpgt_tag, lsm->icl_initiator_name, 1483 lsm->icl_target_name, &error_class, &error_detail); 1484 ASSERT(new_sess != NULL); 1485 1486 /* Session create may have failed even if it returned a value */ 1487 if (error_class != ISCSI_STATUS_CLASS_SUCCESS) { 1488 SET_LOGIN_ERROR(ict, error_class, error_detail); 1489 goto session_bind_error; 1490 } 1491 1492 /* 1493 * If we don't already have an STMF session and this is not 1494 * a discovery session then we need to allocate and register 1495 * one. 1496 */ 1497 if (!ict->ict_op.op_discovery_session) { 1498 if (login_sm_session_register(ict) != 1499 IDM_STATUS_SUCCESS) { 1500 /* login_sm_session_register sets error codes */ 1501 goto session_bind_error; 1502 } 1503 } 1504 1505 } else { 1506 if (lsm->icl_tsih == ISCSI_UNSPEC_TSIH) { 1507 /* 1508 * ISID=existing, TSIH=zero --> Session reinstatement 1509 */ 1510 new_sess = iscsit_sess_reinstate(tgt, existing_sess, 1511 ict, &error_class, &error_detail); 1512 ASSERT(new_sess != NULL); 1513 1514 if (error_class != ISCSI_STATUS_CLASS_SUCCESS) { 1515 SET_LOGIN_ERROR(ict, error_class, error_detail); 1516 goto session_bind_error; 1517 } 1518 1519 /* 1520 * If we don't already have an STMF session and this is 1521 * not a discovery session then we need to allocate and 1522 * register one. 1523 */ 1524 if (!ict->ict_op.op_discovery_session) { 1525 if (login_sm_session_register(ict) != 1526 IDM_STATUS_SUCCESS) { 1527 /* 1528 * login_sm_session_register sets 1529 * error codes 1530 */ 1531 goto session_bind_error; 1532 } 1533 } 1534 } else { 1535 /* 1536 * The following code covers these two cases: 1537 * ISID=existing, TSIH=non-zero existing, CID=new 1538 * --> add new connection to MC/S session 1539 * ISID=existing, TSIH=non-zero existing, CID=existing 1540 * --> do connection reinstatement 1541 * 1542 * Session continuation uses this path as well 1543 */ 1544 cmn_err(CE_NOTE, "login_sm_session_bind: add new " 1545 "conn/sess continue"); 1546 if (existing_ict != NULL) { 1547 /* 1548 * ISID=existing, TSIH=non-zero existing, 1549 * CID=existing --> do connection reinstatement 1550 */ 1551 if (iscsit_conn_reinstate(existing_ict, ict) != 1552 IDM_STATUS_SUCCESS) { 1553 /* 1554 * Most likely this means the connection 1555 * the initiator is trying to reinstate 1556 * is not in an acceptable state. 1557 */ 1558 SET_LOGIN_ERROR(ict, 1559 ISCSI_STATUS_CLASS_INITIATOR_ERR, 1560 ISCSI_LOGIN_STATUS_INIT_ERR); 1561 goto session_bind_error; 1562 } 1563 } 1564 1565 iscsit_sess_sm_event(existing_sess, SE_CONN_IN_LOGIN, 1566 ict); 1567 } 1568 } 1569 1570 if (tgt != NULL) 1571 iscsit_tgt_rele(tgt); 1572 if (existing_sess != NULL) 1573 iscsit_sess_rele(existing_sess); 1574 if (existing_ict != NULL) 1575 iscsit_conn_rele(existing_ict); 1576 1577 mutex_exit(&login_sm_session_mutex); 1578 return (IDM_STATUS_SUCCESS); 1579 1580 session_bind_error: 1581 if (tgt != NULL) 1582 iscsit_tgt_rele(tgt); 1583 if (existing_sess != NULL) 1584 iscsit_sess_rele(existing_sess); 1585 if (existing_ict != NULL) 1586 iscsit_conn_rele(existing_ict); 1587 1588 /* 1589 * If session bind fails we will fail the login but don't destroy 1590 * the session until later. 1591 */ 1592 mutex_exit(&login_sm_session_mutex); 1593 return (IDM_STATUS_FAIL); 1594 } 1595 1596 1597 static idm_status_t 1598 login_sm_set_auth(iscsit_conn_t *ict) 1599 { 1600 idm_status_t idmrc = IDM_STATUS_SUCCESS; 1601 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 1602 iscsit_ini_t *ini; 1603 iscsit_tgt_t *tgt; 1604 char *auth = ""; 1605 char *radiusserver = ""; 1606 char *radiussecret = ""; 1607 char *chapuser = ""; 1608 char *chapsecret = ""; 1609 char *targetchapuser = ""; 1610 char *targetchapsecret = ""; 1611 char *targetalias = ""; 1612 int i; 1613 1614 ISCSIT_GLOBAL_LOCK(RW_READER); 1615 1616 /* 1617 * Set authentication method to none for discovery session. 1618 */ 1619 if (ict->ict_op.op_discovery_session == B_TRUE) { 1620 lsm->icl_auth.ca_method_valid_list[0] = AM_NONE; 1621 ISCSIT_GLOBAL_UNLOCK(); 1622 return (idmrc); 1623 } 1624 1625 /* 1626 * Get all the authentication parameters we need -- since we hold 1627 * the global config lock we guarantee that the parameters will 1628 * be consistent with each other. 1629 */ 1630 (void) nvlist_lookup_string(iscsit_global.global_props, 1631 PROP_AUTH, &auth); 1632 (void) nvlist_lookup_string(iscsit_global.global_props, 1633 PROP_RADIUS_SERVER, &radiusserver); 1634 (void) nvlist_lookup_string(iscsit_global.global_props, 1635 PROP_RADIUS_SECRET, &radiussecret); 1636 1637 ini = iscsit_ini_lookup_locked(lsm->icl_initiator_name); 1638 if (ini != NULL) { 1639 /* Get Initiator CHAP parameters */ 1640 (void) nvlist_lookup_string(ini->ini_props, PROP_CHAP_USER, 1641 &chapuser); 1642 (void) nvlist_lookup_string(ini->ini_props, PROP_CHAP_SECRET, 1643 &chapsecret); 1644 } 1645 1646 tgt = ict->ict_sess->ist_tgt; 1647 if (tgt != NULL) { 1648 /* See if we have a target-specific authentication setting */ 1649 (void) nvlist_lookup_string(tgt->target_props, PROP_AUTH, 1650 &auth); 1651 /* Get target CHAP parameters */ 1652 (void) nvlist_lookup_string(tgt->target_props, 1653 PROP_TARGET_CHAP_USER, &targetchapuser); 1654 (void) nvlist_lookup_string(tgt->target_props, 1655 PROP_TARGET_CHAP_SECRET, &targetchapsecret); 1656 /* Get alias */ 1657 (void) nvlist_lookup_string(tgt->target_props, 1658 PROP_ALIAS, &targetalias); 1659 } 1660 1661 /* Set authentication method */ 1662 i = 0; 1663 if (strcmp(auth, PA_AUTH_RADIUS) == 0) { 1664 /* CHAP authentication using RADIUS server */ 1665 lsm->icl_auth.ca_method_valid_list[i++] = AM_CHAP; 1666 lsm->icl_auth.ca_use_radius = B_TRUE; 1667 } else if (strcmp(auth, PA_AUTH_CHAP) == 0) { 1668 /* Local CHAP authentication */ 1669 lsm->icl_auth.ca_method_valid_list[i++] = AM_CHAP; 1670 lsm->icl_auth.ca_use_radius = B_FALSE; 1671 } else if ((strcmp(auth, PA_AUTH_NONE) == 0) || 1672 (strcmp(auth, "") == 0)) { 1673 /* No authentication */ 1674 lsm->icl_auth.ca_method_valid_list[i++] = AM_NONE; 1675 } 1676 1677 /* 1678 * If initiator/target CHAP username is not set then use the 1679 * node name. If lsm->icl_target_name == NULL then this is 1680 * a discovery session so we don't need to work about the target. 1681 */ 1682 if (strcmp(chapuser, "") == 0) { 1683 (void) strlcpy(lsm->icl_auth.ca_ini_chapuser, 1684 lsm->icl_initiator_name, 1685 min(iscsitAuthStringMaxLength, MAX_ISCSI_NODENAMELEN)); 1686 } else { 1687 (void) strlcpy(lsm->icl_auth.ca_ini_chapuser, chapuser, 1688 iscsitAuthStringMaxLength); 1689 } 1690 if ((lsm->icl_target_name != NULL) && 1691 (strcmp(targetchapuser, "") == 0)) { 1692 (void) strlcpy(lsm->icl_auth.ca_tgt_chapuser, 1693 lsm->icl_target_name, 1694 min(iscsitAuthStringMaxLength, MAX_ISCSI_NODENAMELEN)); 1695 } else { 1696 (void) strlcpy(lsm->icl_auth.ca_tgt_chapuser, 1697 targetchapuser, iscsitAuthStringMaxLength); 1698 } 1699 1700 /* 1701 * Secrets are stored in base64-encoded format so we need to 1702 * decode them into binary form 1703 */ 1704 if (strcmp(chapsecret, "") == 0) { 1705 lsm->icl_auth.ca_ini_chapsecretlen = 0; 1706 } else { 1707 if (iscsi_base64_str_to_binary(chapsecret, 1708 strnlen(chapsecret, iscsitAuthStringMaxLength), 1709 lsm->icl_auth.ca_ini_chapsecret, iscsitAuthStringMaxLength, 1710 &lsm->icl_auth.ca_ini_chapsecretlen) != 0) { 1711 cmn_err(CE_WARN, "Corrupted CHAP secret" 1712 " for initiator %s", lsm->icl_initiator_name); 1713 lsm->icl_auth.ca_ini_chapsecretlen = 0; 1714 } 1715 } 1716 if (strcmp(targetchapsecret, "") == 0) { 1717 lsm->icl_auth.ca_tgt_chapsecretlen = 0; 1718 } else { 1719 if (iscsi_base64_str_to_binary(targetchapsecret, 1720 strnlen(targetchapsecret, iscsitAuthStringMaxLength), 1721 lsm->icl_auth.ca_tgt_chapsecret, iscsitAuthStringMaxLength, 1722 &lsm->icl_auth.ca_tgt_chapsecretlen) != 0) { 1723 cmn_err(CE_WARN, "Corrupted CHAP secret" 1724 " for target %s", lsm->icl_target_name); 1725 lsm->icl_auth.ca_tgt_chapsecretlen = 0; 1726 } 1727 } 1728 if (strcmp(radiussecret, "") == 0) { 1729 lsm->icl_auth.ca_radius_secretlen = 0; 1730 } else { 1731 if (iscsi_base64_str_to_binary(radiussecret, 1732 strnlen(radiussecret, iscsitAuthStringMaxLength), 1733 lsm->icl_auth.ca_radius_secret, iscsitAuthStringMaxLength, 1734 &lsm->icl_auth.ca_radius_secretlen) != 0) { 1735 cmn_err(CE_WARN, "Corrupted RADIUS secret"); 1736 lsm->icl_auth.ca_radius_secretlen = 0; 1737 } 1738 } 1739 1740 /* 1741 * Set alias 1742 */ 1743 (void) strlcpy(lsm->icl_auth.ca_tgt_alias, targetalias, 1744 MAX_ISCSI_NODENAMELEN); 1745 1746 /* 1747 * Now that authentication parameters are setup, validate the parameters 1748 * against the authentication mode 1749 * Decode RADIUS server value int lsm->icl_auth.ca_radius_server 1750 */ 1751 if ((strcmp(auth, PA_AUTH_RADIUS) == 0) && 1752 ((lsm->icl_auth.ca_radius_secretlen == 0) || 1753 (strcmp(radiusserver, "") == 0) || 1754 it_common_convert_sa(radiusserver, 1755 &lsm->icl_auth.ca_radius_server, 1756 DEFAULT_RADIUS_PORT) == NULL)) { 1757 cmn_err(CE_WARN, "RADIUS authentication selected " 1758 "for target %s but RADIUS parameters are not " 1759 "configured.", lsm->icl_target_name); 1760 SET_LOGIN_ERROR(ict, ISCSI_STATUS_CLASS_TARGET_ERR, 1761 ISCSI_LOGIN_STATUS_TARGET_ERROR); 1762 idmrc = IDM_STATUS_FAIL; 1763 } else if ((strcmp(auth, PA_AUTH_CHAP) == 0) && 1764 (lsm->icl_auth.ca_ini_chapsecretlen == 0)) { 1765 SET_LOGIN_ERROR(ict, ISCSI_STATUS_CLASS_INITIATOR_ERR, 1766 ISCSI_LOGIN_STATUS_AUTH_FAILED); 1767 idmrc = IDM_STATUS_FAIL; 1768 } 1769 1770 ISCSIT_GLOBAL_UNLOCK(); 1771 1772 return (idmrc); 1773 } 1774 1775 1776 static idm_status_t 1777 login_sm_session_register(iscsit_conn_t *ict) 1778 { 1779 iscsit_sess_t *ist = ict->ict_sess; 1780 stmf_scsi_session_t *ss; 1781 iscsi_transport_id_t *iscsi_tptid; 1782 uint16_t ident_len, adn_len, tptid_sz; 1783 char prop_buf[KSTAT_STRLEN + 1]; 1784 char peer_buf[IDM_SA_NTOP_BUFSIZ]; 1785 1786 /* 1787 * Hold target mutex until we have finished registering with STMF 1788 */ 1789 mutex_enter(&ist->ist_tgt->target_mutex); 1790 if (ist->ist_tgt->target_state != TS_STMF_ONLINE) { 1791 mutex_exit(&ist->ist_tgt->target_mutex); 1792 SET_LOGIN_ERROR(ict, ISCSI_STATUS_CLASS_INITIATOR_ERR, 1793 ISCSI_LOGIN_STATUS_TGT_REMOVED); 1794 return (IDM_STATUS_FAIL); 1795 } 1796 1797 ss = stmf_alloc(STMF_STRUCT_SCSI_SESSION, 0, 1798 0); 1799 if (ss == NULL) { 1800 mutex_exit(&ist->ist_tgt->target_mutex); 1801 SET_LOGIN_ERROR(ict, ISCSI_STATUS_CLASS_TARGET_ERR, 1802 ISCSI_LOGIN_STATUS_NO_RESOURCES); 1803 return (IDM_STATUS_FAIL); 1804 } 1805 1806 ident_len = strlen(ist->ist_initiator_name) + 1; 1807 ss->ss_rport_id = kmem_zalloc(sizeof (scsi_devid_desc_t) + 1808 ident_len, KM_SLEEP); 1809 (void) strcpy((char *)ss->ss_rport_id->ident, ist->ist_initiator_name); 1810 ss->ss_rport_id->ident_length = ident_len - 1; 1811 ss->ss_rport_id->protocol_id = PROTOCOL_iSCSI; 1812 ss->ss_rport_id->piv = 1; 1813 ss->ss_rport_id->code_set = CODE_SET_ASCII; 1814 ss->ss_rport_id->association = ID_IS_TARGET_PORT; 1815 1816 /* adn_len should be 4 byte aligned, SPC3 rev 23, section 7.54.6 */ 1817 adn_len = (ident_len + 3) & ~ 3; 1818 tptid_sz = sizeof (iscsi_transport_id_t) - 1 + adn_len; 1819 ss->ss_rport = stmf_remote_port_alloc(tptid_sz); 1820 ss->ss_rport->rport_tptid->protocol_id = PROTOCOL_iSCSI; 1821 ss->ss_rport->rport_tptid->format_code = 0; 1822 iscsi_tptid = (iscsi_transport_id_t *)ss->ss_rport->rport_tptid; 1823 SCSI_WRITE16(&iscsi_tptid->add_len, adn_len); 1824 (void) strlcpy((char *)iscsi_tptid->iscsi_name, 1825 ist->ist_initiator_name, ident_len); 1826 1827 ss->ss_lport = ist->ist_lport; 1828 1829 if (stmf_register_scsi_session(ict->ict_sess->ist_lport, ss) != 1830 STMF_SUCCESS) { 1831 mutex_exit(&ist->ist_tgt->target_mutex); 1832 kmem_free(ss->ss_rport_id, 1833 sizeof (scsi_devid_desc_t) + 1834 strlen(ist->ist_initiator_name) + 1); 1835 stmf_remote_port_free(ss->ss_rport); 1836 stmf_free(ss); 1837 SET_LOGIN_ERROR(ict, ISCSI_STATUS_CLASS_TARGET_ERR, 1838 ISCSI_LOGIN_STATUS_TARGET_ERROR); 1839 return (IDM_STATUS_FAIL); 1840 } 1841 1842 ss->ss_port_private = ict->ict_sess; 1843 ict->ict_sess->ist_stmf_sess = ss; 1844 mutex_exit(&ist->ist_tgt->target_mutex); 1845 (void) snprintf(prop_buf, sizeof (prop_buf), "peername_%"PRIxPTR"", 1846 (uintptr_t)ict->ict_sess); 1847 (void) idm_sa_ntop(&ict->ict_ic->ic_raddr, peer_buf, 1848 sizeof (peer_buf)); 1849 (void) stmf_add_rport_info(ss, prop_buf, peer_buf); 1850 1851 return (IDM_STATUS_SUCCESS); 1852 } 1853 1854 1855 static idm_status_t 1856 login_sm_req_pdu_check(iscsit_conn_t *ict, idm_pdu_t *pdu) 1857 { 1858 uint8_t csg_req; 1859 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 1860 iscsi_login_hdr_t *lh = (iscsi_login_hdr_t *)pdu->isp_hdr; 1861 iscsi_login_rsp_hdr_t *lh_resp = lsm->icl_login_resp_tmpl; 1862 1863 /* 1864 * Check CSG 1865 */ 1866 csg_req = ISCSI_LOGIN_CURRENT_STAGE(lh->flags); 1867 switch (csg_req) { 1868 case ISCSI_SECURITY_NEGOTIATION_STAGE: 1869 case ISCSI_OP_PARMS_NEGOTIATION_STAGE: 1870 if ((csg_req != lsm->icl_login_csg) && 1871 (lsm->icl_login_state != ILS_LOGIN_INIT)) { 1872 /* 1873 * Inappropriate CSG change. Initiator can only 1874 * change CSG after we've responded with the 1875 * transit bit set. If we had responded with 1876 * a CSG change previous we would have updated 1877 * our copy of CSG. 1878 * 1879 * The exception is when we are in ILS_LOGIN_INIT 1880 * state since we haven't determined our initial 1881 * CSG value yet. 1882 */ 1883 goto pdu_check_fail; 1884 } 1885 break; 1886 case ISCSI_FULL_FEATURE_PHASE: 1887 default: 1888 goto pdu_check_fail; 1889 } 1890 1891 /* 1892 * If this is the first login PDU for a new connection then 1893 * the session will be NULL. 1894 */ 1895 if (ict->ict_sess != NULL) { 1896 /* 1897 * We've already created a session on a previous PDU. Make 1898 * sure this PDU is consistent with what we've already seen 1899 */ 1900 if ((ict->ict_cid != ntohs(lh->cid)) || 1901 (bcmp(ict->ict_sess->ist_isid, lh->isid, 1902 ISCSI_ISID_LEN) != 0)) { 1903 goto pdu_check_fail; 1904 } 1905 } 1906 1907 /* 1908 * Make sure we are compatible with the version range 1909 */ 1910 #if (ISCSIT_MAX_VERSION > 0) 1911 if ((lh->min_version > ISCSIT_MAX_VERSION) || 1912 (lh->max_version < ISCSIT_MIN_VERSION)) { 1913 goto pdu_check_fail; 1914 } 1915 #endif 1916 1917 /* 1918 * Just in case the initiator changes things up on us along the way 1919 * check against our active_version -- we can't change the active 1920 * version and the initiator is not *supposed* to change its 1921 * min_version and max_version values so this should never happen. 1922 * Of course we only do this if the response header template has 1923 * been built. 1924 */ 1925 if ((lh_resp->opcode == ISCSI_OP_LOGIN_RSP) && /* header valid */ 1926 ((lh->min_version > lh_resp->active_version) || 1927 (lh->max_version < lh_resp->active_version))) { 1928 goto pdu_check_fail; 1929 } 1930 1931 return (IDM_STATUS_SUCCESS); 1932 1933 pdu_check_fail: 1934 return (IDM_STATUS_FAIL); 1935 } 1936 1937 static idm_status_t 1938 login_sm_process_nvlist(iscsit_conn_t *ict) 1939 { 1940 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 1941 char *nvp_name; 1942 nvpair_t *nvp; 1943 nvpair_t *next_nvp; 1944 nvpair_t *negotiated_nvp; 1945 kv_status_t kvrc; 1946 uint8_t error_class; 1947 uint8_t error_detail; 1948 idm_status_t idm_status; 1949 1950 error_class = ISCSI_STATUS_CLASS_SUCCESS; 1951 error_detail = ISCSI_LOGIN_STATUS_ACCEPT; 1952 1953 /* First, request that the transport process the list */ 1954 kvrc = idm_negotiate_key_values(ict->ict_ic, lsm->icl_request_nvlist, 1955 lsm->icl_response_nvlist, lsm->icl_negotiated_values); 1956 idm_kvstat_to_error(kvrc, &error_class, &error_detail); 1957 if (error_class != ISCSI_STATUS_CLASS_SUCCESS) { 1958 SET_LOGIN_ERROR(ict, error_class, error_detail); 1959 idm_status = IDM_STATUS_FAIL; 1960 return (idm_status); 1961 } 1962 1963 /* Ensure we clear transit bit if the transport layer has countered */ 1964 if (kvrc == KV_HANDLED_NO_TRANSIT) { 1965 lsm->icl_login_transit = B_FALSE; 1966 } 1967 1968 /* Prepend the declarative params */ 1969 if (!ict->ict_op.op_declarative_params_set && 1970 lsm->icl_login_csg == ISCSI_OP_PARMS_NEGOTIATION_STAGE) { 1971 if (iscsit_add_declarative_keys(ict) != IDM_STATUS_SUCCESS) { 1972 idm_status = IDM_STATUS_FAIL; 1973 return (idm_status); 1974 } 1975 ict->ict_op.op_declarative_params_set = B_TRUE; 1976 } 1977 1978 /* Now, move on and process the rest of the pairs */ 1979 nvp = nvlist_next_nvpair(lsm->icl_request_nvlist, NULL); 1980 while (nvp != NULL) { 1981 next_nvp = nvlist_next_nvpair(lsm->icl_request_nvlist, nvp); 1982 nvp_name = nvpair_name(nvp); 1983 /* 1984 * If we've already agreed upon a value then make sure this 1985 * is not attempting to change that value. From RFC3270 1986 * section 5.3: 1987 * 1988 * "Neither the initiator nor the target should attempt to 1989 * declare or negotiate a parameter more than once during 1990 * login except for responses to specific keys that 1991 * explicitly allow repeated key declarations (e.g., 1992 * TargetAddress). An attempt to renegotiate/redeclare 1993 * parameters not specifically allowed MUST be detected 1994 * by the initiator and target. If such an attempt is 1995 * detected by the target, the target MUST respond 1996 * with Login reject (initiator error); ..." 1997 */ 1998 if (nvlist_lookup_nvpair(lsm->icl_negotiated_values, 1999 nvp_name, &negotiated_nvp) == 0) { 2000 kvrc = KV_HANDLED; 2001 } else { 2002 kvrc = iscsit_handle_key(ict, nvp, nvp_name); 2003 } 2004 2005 idm_kvstat_to_error(kvrc, &error_class, &error_detail); 2006 if (error_class != ISCSI_STATUS_CLASS_SUCCESS) { 2007 break; 2008 } 2009 2010 nvp = next_nvp; 2011 } 2012 2013 if (error_class == ISCSI_STATUS_CLASS_SUCCESS) { 2014 idm_status = IDM_STATUS_SUCCESS; 2015 } else { 2016 /* supply login class/detail for login errors */ 2017 SET_LOGIN_ERROR(ict, error_class, error_detail); 2018 idm_status = IDM_STATUS_FAIL; 2019 } 2020 2021 return (idm_status); 2022 } 2023 2024 static idm_status_t 2025 login_sm_check_security(iscsit_conn_t *ict) 2026 { 2027 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 2028 conn_auth_t *auth = &lsm->icl_auth; 2029 iscsit_auth_method_t *am_list = &auth->ca_method_valid_list[0]; 2030 kv_status_t kvrc; 2031 uint8_t error_class; 2032 uint8_t error_detail; 2033 idm_status_t idm_status; 2034 2035 error_class = ISCSI_STATUS_CLASS_SUCCESS; 2036 error_detail = ISCSI_LOGIN_STATUS_ACCEPT; 2037 2038 /* Check authentication status. */ 2039 if (lsm->icl_login_csg == ISCSI_SECURITY_NEGOTIATION_STAGE) { 2040 /* 2041 * We should have some authentication key/value pair(s) 2042 * received from initiator and the authentication phase 2043 * has been shifted when the key/value pair(s) are being 2044 * handled in the previous call iscsit_handle_security_key. 2045 * Now it turns to target to check the authentication phase 2046 * and shift it after taking some authentication action. 2047 */ 2048 kvrc = iscsit_reply_security_key(ict); 2049 idm_kvstat_to_error(kvrc, &error_class, &error_detail); 2050 } else if (!ict->ict_login_sm.icl_auth_pass) { 2051 /* 2052 * Check to see if the target allows initiators to bypass the 2053 * security check. If the target is configured to require 2054 * authentication, we reject the connection. 2055 */ 2056 if (am_list[0] == AM_NONE || am_list[0] == 0) { 2057 ict->ict_login_sm.icl_auth_pass = 1; 2058 } else { 2059 error_class = ISCSI_STATUS_CLASS_INITIATOR_ERR; 2060 error_detail = ISCSI_LOGIN_STATUS_AUTH_FAILED; 2061 } 2062 } 2063 2064 if (error_class == ISCSI_STATUS_CLASS_SUCCESS) { 2065 idm_status = IDM_STATUS_SUCCESS; 2066 } else { 2067 /* supply login class/detail for login errors */ 2068 SET_LOGIN_ERROR(ict, error_class, error_detail); 2069 idm_status = IDM_STATUS_FAIL; 2070 } 2071 2072 return (idm_status); 2073 } 2074 2075 static idm_pdu_t * 2076 login_sm_build_login_response(iscsit_conn_t *ict) 2077 { 2078 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 2079 iscsi_login_rsp_hdr_t *lh; 2080 int transit, text_transit = 1; 2081 idm_pdu_t *login_resp; 2082 2083 /* 2084 * Create a response PDU and fill it with as much of 2085 * the response text that will fit. 2086 */ 2087 2088 if (lsm->icl_login_resp_itb) { 2089 /* allocate a pdu with space for text */ 2090 login_resp = idm_pdu_alloc(sizeof (iscsi_hdr_t), 2091 ISCSI_DEFAULT_MAX_RECV_SEG_LEN); 2092 /* copy a chunk of text into the pdu */ 2093 lsm->icl_login_resp_buf = idm_pdu_init_text_data( 2094 login_resp, lsm->icl_login_resp_itb, 2095 ISCSI_DEFAULT_MAX_RECV_SEG_LEN, 2096 lsm->icl_login_resp_buf, &text_transit); 2097 if (text_transit) { 2098 /* text buf has been consumed */ 2099 idm_itextbuf_free(lsm->icl_login_resp_itb); 2100 lsm->icl_login_resp_itb = NULL; 2101 lsm->icl_login_resp_buf = NULL; 2102 } 2103 } else { 2104 /* allocate a pdu for just a header */ 2105 login_resp = idm_pdu_alloc(sizeof (iscsi_hdr_t), 0); 2106 } 2107 /* finish initializing the pdu */ 2108 idm_pdu_init(login_resp, 2109 ict->ict_ic, ict, login_resp_complete_cb); 2110 login_resp->isp_flags |= IDM_PDU_LOGIN_TX; 2111 2112 /* 2113 * Use the BHS header values from the response template 2114 */ 2115 bcopy(lsm->icl_login_resp_tmpl, 2116 login_resp->isp_hdr, sizeof (iscsi_login_rsp_hdr_t)); 2117 2118 lh = (iscsi_login_rsp_hdr_t *)login_resp->isp_hdr; 2119 2120 /* Set error class/detail */ 2121 lh->status_class = lsm->icl_login_resp_err_class; 2122 lh->status_detail = lsm->icl_login_resp_err_detail; 2123 /* Set CSG, NSG and Transit */ 2124 lh->flags = 0; 2125 lh->flags |= lsm->icl_login_csg << 2; 2126 2127 2128 if (lh->status_class == ISCSI_STATUS_CLASS_SUCCESS) { 2129 if (lsm->icl_login_transit && 2130 lsm->icl_auth_pass != 0) { 2131 transit = 1; 2132 } else { 2133 transit = 0; 2134 } 2135 /* 2136 * inititalize the text data 2137 */ 2138 if (transit == 1 && text_transit == 1) { 2139 lh->flags |= lsm->icl_login_nsg; 2140 lsm->icl_login_csg = lsm->icl_login_nsg; 2141 lh->flags |= ISCSI_FLAG_LOGIN_TRANSIT; 2142 } else { 2143 lh->flags &= ~ISCSI_FLAG_LOGIN_TRANSIT; 2144 } 2145 2146 /* If we are transitioning to FFP then set TSIH */ 2147 if (transit && (lh->flags & ISCSI_FLAG_LOGIN_TRANSIT) && 2148 lsm->icl_login_csg == ISCSI_FULL_FEATURE_PHASE) { 2149 lh->tsid = htons(ict->ict_sess->ist_tsih); 2150 } 2151 } else { 2152 login_resp->isp_data = 0; 2153 login_resp->isp_datalen = 0; 2154 } 2155 return (login_resp); 2156 } 2157 2158 static kv_status_t 2159 iscsit_handle_key(iscsit_conn_t *ict, nvpair_t *nvp, char *nvp_name) 2160 { 2161 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 2162 kv_status_t kvrc; 2163 const idm_kv_xlate_t *ikvx; 2164 2165 ikvx = idm_lookup_kv_xlate(nvp_name, strlen(nvp_name)); 2166 if (ikvx->ik_key_id == KI_MAX_KEY) { 2167 /* 2168 * Any key not understood by the acceptor may be igonred 2169 * by the acceptor without affecting the basic function. 2170 * However, the answer for a key not understood MUST be 2171 * key=NotUnderstood. 2172 */ 2173 kvrc = iscsit_reply_string(ict, nvp_name, 2174 ISCSI_TEXT_NOTUNDERSTOOD); 2175 } else { 2176 kvrc = iscsit_handle_common_key(ict, nvp, ikvx); 2177 if (kvrc == KV_UNHANDLED) { 2178 switch (lsm->icl_login_csg) { 2179 case ISCSI_SECURITY_NEGOTIATION_STAGE: 2180 kvrc = iscsit_handle_security_key( 2181 ict, nvp, ikvx); 2182 break; 2183 case ISCSI_OP_PARMS_NEGOTIATION_STAGE: 2184 kvrc = iscsit_handle_operational_key( 2185 ict, nvp, ikvx); 2186 break; 2187 case ISCSI_FULL_FEATURE_PHASE: 2188 default: 2189 /* What are we doing here? */ 2190 ASSERT(0); 2191 kvrc = KV_UNHANDLED; 2192 } 2193 } 2194 } 2195 2196 return (kvrc); 2197 } 2198 2199 static kv_status_t 2200 iscsit_handle_common_key(iscsit_conn_t *ict, nvpair_t *nvp, 2201 const idm_kv_xlate_t *ikvx) 2202 { 2203 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 2204 kv_status_t kvrc; 2205 char *string_val; 2206 int nvrc; 2207 2208 switch (ikvx->ik_key_id) { 2209 case KI_INITIATOR_NAME: 2210 case KI_INITIATOR_ALIAS: 2211 nvrc = nvlist_add_nvpair(lsm->icl_negotiated_values, nvp); 2212 kvrc = idm_nvstat_to_kvstat(nvrc); 2213 break; 2214 case KI_TARGET_NAME: 2215 /* We'll validate the target during login_sm_session_bind() */ 2216 nvrc = nvpair_value_string(nvp, &string_val); 2217 ASSERT(nvrc == 0); /* We built this nvlist */ 2218 2219 nvrc = nvlist_add_nvpair(lsm->icl_negotiated_values, nvp); 2220 kvrc = idm_nvstat_to_kvstat(nvrc); 2221 break; 2222 case KI_TARGET_ALIAS: 2223 case KI_TARGET_ADDRESS: 2224 case KI_TARGET_PORTAL_GROUP_TAG: 2225 kvrc = KV_TARGET_ONLY; /* Only the target can declare this */ 2226 break; 2227 case KI_SESSION_TYPE: 2228 /* 2229 * If we don't receive this key on the initial login 2230 * we assume this is a normal session. 2231 */ 2232 nvrc = nvlist_add_nvpair(lsm->icl_negotiated_values, nvp); 2233 kvrc = idm_nvstat_to_kvstat(nvrc); 2234 nvrc = nvpair_value_string(nvp, &string_val); 2235 ASSERT(nvrc == 0); /* We built this nvlist */ 2236 ict->ict_op.op_discovery_session = 2237 strcmp(string_val, "Discovery") == 0 ? B_TRUE : B_FALSE; 2238 break; 2239 default: 2240 /* 2241 * This is not really an error but we should 2242 * leave this nvpair on the list since we 2243 * didn't do anything with it. Either 2244 * the security or operational phase 2245 * handling functions should process it. 2246 */ 2247 kvrc = KV_UNHANDLED; 2248 break; 2249 } 2250 2251 return (kvrc); 2252 } 2253 2254 static kv_status_t 2255 iscsit_handle_security_key(iscsit_conn_t *ict, nvpair_t *nvp, 2256 const idm_kv_xlate_t *ikvx) 2257 { 2258 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 2259 iscsit_auth_client_t *client = &lsm->icl_auth_client; 2260 iscsikey_id_t kv_id; 2261 kv_status_t kvrc; 2262 iscsit_auth_handler_t handler; 2263 2264 /* 2265 * After all of security keys are handled, this function will 2266 * be called again to verify current authentication status 2267 * and perform some actual authentication work. At this time, 2268 * the nvp and ikvx will be passed in as NULLs. 2269 */ 2270 if (ikvx != NULL) { 2271 kv_id = ikvx->ik_key_id; 2272 } else { 2273 kv_id = 0; 2274 } 2275 2276 handler = iscsit_auth_get_handler(client, kv_id); 2277 if (handler) { 2278 kvrc = handler(ict, nvp, ikvx); 2279 } else { 2280 kvrc = KV_UNHANDLED; /* invalid request */ 2281 } 2282 2283 return (kvrc); 2284 } 2285 2286 static kv_status_t 2287 iscsit_reply_security_key(iscsit_conn_t *ict) 2288 { 2289 return (iscsit_handle_security_key(ict, NULL, NULL)); 2290 } 2291 2292 static kv_status_t 2293 iscsit_handle_operational_key(iscsit_conn_t *ict, nvpair_t *nvp, 2294 const idm_kv_xlate_t *ikvx) 2295 { 2296 kv_status_t kvrc = KV_UNHANDLED; 2297 boolean_t bool_val; 2298 uint64_t num_val; 2299 int nvrc; 2300 2301 /* 2302 * Retrieve values. All value lookups are expected to succeed 2303 * since we build the nvlist while decoding the text buffer. This 2304 * step is intended to eliminate some duplication of code (for example 2305 * we only need to code the numerical value lookup once). We will 2306 * handle the values (if necessary) below. 2307 */ 2308 switch (ikvx->ik_key_id) { 2309 /* Lists */ 2310 case KI_HEADER_DIGEST: 2311 case KI_DATA_DIGEST: 2312 break; 2313 /* Booleans */ 2314 case KI_INITIAL_R2T: 2315 case KI_IMMEDIATE_DATA: 2316 case KI_DATA_PDU_IN_ORDER: 2317 case KI_DATA_SEQUENCE_IN_ORDER: 2318 case KI_IFMARKER: 2319 case KI_OFMARKER: 2320 nvrc = nvpair_value_boolean_value(nvp, &bool_val); 2321 ASSERT(nvrc == 0); /* We built this nvlist */ 2322 break; 2323 /* Numericals */ 2324 case KI_MAX_CONNECTIONS: 2325 case KI_MAX_RECV_DATA_SEGMENT_LENGTH: 2326 case KI_MAX_BURST_LENGTH: 2327 case KI_FIRST_BURST_LENGTH: 2328 case KI_DEFAULT_TIME_2_WAIT: 2329 case KI_DEFAULT_TIME_2_RETAIN: 2330 case KI_MAX_OUTSTANDING_R2T: 2331 case KI_ERROR_RECOVERY_LEVEL: 2332 nvrc = nvpair_value_uint64(nvp, &num_val); 2333 ASSERT(nvrc == 0); 2334 break; 2335 /* Ranges */ 2336 case KI_OFMARKERINT: 2337 case KI_IFMARKERINT: 2338 break; 2339 default: 2340 break; 2341 } 2342 2343 /* 2344 * Now handle the values according to the key name. Sometimes we 2345 * don't care what the value is -- in that case we just add the nvpair 2346 * to the negotiated values list. 2347 */ 2348 switch (ikvx->ik_key_id) { 2349 case KI_HEADER_DIGEST: 2350 kvrc = iscsit_handle_digest(ict, nvp, ikvx); 2351 break; 2352 case KI_DATA_DIGEST: 2353 kvrc = iscsit_handle_digest(ict, nvp, ikvx); 2354 break; 2355 case KI_INITIAL_R2T: 2356 /* We *require* INITIAL_R2T=yes */ 2357 kvrc = iscsit_handle_boolean(ict, nvp, bool_val, ikvx, 2358 B_TRUE); 2359 break; 2360 case KI_IMMEDIATE_DATA: 2361 kvrc = iscsit_handle_boolean(ict, nvp, bool_val, ikvx, 2362 bool_val); 2363 break; 2364 case KI_DATA_PDU_IN_ORDER: 2365 kvrc = iscsit_handle_boolean(ict, nvp, bool_val, ikvx, 2366 B_TRUE); 2367 break; 2368 case KI_DATA_SEQUENCE_IN_ORDER: 2369 /* We allow any value for DATA_SEQUENCE_IN_ORDER */ 2370 kvrc = iscsit_handle_boolean(ict, nvp, bool_val, ikvx, 2371 bool_val); 2372 break; 2373 case KI_OFMARKER: 2374 case KI_IFMARKER: 2375 /* We don't support markers */ 2376 kvrc = iscsit_handle_boolean(ict, nvp, bool_val, ikvx, 2377 B_FALSE); 2378 break; 2379 case KI_MAX_CONNECTIONS: 2380 kvrc = iscsit_handle_numerical(ict, nvp, num_val, ikvx, 2381 ISCSI_MIN_CONNECTIONS, 2382 ISCSI_MAX_CONNECTIONS, 2383 ISCSIT_MAX_CONNECTIONS); 2384 break; 2385 /* this is a declartive param */ 2386 case KI_MAX_RECV_DATA_SEGMENT_LENGTH: 2387 kvrc = iscsit_handle_numerical(ict, nvp, num_val, ikvx, 2388 ISCSI_MIN_RECV_DATA_SEGMENT_LENGTH, 2389 ISCSI_MAX_RECV_DATA_SEGMENT_LENGTH, 2390 ISCSI_MAX_RECV_DATA_SEGMENT_LENGTH); 2391 break; 2392 case KI_MAX_BURST_LENGTH: 2393 kvrc = iscsit_handle_numerical(ict, nvp, num_val, ikvx, 2394 ISCSI_MIN_MAX_BURST_LENGTH, 2395 ISCSI_MAX_BURST_LENGTH, 2396 ISCSIT_MAX_BURST_LENGTH); 2397 break; 2398 case KI_FIRST_BURST_LENGTH: 2399 kvrc = iscsit_handle_numerical(ict, nvp, num_val, ikvx, 2400 ISCSI_MIN_FIRST_BURST_LENGTH, 2401 ISCSI_MAX_FIRST_BURST_LENGTH, 2402 ISCSIT_MAX_FIRST_BURST_LENGTH); 2403 break; 2404 case KI_DEFAULT_TIME_2_WAIT: 2405 kvrc = iscsit_handle_numerical(ict, nvp, num_val, ikvx, 2406 ISCSI_MIN_TIME2WAIT, 2407 ISCSI_MAX_TIME2WAIT, 2408 ISCSIT_MAX_TIME2WAIT); 2409 break; 2410 case KI_DEFAULT_TIME_2_RETAIN: 2411 kvrc = iscsit_handle_numerical(ict, nvp, num_val, ikvx, 2412 ISCSI_MIN_TIME2RETAIN, 2413 ISCSI_MAX_TIME2RETAIN, 2414 ISCSIT_MAX_TIME2RETAIN); 2415 break; 2416 case KI_MAX_OUTSTANDING_R2T: 2417 kvrc = iscsit_handle_numerical(ict, nvp, num_val, ikvx, 2418 ISCSI_MIN_MAX_OUTSTANDING_R2T, 2419 ISCSI_MAX_OUTSTANDING_R2T, 2420 ISCSIT_MAX_OUTSTANDING_R2T); 2421 break; 2422 case KI_ERROR_RECOVERY_LEVEL: 2423 kvrc = iscsit_handle_numerical(ict, nvp, num_val, ikvx, 2424 ISCSI_MIN_ERROR_RECOVERY_LEVEL, 2425 ISCSI_MAX_ERROR_RECOVERY_LEVEL, 2426 ISCSIT_MAX_ERROR_RECOVERY_LEVEL); 2427 break; 2428 case KI_OFMARKERINT: 2429 case KI_IFMARKERINT: 2430 kvrc = iscsit_reply_string(ict, ikvx->ik_key_name, 2431 ISCSI_TEXT_IRRELEVANT); 2432 break; 2433 default: 2434 kvrc = KV_UNHANDLED; /* invalid request */ 2435 break; 2436 } 2437 2438 return (kvrc); 2439 } 2440 2441 static kv_status_t 2442 iscsit_reply_numerical(iscsit_conn_t *ict, 2443 const char *nvp_name, const uint64_t value) 2444 { 2445 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 2446 kv_status_t kvrc; 2447 int nvrc; 2448 2449 nvrc = nvlist_add_uint64(lsm->icl_response_nvlist, 2450 nvp_name, value); 2451 kvrc = idm_nvstat_to_kvstat(nvrc); 2452 2453 return (kvrc); 2454 } 2455 2456 static kv_status_t 2457 iscsit_reply_string(iscsit_conn_t *ict, 2458 const char *nvp_name, const char *text) 2459 { 2460 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 2461 kv_status_t kvrc; 2462 int nvrc; 2463 2464 nvrc = nvlist_add_string(lsm->icl_response_nvlist, 2465 nvp_name, text); 2466 kvrc = idm_nvstat_to_kvstat(nvrc); 2467 2468 return (kvrc); 2469 } 2470 2471 static kv_status_t 2472 iscsit_handle_digest(iscsit_conn_t *ict, nvpair_t *choices, 2473 const idm_kv_xlate_t *ikvx) 2474 { 2475 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 2476 kv_status_t kvrc = KV_VALUE_ERROR; 2477 int nvrc; 2478 nvpair_t *digest_choice; 2479 char *digest_choice_string; 2480 2481 /* 2482 * Need to add persistent config here if we want users to allow 2483 * disabling of digests on the target side. You could argue that 2484 * this makes things too complicated... just let the initiator state 2485 * what it wants and we'll take it. For now that's exactly what 2486 * we'll do. 2487 * 2488 * Basic digest negotiation happens here at iSCSI level. IDM 2489 * can override this during negotiate_key_values phase to 2490 * decline to set up any digest processing. 2491 */ 2492 digest_choice = idm_get_next_listvalue(choices, NULL); 2493 2494 /* 2495 * Loop through all choices. As soon as we find a choice 2496 * that we support add the value to our negotiated values list 2497 * and respond with that value in the login response. 2498 */ 2499 while (digest_choice != NULL) { 2500 nvrc = nvpair_value_string(digest_choice, 2501 &digest_choice_string); 2502 ASSERT(nvrc == 0); 2503 2504 if ((strcasecmp(digest_choice_string, "crc32c") == 0) || 2505 (strcasecmp(digest_choice_string, "none") == 0)) { 2506 /* Add to negotiated values list */ 2507 nvrc = nvlist_add_string(lsm->icl_negotiated_values, 2508 ikvx->ik_key_name, digest_choice_string); 2509 kvrc = idm_nvstat_to_kvstat(nvrc); 2510 if (nvrc == 0) { 2511 /* Add to login response list */ 2512 nvrc = nvlist_add_string( 2513 lsm->icl_response_nvlist, 2514 ikvx->ik_key_name, digest_choice_string); 2515 kvrc = idm_nvstat_to_kvstat(nvrc); 2516 } 2517 break; 2518 } 2519 digest_choice = idm_get_next_listvalue(choices, 2520 digest_choice); 2521 } 2522 2523 if (digest_choice == NULL) 2524 kvrc = KV_VALUE_ERROR; 2525 2526 return (kvrc); 2527 } 2528 2529 static kv_status_t 2530 iscsit_handle_boolean(iscsit_conn_t *ict, nvpair_t *nvp, boolean_t value, 2531 const idm_kv_xlate_t *ikvx, boolean_t iscsit_value) 2532 { 2533 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 2534 kv_status_t kvrc; 2535 int nvrc; 2536 2537 if (ikvx->ik_declarative) { 2538 nvrc = nvlist_add_nvpair(lsm->icl_negotiated_values, nvp); 2539 } else { 2540 if (value != iscsit_value) { 2541 /* Respond back to initiator with our value */ 2542 value = iscsit_value; 2543 nvrc = nvlist_add_boolean_value( 2544 lsm->icl_negotiated_values, 2545 ikvx->ik_key_name, value); 2546 lsm->icl_login_transit = B_FALSE; 2547 } else { 2548 /* Add this to our negotiated values */ 2549 nvrc = nvlist_add_nvpair(lsm->icl_negotiated_values, 2550 nvp); 2551 } 2552 2553 /* Response of Simple-value Negotiation */ 2554 if (nvrc == 0) { 2555 nvrc = nvlist_add_boolean_value( 2556 lsm->icl_response_nvlist, ikvx->ik_key_name, value); 2557 } 2558 } 2559 2560 kvrc = idm_nvstat_to_kvstat(nvrc); 2561 2562 return (kvrc); 2563 } 2564 2565 static kv_status_t 2566 iscsit_handle_numerical(iscsit_conn_t *ict, nvpair_t *nvp, uint64_t value, 2567 const idm_kv_xlate_t *ikvx, 2568 uint64_t iscsi_min_value, uint64_t iscsi_max_value, 2569 uint64_t iscsit_max_value) 2570 { 2571 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 2572 kv_status_t kvrc; 2573 int nvrc; 2574 2575 /* Validate against standard */ 2576 if ((value < iscsi_min_value) || (value > iscsi_max_value)) { 2577 kvrc = KV_VALUE_ERROR; 2578 } else if (ikvx->ik_declarative) { 2579 nvrc = nvlist_add_nvpair(lsm->icl_negotiated_values, nvp); 2580 kvrc = idm_nvstat_to_kvstat(nvrc); 2581 } else { 2582 if (value > iscsit_max_value) { 2583 /* Respond back to initiator with our value */ 2584 value = iscsit_max_value; 2585 nvrc = nvlist_add_uint64(lsm->icl_negotiated_values, 2586 ikvx->ik_key_name, value); 2587 lsm->icl_login_transit = B_FALSE; 2588 } else { 2589 /* Add this to our negotiated values */ 2590 nvrc = nvlist_add_nvpair(lsm->icl_negotiated_values, 2591 nvp); 2592 } 2593 2594 /* Response of Simple-value Negotiation */ 2595 if (nvrc == 0) { 2596 nvrc = nvlist_add_uint64(lsm->icl_response_nvlist, 2597 ikvx->ik_key_name, value); 2598 } 2599 kvrc = idm_nvstat_to_kvstat(nvrc); 2600 } 2601 2602 return (kvrc); 2603 } 2604 2605 2606 static void 2607 iscsit_process_negotiated_values(iscsit_conn_t *ict) 2608 { 2609 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 2610 char *string_val; 2611 boolean_t boolean_val; 2612 uint64_t uint64_val; 2613 int nvrc; 2614 2615 /* Let the IDM level activate its parameters first */ 2616 idm_notice_key_values(ict->ict_ic, lsm->icl_negotiated_values); 2617 2618 /* 2619 * Initiator alias and target alias 2620 */ 2621 if ((nvrc = nvlist_lookup_string(lsm->icl_negotiated_values, 2622 "InitiatorAlias", &string_val)) != ENOENT) { 2623 ASSERT(nvrc == 0); 2624 ict->ict_sess->ist_initiator_alias = 2625 kmem_alloc(strlen(string_val) + 1, KM_SLEEP); 2626 (void) strcpy(ict->ict_sess->ist_initiator_alias, string_val); 2627 if (ict->ict_sess->ist_stmf_sess) 2628 ict->ict_sess->ist_stmf_sess->ss_rport_alias = 2629 strdup(string_val); 2630 } 2631 2632 if ((nvrc = nvlist_lookup_string(lsm->icl_negotiated_values, 2633 "TargetAlias", &string_val)) != ENOENT) { 2634 ASSERT(nvrc == 0); 2635 ict->ict_sess->ist_target_alias = 2636 kmem_alloc(strlen(string_val) + 1, KM_SLEEP); 2637 (void) strcpy(ict->ict_sess->ist_target_alias, string_val); 2638 } 2639 2640 /* 2641 * Operational parameters. We process SessionType when it is 2642 * initially received since it is required on the initial login. 2643 */ 2644 if ((nvrc = nvlist_lookup_boolean_value(lsm->icl_negotiated_values, 2645 "InitialR2T", &boolean_val)) != ENOENT) { 2646 ASSERT(nvrc == 0); 2647 ict->ict_op.op_initial_r2t = boolean_val; 2648 } 2649 2650 if ((nvrc = nvlist_lookup_boolean_value(lsm->icl_negotiated_values, 2651 "ImmediateData", &boolean_val)) != ENOENT) { 2652 ASSERT(nvrc == 0); 2653 ict->ict_op.op_immed_data = boolean_val; 2654 } 2655 2656 if ((nvrc = nvlist_lookup_boolean_value(lsm->icl_negotiated_values, 2657 "DataPDUInOrder", &boolean_val)) != ENOENT) { 2658 ASSERT(nvrc == 0); 2659 ict->ict_op.op_data_pdu_in_order = boolean_val; 2660 } 2661 2662 if ((nvrc = nvlist_lookup_boolean_value(lsm->icl_negotiated_values, 2663 "DataSequenceInOrder", &boolean_val)) != ENOENT) { 2664 ASSERT(nvrc == 0); 2665 ict->ict_op.op_data_sequence_in_order = boolean_val; 2666 } 2667 2668 if ((nvrc = nvlist_lookup_uint64(lsm->icl_negotiated_values, 2669 "MaxConnections", &uint64_val)) != ENOENT) { 2670 ASSERT(nvrc == 0); 2671 ict->ict_op.op_max_connections = uint64_val; 2672 } 2673 2674 if ((nvrc = nvlist_lookup_uint64(lsm->icl_negotiated_values, 2675 "MaxRecvDataSegmentLength", &uint64_val)) != ENOENT) { 2676 ASSERT(nvrc == 0); 2677 ict->ict_op.op_max_recv_data_segment_length = uint64_val; 2678 } 2679 2680 if ((nvrc = nvlist_lookup_uint64(lsm->icl_negotiated_values, 2681 "MaxBurstLength", &uint64_val)) != ENOENT) { 2682 ASSERT(nvrc == 0); 2683 ict->ict_op.op_max_burst_length = uint64_val; 2684 } 2685 2686 if ((nvrc = nvlist_lookup_uint64(lsm->icl_negotiated_values, 2687 "FirstBurstLength", &uint64_val)) != ENOENT) { 2688 ASSERT(nvrc == 0); 2689 ict->ict_op.op_first_burst_length = uint64_val; 2690 } 2691 2692 if ((nvrc = nvlist_lookup_uint64(lsm->icl_negotiated_values, 2693 "DefaultTime2Wait", &uint64_val)) != ENOENT) { 2694 ASSERT(nvrc == 0); 2695 ict->ict_op.op_default_time_2_wait = uint64_val; 2696 } 2697 2698 if ((nvrc = nvlist_lookup_uint64(lsm->icl_negotiated_values, 2699 "DefaultTime2Retain", &uint64_val)) != ENOENT) { 2700 ASSERT(nvrc == 0); 2701 ict->ict_op.op_default_time_2_retain = uint64_val; 2702 } 2703 2704 if ((nvrc = nvlist_lookup_uint64(lsm->icl_negotiated_values, 2705 "MaxOutstandingR2T", &uint64_val)) != ENOENT) { 2706 ASSERT(nvrc == 0); 2707 ict->ict_op.op_max_outstanding_r2t = uint64_val; 2708 } 2709 2710 if ((nvrc = nvlist_lookup_uint64(lsm->icl_negotiated_values, 2711 "ErrorRecoveryLevel", &uint64_val)) != ENOENT) { 2712 ASSERT(nvrc == 0); 2713 ict->ict_op.op_error_recovery_level = uint64_val; 2714 } 2715 } 2716 2717 static idm_status_t 2718 iscsit_add_declarative_keys(iscsit_conn_t *ict) 2719 { 2720 nvlist_t *cfg_nv = NULL; 2721 kv_status_t kvrc; 2722 int nvrc; 2723 iscsit_conn_login_t *lsm = &ict->ict_login_sm; 2724 uint8_t error_class; 2725 uint8_t error_detail; 2726 idm_status_t idm_status; 2727 2728 if ((nvrc = nvlist_alloc(&cfg_nv, NV_UNIQUE_NAME, KM_NOSLEEP)) != 0) { 2729 kvrc = idm_nvstat_to_kvstat(nvrc); 2730 goto alloc_fail; 2731 } 2732 if ((nvrc = nvlist_add_uint64(cfg_nv, "MaxRecvDataSegmentLength", 2733 max_dataseglen_target)) != 0) { 2734 kvrc = idm_nvstat_to_kvstat(nvrc); 2735 goto done; 2736 } 2737 2738 kvrc = idm_declare_key_values(ict->ict_ic, cfg_nv, 2739 lsm->icl_response_nvlist); 2740 done: 2741 nvlist_free(cfg_nv); 2742 alloc_fail: 2743 idm_kvstat_to_error(kvrc, &error_class, &error_detail); 2744 if (error_class == ISCSI_STATUS_CLASS_SUCCESS) { 2745 idm_status = IDM_STATUS_SUCCESS; 2746 } else { 2747 SET_LOGIN_ERROR(ict, error_class, error_detail); 2748 idm_status = IDM_STATUS_FAIL; 2749 } 2750 return (idm_status); 2751 } 2752 2753 static char * 2754 iscsit_fold_name(char *name, size_t *buflen) 2755 { 2756 char *ret; 2757 const char *sns; 2758 int errnum; 2759 int flag = U8_TEXTPREP_NFKC; 2760 size_t inlen, outlen, coff; 2761 2762 if (name == NULL) 2763 return (NULL); 2764 2765 /* Check for one of the supported name types */ 2766 if (strncasecmp(name, SNS_EUI ".", strlen(SNS_EUI) + 1) == 0) { 2767 sns = SNS_EUI; 2768 *buflen = SNS_EUI_LEN_MAX + 1; 2769 flag |= U8_TEXTPREP_TOUPPER; 2770 } else if (strncasecmp(name, SNS_IQN ".", strlen(SNS_IQN) + 1) == 0) { 2771 sns = SNS_IQN; 2772 *buflen = SNS_IQN_LEN_MAX + 1; 2773 flag |= U8_TEXTPREP_TOLOWER; 2774 } else if (strncasecmp(name, SNS_NAA ".", strlen(SNS_NAA) + 1) == 0) { 2775 sns = SNS_NAA; 2776 *buflen = SNS_NAA_LEN_MAX + 1; 2777 flag |= U8_TEXTPREP_TOUPPER; 2778 } else { 2779 return (NULL); 2780 } 2781 2782 ret = kmem_zalloc(*buflen, KM_SLEEP); 2783 coff = strlen(sns); 2784 inlen = strlen(name) - coff; 2785 outlen = *buflen - coff - 1; 2786 2787 /* Fold the case and normalize string */ 2788 if (u8_textprep_str(name + coff, &inlen, ret + coff, &outlen, flag, 2789 U8_UNICODE_320, &errnum) == (size_t)-1) { 2790 kmem_free(ret, *buflen); 2791 return (NULL); 2792 } 2793 2794 /* Copy the name type prefix */ 2795 bcopy(sns, ret, coff); 2796 2797 return (ret); 2798 } 2799