2 * Copyright (c) 1997 - 2005 Kungliga Tekniska Högskolan
3 * (Royal Institute of Technology, Stockholm, Sweden).
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
17 * 3. Neither the name of the Institute nor the names of its contributors
18 * may be used to endorse or promote products derived from this software
19 * without specific prior written permission.
21 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND
22 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24 * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
25 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
26 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
27 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
30 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
34 #include "krb5_locl.h"
37 #include "krb5-v4compat.h"
43 #define RCHECK(r,func,label) \
44 do { (r) = func ; if (r) goto label; } while(0);
47 /* include this here, to avoid dependencies on libkrb */
49 static const int _tkt_lifetimes
[TKTLIFENUMFIXED
] = {
50 38400, 41055, 43894, 46929, 50174, 53643, 57352, 61318,
51 65558, 70091, 74937, 80119, 85658, 91581, 97914, 104684,
52 111922, 119661, 127935, 136781, 146239, 156350, 167161, 178720,
53 191077, 204289, 218415, 233517, 249664, 266926, 285383, 305116,
54 326213, 348769, 372885, 398668, 426234, 455705, 487215, 520904,
55 556921, 595430, 636601, 680618, 727680, 777995, 831789, 889303,
56 950794, 1016537, 1086825, 1161973, 1242318, 1328218, 1420057, 1518247,
57 1623226, 1735464, 1855462, 1983758, 2120925, 2267576, 2424367, 2592000
61 _krb5_krb_time_to_life(time_t start
, time_t end
)
64 time_t life
= end
- start
;
66 if (life
> MAXTKTLIFETIME
|| life
<= 0)
69 if (krb_no_long_lifetimes
)
70 return (life
+ 5*60 - 1)/(5*60);
74 return TKTLIFENOEXPIRE
;
75 if (life
< _tkt_lifetimes
[0])
76 return (life
+ 5*60 - 1)/(5*60);
77 for (i
=0; i
<TKTLIFENUMFIXED
; i
++)
78 if (life
<= _tkt_lifetimes
[i
])
79 return i
+ TKTLIFEMINFIXED
;
84 time_t KRB5_LIB_FUNCTION
85 _krb5_krb_life_to_time(int start
, int life_
)
87 unsigned char life
= (unsigned char) life_
;
90 if (krb_no_long_lifetimes
)
91 return start
+ life
*5*60;
94 if (life
== TKTLIFENOEXPIRE
)
96 if (life
< TKTLIFEMINFIXED
)
97 return start
+ life
*5*60;
98 if (life
> TKTLIFEMAXFIXED
)
99 return start
+ MAXTKTLIFETIME
;
100 return start
+ _tkt_lifetimes
[life
- TKTLIFEMINFIXED
];
104 * Get the name of the krb4 credentials cache, will use `tkfile' as
105 * the name if that is passed in. `cc' must be free()ed by caller,
108 static krb5_error_code
109 get_krb4_cc_name(const char *tkfile
, char **cc
)
116 path
= getenv("KRBTKFILE");
121 if (asprintf(cc
, "%s%u", TKT_ROOT
, (unsigned)getuid()) < 0)
124 *cc
= strdup(tkfile
);
132 * Write a Kerberos 4 ticket file
135 #define KRB5_TF_LCK_RETRY_COUNT 50
136 #define KRB5_TF_LCK_RETRY 1
138 static krb5_error_code
139 write_v4_cc(krb5_context context
, const char *tkfile
,
140 krb5_storage
*sp
, int append
)
148 ret
= get_krb4_cc_name(tkfile
, &path
);
150 krb5_set_error_string(context
,
151 "krb5_krb_tf_setup: failed getting "
152 "the krb4 credentials cache name");
156 fd
= open(path
, O_WRONLY
|O_CREAT
, 0600);
159 krb5_set_error_string(context
,
160 "krb5_krb_tf_setup: error opening file %s",
166 if (fstat(fd
, &sb
) != 0 || !S_ISREG(sb
.st_mode
)) {
167 krb5_set_error_string(context
,
168 "krb5_krb_tf_setup: tktfile %s is not a file",
172 return KRB5_FCC_PERM
;
175 for (i
= 0; i
< KRB5_TF_LCK_RETRY_COUNT
; i
++) {
176 if (flock(fd
, LOCK_EX
| LOCK_NB
) < 0) {
177 sleep(KRB5_TF_LCK_RETRY
);
181 if (i
== KRB5_TF_LCK_RETRY_COUNT
) {
182 krb5_set_error_string(context
,
183 "krb5_krb_tf_setup: failed to lock %s",
187 return KRB5_FCC_PERM
;
191 ret
= ftruncate(fd
, 0);
194 krb5_set_error_string(context
,
195 "krb5_krb_tf_setup: failed to truncate %s",
199 return KRB5_FCC_PERM
;
202 ret
= lseek(fd
, 0L, SEEK_END
);
211 krb5_storage_to_data(sp
, &data
);
213 ret
= write(fd
, data
.data
, data
.length
);
214 if (ret
!= data
.length
)
217 krb5_free_data_contents(context
, &data
);
230 krb5_error_code KRB5_LIB_FUNCTION
231 _krb5_krb_tf_setup(krb5_context context
,
232 struct credentials
*v4creds
,
239 sp
= krb5_storage_emem();
243 krb5_storage_set_byteorder(sp
, KRB5_STORAGE_BYTEORDER_HOST
);
244 krb5_storage_set_eof_code(sp
, KRB5_CC_IO
);
246 krb5_clear_error_string(context
);
249 RCHECK(ret
, krb5_store_stringz(sp
, v4creds
->pname
), error
);
250 RCHECK(ret
, krb5_store_stringz(sp
, v4creds
->pinst
), error
);
254 RCHECK(ret
, krb5_store_stringz(sp
, v4creds
->service
), error
);
255 RCHECK(ret
, krb5_store_stringz(sp
, v4creds
->instance
), error
);
256 RCHECK(ret
, krb5_store_stringz(sp
, v4creds
->realm
), error
);
257 ret
= krb5_storage_write(sp
, v4creds
->session
, 8);
262 RCHECK(ret
, krb5_store_int32(sp
, v4creds
->lifetime
), error
);
263 RCHECK(ret
, krb5_store_int32(sp
, v4creds
->kvno
), error
);
264 RCHECK(ret
, krb5_store_int32(sp
, v4creds
->ticket_st
.length
), error
);
266 ret
= krb5_storage_write(sp
, v4creds
->ticket_st
.dat
,
267 v4creds
->ticket_st
.length
);
268 if (ret
!= v4creds
->ticket_st
.length
) {
272 RCHECK(ret
, krb5_store_int32(sp
, v4creds
->issue_date
), error
);
274 ret
= write_v4_cc(context
, tkfile
, sp
, append
);
277 krb5_storage_free(sp
);
286 krb5_error_code KRB5_LIB_FUNCTION
287 _krb5_krb_dest_tkt(krb5_context context
, const char *tkfile
)
292 ret
= get_krb4_cc_name(tkfile
, &path
);
294 krb5_set_error_string(context
,
295 "krb5_krb_tf_setup: failed getting "
296 "the krb4 credentials cache name");
300 if (unlink(path
) < 0) {
302 krb5_set_error_string(context
,
303 "krb5_krb_dest_tkt failed removing the cache "
304 "with error %s", strerror(ret
));
315 static krb5_error_code
316 decrypt_etext(krb5_context context
, const krb5_keyblock
*key
,
317 const krb5_data
*cdata
, krb5_data
*data
)
322 ret
= krb5_crypto_init(context
, key
, ETYPE_DES_PCBC_NONE
, &crypto
);
326 ret
= krb5_decrypt(context
, crypto
, 0, cdata
->data
, cdata
->length
, data
);
327 krb5_crypto_destroy(context
, crypto
);
337 static const char eightzeros
[8] = "\x00\x00\x00\x00\x00\x00\x00\x00";
339 static krb5_error_code
340 storage_to_etext(krb5_context context
,
342 const krb5_keyblock
*key
,
350 /* multiple of eight bytes */
352 size
= krb5_storage_seek(sp
, 0, SEEK_END
);
354 return KRB4ET_RD_AP_UNDEC
;
355 size
= 8 - (size
& 7);
357 ret
= krb5_storage_write(sp
, eightzeros
, size
);
359 return KRB4ET_RD_AP_UNDEC
;
361 ret
= krb5_storage_to_data(sp
, &data
);
365 ret
= krb5_crypto_init(context
, key
, ETYPE_DES_PCBC_NONE
, &crypto
);
367 krb5_data_free(&data
);
371 ret
= krb5_encrypt(context
, crypto
, 0, data
.data
, data
.length
, enc_data
);
373 krb5_data_free(&data
);
374 krb5_crypto_destroy(context
, crypto
);
383 static krb5_error_code
384 put_nir(krb5_storage
*sp
, const char *name
,
385 const char *instance
, const char *realm
)
389 RCHECK(ret
, krb5_store_stringz(sp
, name
), error
);
390 RCHECK(ret
, krb5_store_stringz(sp
, instance
), error
);
392 RCHECK(ret
, krb5_store_stringz(sp
, realm
), error
);
402 krb5_error_code KRB5_LIB_FUNCTION
403 _krb5_krb_create_ticket(krb5_context context
,
406 const char *pinstance
,
409 const krb5_keyblock
*session
,
413 const char *sinstance
,
414 const krb5_keyblock
*key
,
420 krb5_data_zero(enc_data
);
422 sp
= krb5_storage_emem();
424 krb5_set_error_string(context
, "malloc: out of memory");
427 krb5_storage_set_byteorder(sp
, KRB5_STORAGE_BYTEORDER_BE
);
429 RCHECK(ret
, krb5_store_int8(sp
, flags
), error
);
430 RCHECK(ret
, put_nir(sp
, pname
, pinstance
, prealm
), error
);
431 RCHECK(ret
, krb5_store_int32(sp
, ntohl(paddress
)), error
);
434 ret
= krb5_storage_write(sp
,
435 session
->keyvalue
.data
,
436 session
->keyvalue
.length
);
437 if (ret
!= session
->keyvalue
.length
) {
438 ret
= KRB4ET_INTK_PROT
;
442 RCHECK(ret
, krb5_store_int8(sp
, life
), error
);
443 RCHECK(ret
, krb5_store_int32(sp
, life_sec
), error
);
444 RCHECK(ret
, put_nir(sp
, sname
, sinstance
, NULL
), error
);
446 ret
= storage_to_etext(context
, sp
, key
, enc_data
);
449 krb5_storage_free(sp
);
451 krb5_set_error_string(context
, "Failed to encode kerberos 4 ticket");
460 krb5_error_code KRB5_LIB_FUNCTION
461 _krb5_krb_create_ciph(krb5_context context
,
462 const krb5_keyblock
*session
,
464 const char *instance
,
468 const krb5_data
*ticket
,
470 const krb5_keyblock
*key
,
476 krb5_data_zero(enc_data
);
478 sp
= krb5_storage_emem();
480 krb5_set_error_string(context
, "malloc: out of memory");
483 krb5_storage_set_byteorder(sp
, KRB5_STORAGE_BYTEORDER_BE
);
486 ret
= krb5_storage_write(sp
,
487 session
->keyvalue
.data
,
488 session
->keyvalue
.length
);
489 if (ret
!= session
->keyvalue
.length
) {
490 ret
= KRB4ET_INTK_PROT
;
494 RCHECK(ret
, put_nir(sp
, service
, instance
, realm
), error
);
495 RCHECK(ret
, krb5_store_int8(sp
, life
), error
);
496 RCHECK(ret
, krb5_store_int8(sp
, kvno
), error
);
497 RCHECK(ret
, krb5_store_int8(sp
, ticket
->length
), error
);
498 ret
= krb5_storage_write(sp
, ticket
->data
, ticket
->length
);
499 if (ret
!= ticket
->length
) {
500 ret
= KRB4ET_INTK_PROT
;
503 RCHECK(ret
, krb5_store_int32(sp
, kdc_time
), error
);
505 ret
= storage_to_etext(context
, sp
, key
, enc_data
);
508 krb5_storage_free(sp
);
510 krb5_set_error_string(context
, "Failed to encode kerberos 4 ticket");
519 krb5_error_code KRB5_LIB_FUNCTION
520 _krb5_krb_create_auth_reply(krb5_context context
,
528 const krb5_data
*cipher
,
534 krb5_data_zero(data
);
536 sp
= krb5_storage_emem();
538 krb5_set_error_string(context
, "malloc: out of memory");
541 krb5_storage_set_byteorder(sp
, KRB5_STORAGE_BYTEORDER_BE
);
543 RCHECK(ret
, krb5_store_int8(sp
, KRB_PROT_VERSION
), error
);
544 RCHECK(ret
, krb5_store_int8(sp
, AUTH_MSG_KDC_REPLY
), error
);
545 RCHECK(ret
, put_nir(sp
, pname
, pinst
, prealm
), error
);
546 RCHECK(ret
, krb5_store_int32(sp
, time_ws
), error
);
547 RCHECK(ret
, krb5_store_int8(sp
, n
), error
);
548 RCHECK(ret
, krb5_store_int32(sp
, x_date
), error
);
549 RCHECK(ret
, krb5_store_int8(sp
, kvno
), error
);
550 RCHECK(ret
, krb5_store_int16(sp
, cipher
->length
), error
);
551 ret
= krb5_storage_write(sp
, cipher
->data
, cipher
->length
);
552 if (ret
!= cipher
->length
) {
553 ret
= KRB4ET_INTK_PROT
;
557 ret
= krb5_storage_to_data(sp
, data
);
560 krb5_storage_free(sp
);
562 krb5_set_error_string(context
, "Failed to encode kerberos 4 ticket");
571 krb5_error_code KRB5_LIB_FUNCTION
572 _krb5_krb_cr_err_reply(krb5_context context
,
578 const char *e_string
,
584 krb5_data_zero(data
);
586 if (name
== NULL
) name
= "";
587 if (inst
== NULL
) inst
= "";
588 if (realm
== NULL
) realm
= "";
589 if (e_string
== NULL
) e_string
= "";
591 sp
= krb5_storage_emem();
593 krb5_set_error_string(context
, "malloc: out of memory");
596 krb5_storage_set_byteorder(sp
, KRB5_STORAGE_BYTEORDER_BE
);
598 RCHECK(ret
, krb5_store_int8(sp
, KRB_PROT_VERSION
), error
);
599 RCHECK(ret
, krb5_store_int8(sp
, AUTH_MSG_ERR_REPLY
), error
);
600 RCHECK(ret
, put_nir(sp
, name
, inst
, realm
), error
);
601 RCHECK(ret
, krb5_store_int32(sp
, time_ws
), error
);
602 /* If it is a Kerberos 4 error-code, remove the et BASE */
603 if (e
>= ERROR_TABLE_BASE_krb
&& e
<= ERROR_TABLE_BASE_krb
+ 255)
604 e
-= ERROR_TABLE_BASE_krb
;
605 RCHECK(ret
, krb5_store_int32(sp
, e
), error
);
606 RCHECK(ret
, krb5_store_stringz(sp
, e_string
), error
);
608 ret
= krb5_storage_to_data(sp
, data
);
611 krb5_storage_free(sp
);
613 krb5_set_error_string(context
, "Failed to encode kerberos 4 error");
618 static krb5_error_code
619 get_v4_stringz(krb5_storage
*sp
, char **str
, size_t max_len
)
623 ret
= krb5_ret_stringz(sp
, str
);
626 if (strlen(*str
) > max_len
) {
629 return KRB4ET_INTK_PROT
;
638 krb5_error_code KRB5_LIB_FUNCTION
639 _krb5_krb_decomp_ticket(krb5_context context
,
640 const krb5_data
*enc_ticket
,
641 const krb5_keyblock
*key
,
642 const char *local_realm
,
645 struct _krb5_krb_auth_data
*ad
)
649 krb5_storage
*sp
= NULL
;
651 unsigned char des_key
[8];
653 memset(ad
, 0, sizeof(*ad
));
654 krb5_data_zero(&ticket
);
659 RCHECK(ret
, decrypt_etext(context
, key
, enc_ticket
, &ticket
), error
);
661 sp
= krb5_storage_from_data(&ticket
);
663 krb5_data_free(&ticket
);
664 krb5_set_error_string(context
, "alloc: out of memory");
668 krb5_storage_set_eof_code(sp
, KRB4ET_INTK_PROT
);
670 RCHECK(ret
, krb5_ret_int8(sp
, &ad
->k_flags
), error
);
671 RCHECK(ret
, get_v4_stringz(sp
, &ad
->pname
, ANAME_SZ
), error
);
672 RCHECK(ret
, get_v4_stringz(sp
, &ad
->pinst
, INST_SZ
), error
);
673 RCHECK(ret
, get_v4_stringz(sp
, &ad
->prealm
, REALM_SZ
), error
);
674 RCHECK(ret
, krb5_ret_uint32(sp
, &ad
->address
), error
);
676 size
= krb5_storage_read(sp
, des_key
, sizeof(des_key
));
677 if (size
!= sizeof(des_key
)) {
678 ret
= KRB4ET_INTK_PROT
;
682 RCHECK(ret
, krb5_ret_uint8(sp
, &ad
->life
), error
);
685 krb5_storage_set_byteorder(sp
, KRB5_STORAGE_BYTEORDER_LE
);
687 krb5_storage_set_byteorder(sp
, KRB5_STORAGE_BYTEORDER_BE
);
689 RCHECK(ret
, krb5_ret_uint32(sp
, &ad
->time_sec
), error
);
691 RCHECK(ret
, get_v4_stringz(sp
, sname
, ANAME_SZ
), error
);
692 RCHECK(ret
, get_v4_stringz(sp
, sinstance
, INST_SZ
), error
);
694 ret
= krb5_keyblock_init(context
, ETYPE_DES_PCBC_NONE
,
695 des_key
, sizeof(des_key
), &ad
->session
);
699 if (strlen(ad
->prealm
) == 0) {
701 ad
->prealm
= strdup(local_realm
);
702 if (ad
->prealm
== NULL
) {
709 memset(des_key
, 0, sizeof(des_key
));
711 krb5_storage_free(sp
);
712 krb5_data_free(&ticket
);
722 _krb5_krb_free_auth_data(context
, ad
);
723 krb5_set_error_string(context
, "Failed to decode v4 ticket");
732 krb5_error_code KRB5_LIB_FUNCTION
733 _krb5_krb_rd_req(krb5_context context
,
736 const char *instance
,
737 const char *local_realm
,
739 const krb5_keyblock
*key
,
740 struct _krb5_krb_auth_data
*ad
)
744 krb5_data ticket
, eaut
, aut
;
750 uint8_t ticket_length
;
755 char *sinstance
= NULL
;
756 char *r_realm
= NULL
;
758 char *r_instance
= NULL
;
760 uint32_t r_time_sec
; /* Coarse time from authenticator */
761 unsigned long delta_t
; /* Time in authenticator - local time */
762 long tkt_age
; /* Age of ticket */
766 krb5_data_zero(&ticket
);
767 krb5_data_zero(&eaut
);
768 krb5_data_zero(&aut
);
770 sp
= krb5_storage_from_data(authent
);
772 krb5_set_error_string(context
, "alloc: out of memory");
776 krb5_storage_set_eof_code(sp
, KRB4ET_INTK_PROT
);
778 ret
= krb5_ret_int8(sp
, &pvno
);
780 krb5_set_error_string(context
, "Failed reading v4 pvno");
784 if (pvno
!= KRB_PROT_VERSION
) {
785 ret
= KRB4ET_RD_AP_VERSION
;
786 krb5_set_error_string(context
, "Failed v4 pvno not 4");
790 ret
= krb5_ret_int8(sp
, &type
);
792 krb5_set_error_string(context
, "Failed readin v4 type");
796 little_endian
= type
& 1;
799 if(type
!= AUTH_MSG_APPL_REQUEST
&& type
!= AUTH_MSG_APPL_REQUEST_MUTUAL
) {
800 ret
= KRB4ET_RD_AP_MSG_TYPE
;
801 krb5_set_error_string(context
, "Not a valid v4 request type");
805 RCHECK(ret
, krb5_ret_int8(sp
, &s_kvno
), error
);
806 RCHECK(ret
, get_v4_stringz(sp
, &realm
, REALM_SZ
), error
);
807 RCHECK(ret
, krb5_ret_uint8(sp
, &ticket_length
), error
);
808 RCHECK(ret
, krb5_ret_uint8(sp
, &eaut_length
), error
);
809 RCHECK(ret
, krb5_data_alloc(&ticket
, ticket_length
), error
);
811 size
= krb5_storage_read(sp
, ticket
.data
, ticket
.length
);
812 if (size
!= ticket
.length
) {
813 ret
= KRB4ET_INTK_PROT
;
814 krb5_set_error_string(context
, "Failed reading v4 ticket");
818 /* Decrypt and take apart ticket */
819 ret
= _krb5_krb_decomp_ticket(context
, &ticket
, key
, local_realm
,
820 &sname
, &sinstance
, ad
);
824 RCHECK(ret
, krb5_data_alloc(&eaut
, eaut_length
), error
);
826 size
= krb5_storage_read(sp
, eaut
.data
, eaut
.length
);
827 if (size
!= eaut
.length
) {
828 ret
= KRB4ET_INTK_PROT
;
829 krb5_set_error_string(context
, "Failed reading v4 authenticator");
833 krb5_storage_free(sp
);
836 ret
= decrypt_etext(context
, &ad
->session
, &eaut
, &aut
);
840 sp
= krb5_storage_from_data(&aut
);
843 krb5_set_error_string(context
, "alloc: out of memory");
848 krb5_storage_set_byteorder(sp
, KRB5_STORAGE_BYTEORDER_LE
);
850 krb5_storage_set_byteorder(sp
, KRB5_STORAGE_BYTEORDER_BE
);
852 RCHECK(ret
, get_v4_stringz(sp
, &r_name
, ANAME_SZ
), error
);
853 RCHECK(ret
, get_v4_stringz(sp
, &r_instance
, INST_SZ
), error
);
854 RCHECK(ret
, get_v4_stringz(sp
, &r_realm
, REALM_SZ
), error
);
856 RCHECK(ret
, krb5_ret_uint32(sp
, &ad
->checksum
), error
);
857 RCHECK(ret
, krb5_ret_uint8(sp
, &time_5ms
), error
);
858 RCHECK(ret
, krb5_ret_uint32(sp
, &r_time_sec
), error
);
860 if (strcmp(ad
->pname
, r_name
) != 0 ||
861 strcmp(ad
->pinst
, r_instance
) != 0 ||
862 strcmp(ad
->prealm
, r_realm
) != 0) {
863 krb5_set_error_string(context
, "v4 principal mismatch");
864 ret
= KRB4ET_RD_AP_INCON
;
868 if (from_addr
&& ad
->address
&& from_addr
!= ad
->address
) {
869 krb5_set_error_string(context
, "v4 bad address in ticket");
870 ret
= KRB4ET_RD_AP_BADD
;
874 gettimeofday(&tv
, NULL
);
875 delta_t
= abs((int)(tv
.tv_sec
- r_time_sec
));
876 if (delta_t
> CLOCK_SKEW
) {
877 ret
= KRB4ET_RD_AP_TIME
;
878 krb5_set_error_string(context
, "v4 clock skew");
882 /* Now check for expiration of ticket */
884 tkt_age
= tv
.tv_sec
- ad
->time_sec
;
886 if ((tkt_age
< 0) && (-tkt_age
> CLOCK_SKEW
)) {
887 ret
= KRB4ET_RD_AP_NYV
;
888 krb5_set_error_string(context
, "v4 clock skew for expiration");
892 if (tv
.tv_sec
> _krb5_krb_life_to_time(ad
->time_sec
, ad
->life
)) {
893 ret
= KRB4ET_RD_AP_EXP
;
894 krb5_set_error_string(context
, "v4 ticket expired");
900 krb5_data_free(&ticket
);
901 krb5_data_free(&eaut
);
902 krb5_data_free(&aut
);
916 krb5_storage_free(sp
);
919 krb5_clear_error_string(context
);
928 void KRB5_LIB_FUNCTION
929 _krb5_krb_free_auth_data(krb5_context context
, struct _krb5_krb_auth_data
*ad
)
937 krb5_free_keyblock_contents(context
, &ad
->session
);
938 memset(ad
, 0, sizeof(*ad
));