4
* Copyright 1985, 1986, 1987, 1988,1991 by the Massachusetts Institute
4
* Copyright 1985, 1986, 1987, 1988,1991,2007 by the Massachusetts Institute
6
6
* All Rights Reserved.
69
70
static int compat_decrypt_key (krb5_key_data *, C_Block,
70
71
krb5_keyblock *, int);
71
static int kerb_get_principal (char *, char *, Principal *, int,
72
static int kerb_get_principal (char *, char *, Principal *,
72
73
int *, krb5_keyblock *, krb5_kvno,
73
74
int, krb5_deltat *);
74
75
static int check_princ (char *, char *, int, Principal *,
86
87
#define MSB_FIRST 0 /* 68000, IBM RT/PC */
87
88
#define LSB_FIRST 1 /* Vax, PC8086 */
91
/* XXX several files in libkdb know about this */
94
90
#ifndef BACKWARD_COMPAT
95
91
static Key_schedule master_key_schedule;
96
92
static C_Block master_key;
143
139
#include "extern.h" /* to pick up master_princ */
144
140
#include <errno.h>
146
static krb5_data *response;
148
void kerberos_v4 (struct sockaddr_in *, KTEXT);
149
void kerb_err_reply (struct sockaddr_in *, KTEXT, long, char *);
142
static krb5_data *kerberos_v4 (struct sockaddr_in *, KTEXT);
143
static krb5_data *kerb_err_reply (struct sockaddr_in *, KTEXT, long, char *);
150
144
static int set_tgtkey (char *, krb5_kvno, krb5_boolean);
152
146
/* Attributes converted from V5 to V4 - internal representation */
262
256
(void) klog(L_KRB_PERR, "V4 request too long.");
263
257
return KRB5KRB_ERR_FIELD_TOOLONG;
259
memset( &v4_pkt, 0, sizeof(v4_pkt));
265
260
v4_pkt.length = pkt->length;
267
262
memcpy( v4_pkt.dat, pkt->data, pkt->length);
269
kerberos_v4( &client_sockaddr, &v4_pkt);
264
*resp = kerberos_v4( &client_sockaddr, &v4_pkt);
303
int krb4_sendto(int s, const char *msg, int len, int flags,
304
const struct sockaddr *to, int to_len)
297
krb5_data *make_response(const char *msg, int len)
306
301
if ( !(response = (krb5_data *) malloc( sizeof *response))) {
309
304
if ( !(response->data = (char *) malloc( len))) {
310
305
krb5_free_data(kdc_context, response);
313
308
response->length = len;
314
309
memcpy( response->data, msg, len);
401
396
kerb_get_principal(char *name, char *inst, /* could have wild cards */
402
397
Principal *principal,
403
int maxn, /* max # name structs to return */
404
398
int *more, /* more tuples than room for */
405
399
krb5_keyblock *k5key, krb5_kvno kvno,
406
400
int issrv, /* true if retrieving a service key */
575
565
* this routine clears the keyblock's contents for us.
577
567
krb5_db_free_principal(kdc_context, &entries, nprinc);
578
*more = (int) more5 || (nprinc > maxn);
568
*more = (int) more5 || (nprinc > 1);
642
632
inet_ntoa(client_host));
643
633
/* send an error reply */
644
634
req_name_ptr = req_inst_ptr = req_realm_ptr = "";
645
kerb_err_reply(client, pkt, KERB_ERR_PKT_VER, lt);
635
return kerb_err_reply(client, pkt, KERB_ERR_PKT_VER, lt);
649
638
/* check packet version */
653
642
KRB_PROT_VERSION, req_version, 0);
654
643
/* send an error reply */
655
644
req_name_ptr = req_inst_ptr = req_realm_ptr = "";
656
kerb_err_reply(client, pkt, KERB_ERR_PKT_VER, lt);
645
return kerb_err_reply(client, pkt, KERB_ERR_PKT_VER, lt);
659
647
msg_byte_order = req_msg_type & 1;
713
701
if ((i = check_princ(req_name_ptr, req_inst_ptr, 0,
714
702
&a_name_data, &k5key, 0, &ck5life))) {
715
kerb_err_reply(client, pkt, i, "check_princ failed");
703
response = kerb_err_reply(client, pkt, i, "check_princ failed");
716
704
a_name_data.key_low = a_name_data.key_high = 0;
717
705
krb5_free_keyblock_contents(kdc_context, &k5key);
720
708
/* don't use k5key for client */
721
709
krb5_free_keyblock_contents(kdc_context, &k5key);
727
715
/* this does all the checking */
728
716
if ((i = check_princ(service, instance, lifetime,
729
717
&s_name_data, &k5key, 1, &sk5life))) {
730
kerb_err_reply(client, pkt, i, "check_princ failed");
718
response = kerb_err_reply(client, pkt, i, "check_princ failed");
731
719
a_name_data.key_high = a_name_data.key_low = 0;
732
720
s_name_data.key_high = s_name_data.key_low = 0;
733
721
krb5_free_keyblock_contents(kdc_context, &k5key);
736
724
/* Bound requested lifetime with service and user */
737
725
v4req_end = krb_life_to_time(kerb_time.tv_sec, req_life);
802
790
rpkt = create_auth_reply(req_name_ptr, req_inst_ptr,
803
791
req_realm_ptr, req_time_ws, 0, a_name_data.exp_date,
804
792
a_name_data.key_version, ciph);
805
krb4_sendto(f, (char *) rpkt->dat, rpkt->length, 0,
806
(struct sockaddr *) client, S_AD_SZ);
793
response = make_response((char *) rpkt->dat, rpkt->length);
807
794
memset(&a_name_data, 0, sizeof(a_name_data));
808
795
memset(&s_name_data, 0, sizeof(s_name_data));
829
816
lt = klog(L_KRB_PERR,
830
817
"APPL request with realm length too long from %s",
831
818
inet_ntoa(client_host));
832
kerb_err_reply(client, pkt, RD_AP_INCON,
833
"realm length too long");
819
return kerb_err_reply(client, pkt, RD_AP_INCON,
820
"realm length too long");
837
823
auth->length += (int) *(pkt->dat + auth->length) +
840
826
lt = klog(L_KRB_PERR,
841
827
"APPL request with funky tkt or req_id length from %s",
842
828
inet_ntoa(client_host));
843
kerb_err_reply(client, pkt, RD_AP_INCON,
844
"funky tkt or req_id length");
829
return kerb_err_reply(client, pkt, RD_AP_INCON,
830
"funky tkt or req_id length");
848
833
memcpy(auth->dat, pkt->dat, auth->length);
853
838
if ((!allow_v4_crossrealm)&&strcmp(tktrlm, local_realm) != 0) {
854
839
lt = klog(L_ERR_UNK,
855
840
"Cross realm ticket from %s denied by policy,", tktrlm);
856
kerb_err_reply(client, pkt,
857
KERB_ERR_PRINCIPAL_UNKNOWN, lt);
841
return kerb_err_reply(client, pkt,
842
KERB_ERR_PRINCIPAL_UNKNOWN, lt);
860
844
if (set_tgtkey(tktrlm, kvno, 0)) {
862
846
"FAILED set_tgtkey realm %s, kvno %d. Host: %s ",
863
847
tktrlm, kvno, inet_ntoa(client_host));
864
848
/* no better error code */
865
kerb_err_reply(client, pkt,
866
KERB_ERR_PRINCIPAL_UNKNOWN, lt);
849
return kerb_err_reply(client, pkt,
850
KERB_ERR_PRINCIPAL_UNKNOWN, lt);
869
852
kerno = krb_rd_req(auth, "krbtgt", tktrlm, client_host.s_addr,
874
857
"FAILED 3des set_tgtkey realm %s, kvno %d. Host: %s ",
875
858
tktrlm, kvno, inet_ntoa(client_host));
876
859
/* no better error code */
877
kerb_err_reply(client, pkt,
878
KERB_ERR_PRINCIPAL_UNKNOWN, lt);
860
return kerb_err_reply(client, pkt,
861
KERB_ERR_PRINCIPAL_UNKNOWN, lt);
881
863
kerno = krb_rd_req(auth, "krbtgt", tktrlm, client_host.s_addr,
886
868
klog(L_ERR_UNK, "FAILED krb_rd_req from %s: %s",
887
869
inet_ntoa(client_host), krb_get_err_text(kerno));
888
870
req_name_ptr = req_inst_ptr = req_realm_ptr = "";
889
kerb_err_reply(client, pkt, kerno, "krb_rd_req failed");
871
return kerb_err_reply(client, pkt, kerno, "krb_rd_req failed");
892
873
ptr = (char *) pkt->dat + auth->length;
909
890
req_realm_ptr = ad->prealm;
911
892
if (strcmp(ad->prealm, tktrlm)) {
912
kerb_err_reply(client, pkt, KERB_ERR_PRINCIPAL_UNKNOWN,
893
return kerb_err_reply(client, pkt, KERB_ERR_PRINCIPAL_UNKNOWN,
916
896
if (!strcmp(service, "changepw")) {
917
kerb_err_reply(client, pkt, KERB_ERR_PRINCIPAL_UNKNOWN,
918
"Can't authorize password changed based on TGT");
897
return kerb_err_reply(client, pkt, KERB_ERR_PRINCIPAL_UNKNOWN,
898
"Can't authorize password changed based on TGT");
921
900
kerno = check_princ(service, instance, req_life,
922
901
&s_name_data, &k5key, 1, &sk5life);
924
kerb_err_reply(client, pkt, kerno, "check_princ failed");
903
response = kerb_err_reply(client, pkt, kerno,
904
"check_princ failed");
925
905
s_name_data.key_high = s_name_data.key_low = 0;
926
906
krb5_free_keyblock_contents(kdc_context, &k5key);
929
909
/* Bound requested lifetime with service and user */
930
910
v4endtime = krb_life_to_time((KRB4_32)ad->time_sec, ad->life);
980
960
rpkt = create_auth_reply(ad->pname, ad->pinst,
981
961
ad->prealm, time_ws,
983
krb4_sendto(f, (char *) rpkt->dat, rpkt->length, 0,
984
(struct sockaddr *) client, S_AD_SZ);
963
response = make_response((char *) rpkt->dat, rpkt->length);
985
964
memset(&s_name_data, 0, sizeof(s_name_data));
1026
1006
strncat(e_msg, string, sizeof(e_msg) - 1 - 19);
1027
1007
cr_err_reply(e_pkt, req_name_ptr, req_inst_ptr, req_realm_ptr,
1028
1008
req_time_ws, err, e_msg);
1029
krb4_sendto(f, (char *) e_pkt->dat, e_pkt->length, 0,
1030
(struct sockaddr *) client, S_AD_SZ);
1009
return make_response((char *) e_pkt->dat, e_pkt->length);
1039
1017
static int more;
1040
1018
/* long trans; */
1042
n = kerb_get_principal(p_name, instance, p, 1, &more, k5key, 0,
1020
n = kerb_get_principal(p_name, instance, p, &more, k5key, 0,
1043
1021
issrv, k5life);
1044
1022
klog(L_ALL_REQ,
1045
1023
"Principal: \"%s\", Instance: \"%s\" Lifetime = %d n = %d",
1161
1139
/* log("Getting key for %s", r); */
1163
n = kerb_get_principal("krbtgt", r, p, 1, &more, &k5key, kvno, 1, NULL);
1141
n = kerb_get_principal("krbtgt", r, p, &more, &k5key, kvno, 1, NULL);
1165
1143
return (KFAILURE);