1*0a6a1f1dSLionel Sambuc /* $NetBSD: build_auth.c,v 1.1.1.2 2014/04/24 12:45:49 pettai Exp $ */
2ebfedea0SLionel Sambuc
3ebfedea0SLionel Sambuc /*
4ebfedea0SLionel Sambuc * Copyright (c) 1997 - 2003 Kungliga Tekniska Högskolan
5ebfedea0SLionel Sambuc * (Royal Institute of Technology, Stockholm, Sweden).
6ebfedea0SLionel Sambuc * All rights reserved.
7ebfedea0SLionel Sambuc *
8ebfedea0SLionel Sambuc * Redistribution and use in source and binary forms, with or without
9ebfedea0SLionel Sambuc * modification, are permitted provided that the following conditions
10ebfedea0SLionel Sambuc * are met:
11ebfedea0SLionel Sambuc *
12ebfedea0SLionel Sambuc * 1. Redistributions of source code must retain the above copyright
13ebfedea0SLionel Sambuc * notice, this list of conditions and the following disclaimer.
14ebfedea0SLionel Sambuc *
15ebfedea0SLionel Sambuc * 2. Redistributions in binary form must reproduce the above copyright
16ebfedea0SLionel Sambuc * notice, this list of conditions and the following disclaimer in the
17ebfedea0SLionel Sambuc * documentation and/or other materials provided with the distribution.
18ebfedea0SLionel Sambuc *
19ebfedea0SLionel Sambuc * 3. Neither the name of the Institute nor the names of its contributors
20ebfedea0SLionel Sambuc * may be used to endorse or promote products derived from this software
21ebfedea0SLionel Sambuc * without specific prior written permission.
22ebfedea0SLionel Sambuc *
23ebfedea0SLionel Sambuc * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND
24ebfedea0SLionel Sambuc * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
25ebfedea0SLionel Sambuc * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
26ebfedea0SLionel Sambuc * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
27ebfedea0SLionel Sambuc * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
28ebfedea0SLionel Sambuc * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
29ebfedea0SLionel Sambuc * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
30ebfedea0SLionel Sambuc * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
31ebfedea0SLionel Sambuc * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
32ebfedea0SLionel Sambuc * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
33ebfedea0SLionel Sambuc * SUCH DAMAGE.
34ebfedea0SLionel Sambuc */
35ebfedea0SLionel Sambuc
36ebfedea0SLionel Sambuc #include "krb5_locl.h"
37ebfedea0SLionel Sambuc
38ebfedea0SLionel Sambuc static krb5_error_code
make_etypelist(krb5_context context,krb5_authdata ** auth_data)39ebfedea0SLionel Sambuc make_etypelist(krb5_context context,
40ebfedea0SLionel Sambuc krb5_authdata **auth_data)
41ebfedea0SLionel Sambuc {
42ebfedea0SLionel Sambuc EtypeList etypes;
43ebfedea0SLionel Sambuc krb5_error_code ret;
44ebfedea0SLionel Sambuc krb5_authdata ad;
45ebfedea0SLionel Sambuc u_char *buf;
46*0a6a1f1dSLionel Sambuc size_t len = 0;
47ebfedea0SLionel Sambuc size_t buf_size;
48ebfedea0SLionel Sambuc
49*0a6a1f1dSLionel Sambuc ret = _krb5_init_etype(context, KRB5_PDU_NONE,
50*0a6a1f1dSLionel Sambuc &etypes.len, &etypes.val,
51*0a6a1f1dSLionel Sambuc NULL);
52ebfedea0SLionel Sambuc if (ret)
53ebfedea0SLionel Sambuc return ret;
54ebfedea0SLionel Sambuc
55ebfedea0SLionel Sambuc ASN1_MALLOC_ENCODE(EtypeList, buf, buf_size, &etypes, &len, ret);
56ebfedea0SLionel Sambuc if (ret) {
57ebfedea0SLionel Sambuc free_EtypeList(&etypes);
58ebfedea0SLionel Sambuc return ret;
59ebfedea0SLionel Sambuc }
60ebfedea0SLionel Sambuc if(buf_size != len)
61ebfedea0SLionel Sambuc krb5_abortx(context, "internal error in ASN.1 encoder");
62ebfedea0SLionel Sambuc free_EtypeList(&etypes);
63ebfedea0SLionel Sambuc
64ebfedea0SLionel Sambuc ALLOC_SEQ(&ad, 1);
65ebfedea0SLionel Sambuc if (ad.val == NULL) {
66ebfedea0SLionel Sambuc free(buf);
67ebfedea0SLionel Sambuc krb5_set_error_message(context, ENOMEM, N_("malloc: out of memory", ""));
68ebfedea0SLionel Sambuc return ENOMEM;
69ebfedea0SLionel Sambuc }
70ebfedea0SLionel Sambuc
71ebfedea0SLionel Sambuc ad.val[0].ad_type = KRB5_AUTHDATA_GSS_API_ETYPE_NEGOTIATION;
72ebfedea0SLionel Sambuc ad.val[0].ad_data.length = len;
73ebfedea0SLionel Sambuc ad.val[0].ad_data.data = buf;
74ebfedea0SLionel Sambuc
75ebfedea0SLionel Sambuc ASN1_MALLOC_ENCODE(AD_IF_RELEVANT, buf, buf_size, &ad, &len, ret);
76ebfedea0SLionel Sambuc if (ret) {
77ebfedea0SLionel Sambuc free_AuthorizationData(&ad);
78ebfedea0SLionel Sambuc return ret;
79ebfedea0SLionel Sambuc }
80ebfedea0SLionel Sambuc if(buf_size != len)
81ebfedea0SLionel Sambuc krb5_abortx(context, "internal error in ASN.1 encoder");
82ebfedea0SLionel Sambuc free_AuthorizationData(&ad);
83ebfedea0SLionel Sambuc
84ebfedea0SLionel Sambuc ALLOC(*auth_data, 1);
85ebfedea0SLionel Sambuc if (*auth_data == NULL) {
86ebfedea0SLionel Sambuc free(buf);
87ebfedea0SLionel Sambuc krb5_set_error_message(context, ENOMEM, N_("malloc: out of memory", ""));
88ebfedea0SLionel Sambuc return ENOMEM;
89ebfedea0SLionel Sambuc }
90ebfedea0SLionel Sambuc
91ebfedea0SLionel Sambuc ALLOC_SEQ(*auth_data, 1);
92ebfedea0SLionel Sambuc if ((*auth_data)->val == NULL) {
93ebfedea0SLionel Sambuc free(*auth_data);
94ebfedea0SLionel Sambuc free(buf);
95ebfedea0SLionel Sambuc krb5_set_error_message(context, ENOMEM, N_("malloc: out of memory", ""));
96ebfedea0SLionel Sambuc return ENOMEM;
97ebfedea0SLionel Sambuc }
98ebfedea0SLionel Sambuc
99ebfedea0SLionel Sambuc (*auth_data)->val[0].ad_type = KRB5_AUTHDATA_IF_RELEVANT;
100ebfedea0SLionel Sambuc (*auth_data)->val[0].ad_data.length = len;
101ebfedea0SLionel Sambuc (*auth_data)->val[0].ad_data.data = buf;
102ebfedea0SLionel Sambuc
103ebfedea0SLionel Sambuc return 0;
104ebfedea0SLionel Sambuc }
105ebfedea0SLionel Sambuc
106ebfedea0SLionel Sambuc KRB5_LIB_FUNCTION krb5_error_code KRB5_LIB_CALL
_krb5_build_authenticator(krb5_context context,krb5_auth_context auth_context,krb5_enctype enctype,krb5_creds * cred,Checksum * cksum,krb5_data * result,krb5_key_usage usage)107ebfedea0SLionel Sambuc _krb5_build_authenticator (krb5_context context,
108ebfedea0SLionel Sambuc krb5_auth_context auth_context,
109ebfedea0SLionel Sambuc krb5_enctype enctype,
110ebfedea0SLionel Sambuc krb5_creds *cred,
111ebfedea0SLionel Sambuc Checksum *cksum,
112ebfedea0SLionel Sambuc krb5_data *result,
113ebfedea0SLionel Sambuc krb5_key_usage usage)
114ebfedea0SLionel Sambuc {
115ebfedea0SLionel Sambuc Authenticator auth;
116ebfedea0SLionel Sambuc u_char *buf = NULL;
117ebfedea0SLionel Sambuc size_t buf_size;
118*0a6a1f1dSLionel Sambuc size_t len = 0;
119ebfedea0SLionel Sambuc krb5_error_code ret;
120ebfedea0SLionel Sambuc krb5_crypto crypto;
121ebfedea0SLionel Sambuc
122ebfedea0SLionel Sambuc memset(&auth, 0, sizeof(auth));
123ebfedea0SLionel Sambuc
124ebfedea0SLionel Sambuc auth.authenticator_vno = 5;
125ebfedea0SLionel Sambuc copy_Realm(&cred->client->realm, &auth.crealm);
126ebfedea0SLionel Sambuc copy_PrincipalName(&cred->client->name, &auth.cname);
127ebfedea0SLionel Sambuc
128ebfedea0SLionel Sambuc krb5_us_timeofday (context, &auth.ctime, &auth.cusec);
129ebfedea0SLionel Sambuc
130ebfedea0SLionel Sambuc ret = krb5_auth_con_getlocalsubkey(context, auth_context, &auth.subkey);
131ebfedea0SLionel Sambuc if(ret)
132ebfedea0SLionel Sambuc goto fail;
133ebfedea0SLionel Sambuc
134ebfedea0SLionel Sambuc if (auth_context->flags & KRB5_AUTH_CONTEXT_DO_SEQUENCE) {
135ebfedea0SLionel Sambuc if(auth_context->local_seqnumber == 0)
136ebfedea0SLionel Sambuc krb5_generate_seq_number (context,
137ebfedea0SLionel Sambuc &cred->session,
138ebfedea0SLionel Sambuc &auth_context->local_seqnumber);
139ebfedea0SLionel Sambuc ALLOC(auth.seq_number, 1);
140ebfedea0SLionel Sambuc if(auth.seq_number == NULL) {
141ebfedea0SLionel Sambuc ret = ENOMEM;
142ebfedea0SLionel Sambuc goto fail;
143ebfedea0SLionel Sambuc }
144ebfedea0SLionel Sambuc *auth.seq_number = auth_context->local_seqnumber;
145ebfedea0SLionel Sambuc } else
146ebfedea0SLionel Sambuc auth.seq_number = NULL;
147ebfedea0SLionel Sambuc auth.authorization_data = NULL;
148ebfedea0SLionel Sambuc
149ebfedea0SLionel Sambuc if (cksum) {
150ebfedea0SLionel Sambuc ALLOC(auth.cksum, 1);
151ebfedea0SLionel Sambuc if (auth.cksum == NULL) {
152ebfedea0SLionel Sambuc ret = ENOMEM;
153ebfedea0SLionel Sambuc goto fail;
154ebfedea0SLionel Sambuc }
155ebfedea0SLionel Sambuc ret = copy_Checksum(cksum, auth.cksum);
156ebfedea0SLionel Sambuc if (ret)
157ebfedea0SLionel Sambuc goto fail;
158ebfedea0SLionel Sambuc
159ebfedea0SLionel Sambuc if (auth.cksum->cksumtype == CKSUMTYPE_GSSAPI) {
160ebfedea0SLionel Sambuc /*
161ebfedea0SLionel Sambuc * This is not GSS-API specific, we only enable it for
162ebfedea0SLionel Sambuc * GSS for now
163ebfedea0SLionel Sambuc */
164ebfedea0SLionel Sambuc ret = make_etypelist(context, &auth.authorization_data);
165ebfedea0SLionel Sambuc if (ret)
166ebfedea0SLionel Sambuc goto fail;
167ebfedea0SLionel Sambuc }
168ebfedea0SLionel Sambuc }
169ebfedea0SLionel Sambuc
170ebfedea0SLionel Sambuc /* XXX - Copy more to auth_context? */
171ebfedea0SLionel Sambuc
172ebfedea0SLionel Sambuc auth_context->authenticator->ctime = auth.ctime;
173ebfedea0SLionel Sambuc auth_context->authenticator->cusec = auth.cusec;
174ebfedea0SLionel Sambuc
175ebfedea0SLionel Sambuc ASN1_MALLOC_ENCODE(Authenticator, buf, buf_size, &auth, &len, ret);
176ebfedea0SLionel Sambuc if (ret)
177ebfedea0SLionel Sambuc goto fail;
178ebfedea0SLionel Sambuc if(buf_size != len)
179ebfedea0SLionel Sambuc krb5_abortx(context, "internal error in ASN.1 encoder");
180ebfedea0SLionel Sambuc
181ebfedea0SLionel Sambuc ret = krb5_crypto_init(context, &cred->session, enctype, &crypto);
182ebfedea0SLionel Sambuc if (ret)
183ebfedea0SLionel Sambuc goto fail;
184ebfedea0SLionel Sambuc ret = krb5_encrypt (context,
185ebfedea0SLionel Sambuc crypto,
186ebfedea0SLionel Sambuc usage /* KRB5_KU_AP_REQ_AUTH */,
187ebfedea0SLionel Sambuc buf,
188ebfedea0SLionel Sambuc len,
189ebfedea0SLionel Sambuc result);
190ebfedea0SLionel Sambuc krb5_crypto_destroy(context, crypto);
191ebfedea0SLionel Sambuc
192ebfedea0SLionel Sambuc if (ret)
193ebfedea0SLionel Sambuc goto fail;
194ebfedea0SLionel Sambuc
195ebfedea0SLionel Sambuc fail:
196ebfedea0SLionel Sambuc free_Authenticator (&auth);
197ebfedea0SLionel Sambuc free (buf);
198ebfedea0SLionel Sambuc
199ebfedea0SLionel Sambuc return ret;
200ebfedea0SLionel Sambuc }
201