iscsi_text.c revision 1.12 1 /* $NetBSD: iscsi_text.c,v 1.12 2019/04/21 11:26:46 mlelstv Exp $ */
2
3 /*-
4 * Copyright (c) 2005,2006,2011 The NetBSD Foundation, Inc.
5 * All rights reserved.
6 *
7 * This code is derived from software contributed to The NetBSD Foundation
8 * by Wasabi Systems, Inc.
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in the
17 * documentation and/or other materials provided with the distribution.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 * POSSIBILITY OF SUCH DAMAGE.
30 */
31
32 #include "iscsi_globals.h"
33 #include "base64.h"
34 #include <sys/md5.h>
35 #include <sys/cprng.h>
36
37 #define isdigit(x) ((x) >= '0' && (x) <= '9')
38 #define toupper(x) ((x) & ~0x20)
39
40 /*****************************************************************************/
41
42 #define MAX_STRING 255 /* Maximum length of parameter value */
43 #define MAX_LIST 4 /* Maximum number of list elements we'll ever send */
44
45 /* Maximum number of negotiation parameters in the operational negotiation phase */
46 /* 48 should be more than enough even with the target defining its own keys */
47 #define MAX_NEG 48
48
49 #define CHAP_CHALLENGE_LEN 32 /* Number of bytes to send in challenge */
50 #define CHAP_MD5_SIZE 16 /* Number of bytes in MD5 hash */
51
52 /*****************************************************************************/
53
54 /* authentication states */
55
56 typedef enum
57 {
58 AUTH_INITIAL, /* sending choice of algorithms */
59 AUTH_METHOD_SELECTED, /* received choice, sending first parameter */
60 /* from here it's alg dependent */
61 AUTH_CHAP_ALG_SENT, /* CHAP: Algorithm selected */
62 AUTH_CHAP_RSP_SENT, /* CHAP: Response sent */
63 /* for all algorithms */
64 AUTH_DONE /* in parameter negotiation stage */
65 } auth_state_t;
66
67
68 /* enumeration of all the keys we know, and a place for the ones we don't */
69
70 typedef enum
71 {
72 K_AuthMethod,
73 K_Auth_CHAP_Algorithm,
74 K_Auth_CHAP_Challenge,
75 K_Auth_CHAP_Identifier,
76 K_Auth_CHAP_Name,
77 K_Auth_CHAP_Response,
78 K_DataDigest,
79 K_DataPDUInOrder,
80 K_DataSequenceInOrder,
81 K_DefaultTime2Retain,
82 K_DefaultTime2Wait,
83 K_ErrorRecoveryLevel,
84 K_FirstBurstLength,
85 K_HeaderDigest,
86 K_IFMarker,
87 K_IFMarkInt,
88 K_ImmediateData,
89 K_InitialR2T,
90 K_InitiatorAlias,
91 K_InitiatorName,
92 K_MaxBurstLength,
93 K_MaxConnections,
94 K_MaxOutstandingR2T,
95 K_MaxRecvDataSegmentLength,
96 K_OFMarker,
97 K_OFMarkInt,
98 K_SendTargets,
99 K_SessionType,
100 K_TargetAddress,
101 K_TargetAlias,
102 K_TargetName,
103 K_TargetPortalGroupTag,
104 K_NotUnderstood
105 } text_key_t;
106
107 /* maximum known key */
108 #define MAX_KEY K_TargetPortalGroupTag
109
110 /* value types */
111 typedef enum
112 { /* Value is... */
113 T_NUM, /* numeric */
114 T_BIGNUM, /* large numeric */
115 T_STRING, /* string */
116 T_YESNO, /* boolean (Yes or No) */
117 T_AUTH, /* authentication type (CHAP or None for now) */
118 T_DIGEST, /* digest (None or CRC32C) */
119 T_RANGE, /* numeric range */
120 T_SENDT, /* send target options (ALL, target-name, empty) */
121 T_SESS /* session type (Discovery or Normal) */
122 } val_kind_t;
123
124
125 /* table of negotiation key strings with value type and default */
126
127 typedef struct
128 {
129 const uint8_t *name; /* the key name */
130 val_kind_t val; /* the value type */
131 uint32_t defval; /* default value */
132 } key_entry_t;
133
134 STATIC key_entry_t entries[] = {
135 {"AuthMethod", T_AUTH, 0},
136 {"CHAP_A", T_NUM, 5},
137 {"CHAP_C", T_BIGNUM, 0},
138 {"CHAP_I", T_NUM, 0},
139 {"CHAP_N", T_STRING, 0},
140 {"CHAP_R", T_BIGNUM, 0},
141 {"DataDigest", T_DIGEST, 0},
142 {"DataPDUInOrder", T_YESNO, 1},
143 {"DataSequenceInOrder", T_YESNO, 1},
144 {"DefaultTime2Retain", T_NUM, 20},
145 {"DefaultTime2Wait", T_NUM, 2},
146 {"ErrorRecoveryLevel", T_NUM, 0},
147 {"FirstBurstLength", T_NUM, 64 * 1024},
148 {"HeaderDigest", T_DIGEST, 0},
149 {"IFMarker", T_YESNO, 0},
150 {"IFMarkInt", T_RANGE, 2048},
151 {"ImmediateData", T_YESNO, 1},
152 {"InitialR2T", T_YESNO, 1},
153 {"InitiatorAlias", T_STRING, 0},
154 {"InitiatorName", T_STRING, 0},
155 {"MaxBurstLength", T_NUM, 256 * 1024},
156 {"MaxConnections", T_NUM, 1},
157 {"MaxOutstandingR2T", T_NUM, 1},
158 {"MaxRecvDataSegmentLength", T_NUM, 8192},
159 {"OFMarker", T_YESNO, 0},
160 {"OFMarkInt", T_RANGE, 2048},
161 {"SendTargets", T_SENDT, 0},
162 {"SessionType", T_SESS, 0},
163 {"TargetAddress", T_STRING, 0},
164 {"TargetAlias", T_STRING, 0},
165 {"TargetName", T_STRING, 0},
166 {"TargetPortalGroupTag", T_NUM, 0},
167 {NULL, T_STRING, 0}
168 };
169
170 /* a negotiation parameter: key and values (there may be more than 1 for lists) */
171 typedef struct
172 {
173 text_key_t key; /* the key */
174 int list_num; /* number of elements in list, doubles as */
175 bool hex_bignums; /* wether to encode in hex or base64 */
176 /* data size for large numeric values */
177 union
178 {
179 uint32_t nval[MAX_LIST]; /* numeric or enumeration values */
180 uint8_t *sval; /* string or data pointer */
181 } val;
182 } negotiation_parameter_t;
183
184
185 /* Negotiation state flags */
186 #define NS_SENT 0x01 /* key was sent to target */
187 #define NS_RECEIVED 0x02 /* key was received from target */
188
189 typedef struct
190 {
191 negotiation_parameter_t pars[MAX_NEG]; /* the parameters to send */
192 negotiation_parameter_t *cpar; /* the last parameter set */
193 uint16_t num_pars; /* number of parameters to send */
194 auth_state_t auth_state; /* authentication state */
195 iscsi_auth_types_t auth_alg; /* authentication algorithm */
196 uint8_t kflags[MAX_KEY + 2]; /* negotiation flags for each key */
197 uint8_t password[MAX_STRING + 1]; /* authentication secret */
198 uint8_t target_password[MAX_STRING + 1]; /* target authentication secret */
199 uint8_t user_name[MAX_STRING + 1]; /* authentication user ID */
200 uint8_t temp_buf[MAX_STRING + 1]; /* scratch buffer */
201
202 bool HeaderDigest;
203 bool DataDigest;
204 bool InitialR2T;
205 bool ImmediateData;
206 uint32_t ErrorRecoveryLevel;
207 uint32_t MaxRecvDataSegmentLength;
208 uint32_t MaxConnections;
209 uint32_t DefaultTime2Wait;
210 uint32_t DefaultTime2Retain;
211 uint32_t MaxBurstLength;
212 uint32_t FirstBurstLength;
213 uint32_t MaxOutstandingR2T;
214
215 } negotiation_state_t;
216
217
218 #define TX(state, key) (state->kflags [key] & NS_SENT)
219 #define RX(state, key) (state->kflags [key] & NS_RECEIVED)
220
221 /*****************************************************************************/
222
223
224 STATIC void
225 chap_md5_response(uint8_t *buffer, uint8_t identifier, uint8_t *secret,
226 uint8_t *challenge, int challenge_size)
227 {
228 MD5_CTX md5;
229
230 MD5Init(&md5);
231 MD5Update(&md5, &identifier, 1);
232 MD5Update(&md5, secret, strlen(secret));
233 MD5Update(&md5, challenge, challenge_size);
234 MD5Final(buffer, &md5);
235 }
236
237
238 /*****************************************************************************/
239
240 /*
241 * hexdig:
242 * Return value of hex digit.
243 * Note: a null character is acceptable, and returns 0.
244 *
245 * Parameter:
246 * c The character
247 *
248 * Returns: The value, -1 on error.
249 */
250
251 static __inline int
252 hexdig(uint8_t c)
253 {
254
255 if (!c) {
256 return 0;
257 }
258 if (isdigit(c)) {
259 return c - '0';
260 }
261 c = toupper(c);
262 if (c >= 'A' && c <= 'F') {
263 return c - 'A' + 10;
264 }
265 return -1;
266 }
267
268 /*
269 * skiptozero:
270 * Skip to next zero character in buffer.
271 *
272 * Parameter:
273 * buf The buffer pointer
274 *
275 * Returns: The pointer to the character after the zero character.
276 */
277
278 static __inline uint8_t *
279 skiptozero(uint8_t *buf)
280 {
281
282 while (*buf) {
283 buf++;
284 }
285 return buf + 1;
286 }
287
288
289 /*
290 * get_bignumval:
291 * Get a large numeric value.
292 * NOTE: Overwrites source string.
293 *
294 * Parameter:
295 * buf The buffer pointer
296 * par The parameter
297 *
298 * Returns: The pointer to the next parameter, NULL on error.
299 */
300
301 STATIC uint8_t *
302 get_bignumval(uint8_t *buf, negotiation_parameter_t *par)
303 {
304 int val;
305 char c;
306 uint8_t *dp = buf;
307
308 par->val.sval = buf;
309
310 if (buf[0] == '0' && (buf[1] == 'x' || buf[1] == 'X')) {
311 buf += 2;
312 while ((c = *buf) != 0x0) {
313 buf++;
314 val = (hexdig(c) << 4) | hexdig(*buf);
315 if (val < 0) {
316 return NULL;
317 }
318 *dp++ = (uint8_t) val;
319 if (*buf) {
320 buf++;
321 }
322 }
323 buf++;
324 par->list_num = dp - par->val.sval;
325 } else if (buf[0] == '0' && (buf[1] == 'b' || buf[1] == 'B')) {
326 buf = base64_decode(&buf[2], par->val.sval, &par->list_num);
327 } else {
328 DEBOUT(("Ill-formatted large number <%s>\n", buf));
329 return NULL;
330 }
331
332 return buf;
333 }
334
335
336 /*
337 * get_numval:
338 * Get a numeric value.
339 *
340 * Parameter:
341 * buf The buffer pointer
342 * pval The pointer to the result.
343 *
344 * Returns: The pointer to the next parameter, NULL on error.
345 */
346
347 STATIC uint8_t *
348 get_numval(uint8_t *buf, uint32_t *pval)
349 {
350 uint32_t val = 0;
351 char c;
352
353 if (buf[0] == '0' && (buf[1] == 'x' || buf[1] == 'X')) {
354 buf += 2;
355 while (*buf && *buf != '~') {
356 int n;
357
358 if ((n = hexdig(*buf++)) < 0)
359 return NULL;
360 val = (val << 4) | n;
361 }
362 } else
363 while (*buf && *buf != '~') {
364 c = *buf++;
365 if (!isdigit(c))
366 return NULL;
367 val = val * 10 + (c - '0');
368 }
369
370 *pval = val;
371
372 return buf + 1;
373 }
374
375
376 /*
377 * get_range:
378 * Get a numeric range.
379 *
380 * Parameter:
381 * buf The buffer pointer
382 * pval1 The pointer to the first result.
383 * pval2 The pointer to the second result.
384 *
385 * Returns: The pointer to the next parameter, NULL on error.
386 */
387
388 STATIC uint8_t *
389 get_range(uint8_t *buf, uint32_t *pval1, uint32_t *pval2)
390 {
391
392 if ((buf = get_numval(buf, pval1)) == NULL)
393 return NULL;
394 if (!*buf)
395 return NULL;
396 if ((buf = get_numval(buf, pval2)) == NULL)
397 return NULL;
398 return buf;
399 }
400
401
402 /*
403 * get_ynval:
404 * Get a yes/no selection.
405 *
406 * Parameter:
407 * buf The buffer pointer
408 * pval The pointer to the result.
409 *
410 * Returns: The pointer to the next parameter, NULL on error.
411 */
412
413 STATIC uint8_t *
414 get_ynval(uint8_t *buf, uint32_t *pval)
415 {
416
417 if (strcmp(buf, "Yes") == 0)
418 *pval = 1;
419 else if (strcmp(buf, "No") == 0)
420 *pval = 0;
421 else
422 return NULL;
423
424 return skiptozero(buf);
425 }
426
427
428 /*
429 * get_digestval:
430 * Get a digest selection.
431 *
432 * Parameter:
433 * buf The buffer pointer
434 * pval The pointer to the result.
435 *
436 * Returns: The pointer to the next parameter, NULL on error.
437 */
438
439 STATIC uint8_t *
440 get_digestval(uint8_t *buf, uint32_t *pval)
441 {
442
443 if (strcmp(buf, "CRC32C") == 0)
444 *pval = 1;
445 else if (strcmp(buf, "None") == 0)
446 *pval = 0;
447 else
448 return NULL;
449
450 return skiptozero(buf);
451 }
452
453
454 /*
455 * get_authval:
456 * Get an authentication method.
457 *
458 * Parameter:
459 * buf The buffer pointer
460 * pval The pointer to the result.
461 *
462 * Returns: The pointer to the next parameter, NULL on error.
463 */
464
465 STATIC uint8_t *
466 get_authval(uint8_t *buf, uint32_t *pval)
467 {
468
469 if (strcmp(buf, "None") == 0)
470 *pval = ISCSI_AUTH_None;
471 else if (strcmp(buf, "CHAP") == 0)
472 *pval = ISCSI_AUTH_CHAP;
473 else if (strcmp(buf, "KRB5") == 0)
474 *pval = ISCSI_AUTH_KRB5;
475 else if (strcmp(buf, "SRP") == 0)
476 *pval = ISCSI_AUTH_SRP;
477 else
478 return NULL;
479
480 return skiptozero(buf);
481 }
482
483
484 /*
485 * get_strval:
486 * Get a string value (returns pointer to original buffer, not a copy).
487 *
488 * Parameter:
489 * buf The buffer pointer
490 * pval The pointer to the result pointer.
491 *
492 * Returns: The pointer to the next parameter, NULL on error.
493 */
494
495 STATIC uint8_t *
496 get_strval(uint8_t *buf, uint8_t **pval)
497 {
498
499 if (strlen(buf) > MAX_STRING)
500 return NULL;
501
502 *pval = buf;
503
504 return skiptozero(buf);
505 }
506
507
508 /*
509 * get_parameter:
510 * Analyze a key=value string.
511 * NOTE: The string is modified in the process.
512 *
513 * Parameter:
514 * buf The buffer pointer
515 * par The parameter descriptor to be filled in
516 *
517 * Returns: The pointer to the next parameter, NULL on error.
518 */
519
520 STATIC uint8_t *
521 get_parameter(uint8_t *buf, negotiation_parameter_t *par)
522 {
523 uint8_t *bp = buf;
524 int i;
525
526 while (*bp && *bp != '=') {
527 bp++;
528 }
529 if (!*bp) {
530 DEBOUT(("get_parameter: Premature end of parameter\n"));
531 return NULL;
532 }
533
534 *bp++ = 0;
535
536 for (i = 0; i <= MAX_KEY; i++)
537 if (!strcmp(buf, entries[i].name))
538 break;
539
540 par->key = i;
541 par->list_num = 1;
542
543 if (i > MAX_KEY) {
544 DEBOUT(("get_parameter: unrecognized key <%s>\n", buf));
545 if (strlen(buf) > MAX_STRING) {
546 DEBOUT(("get_parameter: key name > MAX_STRING\n"));
547 return NULL;
548 }
549 par->val.sval = buf;
550 return skiptozero(bp);
551 }
552
553 DEB(10, ("get_par: key <%s>=%d, val=%d, ret %p\n",
554 buf, i, entries[i].val, bp));
555 DEB(10, ("get_par: value '%s'\n",bp));
556
557 switch (entries[i].val) {
558 case T_NUM:
559 bp = get_numval(bp, &par->val.nval[0]);
560 break;
561
562 case T_BIGNUM:
563 bp = get_bignumval(bp, par);
564 break;
565
566 case T_STRING:
567 bp = get_strval(bp, &par->val.sval);
568 break;
569
570 case T_YESNO:
571 bp = get_ynval(bp, &par->val.nval[0]);
572 break;
573
574 case T_AUTH:
575 bp = get_authval(bp, &par->val.nval[0]);
576 break;
577
578 case T_DIGEST:
579 bp = get_digestval(bp, &par->val.nval[0]);
580 break;
581
582 case T_RANGE:
583 bp = get_range(bp, &par->val.nval[0], &par->val.nval[1]);
584 break;
585
586 default:
587 /* Target sending any other types is wrong */
588 bp = NULL;
589 break;
590 }
591 return bp;
592 }
593
594 /*****************************************************************************/
595
596 /*
597 * my_strcpy:
598 * Replacement for strcpy that returns the end of the result string
599 *
600 * Parameter:
601 * dest The destination buffer pointer
602 * src The source string
603 *
604 * Returns: A pointer to the terminating zero of the result.
605 */
606
607 static __inline unsigned
608 my_strcpy(uint8_t *dest, const uint8_t *src)
609 {
610 unsigned cc;
611
612 for (cc = 0 ; (*dest = *src) != 0x0 ; cc++) {
613 dest++;
614 src++;
615 }
616 return cc;
617 }
618
619 /*
620 * put_bignumval:
621 * Write a large numeric value.
622 * NOTE: Overwrites source string.
623 *
624 * Parameter:
625 * buf The buffer pointer
626 * par The parameter
627 *
628 * Returns: The pointer to the next parameter, NULL on error.
629 */
630
631 STATIC unsigned
632 put_bignumval(negotiation_parameter_t *par, uint8_t *buf)
633 {
634 int k, c;
635
636 if (par->hex_bignums) {
637 my_strcpy(buf, "0x");
638 for (k=0; k<par->list_num; ++k) {
639 c = par->val.sval[k] >> 4;
640 buf[2+2*k] = c < 10 ? '0' + c : 'a' + (c-10);
641 c = par->val.sval[k] & 0xf;
642 buf[2+2*k+1] = c < 10 ? '0' + c : 'a' + (c-10);
643 }
644 buf[2+2*k] = '\0';
645
646 return 2+2*par->list_num;
647 }
648 return base64_encode(par->val.sval, par->list_num, buf);
649 }
650
651 /*
652 * put_parameter:
653 * Create a key=value string.
654 *
655 * Parameter:
656 * buf The buffer pointer
657 * par The parameter descriptor
658 *
659 * Returns: The pointer to the next free buffer space, NULL on error.
660 */
661
662 STATIC unsigned
663 put_parameter(uint8_t *buf, unsigned len, negotiation_parameter_t *par)
664 {
665 int i;
666 unsigned cc, cl;
667 const uint8_t *sp;
668
669 DEB(10, ("put_par: key <%s>=%d, val=%d\n",
670 entries[par->key].name, par->key, entries[par->key].val));
671
672 if (par->key > MAX_KEY) {
673 return snprintf(buf, len, "%s=NotUnderstood", par->val.sval);
674 }
675
676 cc = snprintf(buf, len, "%s=", entries[par->key].name);
677 if (cc >= len)
678 return len;
679
680 for (i = 0; i < par->list_num; i++) {
681 switch (entries[par->key].val) {
682 case T_NUM:
683 cl = snprintf(&buf[cc], len - cc, "%d",
684 par->val.nval[i]);
685 break;
686
687 case T_BIGNUM:
688 cl = put_bignumval(par, &buf[cc]);
689 i = par->list_num;
690 break;
691
692 case T_STRING:
693 cl = my_strcpy(&buf[cc], par->val.sval);
694 break;
695
696 case T_YESNO:
697 cl = my_strcpy(&buf[cc],
698 (par->val.nval[i]) ? "Yes" : "No");
699 break;
700
701 case T_AUTH:
702 switch (par->val.nval[i]) {
703 case ISCSI_AUTH_CHAP:
704 sp = "CHAP";
705 break;
706 case ISCSI_AUTH_KRB5:
707 sp = "KRB5";
708 break;
709 case ISCSI_AUTH_SRP:
710 sp = "SRP";
711 break;
712 default:
713 sp = "None";
714 break;
715 }
716 cl = my_strcpy(&buf[cc], sp);
717 break;
718
719 case T_DIGEST:
720 cl = my_strcpy(&buf[cc],
721 (par->val.nval[i]) ? "CRC32C" : "None");
722 break;
723
724 case T_RANGE:
725 if ((i + 1) >= par->list_num) {
726 cl = my_strcpy(&buf[cc], "Reject");
727 } else {
728 cl = snprintf(&buf[cc], len - cc,
729 "%d~%d", par->val.nval[i],
730 par->val.nval[i + 1]);
731 i++;
732 }
733 break;
734
735 case T_SENDT:
736 cl = my_strcpy(&buf[cc], par->val.sval);
737 break;
738
739 case T_SESS:
740 cl = my_strcpy(&buf[cc],
741 (par->val.nval[i]) ? "Normal" : "Discovery");
742 break;
743
744 default:
745 cl = 0;
746 /* We should't be here... */
747 DEBOUT(("Invalid type %d in put_parameter!\n",
748 entries[par->key].val));
749 break;
750 }
751
752 DEB(10, ("put_par: value '%s'\n",&buf[cc]));
753
754 cc += cl;
755 if (cc >= len)
756 return len;
757 if ((i + 1) < par->list_num) {
758 if (cc >= len)
759 return len;
760 buf[cc++] = ',';
761 }
762 }
763
764 if (cc >= len)
765 return len;
766 buf[cc] = 0x0; /* make sure it's terminated */
767 return cc + 1; /* return next place in list */
768 }
769
770
771 /*
772 * put_par_block:
773 * Fill a parameter block
774 *
775 * Parameter:
776 * buf The buffer pointer
777 * pars The parameter descriptor array
778 * n The number of elements
779 *
780 * Returns: result from put_parameter (ptr to buffer, NULL on error)
781 */
782
783 static __inline unsigned
784 put_par_block(uint8_t *buf, unsigned len, negotiation_parameter_t *pars, int n)
785 {
786 unsigned cc;
787 int i;
788
789 for (cc = 0, i = 0; i < n; i++) {
790 cc += put_parameter(&buf[cc], len - cc, pars++);
791 if (cc >= len) {
792 break;
793 }
794 }
795 return cc;
796 }
797
798 /*
799 * parameter_size:
800 * Determine the size of a key=value string.
801 *
802 * Parameter:
803 * par The parameter descriptor
804 *
805 * Returns: The size of the resulting string.
806 */
807
808 STATIC int
809 parameter_size(negotiation_parameter_t *par)
810 {
811 int i, size;
812 char buf[24]; /* max. 2 10-digit numbers + sep. */
813
814 if (par->key > MAX_KEY) {
815 return strlen(par->val.sval) + 15;
816 }
817 /* count '=' and terminal zero */
818 size = strlen(entries[par->key].name) + 2;
819
820 for (i = 0; i < par->list_num; i++) {
821 switch (entries[par->key].val) {
822 case T_NUM:
823 size += snprintf(buf, sizeof(buf), "%d",
824 par->val.nval[i]);
825 break;
826
827 case T_BIGNUM:
828 /* list_num holds value size */
829 if (par->hex_bignums)
830 size += 2 + 2*par->list_num;
831 else
832 size += base64_enclen(par->list_num);
833 i = par->list_num;
834 break;
835
836 case T_STRING:
837 case T_SENDT:
838 size += strlen(par->val.sval);
839 break;
840
841 case T_YESNO:
842 size += (par->val.nval[i]) ? 3 : 2;
843 break;
844
845 case T_AUTH:
846 size += (par->val.nval[i] == ISCSI_AUTH_SRP) ? 3 : 4;
847 break;
848
849 case T_DIGEST:
850 size += (par->val.nval[i]) ? 6 : 4;
851 break;
852
853 case T_RANGE:
854 if (i+1 < par->list_num) {
855 size += snprintf(buf, sizeof(buf), "%d~%d",
856 par->val.nval[i],
857 par->val.nval[i + 1]);
858 i++;
859 } else
860 DEBOUT(("Incomplete range parameter\n"));
861 break;
862
863 case T_SESS:
864 size += (par->val.nval[i]) ? 6 : 9;
865 break;
866
867 default:
868 /* We should't be here... */
869 DEBOUT(("Invalid type %d in parameter_size!\n",
870 entries[par->key].val));
871 break;
872 }
873 if ((i + 1) < par->list_num) {
874 size++;
875 }
876 }
877
878 return size;
879 }
880
881
882 /*
883 * total_size:
884 * Determine the size of a negotiation data block
885 *
886 * Parameter:
887 * pars The parameter descriptor array
888 * n The number of elements
889 *
890 * Returns: The size of the block
891 */
892
893 static __inline int
894 total_size(negotiation_parameter_t *pars, int n)
895 {
896 int i, size;
897
898 for (i = 0, size = 0; i < n; i++) {
899 size += parameter_size(pars++);
900 }
901 return size;
902 }
903
904 /*****************************************************************************/
905
906
907 /*
908 * complete_pars:
909 * Allocate space for text parameters, translate parameter values into
910 * text.
911 *
912 * Parameter:
913 * state Negotiation state
914 * pdu The transmit PDU
915 *
916 * Returns: 0 On success
917 * > 0 (an ISCSI error code) if an error occurred.
918 */
919
920 STATIC int
921 complete_pars(negotiation_state_t *state, pdu_t *pdu)
922 {
923 int len;
924 uint8_t *bp;
925
926 len = total_size(state->pars, state->num_pars);
927
928 DEB(10, ("complete_pars: n=%d, len=%d\n", state->num_pars, len));
929
930 if ((bp = malloc(len, M_TEMP, M_WAITOK)) == NULL) {
931 DEBOUT(("*** Out of memory in complete_pars\n"));
932 return ISCSI_STATUS_NO_RESOURCES;
933 }
934 pdu->pdu_temp_data = bp;
935
936 if (put_par_block(pdu->pdu_temp_data, len, state->pars,
937 state->num_pars) == 0) {
938 DEBOUT(("Bad parameter in complete_pars\n"));
939 return ISCSI_STATUS_PARAMETER_INVALID;
940 }
941
942 pdu->pdu_temp_data_len = len;
943 return 0;
944 }
945
946
947 /*
948 * set_key_n:
949 * Initialize a key and its numeric value.
950 *
951 * Parameter:
952 * state Negotiation state
953 * key The key
954 * val The value
955 */
956
957 STATIC negotiation_parameter_t *
958 set_key_n(negotiation_state_t *state, text_key_t key, uint32_t val)
959 {
960 negotiation_parameter_t *par;
961
962 if (state->num_pars >= MAX_NEG) {
963 DEBOUT(("set_key_n: num_pars (%d) >= MAX_NEG (%d)\n",
964 state->num_pars, MAX_NEG));
965 return NULL;
966 }
967 par = &state->pars[state->num_pars];
968 par->key = key;
969 par->list_num = 1;
970 par->val.nval[0] = val;
971 state->num_pars++;
972 state->kflags[key] |= NS_SENT;
973
974 return par;
975 }
976
977 /*
978 * set_key_s:
979 * Initialize a key and its string value.
980 *
981 * Parameter:
982 * state Negotiation state
983 * key The key
984 * val The value
985 */
986
987 STATIC negotiation_parameter_t *
988 set_key_s(negotiation_state_t *state, text_key_t key, uint8_t *val)
989 {
990 negotiation_parameter_t *par;
991
992 if (state->num_pars >= MAX_NEG) {
993 DEBOUT(("set_key_s: num_pars (%d) >= MAX_NEG (%d)\n",
994 state->num_pars, MAX_NEG));
995 return NULL;
996 }
997 par = &state->pars[state->num_pars];
998 par->key = key;
999 par->list_num = 1;
1000 par->val.sval = val;
1001 par->hex_bignums = iscsi_hex_bignums;
1002 state->num_pars++;
1003 state->kflags[key] |= NS_SENT;
1004
1005 return par;
1006 }
1007
1008
1009 /*****************************************************************************/
1010
1011 /*
1012 * eval_parameter:
1013 * Evaluate a received negotiation value.
1014 *
1015 * Parameter:
1016 * conn The connection
1017 * state The negotiation state
1018 * par The parameter
1019 *
1020 * Returns: 0 on success, else an ISCSI status value.
1021 */
1022
1023 STATIC int
1024 eval_parameter(connection_t *conn, negotiation_state_t *state,
1025 negotiation_parameter_t *par)
1026 {
1027 uint32_t n = par->val.nval[0];
1028 size_t sz;
1029 text_key_t key = par->key;
1030 bool sent = (state->kflags[key] & NS_SENT) != 0;
1031
1032 state->kflags[key] |= NS_RECEIVED;
1033
1034 switch (key) {
1035 /*
1036 * keys connected to security negotiation
1037 */
1038 case K_AuthMethod:
1039 if (n) {
1040 DEBOUT(("eval_par: AuthMethod nonzero (%d)\n", n));
1041 return ISCSI_STATUS_NEGOTIATION_ERROR;
1042 }
1043 break;
1044
1045 case K_Auth_CHAP_Algorithm:
1046 case K_Auth_CHAP_Challenge:
1047 case K_Auth_CHAP_Identifier:
1048 case K_Auth_CHAP_Name:
1049 case K_Auth_CHAP_Response:
1050 DEBOUT(("eval_par: Authorization Key in Operational Phase\n"));
1051 return ISCSI_STATUS_NEGOTIATION_ERROR;
1052
1053 /*
1054 * keys we always send
1055 */
1056 case K_DataDigest:
1057 state->DataDigest = n;
1058 if (!sent)
1059 set_key_n(state, key, n);
1060 break;
1061
1062 case K_HeaderDigest:
1063 state->HeaderDigest = n;
1064 if (!sent)
1065 set_key_n(state, key, n);
1066 break;
1067
1068 case K_ErrorRecoveryLevel:
1069 state->ErrorRecoveryLevel = n;
1070 if (!sent)
1071 set_key_n(state, key, n);
1072 break;
1073
1074 case K_ImmediateData:
1075 state->ImmediateData = n;
1076 if (!sent)
1077 set_key_n(state, key, n);
1078 break;
1079
1080 case K_InitialR2T:
1081 state->InitialR2T = n;
1082 if (!sent)
1083 set_key_n(state, key, n);
1084 break;
1085
1086 case K_MaxRecvDataSegmentLength:
1087 state->MaxRecvDataSegmentLength = n;
1088 /* this is basically declarative, not negotiated */
1089 /* (each side has its own value) */
1090 break;
1091
1092 /*
1093 * keys we don't always send, so we may have to reflect the value
1094 */
1095 case K_DefaultTime2Retain:
1096 state->DefaultTime2Retain = n = min(state->DefaultTime2Retain, n);
1097 if (!sent)
1098 set_key_n(state, key, n);
1099 break;
1100
1101 case K_DefaultTime2Wait:
1102 state->DefaultTime2Wait = n = min(state->DefaultTime2Wait, n);
1103 if (!sent)
1104 set_key_n(state, key, n);
1105 break;
1106
1107 case K_MaxConnections:
1108 if (state->MaxConnections)
1109 state->MaxConnections = n = min(state->MaxConnections, n);
1110 else
1111 state->MaxConnections = n;
1112
1113 if (!sent)
1114 set_key_n(state, key, n);
1115 break;
1116
1117 case K_MaxOutstandingR2T:
1118 state->MaxOutstandingR2T = n;
1119 if (!sent)
1120 set_key_n(state, key, n);
1121 break;
1122
1123 case K_FirstBurstLength:
1124 state->FirstBurstLength = n;
1125 if (!sent)
1126 set_key_n(state, key, n);
1127 break;
1128
1129 case K_MaxBurstLength:
1130 state->MaxBurstLength = n;
1131 if (!sent)
1132 set_key_n(state, key, n);
1133 break;
1134
1135 case K_IFMarker:
1136 case K_OFMarker:
1137 /* not (yet) supported */
1138 if (!sent)
1139 set_key_n(state, key, 0);
1140 break;
1141
1142 case K_IFMarkInt:
1143 case K_OFMarkInt:
1144 /* it's a range, and list_num will be 1, so this will reply "Reject" */
1145 if (!sent)
1146 set_key_n(state, key, 0);
1147 break;
1148
1149 case K_DataPDUInOrder:
1150 case K_DataSequenceInOrder:
1151 /* values are don't care */
1152 if (!sent)
1153 set_key_n(state, key, n);
1154 break;
1155
1156 case K_NotUnderstood:
1157 /* return "NotUnderstood" */
1158 set_key_s(state, key, par->val.sval);
1159 break;
1160
1161 /*
1162 * Declarative keys (no response required)
1163 */
1164 case K_TargetAddress:
1165 /* ignore for now... */
1166 break;
1167
1168 case K_TargetAlias:
1169 if (conn->c_login_par->is_present.TargetAlias) {
1170 copyoutstr(par->val.sval, conn->c_login_par->TargetAlias,
1171 ISCSI_STRING_LENGTH - 1, &sz);
1172 /* do anything with return code?? */
1173 }
1174 break;
1175
1176 case K_TargetPortalGroupTag:
1177 /* ignore for now... */
1178 break;
1179
1180 default:
1181 DEBOUT(("eval_par: Invalid parameter type %d\n", par->key));
1182 return ISCSI_STATUS_NEGOTIATION_ERROR;
1183 }
1184 return 0;
1185 }
1186
1187 /*****************************************************************************/
1188
1189
1190 /*
1191 * init_session_parameters:
1192 * Initialize session-related negotiation parameters from existing session
1193 *
1194 * Parameter:
1195 * sess The session
1196 * state The negotiation state
1197 */
1198
1199 STATIC void
1200 init_session_parameters(session_t *sess, negotiation_state_t *state)
1201 {
1202
1203 state->ErrorRecoveryLevel = sess->s_ErrorRecoveryLevel;
1204 state->InitialR2T = sess->s_InitialR2T;
1205 state->ImmediateData = sess->s_ImmediateData;
1206 state->MaxConnections = sess->s_MaxConnections;
1207 state->DefaultTime2Wait = sess->s_DefaultTime2Wait;
1208 state->DefaultTime2Retain = sess->s_DefaultTime2Retain;
1209 state->MaxBurstLength = sess->s_MaxBurstLength;
1210 state->FirstBurstLength = sess->s_FirstBurstLength;
1211 state->MaxOutstandingR2T = sess->s_MaxOutstandingR2T;
1212 }
1213
1214
1215
1216 /*
1217 * assemble_login_parameters:
1218 * Assemble the initial login negotiation parameters.
1219 *
1220 * Parameter:
1221 * conn The connection
1222 * ccb The CCB for the login exchange
1223 * pdu The PDU to use for sending
1224 *
1225 * Returns: < 0 if more security negotiation is required
1226 * 0 if this is the last security negotiation block
1227 * > 0 (an ISCSI error code) if an error occurred.
1228 */
1229
1230 int
1231 assemble_login_parameters(connection_t *conn, ccb_t *ccb, pdu_t *pdu)
1232 {
1233 iscsi_login_parameters_t *par = conn->c_login_par;
1234 size_t sz;
1235 int rc, i, next;
1236 negotiation_state_t *state;
1237 negotiation_parameter_t *cpar;
1238
1239 state = malloc(sizeof(*state), M_TEMP, M_WAITOK | M_ZERO);
1240 if (state == NULL) {
1241 DEBOUT(("*** Out of memory in assemble_login_params\n"));
1242 return ISCSI_STATUS_NO_RESOURCES;
1243 }
1244 ccb->ccb_temp_data = state;
1245
1246 if (!iscsi_InitiatorName[0]) {
1247 DEBOUT(("No InitiatorName\n"));
1248 return ISCSI_STATUS_PARAMETER_MISSING;
1249 }
1250 set_key_s(state, K_InitiatorName, iscsi_InitiatorName);
1251
1252 if (iscsi_InitiatorAlias[0])
1253 set_key_s(state, K_InitiatorAlias, iscsi_InitiatorAlias);
1254
1255 conn->c_Our_MaxRecvDataSegmentLength =
1256 (par->is_present.MaxRecvDataSegmentLength)
1257 ? par->MaxRecvDataSegmentLength : DEFAULT_MaxRecvDataSegmentLength;
1258
1259 /* setup some values for authentication */
1260 if (par->is_present.password)
1261 copyinstr(par->password, state->password, MAX_STRING, &sz);
1262 if (par->is_present.target_password)
1263 copyinstr(par->target_password, state->target_password,
1264 MAX_STRING, &sz);
1265 if (par->is_present.user_name)
1266 copyinstr(par->user_name, state->user_name, MAX_STRING, &sz);
1267 else
1268 strlcpy(state->user_name, iscsi_InitiatorName,
1269 sizeof(state->user_name));
1270
1271 next = TRUE;
1272
1273 set_key_n(state, K_SessionType,
1274 par->login_type > ISCSI_LOGINTYPE_DISCOVERY);
1275
1276 cpar = set_key_n(state, K_AuthMethod, ISCSI_AUTH_None);
1277
1278 if (cpar != NULL && par->is_present.auth_info &&
1279 par->auth_info.auth_number > 0) {
1280 if (par->auth_info.auth_number > ISCSI_AUTH_OPTIONS) {
1281 DEBOUT(("Auth number too big in asm_login\n"));
1282 return ISCSI_STATUS_PARAMETER_INVALID;
1283 }
1284 cpar->list_num = par->auth_info.auth_number;
1285 for (i = 0; i < cpar->list_num; i++) {
1286 cpar->val.nval[i] = par->auth_info.auth_type[i];
1287 if (par->auth_info.auth_type[i])
1288 next = FALSE;
1289 }
1290 }
1291
1292 if (par->is_present.TargetName)
1293 copyinstr(par->TargetName, state->temp_buf, ISCSI_STRING_LENGTH - 1,
1294 &sz);
1295 else {
1296 state->temp_buf[0] = 0;
1297 sz = 0;
1298 }
1299
1300 if ((!sz || !state->temp_buf[0]) &&
1301 par->login_type != ISCSI_LOGINTYPE_DISCOVERY) {
1302 DEBOUT(("No TargetName\n"));
1303 return ISCSI_STATUS_PARAMETER_MISSING;
1304 }
1305
1306 if (state->temp_buf[0]) {
1307 set_key_s(state, K_TargetName, state->temp_buf);
1308 }
1309
1310 if ((rc = complete_pars(state, pdu)) != 0)
1311 return rc;
1312
1313 return (next) ? 0 : -1;
1314 }
1315
1316
1317 /*
1318 * assemble_security_parameters:
1319 * Assemble the security negotiation parameters.
1320 *
1321 * Parameter:
1322 * conn The connection
1323 * rx_pdu The received login response PDU
1324 * tx_pdu The transmit PDU
1325 *
1326 * Returns: < 0 if more security negotiation is required
1327 * 0 if this is the last security negotiation block
1328 * > 0 (an ISCSI error code) if an error occurred.
1329 */
1330
1331 int
1332 assemble_security_parameters(connection_t *conn, ccb_t *ccb, pdu_t *rx_pdu,
1333 pdu_t *tx_pdu)
1334 {
1335 negotiation_state_t *state = (negotiation_state_t *) ccb->ccb_temp_data;
1336 iscsi_login_parameters_t *par = conn->c_login_par;
1337 negotiation_parameter_t rxp, *cpar;
1338 uint8_t *rxpars;
1339 int rc, next;
1340 uint8_t identifier = 0;
1341 uint8_t *challenge = NULL;
1342 int challenge_size = 0;
1343 uint8_t *response = NULL;
1344 int response_size = 0;
1345
1346 state->num_pars = 0;
1347 next = 0;
1348
1349 rxpars = (uint8_t *) rx_pdu->pdu_temp_data;
1350 if (rxpars == NULL) {
1351 DEBOUT(("No received parameters!\n"));
1352 return ISCSI_STATUS_NEGOTIATION_ERROR;
1353 }
1354 /* Note: There are always at least 2 extra bytes past temp_data_len */
1355 rxpars[rx_pdu->pdu_temp_data_len] = '\0';
1356 rxpars[rx_pdu->pdu_temp_data_len + 1] = '\0';
1357
1358 while (*rxpars) {
1359 if ((rxpars = get_parameter(rxpars, &rxp)) == NULL) {
1360 DEBOUT(("get_parameter returned error\n"));
1361 return ISCSI_STATUS_NEGOTIATION_ERROR;
1362 }
1363
1364 state->kflags[rxp.key] |= NS_RECEIVED;
1365
1366 switch (rxp.key) {
1367 case K_AuthMethod:
1368 if (state->auth_state != AUTH_INITIAL) {
1369 DEBOUT(("AuthMethod received, auth_state = %d\n",
1370 state->auth_state));
1371 return ISCSI_STATUS_NEGOTIATION_ERROR;
1372 }
1373
1374 /* Note: if the selection is None, we shouldn't be here,
1375 * the target should have transited the state to op-neg.
1376 */
1377 if (rxp.val.nval[0] != ISCSI_AUTH_CHAP) {
1378 DEBOUT(("AuthMethod isn't CHAP (%d)\n", rxp.val.nval[0]));
1379 return ISCSI_STATUS_NEGOTIATION_ERROR;
1380 }
1381
1382 state->auth_state = AUTH_METHOD_SELECTED;
1383 state->auth_alg = rxp.val.nval[0];
1384 break;
1385
1386 case K_Auth_CHAP_Algorithm:
1387 if (state->auth_state != AUTH_CHAP_ALG_SENT ||
1388 rxp.val.nval[0] != 5) {
1389 DEBOUT(("Bad algorithm, auth_state = %d, alg %d\n",
1390 state->auth_state, rxp.val.nval[0]));
1391 return ISCSI_STATUS_NEGOTIATION_ERROR;
1392 }
1393 break;
1394
1395 case K_Auth_CHAP_Challenge:
1396 if (state->auth_state != AUTH_CHAP_ALG_SENT || !rxp.list_num) {
1397 DEBOUT(("Bad Challenge, auth_state = %d, len %d\n",
1398 state->auth_state, rxp.list_num));
1399 return ISCSI_STATUS_NEGOTIATION_ERROR;
1400 }
1401 challenge = rxp.val.sval;
1402 challenge_size = rxp.list_num;
1403 break;
1404
1405 case K_Auth_CHAP_Identifier:
1406 if (state->auth_state != AUTH_CHAP_ALG_SENT) {
1407 DEBOUT(("Bad ID, auth_state = %d, id %d\n",
1408 state->auth_state, rxp.val.nval[0]));
1409 return ISCSI_STATUS_NEGOTIATION_ERROR;
1410 }
1411 identifier = (uint8_t) rxp.val.nval[0];
1412 break;
1413
1414 case K_Auth_CHAP_Name:
1415 if (state->auth_state != AUTH_CHAP_RSP_SENT) {
1416 DEBOUT(("Bad Name, auth_state = %d, name <%s>\n",
1417 state->auth_state, rxp.val.sval));
1418 return ISCSI_STATUS_NEGOTIATION_ERROR;
1419 }
1420 /* what do we do with the name?? */
1421 break;
1422
1423 case K_Auth_CHAP_Response:
1424 if (state->auth_state != AUTH_CHAP_RSP_SENT) {
1425 DEBOUT(("Bad Response, auth_state = %d, size %d\n",
1426 state->auth_state, rxp.list_num));
1427 return ISCSI_STATUS_NEGOTIATION_ERROR;
1428 }
1429 response = rxp.val.sval;
1430 response_size = rxp.list_num;
1431 if (response_size != CHAP_MD5_SIZE)
1432 return ISCSI_STATUS_NEGOTIATION_ERROR;
1433 break;
1434
1435 default:
1436 rc = eval_parameter(conn, state, &rxp);
1437 if (rc)
1438 return rc;
1439 break;
1440 }
1441 }
1442
1443 switch (state->auth_state) {
1444 case AUTH_INITIAL:
1445 DEBOUT(("Didn't receive Method\n"));
1446 return ISCSI_STATUS_NEGOTIATION_ERROR;
1447
1448 case AUTH_METHOD_SELECTED:
1449 set_key_n(state, K_Auth_CHAP_Algorithm, 5);
1450 state->auth_state = AUTH_CHAP_ALG_SENT;
1451 next = -1;
1452 break;
1453
1454 case AUTH_CHAP_ALG_SENT:
1455 if (!RX(state, K_Auth_CHAP_Algorithm) ||
1456 !RX(state, K_Auth_CHAP_Identifier) ||
1457 !RX(state, K_Auth_CHAP_Challenge)) {
1458 DEBOUT(("Didn't receive all parameters\n"));
1459 return ISCSI_STATUS_NEGOTIATION_ERROR;
1460 }
1461
1462 set_key_s(state, K_Auth_CHAP_Name, state->user_name);
1463
1464 chap_md5_response(state->temp_buf, identifier, state->password,
1465 challenge, challenge_size);
1466
1467 cpar = set_key_s(state, K_Auth_CHAP_Response, state->temp_buf);
1468 if (cpar != NULL)
1469 cpar->list_num = CHAP_MD5_SIZE;
1470
1471 if (par->auth_info.mutual_auth) {
1472 if (!state->target_password[0]) {
1473 DEBOUT(("No target password with mutual authentication!\n"));
1474 return ISCSI_STATUS_PARAMETER_MISSING;
1475 }
1476
1477 cprng_strong(kern_cprng,
1478 &state->temp_buf[CHAP_MD5_SIZE],
1479 CHAP_CHALLENGE_LEN + 1, 0);
1480 set_key_n(state, K_Auth_CHAP_Identifier,
1481 state->temp_buf[CHAP_MD5_SIZE]);
1482 cpar = set_key_s(state, K_Auth_CHAP_Challenge,
1483 &state->temp_buf[CHAP_MD5_SIZE + 1]);
1484 if (cpar != NULL)
1485 cpar->list_num = CHAP_CHALLENGE_LEN;
1486 next = -1;
1487 }
1488 state->auth_state = AUTH_CHAP_RSP_SENT;
1489 break;
1490
1491 case AUTH_CHAP_RSP_SENT:
1492 /* we can only be here for mutual authentication */
1493 if (!par->auth_info.mutual_auth || response == NULL) {
1494 DEBOUT(("Mutual authentication not requested\n"));
1495 return ISCSI_STATUS_NEGOTIATION_ERROR;
1496 }
1497
1498 chap_md5_response(state->temp_buf,
1499 state->temp_buf[CHAP_MD5_SIZE],
1500 state->password,
1501 &state->temp_buf[CHAP_MD5_SIZE + 1],
1502 CHAP_CHALLENGE_LEN);
1503
1504 if (memcmp(state->temp_buf, response, response_size)) {
1505 DEBOUT(("Mutual authentication mismatch\n"));
1506 return ISCSI_STATUS_AUTHENTICATION_FAILED;
1507 }
1508 break;
1509
1510 default:
1511 break;
1512 }
1513
1514 complete_pars(state, tx_pdu);
1515
1516 return next;
1517 }
1518
1519
1520 /*
1521 * set_first_opnegs:
1522 * Set the operational negotiation parameters we want to negotiate in
1523 * the first login request in op_neg phase.
1524 *
1525 * Parameter:
1526 * conn The connection
1527 * state Negotiation state
1528 */
1529
1530 STATIC void
1531 set_first_opnegs(connection_t *conn, negotiation_state_t *state)
1532 {
1533 iscsi_login_parameters_t *lpar = conn->c_login_par;
1534 negotiation_parameter_t *cpar;
1535
1536 /* Digests - suggest None,CRC32C unless the user forces a value */
1537 cpar = set_key_n(state, K_HeaderDigest,
1538 (lpar->is_present.HeaderDigest) ? lpar->HeaderDigest : 0);
1539 if (cpar != NULL && !lpar->is_present.HeaderDigest) {
1540 cpar->list_num = 2;
1541 cpar->val.nval[1] = 1;
1542 }
1543
1544 cpar = set_key_n(state, K_DataDigest, (lpar->is_present.DataDigest)
1545 ? lpar->DataDigest : 0);
1546 if (cpar != NULL && !lpar->is_present.DataDigest) {
1547 cpar->list_num = 2;
1548 cpar->val.nval[1] = 1;
1549 }
1550
1551 set_key_n(state, K_MaxRecvDataSegmentLength,
1552 conn->c_Our_MaxRecvDataSegmentLength);
1553 /* This is direction-specific, we may have a different default */
1554 state->MaxRecvDataSegmentLength =
1555 entries[K_MaxRecvDataSegmentLength].defval;
1556
1557 /* First connection only */
1558 if (!conn->c_session->s_TSIH) {
1559 state->ErrorRecoveryLevel =
1560 (lpar->is_present.ErrorRecoveryLevel) ? lpar->ErrorRecoveryLevel
1561 : 2;
1562 /*
1563 Negotiate InitialR2T to FALSE and ImmediateData to TRUE, should
1564 be slightly more efficient than the default InitialR2T=TRUE.
1565 */
1566 state->InitialR2T = FALSE;
1567 state->ImmediateData = TRUE;
1568
1569 /* We don't really care about this, so don't negotiate by default */
1570 state->MaxBurstLength = entries[K_MaxBurstLength].defval;
1571 state->FirstBurstLength = entries[K_FirstBurstLength].defval;
1572 state->MaxOutstandingR2T = entries[K_MaxOutstandingR2T].defval;
1573
1574 set_key_n(state, K_ErrorRecoveryLevel, state->ErrorRecoveryLevel);
1575 set_key_n(state, K_InitialR2T, state->InitialR2T);
1576 set_key_n(state, K_ImmediateData, state->ImmediateData);
1577
1578 if (lpar->is_present.MaxConnections) {
1579 state->MaxConnections = lpar->MaxConnections;
1580 set_key_n(state, K_MaxConnections, lpar->MaxConnections);
1581 }
1582
1583 if (lpar->is_present.DefaultTime2Wait)
1584 set_key_n(state, K_DefaultTime2Wait, lpar->DefaultTime2Wait);
1585 else
1586 state->DefaultTime2Wait = entries[K_DefaultTime2Wait].defval;
1587
1588 if (lpar->is_present.DefaultTime2Retain)
1589 set_key_n(state, K_DefaultTime2Retain, lpar->DefaultTime2Retain);
1590 else
1591 state->DefaultTime2Retain = entries[K_DefaultTime2Retain].defval;
1592 } else
1593 init_session_parameters(conn->c_session, state);
1594
1595 DEBC(conn, 10, ("SetFirstOpnegs: recover=%d, MRDSL=%d\n",
1596 conn->c_recover, state->MaxRecvDataSegmentLength));
1597 }
1598
1599
1600 /*
1601 * assemble_negotiation_parameters:
1602 * Assemble any negotiation parameters requested by the other side.
1603 *
1604 * Parameter:
1605 * conn The connection
1606 * ccb The login ccb
1607 * rx_pdu The received login response PDU
1608 * tx_pdu The transmit PDU
1609 *
1610 * Returns: 0 On success
1611 * > 0 (an ISCSI error code) if an error occurred.
1612 */
1613
1614 int
1615 assemble_negotiation_parameters(connection_t *conn, ccb_t *ccb, pdu_t *rx_pdu,
1616 pdu_t *tx_pdu)
1617 {
1618 negotiation_state_t *state = (negotiation_state_t *) ccb->ccb_temp_data;
1619 negotiation_parameter_t rxp;
1620 uint8_t *rxpars;
1621 int rc;
1622
1623 state->num_pars = 0;
1624
1625 DEBC(conn, 10, ("AsmNegParams: connState=%d, MRDSL=%d\n",
1626 conn->c_state, state->MaxRecvDataSegmentLength));
1627
1628 if (conn->c_state == ST_SEC_NEG) {
1629 conn->c_state = ST_OP_NEG;
1630 set_first_opnegs(conn, state);
1631 }
1632
1633 rxpars = (uint8_t *) rx_pdu->pdu_temp_data;
1634 if (rxpars != NULL) {
1635 /* Note: There are always at least 2 extra bytes past temp_data_len */
1636 rxpars[rx_pdu->pdu_temp_data_len] = '\0';
1637 rxpars[rx_pdu->pdu_temp_data_len + 1] = '\0';
1638
1639 while (*rxpars) {
1640 if ((rxpars = get_parameter(rxpars, &rxp)) == NULL)
1641 return ISCSI_STATUS_NEGOTIATION_ERROR;
1642
1643 rc = eval_parameter(conn, state, &rxp);
1644 if (rc)
1645 return rc;
1646 }
1647 }
1648
1649 if (tx_pdu == NULL)
1650 return 0;
1651
1652 complete_pars(state, tx_pdu);
1653
1654 return 0;
1655 }
1656
1657 /*
1658 * init_text_parameters:
1659 * Initialize text negotiation.
1660 *
1661 * Parameter:
1662 * conn The connection
1663 * tx_pdu The transmit PDU
1664 *
1665 * Returns: 0 On success
1666 * > 0 (an ISCSI error code) if an error occurred.
1667 */
1668
1669 int
1670 init_text_parameters(connection_t *conn, ccb_t *ccb)
1671 {
1672 negotiation_state_t *state;
1673
1674 state = malloc(sizeof(*state), M_TEMP, M_WAITOK | M_ZERO);
1675 if (state == NULL) {
1676 DEBOUT(("*** Out of memory in init_text_params\n"));
1677 return ISCSI_STATUS_NO_RESOURCES;
1678 }
1679 ccb->ccb_temp_data = state;
1680
1681 state->HeaderDigest = conn->c_HeaderDigest;
1682 state->DataDigest = conn->c_DataDigest;
1683 state->MaxRecvDataSegmentLength = conn->c_MaxRecvDataSegmentLength;
1684 init_session_parameters(conn->c_session, state);
1685
1686 return 0;
1687 }
1688
1689
1690 /*
1691 * assemble_send_targets:
1692 * Assemble send targets request
1693 *
1694 * Parameter:
1695 * pdu The transmit PDU
1696 * val The SendTargets key value
1697 *
1698 * Returns: 0 On success
1699 * > 0 (an ISCSI error code) if an error occurred.
1700 */
1701
1702 int
1703 assemble_send_targets(pdu_t *pdu, uint8_t *val)
1704 {
1705 negotiation_parameter_t par;
1706 uint8_t *buf;
1707 int len;
1708
1709 par.key = K_SendTargets;
1710 par.list_num = 1;
1711 par.val.sval = val;
1712
1713 len = parameter_size(&par);
1714
1715 if ((buf = malloc(len, M_TEMP, M_WAITOK)) == NULL) {
1716 DEBOUT(("*** Out of memory in assemble_send_targets\n"));
1717 return ISCSI_STATUS_NO_RESOURCES;
1718 }
1719 pdu->pdu_temp_data = buf;
1720 pdu->pdu_temp_data_len = len;
1721
1722 if (put_parameter(buf, len, &par) == 0)
1723 return ISCSI_STATUS_PARAMETER_INVALID;
1724
1725 return 0;
1726 }
1727
1728
1729 /*
1730 * set_negotiated_parameters:
1731 * Copy the negotiated parameters into the connection and session structure.
1732 *
1733 * Parameter:
1734 * ccb The ccb containing the state information
1735 */
1736
1737 void
1738 set_negotiated_parameters(ccb_t *ccb)
1739 {
1740 negotiation_state_t *state = (negotiation_state_t *) ccb->ccb_temp_data;
1741 connection_t *conn = ccb->ccb_connection;
1742 session_t *sess = ccb->ccb_session;
1743
1744 conn->c_HeaderDigest = state->HeaderDigest;
1745 conn->c_DataDigest = state->DataDigest;
1746 sess->s_ErrorRecoveryLevel = state->ErrorRecoveryLevel;
1747 sess->s_InitialR2T = state->InitialR2T;
1748 sess->s_ImmediateData = state->ImmediateData;
1749 conn->c_MaxRecvDataSegmentLength = state->MaxRecvDataSegmentLength;
1750 sess->s_MaxConnections = state->MaxConnections;
1751 sess->s_DefaultTime2Wait = conn->c_Time2Wait = state->DefaultTime2Wait;
1752 sess->s_DefaultTime2Retain = conn->c_Time2Retain =
1753 state->DefaultTime2Retain;
1754
1755 /* set idle connection timeout to half the Time2Retain window so we */
1756 /* don't miss it, unless Time2Retain is ridiculously small. */
1757 conn->c_idle_timeout_val = (conn->c_Time2Retain >= 10) ?
1758 (conn->c_Time2Retain / 2) * hz : CONNECTION_IDLE_TIMEOUT;
1759
1760 sess->s_MaxBurstLength = state->MaxBurstLength;
1761 sess->s_FirstBurstLength = state->FirstBurstLength;
1762 sess->s_MaxOutstandingR2T = state->MaxOutstandingR2T;
1763
1764 DEBC(conn, 10,("SetNegPar: MRDSL=%d, MBL=%d, FBL=%d, IR2T=%d, ImD=%d\n",
1765 state->MaxRecvDataSegmentLength, state->MaxBurstLength,
1766 state->FirstBurstLength, state->InitialR2T,
1767 state->ImmediateData));
1768
1769 conn->c_max_transfer = min(sess->s_MaxBurstLength, conn->c_MaxRecvDataSegmentLength);
1770
1771 conn->c_max_firstimmed = (!sess->s_ImmediateData) ? 0 :
1772 min(sess->s_FirstBurstLength, conn->c_max_transfer);
1773
1774 conn->c_max_firstdata = (sess->s_InitialR2T || sess->s_FirstBurstLength < conn->c_max_firstimmed) ? 0 :
1775 min(sess->s_FirstBurstLength - conn->c_max_firstimmed, conn->c_max_transfer);
1776
1777 }
1778