1 /* $NetBSD: spnego_asn1.c,v 1.7 2015/07/08 17:28:59 christos Exp $ */
2
3 /*
4 * Copyright (C) 2006, 2007, 2012, 2013, 2015 Internet Systems Consortium, Inc. ("ISC")
5 *
6 * Permission to use, copy, modify, and/or distribute this software for any
7 * purpose with or without fee is hereby granted, provided that the above
8 * copyright notice and this permission notice appear in all copies.
9 *
10 * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
11 * REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
12 * AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
13 * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
14 * LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
15 * OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
16 * PERFORMANCE OF THIS SOFTWARE.
17 */
18
19 /* Id: spnego_asn1.c,v 1.4 2007/06/19 23:47:16 tbox Exp */
20
21 /*! \file
22 * \brief Method routines generated from SPNEGO ASN.1 module.
23 * See spnego_asn1.pl for details. Do not edit.
24 */
25
26 /* Generated from spnego.asn1 */
27 /* Do not edit */
28
29 #ifndef __asn1_h__
30 #define __asn1_h__
31
32
33 #ifndef __asn1_common_definitions__
34 #define __asn1_common_definitions__
35
36 typedef struct octet_string {
37 size_t length;
38 void *data;
39 } octet_string;
40
41 typedef char *general_string;
42
43 typedef char *utf8_string;
44
45 typedef struct oid {
46 size_t length;
47 unsigned *components;
48 } oid;
49
50 #define ASN1_MALLOC_ENCODE(T, B, BL, S, L, R) \
51 do { \
52 (BL) = length_##T((S)); \
53 (B) = malloc((BL)); \
54 if((B) == NULL) { \
55 (R) = ENOMEM; \
56 } else { \
57 (R) = encode_##T(((unsigned char*)(B)) + (BL) - 1, (BL), \
58 (S), (L)); \
59 if((R) != 0) { \
60 free((B)); \
61 (B) = NULL; \
62 } \
63 } \
64 } while (/*CONSTCOND*/0)
65
66 #endif
67
68 /*
69 * MechType ::= OBJECT IDENTIFIER
70 */
71
72 typedef oid MechType;
73
74 static int encode_MechType(unsigned char *, size_t, const MechType *, size_t *);
75 static int decode_MechType(const unsigned char *, size_t, MechType *, size_t *);
76 static void free_MechType(MechType *);
77 /* unused declaration: length_MechType */
78 /* unused declaration: copy_MechType */
79
80
81 /*
82 * MechTypeList ::= SEQUENCE OF MechType
83 */
84
85 typedef struct MechTypeList {
86 unsigned int len;
87 MechType *val;
88 } MechTypeList;
89
90 static int encode_MechTypeList(unsigned char *, size_t, const MechTypeList *, size_t *);
91 static int decode_MechTypeList(const unsigned char *, size_t, MechTypeList *, size_t *);
92 static void free_MechTypeList(MechTypeList *);
93 /* unused declaration: length_MechTypeList */
94 /* unused declaration: copy_MechTypeList */
95
96
97 /*
98 * ContextFlags ::= BIT STRING { delegFlag(0), mutualFlag(1), replayFlag(2),
99 * sequenceFlag(3), anonFlag(4), confFlag(5), integFlag(6) }
100 */
101
102 typedef struct ContextFlags {
103 unsigned int delegFlag:1;
104 unsigned int mutualFlag:1;
105 unsigned int replayFlag:1;
106 unsigned int sequenceFlag:1;
107 unsigned int anonFlag:1;
108 unsigned int confFlag:1;
109 unsigned int integFlag:1;
110 } ContextFlags;
111
112
113 static int encode_ContextFlags(unsigned char *, size_t, const ContextFlags *, size_t *);
114 static int decode_ContextFlags(const unsigned char *, size_t, ContextFlags *, size_t *);
115 static void free_ContextFlags(ContextFlags *);
116 /* unused declaration: length_ContextFlags */
117 /* unused declaration: copy_ContextFlags */
118 /* unused declaration: ContextFlags2int */
119 /* unused declaration: int2ContextFlags */
120 /* unused declaration: asn1_ContextFlags_units */
121
122 /*
123 * NegTokenInit ::= SEQUENCE { mechTypes[0] MechTypeList, reqFlags[1]
124 * ContextFlags OPTIONAL, mechToken[2] OCTET STRING OPTIONAL,
125 * mechListMIC[3] OCTET STRING OPTIONAL }
126 */
127
128 typedef struct NegTokenInit {
129 MechTypeList mechTypes;
130 ContextFlags *reqFlags;
131 octet_string *mechToken;
132 octet_string *mechListMIC;
133 } NegTokenInit;
134
135 static int encode_NegTokenInit(unsigned char *, size_t, const NegTokenInit *, size_t *);
136 static int decode_NegTokenInit(const unsigned char *, size_t, NegTokenInit *, size_t *);
137 static void free_NegTokenInit(NegTokenInit *);
138 /* unused declaration: length_NegTokenInit */
139 /* unused declaration: copy_NegTokenInit */
140
141
142 /*
143 * NegTokenResp ::= SEQUENCE { negState[0] ENUMERATED {
144 * accept-completed(0), accept-incomplete(1), reject(2), request-mic(3) }
145 * OPTIONAL, supportedMech[1] MechType OPTIONAL, responseToken[2] OCTET
146 * STRING OPTIONAL, mechListMIC[3] OCTET STRING OPTIONAL }
147 */
148
149 typedef struct NegTokenResp {
150 enum {
151 accept_completed = 0,
152 accept_incomplete = 1,
153 reject = 2,
154 request_mic = 3
155 } *negState;
156
157 MechType *supportedMech;
158 octet_string *responseToken;
159 octet_string *mechListMIC;
160 } NegTokenResp;
161
162 static int encode_NegTokenResp(unsigned char *, size_t, const NegTokenResp *, size_t *);
163 static int decode_NegTokenResp(const unsigned char *, size_t, NegTokenResp *, size_t *);
164 static void free_NegTokenResp(NegTokenResp *);
165 /* unused declaration: length_NegTokenResp */
166 /* unused declaration: copy_NegTokenResp */
167
168
169
170
171 #endif /* __asn1_h__ */
172 /* Generated from spnego.asn1 */
173 /* Do not edit */
174
175
176 #define BACK if (e) return e; p -= l; len -= l; ret += l; POST(p); POST(len); POST(ret)
177
178 static int
encode_MechType(unsigned char * p,size_t len,const MechType * data,size_t * size)179 encode_MechType(unsigned char *p, size_t len, const MechType * data, size_t * size)
180 {
181 size_t ret = 0;
182 size_t l;
183 int e;
184
185 e = encode_oid(p, len, data, &l);
186 BACK;
187 *size = ret;
188 return 0;
189 }
190
191 #define FORW if(e) goto fail; p += l; len -= l; ret += l; POST(p); POST(len); POST(ret)
192
193 static int
decode_MechType(const unsigned char * p,size_t len,MechType * data,size_t * size)194 decode_MechType(const unsigned char *p, size_t len, MechType * data, size_t * size)
195 {
196 size_t ret = 0;
197 size_t l;
198 int e;
199
200 memset(data, 0, sizeof(*data));
201 e = decode_oid(p, len, data, &l);
202 FORW;
203 if (size)
204 *size = ret;
205 return 0;
206 fail:
207 free_MechType(data);
208 return e;
209 }
210
211 static void
free_MechType(MechType * data)212 free_MechType(MechType * data)
213 {
214 free_oid(data);
215 }
216
217 /* unused function: length_MechType */
218
219
220 /* unused function: copy_MechType */
221
222 /* Generated from spnego.asn1 */
223 /* Do not edit */
224
225
226 static int
encode_MechTypeList(unsigned char * p,size_t len,const MechTypeList * data,size_t * size)227 encode_MechTypeList(unsigned char *p, size_t len, const MechTypeList * data, size_t * size)
228 {
229 size_t ret = 0;
230 size_t l;
231 int i, e;
232
233 for (i = (data)->len - 1; i >= 0; --i) {
234 size_t oldret = ret;
235 ret = 0;
236 e = encode_MechType(p, len, &(data)->val[i], &l);
237 BACK;
238 ret += oldret;
239 }
240 e = der_put_length_and_tag(p, len, ret, ASN1_C_UNIV, CONS, UT_Sequence, &l);
241 BACK;
242 *size = ret;
243 return 0;
244 }
245
246 static int
decode_MechTypeList(const unsigned char * p,size_t len,MechTypeList * data,size_t * size)247 decode_MechTypeList(const unsigned char *p, size_t len, MechTypeList * data, size_t * size)
248 {
249 size_t ret = 0, reallen;
250 size_t l;
251 int e;
252
253 memset(data, 0, sizeof(*data));
254 reallen = 0;
255 e = der_match_tag_and_length(p, len, ASN1_C_UNIV, CONS, UT_Sequence, &reallen, &l);
256 FORW;
257 if (len < reallen)
258 return ASN1_OVERRUN;
259 len = reallen;
260 {
261 size_t origlen = len;
262 size_t oldret = ret;
263 ret = 0;
264 (data)->len = 0;
265 (data)->val = NULL;
266 while (ret < origlen) {
267 void *old = (data)->val;
268 (data)->len++;
269 (data)->val = realloc((data)->val, sizeof(*((data)->val)) * (data)->len);
270 if ((data)->val == NULL) {
271 (data)->val = old;
272 (data)->len--;
273 return ENOMEM;
274 }
275 e = decode_MechType(p, len, &(data)->val[(data)->len - 1], &l);
276 FORW;
277 len = origlen - ret;
278 }
279 ret += oldret;
280 }
281 if (size)
282 *size = ret;
283 return 0;
284 fail:
285 free_MechTypeList(data);
286 return e;
287 }
288
289 static void
free_MechTypeList(MechTypeList * data)290 free_MechTypeList(MechTypeList * data)
291 {
292 while ((data)->len) {
293 free_MechType(&(data)->val[(data)->len - 1]);
294 (data)->len--;
295 }
296 free((data)->val);
297 (data)->val = NULL;
298 }
299
300 /* unused function: length_MechTypeList */
301
302
303 /* unused function: copy_MechTypeList */
304
305 /* Generated from spnego.asn1 */
306 /* Do not edit */
307
308
309 static int
encode_ContextFlags(unsigned char * p,size_t len,const ContextFlags * data,size_t * size)310 encode_ContextFlags(unsigned char *p, size_t len, const ContextFlags * data, size_t * size)
311 {
312 size_t ret = 0;
313 size_t l;
314 int e;
315
316 {
317 unsigned char c = 0;
318 *p-- = c;
319 len--;
320 ret++;
321 c = 0;
322 *p-- = c;
323 len--;
324 ret++;
325 c = 0;
326 *p-- = c;
327 len--;
328 ret++;
329 c = 0;
330 if (data->integFlag)
331 c |= 1 << 1;
332 if (data->confFlag)
333 c |= 1 << 2;
334 if (data->anonFlag)
335 c |= 1 << 3;
336 if (data->sequenceFlag)
337 c |= 1 << 4;
338 if (data->replayFlag)
339 c |= 1 << 5;
340 if (data->mutualFlag)
341 c |= 1 << 6;
342 if (data->delegFlag)
343 c |= 1 << 7;
344 *p-- = c;
345 *p-- = 0;
346 len -= 2;
347 ret += 2;
348 }
349
350 e = der_put_length_and_tag(p, len, ret, ASN1_C_UNIV, PRIM, UT_BitString, &l);
351 BACK;
352 *size = ret;
353 return 0;
354 }
355
356 static int
decode_ContextFlags(const unsigned char * p,size_t len,ContextFlags * data,size_t * size)357 decode_ContextFlags(const unsigned char *p, size_t len, ContextFlags * data, size_t * size)
358 {
359 size_t ret = 0, reallen;
360 size_t l;
361 int e;
362
363 memset(data, 0, sizeof(*data));
364 reallen = 0;
365 e = der_match_tag_and_length(p, len, ASN1_C_UNIV, PRIM, UT_BitString, &reallen, &l);
366 FORW;
367 if (len < reallen)
368 return ASN1_OVERRUN;
369 p++;
370 len--;
371 reallen--;
372 ret++;
373 data->delegFlag = (*p >> 7) & 1;
374 data->mutualFlag = (*p >> 6) & 1;
375 data->replayFlag = (*p >> 5) & 1;
376 data->sequenceFlag = (*p >> 4) & 1;
377 data->anonFlag = (*p >> 3) & 1;
378 data->confFlag = (*p >> 2) & 1;
379 data->integFlag = (*p >> 1) & 1;
380 ret += reallen;
381 if (size)
382 *size = ret;
383 return 0;
384 fail:
385 free_ContextFlags(data);
386 return e;
387 }
388
389 static void
free_ContextFlags(ContextFlags * data)390 free_ContextFlags(ContextFlags * data)
391 {
392 (void)data;
393 }
394
395 /* unused function: length_ContextFlags */
396
397
398 /* unused function: copy_ContextFlags */
399
400
401 /* unused function: ContextFlags2int */
402
403
404 /* unused function: int2ContextFlags */
405
406
407 /* unused variable: ContextFlags_units */
408
409 /* unused function: asn1_ContextFlags_units */
410
411 /* Generated from spnego.asn1 */
412 /* Do not edit */
413
414
415 static int
encode_NegTokenInit(unsigned char * p,size_t len,const NegTokenInit * data,size_t * size)416 encode_NegTokenInit(unsigned char *p, size_t len, const NegTokenInit * data, size_t * size)
417 {
418 size_t ret = 0;
419 size_t l;
420 int e;
421
422 if ((data)->mechListMIC) {
423 size_t oldret = ret;
424 ret = 0;
425 e = encode_octet_string(p, len, (data)->mechListMIC, &l);
426 BACK;
427 e = der_put_length_and_tag(p, len, ret, ASN1_C_CONTEXT, CONS, 3, &l);
428 BACK;
429 ret += oldret;
430 }
431 if ((data)->mechToken) {
432 size_t oldret = ret;
433 ret = 0;
434 e = encode_octet_string(p, len, (data)->mechToken, &l);
435 BACK;
436 e = der_put_length_and_tag(p, len, ret, ASN1_C_CONTEXT, CONS, 2, &l);
437 BACK;
438 ret += oldret;
439 }
440 if ((data)->reqFlags) {
441 size_t oldret = ret;
442 ret = 0;
443 e = encode_ContextFlags(p, len, (data)->reqFlags, &l);
444 BACK;
445 e = der_put_length_and_tag(p, len, ret, ASN1_C_CONTEXT, CONS, 1, &l);
446 BACK;
447 ret += oldret;
448 } {
449 size_t oldret = ret;
450 ret = 0;
451 e = encode_MechTypeList(p, len, &(data)->mechTypes, &l);
452 BACK;
453 e = der_put_length_and_tag(p, len, ret, ASN1_C_CONTEXT, CONS, 0, &l);
454 BACK;
455 ret += oldret;
456 }
457 e = der_put_length_and_tag(p, len, ret, ASN1_C_UNIV, CONS, UT_Sequence, &l);
458 BACK;
459 *size = ret;
460 return 0;
461 }
462
463 static int
decode_NegTokenInit(const unsigned char * p,size_t len,NegTokenInit * data,size_t * size)464 decode_NegTokenInit(const unsigned char *p, size_t len, NegTokenInit * data, size_t * size)
465 {
466 size_t ret = 0, reallen;
467 size_t l;
468 int e;
469
470 memset(data, 0, sizeof(*data));
471 reallen = 0;
472 e = der_match_tag_and_length(p, len, ASN1_C_UNIV, CONS, UT_Sequence, &reallen, &l);
473 FORW;
474 {
475 int dce_fix;
476 if ((dce_fix = fix_dce(reallen, &len)) < 0)
477 return ASN1_BAD_FORMAT;
478 {
479 size_t newlen, oldlen;
480
481 e = der_match_tag(p, len, ASN1_C_CONTEXT, CONS, 0, &l);
482 if (e)
483 return e;
484 else {
485 p += l;
486 len -= l;
487 ret += l;
488 e = der_get_length(p, len, &newlen, &l);
489 FORW;
490 {
491 int mydce_fix;
492 oldlen = len;
493 if ((mydce_fix = fix_dce(newlen, &len)) < 0)
494 return ASN1_BAD_FORMAT;
495 e = decode_MechTypeList(p, len, &(data)->mechTypes, &l);
496 FORW;
497 if (mydce_fix) {
498 e = der_match_tag_and_length(p, len, (Der_class) 0, (Der_type) 0, 0, &reallen, &l);
499 FORW;
500 } else
501 len = oldlen - newlen;
502 }
503 }
504 }
505 {
506 size_t newlen, oldlen;
507
508 e = der_match_tag(p, len, ASN1_C_CONTEXT, CONS, 1, &l);
509 if (e)
510 (data)->reqFlags = NULL;
511 else {
512 p += l;
513 len -= l;
514 ret += l;
515 e = der_get_length(p, len, &newlen, &l);
516 FORW;
517 {
518 int mydce_fix;
519 oldlen = len;
520 if ((mydce_fix = fix_dce(newlen, &len)) < 0)
521 return ASN1_BAD_FORMAT;
522 (data)->reqFlags = malloc(sizeof(*(data)->reqFlags));
523 if ((data)->reqFlags == NULL)
524 return ENOMEM;
525 e = decode_ContextFlags(p, len, (data)->reqFlags, &l);
526 FORW;
527 if (mydce_fix) {
528 e = der_match_tag_and_length(p, len, (Der_class) 0, (Der_type) 0, 0, &reallen, &l);
529 FORW;
530 } else
531 len = oldlen - newlen;
532 }
533 }
534 }
535 {
536 size_t newlen, oldlen;
537
538 e = der_match_tag(p, len, ASN1_C_CONTEXT, CONS, 2, &l);
539 if (e)
540 (data)->mechToken = NULL;
541 else {
542 p += l;
543 len -= l;
544 ret += l;
545 e = der_get_length(p, len, &newlen, &l);
546 FORW;
547 {
548 int mydce_fix;
549 oldlen = len;
550 if ((mydce_fix = fix_dce(newlen, &len)) < 0)
551 return ASN1_BAD_FORMAT;
552 (data)->mechToken = malloc(sizeof(*(data)->mechToken));
553 if ((data)->mechToken == NULL)
554 return ENOMEM;
555 e = decode_octet_string(p, len, (data)->mechToken, &l);
556 FORW;
557 if (mydce_fix) {
558 e = der_match_tag_and_length(p, len, (Der_class) 0, (Der_type) 0, 0, &reallen, &l);
559 FORW;
560 } else
561 len = oldlen - newlen;
562 }
563 }
564 }
565 {
566 size_t newlen, oldlen;
567
568 e = der_match_tag(p, len, ASN1_C_CONTEXT, CONS, 3, &l);
569 if (e)
570 (data)->mechListMIC = NULL;
571 else {
572 p += l;
573 len -= l;
574 ret += l;
575 e = der_get_length(p, len, &newlen, &l);
576 FORW;
577 {
578 int mydce_fix;
579 oldlen = len;
580 if ((mydce_fix = fix_dce(newlen, &len)) < 0)
581 return ASN1_BAD_FORMAT;
582 (data)->mechListMIC = malloc(sizeof(*(data)->mechListMIC));
583 if ((data)->mechListMIC == NULL)
584 return ENOMEM;
585 e = decode_octet_string(p, len, (data)->mechListMIC, &l);
586 FORW;
587 if (mydce_fix) {
588 e = der_match_tag_and_length(p, len, (Der_class) 0, (Der_type) 0, 0, &reallen, &l);
589 FORW;
590 } else
591 len = oldlen - newlen;
592 }
593 }
594 }
595 if (dce_fix) {
596 e = der_match_tag_and_length(p, len, (Der_class) 0, (Der_type) 0, 0, &reallen, &l);
597 FORW;
598 }
599 }
600 if (size)
601 *size = ret;
602 return 0;
603 fail:
604 free_NegTokenInit(data);
605 return e;
606 }
607
608 static void
free_NegTokenInit(NegTokenInit * data)609 free_NegTokenInit(NegTokenInit * data)
610 {
611 free_MechTypeList(&(data)->mechTypes);
612 if ((data)->reqFlags) {
613 free_ContextFlags((data)->reqFlags);
614 free((data)->reqFlags);
615 (data)->reqFlags = NULL;
616 }
617 if ((data)->mechToken) {
618 free_octet_string((data)->mechToken);
619 free((data)->mechToken);
620 (data)->mechToken = NULL;
621 }
622 if ((data)->mechListMIC) {
623 free_octet_string((data)->mechListMIC);
624 free((data)->mechListMIC);
625 (data)->mechListMIC = NULL;
626 }
627 }
628
629 /* unused function: length_NegTokenInit */
630
631
632 /* unused function: copy_NegTokenInit */
633
634 /* Generated from spnego.asn1 */
635 /* Do not edit */
636
637
638 static int
encode_NegTokenResp(unsigned char * p,size_t len,const NegTokenResp * data,size_t * size)639 encode_NegTokenResp(unsigned char *p, size_t len, const NegTokenResp * data, size_t * size)
640 {
641 size_t ret = 0;
642 size_t l;
643 int e;
644
645 if ((data)->mechListMIC) {
646 size_t oldret = ret;
647 ret = 0;
648 e = encode_octet_string(p, len, (data)->mechListMIC, &l);
649 BACK;
650 e = der_put_length_and_tag(p, len, ret, ASN1_C_CONTEXT, CONS, 3, &l);
651 BACK;
652 ret += oldret;
653 }
654 if ((data)->responseToken) {
655 size_t oldret = ret;
656 ret = 0;
657 e = encode_octet_string(p, len, (data)->responseToken, &l);
658 BACK;
659 e = der_put_length_and_tag(p, len, ret, ASN1_C_CONTEXT, CONS, 2, &l);
660 BACK;
661 ret += oldret;
662 }
663 if ((data)->supportedMech) {
664 size_t oldret = ret;
665 ret = 0;
666 e = encode_MechType(p, len, (data)->supportedMech, &l);
667 BACK;
668 e = der_put_length_and_tag(p, len, ret, ASN1_C_CONTEXT, CONS, 1, &l);
669 BACK;
670 ret += oldret;
671 }
672 if ((data)->negState) {
673 size_t oldret = ret;
674 ret = 0;
675 e = encode_enumerated(p, len, (data)->negState, &l);
676 BACK;
677 e = der_put_length_and_tag(p, len, ret, ASN1_C_CONTEXT, CONS, 0, &l);
678 BACK;
679 ret += oldret;
680 }
681 e = der_put_length_and_tag(p, len, ret, ASN1_C_UNIV, CONS, UT_Sequence, &l);
682 BACK;
683 *size = ret;
684 return 0;
685 }
686
687 static int
decode_NegTokenResp(const unsigned char * p,size_t len,NegTokenResp * data,size_t * size)688 decode_NegTokenResp(const unsigned char *p, size_t len, NegTokenResp * data, size_t * size)
689 {
690 size_t ret = 0, reallen;
691 size_t l;
692 int e;
693
694 memset(data, 0, sizeof(*data));
695 reallen = 0;
696 e = der_match_tag_and_length(p, len, ASN1_C_UNIV, CONS, UT_Sequence, &reallen, &l);
697 FORW;
698 {
699 int dce_fix;
700 if ((dce_fix = fix_dce(reallen, &len)) < 0)
701 return ASN1_BAD_FORMAT;
702 {
703 size_t newlen, oldlen;
704
705 e = der_match_tag(p, len, ASN1_C_CONTEXT, CONS, 0, &l);
706 if (e)
707 (data)->negState = NULL;
708 else {
709 p += l;
710 len -= l;
711 ret += l;
712 e = der_get_length(p, len, &newlen, &l);
713 FORW;
714 {
715 int mydce_fix;
716 oldlen = len;
717 if ((mydce_fix = fix_dce(newlen, &len)) < 0)
718 return ASN1_BAD_FORMAT;
719 (data)->negState = malloc(sizeof(*(data)->negState));
720 if ((data)->negState == NULL)
721 return ENOMEM;
722 e = decode_enumerated(p, len, (data)->negState, &l);
723 FORW;
724 if (mydce_fix) {
725 e = der_match_tag_and_length(p, len, (Der_class) 0, (Der_type) 0, 0, &reallen, &l);
726 FORW;
727 } else
728 len = oldlen - newlen;
729 }
730 }
731 }
732 {
733 size_t newlen, oldlen;
734
735 e = der_match_tag(p, len, ASN1_C_CONTEXT, CONS, 1, &l);
736 if (e)
737 (data)->supportedMech = NULL;
738 else {
739 p += l;
740 len -= l;
741 ret += l;
742 e = der_get_length(p, len, &newlen, &l);
743 FORW;
744 {
745 int mydce_fix;
746 oldlen = len;
747 if ((mydce_fix = fix_dce(newlen, &len)) < 0)
748 return ASN1_BAD_FORMAT;
749 (data)->supportedMech = malloc(sizeof(*(data)->supportedMech));
750 if ((data)->supportedMech == NULL)
751 return ENOMEM;
752 e = decode_MechType(p, len, (data)->supportedMech, &l);
753 FORW;
754 if (mydce_fix) {
755 e = der_match_tag_and_length(p, len, (Der_class) 0, (Der_type) 0, 0, &reallen, &l);
756 FORW;
757 } else
758 len = oldlen - newlen;
759 }
760 }
761 }
762 {
763 size_t newlen, oldlen;
764
765 e = der_match_tag(p, len, ASN1_C_CONTEXT, CONS, 2, &l);
766 if (e)
767 (data)->responseToken = NULL;
768 else {
769 p += l;
770 len -= l;
771 ret += l;
772 e = der_get_length(p, len, &newlen, &l);
773 FORW;
774 {
775 int mydce_fix;
776 oldlen = len;
777 if ((mydce_fix = fix_dce(newlen, &len)) < 0)
778 return ASN1_BAD_FORMAT;
779 (data)->responseToken = malloc(sizeof(*(data)->responseToken));
780 if ((data)->responseToken == NULL)
781 return ENOMEM;
782 e = decode_octet_string(p, len, (data)->responseToken, &l);
783 FORW;
784 if (mydce_fix) {
785 e = der_match_tag_and_length(p, len, (Der_class) 0, (Der_type) 0, 0, &reallen, &l);
786 FORW;
787 } else
788 len = oldlen - newlen;
789 }
790 }
791 }
792 {
793 size_t newlen, oldlen;
794
795 e = der_match_tag(p, len, ASN1_C_CONTEXT, CONS, 3, &l);
796 if (e)
797 (data)->mechListMIC = NULL;
798 else {
799 p += l;
800 len -= l;
801 ret += l;
802 e = der_get_length(p, len, &newlen, &l);
803 FORW;
804 {
805 int mydce_fix;
806 oldlen = len;
807 if ((mydce_fix = fix_dce(newlen, &len)) < 0)
808 return ASN1_BAD_FORMAT;
809 (data)->mechListMIC = malloc(sizeof(*(data)->mechListMIC));
810 if ((data)->mechListMIC == NULL)
811 return ENOMEM;
812 e = decode_octet_string(p, len, (data)->mechListMIC, &l);
813 FORW;
814 if (mydce_fix) {
815 e = der_match_tag_and_length(p, len, (Der_class) 0, (Der_type) 0, 0, &reallen, &l);
816 FORW;
817 } else
818 len = oldlen - newlen;
819 }
820 }
821 }
822 if (dce_fix) {
823 e = der_match_tag_and_length(p, len, (Der_class) 0, (Der_type) 0, 0, &reallen, &l);
824 FORW;
825 }
826 }
827 if (size)
828 *size = ret;
829 return 0;
830 fail:
831 free_NegTokenResp(data);
832 return e;
833 }
834
835 static void
free_NegTokenResp(NegTokenResp * data)836 free_NegTokenResp(NegTokenResp * data)
837 {
838 if ((data)->negState) {
839 free((data)->negState);
840 (data)->negState = NULL;
841 }
842 if ((data)->supportedMech) {
843 free_MechType((data)->supportedMech);
844 free((data)->supportedMech);
845 (data)->supportedMech = NULL;
846 }
847 if ((data)->responseToken) {
848 free_octet_string((data)->responseToken);
849 free((data)->responseToken);
850 (data)->responseToken = NULL;
851 }
852 if ((data)->mechListMIC) {
853 free_octet_string((data)->mechListMIC);
854 free((data)->mechListMIC);
855 (data)->mechListMIC = NULL;
856 }
857 }
858
859 /* unused function: length_NegTokenResp */
860
861
862 /* unused function: copy_NegTokenResp */
863
864 /* Generated from spnego.asn1 */
865 /* Do not edit */
866
867
868 /* CHOICE */
869 /* unused variable: asn1_NegotiationToken_dummy_holder */
870