Imported Upstream version 1.10.2
[platform/upstream/krb5.git] / src / lib / krb5 / krb / kfree.c
1 /* -*- mode: c; c-basic-offset: 4; indent-tabs-mode: nil -*- */
2 /* lib/krb5/krb/kfree.c */
3 /*
4  * Copyright 1990-1998, 2009 by the Massachusetts Institute of Technology.
5  *
6  * Export of this software from the United States of America may
7  *   require a specific license from the United States Government.
8  *   It is the responsibility of any person or organization contemplating
9  *   export to obtain such a license before exporting.
10  *
11  * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and
12  * distribute this software and its documentation for any purpose and
13  * without fee is hereby granted, provided that the above copyright
14  * notice appear in all copies and that both that copyright notice and
15  * this permission notice appear in supporting documentation, and that
16  * the name of M.I.T. not be used in advertising or publicity pertaining
17  * to distribution of the software without specific, written prior
18  * permission.  Furthermore if you modify this software you must label
19  * your software as modified software and not distribute it in such a
20  * fashion that it might be confused with the original M.I.T. software.
21  * M.I.T. makes no representations about the suitability of
22  * this software for any purpose.  It is provided "as is" without express
23  * or implied warranty.
24  */
25 /*
26  * Copyright (c) 2006-2008, Novell, Inc.
27  * All rights reserved.
28  *
29  * Redistribution and use in source and binary forms, with or without
30  * modification, are permitted provided that the following conditions are met:
31  *
32  *   * Redistributions of source code must retain the above copyright notice,
33  *       this list of conditions and the following disclaimer.
34  *   * Redistributions in binary form must reproduce the above copyright
35  *       notice, this list of conditions and the following disclaimer in the
36  *       documentation and/or other materials provided with the distribution.
37  *   * The copyright holder's name is not used to endorse or promote products
38  *       derived from this software without specific prior written permission.
39  *
40  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
41  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
42  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
43  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
44  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
45  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
46  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
47  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
48  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
49  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
50  * POSSIBILITY OF SUCH DAMAGE.
51  */
52
53 #include "k5-int.h"
54 #include <assert.h>
55
56 void KRB5_CALLCONV
57 krb5_free_address(krb5_context context, krb5_address *val)
58 {
59     if (val == NULL)
60         return;
61     free(val->contents);
62     free(val);
63 }
64
65 void KRB5_CALLCONV
66 krb5_free_addresses(krb5_context context, krb5_address **val)
67 {
68     register krb5_address **temp;
69
70     if (val == NULL)
71         return;
72     for (temp = val; *temp; temp++) {
73         free((*temp)->contents);
74         free(*temp);
75     }
76     free(val);
77 }
78
79
80 void KRB5_CALLCONV
81 krb5_free_alt_method(krb5_context context,
82                      krb5_alt_method *alt)
83 {
84     if (alt) {
85         free(alt->data);
86         free(alt);
87     }
88 }
89 void KRB5_CALLCONV
90 krb5_free_ap_rep(krb5_context context, register krb5_ap_rep *val)
91 {
92     if (val == NULL)
93         return;
94     free(val->enc_part.ciphertext.data);
95     free(val);
96 }
97
98 void KRB5_CALLCONV
99 krb5_free_ap_req(krb5_context context, register krb5_ap_req *val)
100 {
101     if (val == NULL)
102         return;
103     krb5_free_ticket(context, val->ticket);
104     free(val->authenticator.ciphertext.data);
105     free(val);
106 }
107
108 void KRB5_CALLCONV
109 krb5_free_ap_rep_enc_part(krb5_context context, krb5_ap_rep_enc_part *val)
110 {
111     if (val == NULL)
112         return;
113     krb5_free_keyblock(context, val->subkey);
114     free(val);
115 }
116
117 void KRB5_CALLCONV
118 krb5_free_authenticator_contents(krb5_context context, krb5_authenticator *val)
119 {
120     if (val == NULL)
121         return;
122     krb5_free_checksum(context, val->checksum);
123     val->checksum = 0;
124     krb5_free_principal(context, val->client);
125     val->client = 0;
126     krb5_free_keyblock(context, val->subkey);
127     val->subkey = 0;
128     krb5_free_authdata(context, val->authorization_data);
129     val->authorization_data = 0;
130 }
131
132 void KRB5_CALLCONV
133 krb5_free_authenticator(krb5_context context, krb5_authenticator *val)
134 {
135     if (val == NULL)
136         return;
137     krb5_free_authenticator_contents(context, val);
138     free(val);
139 }
140
141 void KRB5_CALLCONV
142 krb5_free_checksum(krb5_context context, register krb5_checksum *val)
143 {
144     if (val == NULL)
145         return;
146     krb5_free_checksum_contents(context, val);
147     free(val);
148 }
149
150 void KRB5_CALLCONV
151 krb5_free_checksum_contents(krb5_context context, register krb5_checksum *val)
152 {
153     if (val == NULL)
154         return;
155     free(val->contents);
156     val->contents = NULL;
157 }
158
159 void KRB5_CALLCONV
160 krb5_free_cred(krb5_context context, register krb5_cred *val)
161 {
162     if (val == NULL)
163         return;
164     krb5_free_tickets(context, val->tickets);
165     free(val->enc_part.ciphertext.data);
166     free(val);
167 }
168
169 /*
170  * krb5_free_cred_contents zeros out the session key, and then frees
171  * the credentials structures
172  */
173
174 void KRB5_CALLCONV
175 krb5_free_cred_contents(krb5_context context, krb5_creds *val)
176 {
177     if (val == NULL)
178         return;
179     krb5_free_principal(context, val->client);
180     val->client = 0;
181     krb5_free_principal(context, val->server);
182     val->server = 0;
183     krb5_free_keyblock_contents(context, &val->keyblock);
184     free(val->ticket.data);
185     val->ticket.data = 0;
186     free(val->second_ticket.data);
187     val->second_ticket.data = 0;
188     krb5_free_addresses(context, val->addresses);
189     val->addresses = 0;
190     krb5_free_authdata(context, val->authdata);
191     val->authdata = 0;
192 }
193
194 void KRB5_CALLCONV
195 krb5_free_cred_enc_part(krb5_context context, register krb5_cred_enc_part *val)
196 {
197     register krb5_cred_info **temp;
198
199     if (val == NULL)
200         return;
201     krb5_free_address(context, val->r_address);
202     val->r_address = 0;
203     krb5_free_address(context, val->s_address);
204     val->s_address = 0;
205
206     if (val->ticket_info) {
207         for (temp = val->ticket_info; *temp; temp++) {
208             krb5_free_keyblock(context, (*temp)->session);
209             krb5_free_principal(context, (*temp)->client);
210             krb5_free_principal(context, (*temp)->server);
211             krb5_free_addresses(context, (*temp)->caddrs);
212             free(*temp);
213         }
214         free(val->ticket_info);
215         val->ticket_info = 0;
216     }
217 }
218
219
220 void KRB5_CALLCONV
221 krb5_free_creds(krb5_context context, krb5_creds *val)
222 {
223     if (val == NULL)
224         return;
225     krb5_free_cred_contents(context, val);
226     free(val);
227 }
228
229
230 void KRB5_CALLCONV
231 krb5_free_data(krb5_context context, krb5_data *val)
232 {
233     if (val == NULL)
234         return;
235     free(val->data);
236     free(val);
237 }
238
239
240 void KRB5_CALLCONV
241 krb5_free_octet_data(krb5_context context, krb5_octet_data *val)
242 {
243     if (val == NULL)
244         return;
245     free(val->data);
246     free(val);
247 }
248
249 void KRB5_CALLCONV
250 krb5_free_data_contents(krb5_context context, krb5_data *val)
251 {
252     if (val == NULL)
253         return;
254     if (val->data) {
255         free(val->data);
256         val->data = 0;
257     }
258 }
259
260 void KRB5_CALLCONV
261 krb5_free_enc_data(krb5_context context, krb5_enc_data *val)
262 {
263     if (val == NULL)
264         return;
265     krb5_free_data_contents(context, &val->ciphertext);
266     free(val);
267 }
268
269 void krb5_free_etype_info(krb5_context context, krb5_etype_info info)
270 {
271     int i;
272
273     if (info == NULL)
274         return;
275     for (i=0; info[i] != NULL; i++) {
276         free(info[i]->salt);
277         krb5_free_data_contents(context, &info[i]->s2kparams);
278         free(info[i]);
279     }
280     free(info);
281 }
282
283
284 void KRB5_CALLCONV
285 krb5_free_enc_kdc_rep_part(krb5_context context, register krb5_enc_kdc_rep_part *val)
286 {
287     if (val == NULL)
288         return;
289     krb5_free_keyblock(context, val->session);
290     krb5_free_last_req(context, val->last_req);
291     krb5_free_principal(context, val->server);
292     krb5_free_addresses(context, val->caddrs);
293     krb5_free_pa_data(context, val->enc_padata);
294     free(val);
295 }
296
297 void KRB5_CALLCONV
298 krb5_free_enc_tkt_part(krb5_context context, krb5_enc_tkt_part *val)
299 {
300     if (val == NULL)
301         return;
302     krb5_free_keyblock(context, val->session);
303     krb5_free_principal(context, val->client);
304     free(val->transited.tr_contents.data);
305     krb5_free_addresses(context, val->caddrs);
306     krb5_free_authdata(context, val->authorization_data);
307     free(val);
308 }
309
310
311 void KRB5_CALLCONV
312 krb5_free_error(krb5_context context, register krb5_error *val)
313 {
314     if (val == NULL)
315         return;
316     krb5_free_principal(context, val->client);
317     krb5_free_principal(context, val->server);
318     free(val->text.data);
319     free(val->e_data.data);
320     free(val);
321 }
322
323 void KRB5_CALLCONV
324 krb5_free_kdc_rep(krb5_context context, krb5_kdc_rep *val)
325 {
326     if (val == NULL)
327         return;
328     krb5_free_pa_data(context, val->padata);
329     krb5_free_principal(context, val->client);
330     krb5_free_ticket(context, val->ticket);
331     free(val->enc_part.ciphertext.data);
332     krb5_free_enc_kdc_rep_part(context, val->enc_part2);
333     free(val);
334 }
335
336
337 void KRB5_CALLCONV
338 krb5_free_kdc_req(krb5_context context, krb5_kdc_req *val)
339 {
340     if (val == NULL)
341         return;
342     krb5_free_pa_data(context, val->padata);
343     krb5_free_principal(context, val->client);
344     krb5_free_principal(context, val->server);
345     free(val->ktype);
346     krb5_free_addresses(context, val->addresses);
347     free(val->authorization_data.ciphertext.data);
348     krb5_free_authdata(context, val->unenc_authdata);
349     krb5_free_tickets(context, val->second_ticket);
350     free(val);
351 }
352
353 void KRB5_CALLCONV
354 krb5_free_keyblock_contents(krb5_context context, register krb5_keyblock *key)
355 {
356     krb5int_c_free_keyblock_contents (context, key);
357 }
358
359 void KRB5_CALLCONV
360 krb5_free_keyblock(krb5_context context, register krb5_keyblock *val)
361 {
362     krb5int_c_free_keyblock (context, val);
363 }
364
365
366
367 void KRB5_CALLCONV
368 krb5_free_last_req(krb5_context context, krb5_last_req_entry **val)
369 {
370     register krb5_last_req_entry **temp;
371
372     if (val == NULL)
373         return;
374     for (temp = val; *temp; temp++)
375         free(*temp);
376     free(val);
377 }
378
379 void KRB5_CALLCONV
380 krb5_free_pa_data(krb5_context context, krb5_pa_data **val)
381 {
382     register krb5_pa_data **temp;
383
384     if (val == NULL)
385         return;
386     for (temp = val; *temp; temp++) {
387         free((*temp)->contents);
388         free(*temp);
389     }
390     free(val);
391 }
392
393 void KRB5_CALLCONV
394 krb5_free_principal(krb5_context context, krb5_principal val)
395 {
396     register krb5_int32 i;
397
398     if (!val)
399         return;
400
401     if (val->data) {
402         i = krb5_princ_size(context, val);
403         while(--i >= 0)
404             free(krb5_princ_component(context, val, i)->data);
405         free(val->data);
406     }
407     free(val->realm.data);
408     free(val);
409 }
410
411 void KRB5_CALLCONV
412 krb5_free_priv(krb5_context context, register krb5_priv *val)
413 {
414     if (val == NULL)
415         return;
416     free(val->enc_part.ciphertext.data);
417     free(val);
418 }
419
420 void KRB5_CALLCONV
421 krb5_free_priv_enc_part(krb5_context context, register krb5_priv_enc_part *val)
422 {
423     if (val == NULL)
424         return;
425     free(val->user_data.data);
426     krb5_free_address(context, val->r_address);
427     krb5_free_address(context, val->s_address);
428     free(val);
429 }
430
431 void KRB5_CALLCONV
432 krb5_free_pwd_data(krb5_context context, krb5_pwd_data *val)
433 {
434     if (val == NULL)
435         return;
436     krb5_free_pwd_sequences(context, val->element);
437     free(val);
438 }
439
440
441 void KRB5_CALLCONV
442 krb5_free_passwd_phrase_element(krb5_context context,
443                                 passwd_phrase_element *val)
444 {
445     if (val == NULL)
446         return;
447     krb5_free_data(context, val->passwd);
448     val->passwd = NULL;
449     krb5_free_data(context, val->phrase);
450     val->phrase = NULL;
451     free(val);
452 }
453
454
455 void KRB5_CALLCONV
456 krb5_free_pwd_sequences(krb5_context context, passwd_phrase_element **val)
457 {
458     register passwd_phrase_element **temp;
459
460     if (val == NULL)
461         return;
462     for (temp = val; *temp; temp++)
463         krb5_free_passwd_phrase_element(context, *temp);
464     free(val);
465 }
466
467
468 void KRB5_CALLCONV
469 krb5_free_safe(krb5_context context, register krb5_safe *val)
470 {
471     if (val == NULL)
472         return;
473     free(val->user_data.data);
474     krb5_free_address(context, val->r_address);
475     krb5_free_address(context, val->s_address);
476     krb5_free_checksum(context, val->checksum);
477     free(val);
478 }
479
480
481 void KRB5_CALLCONV
482 krb5_free_ticket(krb5_context context, krb5_ticket *val)
483 {
484     if (val == NULL)
485         return;
486     krb5_free_principal(context, val->server);
487     free(val->enc_part.ciphertext.data);
488     krb5_free_enc_tkt_part(context, val->enc_part2);
489     free(val);
490 }
491
492 void KRB5_CALLCONV
493 krb5_free_tickets(krb5_context context, krb5_ticket **val)
494 {
495     register krb5_ticket **temp;
496
497     if (val == NULL)
498         return;
499     for (temp = val; *temp; temp++)
500         krb5_free_ticket(context, *temp);
501     free(val);
502 }
503
504
505 void KRB5_CALLCONV
506 krb5_free_tgt_creds(krb5_context context, krb5_creds **tgts)
507 {
508     register krb5_creds **tgtpp;
509     if (tgts == NULL)
510         return;
511     for (tgtpp = tgts; *tgtpp; tgtpp++)
512         krb5_free_creds(context, *tgtpp);
513     free(tgts);
514 }
515
516 void KRB5_CALLCONV
517 krb5_free_tkt_authent(krb5_context context, krb5_tkt_authent *val)
518 {
519     if (val == NULL)
520         return;
521     krb5_free_ticket(context, val->ticket);
522     krb5_free_authenticator(context, val->authenticator);
523     free(val);
524 }
525
526 void KRB5_CALLCONV
527 krb5_free_unparsed_name(krb5_context context, char *val)
528 {
529     if (val != NULL)
530         free(val);
531 }
532
533 void KRB5_CALLCONV
534 krb5_free_string(krb5_context context, char *val)
535 {
536     free(val);
537 }
538
539 void KRB5_CALLCONV
540 krb5_free_sam_challenge(krb5_context ctx, krb5_sam_challenge *sc)
541 {
542     if (!sc)
543         return;
544     krb5_free_sam_challenge_contents(ctx, sc);
545     free(sc);
546 }
547
548 void KRB5_CALLCONV
549 krb5_free_sam_challenge_2(krb5_context ctx, krb5_sam_challenge_2 *sc2)
550 {
551     if (!sc2)
552         return;
553     krb5_free_sam_challenge_2_contents(ctx, sc2);
554     free(sc2);
555 }
556
557 void KRB5_CALLCONV
558 krb5_free_sam_challenge_contents(krb5_context ctx, krb5_sam_challenge *sc)
559 {
560     if (!sc)
561         return;
562     if (sc->sam_type_name.data)
563         krb5_free_data_contents(ctx, &sc->sam_type_name);
564     if (sc->sam_track_id.data)
565         krb5_free_data_contents(ctx, &sc->sam_track_id);
566     if (sc->sam_challenge_label.data)
567         krb5_free_data_contents(ctx, &sc->sam_challenge_label);
568     if (sc->sam_challenge.data)
569         krb5_free_data_contents(ctx, &sc->sam_challenge);
570     if (sc->sam_response_prompt.data)
571         krb5_free_data_contents(ctx, &sc->sam_response_prompt);
572     if (sc->sam_pk_for_sad.data)
573         krb5_free_data_contents(ctx, &sc->sam_pk_for_sad);
574     free(sc->sam_cksum.contents);
575     sc->sam_cksum.contents = 0;
576 }
577
578 void KRB5_CALLCONV
579 krb5_free_sam_challenge_2_contents(krb5_context ctx,
580                                    krb5_sam_challenge_2 *sc2)
581 {
582     krb5_checksum **cksump;
583
584     if (!sc2)
585         return;
586     if (sc2->sam_challenge_2_body.data)
587         krb5_free_data_contents(ctx, &sc2->sam_challenge_2_body);
588     if (sc2->sam_cksum) {
589         cksump = sc2->sam_cksum;
590         while (*cksump) {
591             krb5_free_checksum(ctx, *cksump);
592             cksump++;
593         }
594         free(sc2->sam_cksum);
595         sc2->sam_cksum = 0;
596     }
597 }
598
599 void KRB5_CALLCONV
600 krb5_free_sam_challenge_2_body(krb5_context ctx,
601                                krb5_sam_challenge_2_body *sc2)
602 {
603     if (!sc2)
604         return;
605     krb5_free_sam_challenge_2_body_contents(ctx, sc2);
606     free(sc2);
607 }
608
609 void KRB5_CALLCONV
610 krb5_free_sam_challenge_2_body_contents(krb5_context ctx,
611                                         krb5_sam_challenge_2_body *sc2)
612 {
613     if (!sc2)
614         return;
615     if (sc2->sam_type_name.data)
616         krb5_free_data_contents(ctx, &sc2->sam_type_name);
617     if (sc2->sam_track_id.data)
618         krb5_free_data_contents(ctx, &sc2->sam_track_id);
619     if (sc2->sam_challenge_label.data)
620         krb5_free_data_contents(ctx, &sc2->sam_challenge_label);
621     if (sc2->sam_challenge.data)
622         krb5_free_data_contents(ctx, &sc2->sam_challenge);
623     if (sc2->sam_response_prompt.data)
624         krb5_free_data_contents(ctx, &sc2->sam_response_prompt);
625     if (sc2->sam_pk_for_sad.data)
626         krb5_free_data_contents(ctx, &sc2->sam_pk_for_sad);
627 }
628
629 void KRB5_CALLCONV
630 krb5_free_sam_response(krb5_context ctx, krb5_sam_response *sr)
631 {
632     if (!sr)
633         return;
634     krb5_free_sam_response_contents(ctx, sr);
635     free(sr);
636 }
637
638 void KRB5_CALLCONV
639 krb5_free_sam_response_2(krb5_context ctx, krb5_sam_response_2 *sr2)
640 {
641     if (!sr2)
642         return;
643     krb5_free_sam_response_2_contents(ctx, sr2);
644     free(sr2);
645 }
646
647 void KRB5_CALLCONV
648 krb5_free_sam_response_contents(krb5_context ctx, krb5_sam_response *sr)
649 {
650     if (!sr)
651         return;
652     if (sr->sam_track_id.data)
653         krb5_free_data_contents(ctx, &sr->sam_track_id);
654     if (sr->sam_enc_key.ciphertext.data)
655         krb5_free_data_contents(ctx, &sr->sam_enc_key.ciphertext);
656     if (sr->sam_enc_nonce_or_ts.ciphertext.data)
657         krb5_free_data_contents(ctx, &sr->sam_enc_nonce_or_ts.ciphertext);
658 }
659
660 void KRB5_CALLCONV
661 krb5_free_sam_response_2_contents(krb5_context ctx, krb5_sam_response_2 *sr2)
662 {
663     if (!sr2)
664         return;
665     if (sr2->sam_track_id.data)
666         krb5_free_data_contents(ctx, &sr2->sam_track_id);
667     if (sr2->sam_enc_nonce_or_sad.ciphertext.data)
668         krb5_free_data_contents(ctx, &sr2->sam_enc_nonce_or_sad.ciphertext);
669 }
670
671 void KRB5_CALLCONV
672 krb5_free_predicted_sam_response(krb5_context ctx,
673                                  krb5_predicted_sam_response *psr)
674 {
675     if (!psr)
676         return;
677     krb5_free_predicted_sam_response_contents(ctx, psr);
678     free(psr);
679 }
680
681 void KRB5_CALLCONV
682 krb5_free_predicted_sam_response_contents(krb5_context ctx,
683                                           krb5_predicted_sam_response *psr)
684 {
685     if (!psr)
686         return;
687     if (psr->sam_key.contents)
688         krb5_free_keyblock_contents(ctx, &psr->sam_key);
689     krb5_free_principal(ctx, psr->client);
690     psr->client = 0;
691     if (psr->msd.data)
692         krb5_free_data_contents(ctx, &psr->msd);
693 }
694
695 void KRB5_CALLCONV
696 krb5_free_enc_sam_response_enc(krb5_context ctx,
697                                krb5_enc_sam_response_enc *esre)
698 {
699     if (!esre)
700         return;
701     krb5_free_enc_sam_response_enc_contents(ctx, esre);
702     free(esre);
703 }
704
705 void KRB5_CALLCONV
706 krb5_free_enc_sam_response_enc_2(krb5_context ctx,
707                                  krb5_enc_sam_response_enc_2 *esre2)
708 {
709     if (!esre2)
710         return;
711     krb5_free_enc_sam_response_enc_2_contents(ctx, esre2);
712     free(esre2);
713 }
714
715 void KRB5_CALLCONV
716 krb5_free_enc_sam_response_enc_contents(krb5_context ctx,
717                                         krb5_enc_sam_response_enc *esre)
718 {
719     if (!esre)
720         return;
721     if (esre->sam_sad.data)
722         krb5_free_data_contents(ctx, &esre->sam_sad);
723 }
724
725 void KRB5_CALLCONV
726 krb5_free_enc_sam_response_enc_2_contents(krb5_context ctx,
727                                           krb5_enc_sam_response_enc_2 *esre2)
728 {
729     if (!esre2)
730         return;
731     if (esre2->sam_sad.data)
732         krb5_free_data_contents(ctx, &esre2->sam_sad);
733 }
734
735 void KRB5_CALLCONV
736 krb5_free_pa_enc_ts(krb5_context ctx, krb5_pa_enc_ts *pa_enc_ts)
737 {
738     if (!pa_enc_ts)
739         return;
740     free(pa_enc_ts);
741 }
742
743 void KRB5_CALLCONV
744 krb5_free_pa_for_user(krb5_context context, krb5_pa_for_user *req)
745 {
746     if (req == NULL)
747         return;
748     krb5_free_principal(context, req->user);
749     req->user = NULL;
750     krb5_free_checksum_contents(context, &req->cksum);
751     krb5_free_data_contents(context, &req->auth_package);
752     free(req);
753 }
754
755 void KRB5_CALLCONV
756 krb5_free_s4u_userid_contents(krb5_context context, krb5_s4u_userid *user_id)
757 {
758     if (user_id == NULL)
759         return;
760     user_id->nonce = 0;
761     krb5_free_principal(context, user_id->user);
762     user_id->user = NULL;
763     krb5_free_data_contents(context, &user_id->subject_cert);
764     user_id->subject_cert.length = 0;
765     user_id->subject_cert.data = NULL;
766     user_id->options = 0;
767 }
768
769 void KRB5_CALLCONV
770 krb5_free_pa_s4u_x509_user(krb5_context context, krb5_pa_s4u_x509_user *req)
771 {
772     if (req == NULL)
773         return;
774     krb5_free_s4u_userid_contents(context, &req->user_id);
775     krb5_free_checksum_contents(context, &req->cksum);
776     free(req);
777 }
778
779 void KRB5_CALLCONV
780 krb5_free_pa_server_referral_data(krb5_context context,
781                                   krb5_pa_server_referral_data *ref)
782 {
783     if (ref == NULL)
784         return;
785     krb5_free_data(context, ref->referred_realm);
786     ref->referred_realm = NULL;
787     krb5_free_principal(context, ref->true_principal_name);
788     ref->true_principal_name = NULL;
789     krb5_free_principal(context, ref->requested_principal_name);
790     ref->requested_principal_name = NULL;
791     krb5_free_checksum_contents(context, &ref->rep_cksum);
792     free(ref);
793 }
794
795 void KRB5_CALLCONV
796 krb5_free_pa_svr_referral_data(krb5_context context,
797                                krb5_pa_svr_referral_data *ref)
798 {
799     if (ref == NULL)
800         return;
801     krb5_free_principal(context, ref->principal);
802     ref->principal = NULL;
803     free(ref);
804 }
805
806 void KRB5_CALLCONV
807 krb5_free_pa_pac_req(krb5_context context,
808                      krb5_pa_pac_req *req)
809 {
810     free(req);
811 }
812
813 void KRB5_CALLCONV
814 krb5_free_etype_list(krb5_context context,
815                      krb5_etype_list *etypes)
816 {
817     if (etypes != NULL) {
818         free(etypes->etypes);
819         free(etypes);
820     }
821 }
822 void KRB5_CALLCONV
823 krb5_free_fast_req(krb5_context context, krb5_fast_req *val)
824 {
825     if (val == NULL)
826         return;
827     krb5_free_kdc_req(context, val->req_body);
828     free(val);
829 }
830
831 void KRB5_CALLCONV
832 krb5_free_fast_armor(krb5_context context, krb5_fast_armor *val)
833 {
834     if (val == NULL)
835         return;
836     krb5_free_data_contents(context, &val->armor_value);
837     free(val);
838 }
839
840 void KRB5_CALLCONV
841 krb5_free_fast_response(krb5_context context, krb5_fast_response *val)
842 {
843     if (!val)
844         return;
845     krb5_free_pa_data(context, val->padata);
846     krb5_free_fast_finished(context, val->finished);
847     krb5_free_keyblock(context, val->strengthen_key);
848     free(val);
849 }
850
851 void KRB5_CALLCONV
852 krb5_free_fast_finished(krb5_context context, krb5_fast_finished *val)
853 {
854     if (!val)
855         return;
856     krb5_free_principal(context, val->client);
857     krb5_free_checksum_contents(context, &val->ticket_checksum);
858     free(val);
859 }
860
861 void
862 krb5_free_typed_data(krb5_context context, krb5_typed_data **in)
863 {
864     int i = 0;
865     if (in == NULL) return;
866     while (in[i] != NULL) {
867         if (in[i]->data != NULL)
868             free(in[i]->data);
869         free(in[i]);
870         i++;
871     }
872     free(in);
873 }
874
875 void KRB5_CALLCONV
876 krb5_free_fast_armored_req(krb5_context context, krb5_fast_armored_req *val)
877 {
878     if (val == NULL)
879         return;
880     if (val->armor)
881         krb5_free_fast_armor(context, val->armor);
882     krb5_free_data_contents(context, &val->enc_part.ciphertext);
883     if (val->req_checksum.contents)
884         krb5_free_checksum_contents(context, &val->req_checksum);
885     free(val);
886 }
887
888 void KRB5_CALLCONV
889 krb5int_free_data_list(krb5_context context, krb5_data *data)
890 {
891     int i;
892
893     if (data == NULL)
894         return;
895
896     for (i = 0; data[i].data != NULL; i++)
897         free(data[i].data);
898
899     free(data);
900 }
901
902 void KRB5_CALLCONV
903 krb5_free_ad_kdcissued(krb5_context context, krb5_ad_kdcissued *val)
904 {
905     if (val == NULL)
906         return;
907
908     krb5_free_checksum_contents(context, &val->ad_checksum);
909     krb5_free_principal(context, val->i_principal);
910     krb5_free_authdata(context, val->elements);
911     free(val);
912 }
913
914 void KRB5_CALLCONV
915 krb5_free_ad_signedpath(krb5_context context, krb5_ad_signedpath *val)
916 {
917     int i;
918
919     if (val == NULL)
920         return;
921
922     krb5_free_checksum_contents(context, &val->checksum);
923     if (val->delegated != NULL) {
924         for (i = 0; val->delegated[i] != NULL; i++)
925             krb5_free_principal(context, val->delegated[i]);
926         free(val->delegated);
927     }
928     krb5_free_pa_data(context, val->method_data);
929     free(val);
930 }
931
932 void KRB5_CALLCONV
933 krb5_free_iakerb_header(krb5_context context, krb5_iakerb_header *val)
934 {
935     if (val == NULL)
936         return ;
937
938     krb5_free_data_contents(context, &val->target_realm);
939     krb5_free_data(context, val->cookie);
940     free(val);
941 }
942
943 void KRB5_CALLCONV
944 krb5_free_iakerb_finished(krb5_context context, krb5_iakerb_finished *val)
945 {
946     if (val == NULL)
947         return ;
948
949     krb5_free_checksum_contents(context, &val->checksum);
950     free(val);
951 }