1b528cefcSMark Murray /*
2*ae771770SStanislav Sedov * Copyright (c) 1999-2005 Kungliga Tekniska Högskolan
3b528cefcSMark Murray * (Royal Institute of Technology, Stockholm, Sweden).
4b528cefcSMark Murray * All rights reserved.
5b528cefcSMark Murray *
6b528cefcSMark Murray * Redistribution and use in source and binary forms, with or without
7b528cefcSMark Murray * modification, are permitted provided that the following conditions
8b528cefcSMark Murray * are met:
9b528cefcSMark Murray *
10b528cefcSMark Murray * 1. Redistributions of source code must retain the above copyright
11b528cefcSMark Murray * notice, this list of conditions and the following disclaimer.
12b528cefcSMark Murray *
13b528cefcSMark Murray * 2. Redistributions in binary form must reproduce the above copyright
14b528cefcSMark Murray * notice, this list of conditions and the following disclaimer in the
15b528cefcSMark Murray * documentation and/or other materials provided with the distribution.
16b528cefcSMark Murray *
17b528cefcSMark Murray * 3. Neither the name of KTH nor the names of its contributors may be
18b528cefcSMark Murray * used to endorse or promote products derived from this software without
19b528cefcSMark Murray * specific prior written permission.
20b528cefcSMark Murray *
21b528cefcSMark Murray * THIS SOFTWARE IS PROVIDED BY KTH AND ITS CONTRIBUTORS ``AS IS'' AND ANY
22b528cefcSMark Murray * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23b528cefcSMark Murray * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
24b528cefcSMark Murray * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL KTH OR ITS CONTRIBUTORS BE
25b528cefcSMark Murray * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
26b528cefcSMark Murray * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
27b528cefcSMark Murray * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
28b528cefcSMark Murray * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
29b528cefcSMark Murray * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
30b528cefcSMark Murray * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
31b528cefcSMark Murray * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
32b528cefcSMark Murray
33b528cefcSMark Murray #include "hdb_locl.h"
34c19800e8SDoug Rabson #include <hex.h>
35b528cefcSMark Murray #include <ctype.h>
36b528cefcSMark Murray
37b528cefcSMark Murray /*
38b528cefcSMark Murray This is the present contents of a dump line. This might change at
39b528cefcSMark Murray any time. Fields are separated by white space.
40b528cefcSMark Murray
41b528cefcSMark Murray principal
42b528cefcSMark Murray keyblock
43b528cefcSMark Murray kvno
44b528cefcSMark Murray keys...
45b528cefcSMark Murray mkvno
46b528cefcSMark Murray enctype
47b528cefcSMark Murray keyvalue
48b528cefcSMark Murray salt (- means use normal salt)
49b528cefcSMark Murray creation date and principal
50b528cefcSMark Murray modification date and principal
51b528cefcSMark Murray principal valid from date (not used)
52b528cefcSMark Murray principal valid end date (not used)
53b528cefcSMark Murray principal key expires (not used)
54b528cefcSMark Murray max ticket life
55b528cefcSMark Murray max renewable life
56b528cefcSMark Murray flags
574137ff4cSJacques Vidrine generation number
58b528cefcSMark Murray */
59b528cefcSMark Murray
604137ff4cSJacques Vidrine static krb5_error_code
append_string(krb5_context context,krb5_storage * sp,const char * fmt,...)614137ff4cSJacques Vidrine append_string(krb5_context context, krb5_storage *sp, const char *fmt, ...)
62b528cefcSMark Murray {
634137ff4cSJacques Vidrine krb5_error_code ret;
644137ff4cSJacques Vidrine char *s;
654137ff4cSJacques Vidrine va_list ap;
664137ff4cSJacques Vidrine va_start(ap, fmt);
674137ff4cSJacques Vidrine vasprintf(&s, fmt, ap);
684137ff4cSJacques Vidrine va_end(ap);
694137ff4cSJacques Vidrine if(s == NULL) {
70*ae771770SStanislav Sedov krb5_set_error_message(context, ENOMEM, "malloc: out of memory");
714137ff4cSJacques Vidrine return ENOMEM;
724137ff4cSJacques Vidrine }
738373020dSJacques Vidrine ret = krb5_storage_write(sp, s, strlen(s));
744137ff4cSJacques Vidrine free(s);
754137ff4cSJacques Vidrine return ret;
764137ff4cSJacques Vidrine }
774137ff4cSJacques Vidrine
784137ff4cSJacques Vidrine static krb5_error_code
append_hex(krb5_context context,krb5_storage * sp,krb5_data * data)794137ff4cSJacques Vidrine append_hex(krb5_context context, krb5_storage *sp, krb5_data *data)
804137ff4cSJacques Vidrine {
81*ae771770SStanislav Sedov int printable = 1;
82*ae771770SStanislav Sedov size_t i;
83b528cefcSMark Murray char *p;
84b528cefcSMark Murray
85b528cefcSMark Murray p = data->data;
86b528cefcSMark Murray for(i = 0; i < data->length; i++)
87b528cefcSMark Murray if(!isalnum((unsigned char)p[i]) && p[i] != '.'){
884137ff4cSJacques Vidrine printable = 0;
89b528cefcSMark Murray break;
90b528cefcSMark Murray }
914137ff4cSJacques Vidrine if(printable)
924137ff4cSJacques Vidrine return append_string(context, sp, "\"%.*s\"",
934137ff4cSJacques Vidrine data->length, data->data);
94c19800e8SDoug Rabson hex_encode(data->data, data->length, &p);
95c19800e8SDoug Rabson append_string(context, sp, "%s", p);
96c19800e8SDoug Rabson free(p);
974137ff4cSJacques Vidrine return 0;
98b528cefcSMark Murray }
99b528cefcSMark Murray
100b528cefcSMark Murray static char *
time2str(time_t t)101b528cefcSMark Murray time2str(time_t t)
102b528cefcSMark Murray {
103b528cefcSMark Murray static char buf[128];
104b528cefcSMark Murray strftime(buf, sizeof(buf), "%Y%m%d%H%M%S", gmtime(&t));
105b528cefcSMark Murray return buf;
106b528cefcSMark Murray }
107b528cefcSMark Murray
108b528cefcSMark Murray static krb5_error_code
append_event(krb5_context context,krb5_storage * sp,Event * ev)1094137ff4cSJacques Vidrine append_event(krb5_context context, krb5_storage *sp, Event *ev)
110b528cefcSMark Murray {
1114137ff4cSJacques Vidrine char *pr = NULL;
112b528cefcSMark Murray krb5_error_code ret;
1134137ff4cSJacques Vidrine if(ev == NULL)
1144137ff4cSJacques Vidrine return append_string(context, sp, "- ");
1154137ff4cSJacques Vidrine if (ev->principal != NULL) {
116b528cefcSMark Murray ret = krb5_unparse_name(context, ev->principal, &pr);
117b528cefcSMark Murray if(ret)
118b528cefcSMark Murray return ret;
119b528cefcSMark Murray }
1204137ff4cSJacques Vidrine ret = append_string(context, sp, "%s:%s ",
1214137ff4cSJacques Vidrine time2str(ev->time), pr ? pr : "UNKNOWN");
122b528cefcSMark Murray free(pr);
1234137ff4cSJacques Vidrine return ret;
124b528cefcSMark Murray }
125b528cefcSMark Murray
1264137ff4cSJacques Vidrine static krb5_error_code
entry2string_int(krb5_context context,krb5_storage * sp,hdb_entry * ent)1274137ff4cSJacques Vidrine entry2string_int (krb5_context context, krb5_storage *sp, hdb_entry *ent)
128b528cefcSMark Murray {
129b528cefcSMark Murray char *p;
130*ae771770SStanislav Sedov size_t i;
131b528cefcSMark Murray krb5_error_code ret;
132b528cefcSMark Murray
133b528cefcSMark Murray /* --- principal */
134b528cefcSMark Murray ret = krb5_unparse_name(context, ent->principal, &p);
135b528cefcSMark Murray if(ret)
136b528cefcSMark Murray return ret;
1374137ff4cSJacques Vidrine append_string(context, sp, "%s ", p);
138b528cefcSMark Murray free(p);
139b528cefcSMark Murray /* --- kvno */
1404137ff4cSJacques Vidrine append_string(context, sp, "%d", ent->kvno);
141b528cefcSMark Murray /* --- keys */
142b528cefcSMark Murray for(i = 0; i < ent->keys.len; i++){
143b528cefcSMark Murray /* --- mkvno, keytype */
144b528cefcSMark Murray if(ent->keys.val[i].mkvno)
1454137ff4cSJacques Vidrine append_string(context, sp, ":%d:%d:",
146b528cefcSMark Murray *ent->keys.val[i].mkvno,
147b528cefcSMark Murray ent->keys.val[i].key.keytype);
148b528cefcSMark Murray else
1494137ff4cSJacques Vidrine append_string(context, sp, "::%d:",
150b528cefcSMark Murray ent->keys.val[i].key.keytype);
151b528cefcSMark Murray /* --- keydata */
1524137ff4cSJacques Vidrine append_hex(context, sp, &ent->keys.val[i].key.keyvalue);
1534137ff4cSJacques Vidrine append_string(context, sp, ":");
154b528cefcSMark Murray /* --- salt */
155b528cefcSMark Murray if(ent->keys.val[i].salt){
1564137ff4cSJacques Vidrine append_string(context, sp, "%u/", ent->keys.val[i].salt->type);
1574137ff4cSJacques Vidrine append_hex(context, sp, &ent->keys.val[i].salt->salt);
158b528cefcSMark Murray }else
1594137ff4cSJacques Vidrine append_string(context, sp, "-");
160b528cefcSMark Murray }
1614137ff4cSJacques Vidrine append_string(context, sp, " ");
162b528cefcSMark Murray /* --- created by */
1634137ff4cSJacques Vidrine append_event(context, sp, &ent->created_by);
164b528cefcSMark Murray /* --- modified by */
1654137ff4cSJacques Vidrine append_event(context, sp, ent->modified_by);
166b528cefcSMark Murray
167b528cefcSMark Murray /* --- valid start */
168b528cefcSMark Murray if(ent->valid_start)
1694137ff4cSJacques Vidrine append_string(context, sp, "%s ", time2str(*ent->valid_start));
170b528cefcSMark Murray else
1714137ff4cSJacques Vidrine append_string(context, sp, "- ");
172b528cefcSMark Murray
173b528cefcSMark Murray /* --- valid end */
174b528cefcSMark Murray if(ent->valid_end)
1754137ff4cSJacques Vidrine append_string(context, sp, "%s ", time2str(*ent->valid_end));
176b528cefcSMark Murray else
1774137ff4cSJacques Vidrine append_string(context, sp, "- ");
178b528cefcSMark Murray
179b528cefcSMark Murray /* --- password ends */
180b528cefcSMark Murray if(ent->pw_end)
1814137ff4cSJacques Vidrine append_string(context, sp, "%s ", time2str(*ent->pw_end));
182b528cefcSMark Murray else
1834137ff4cSJacques Vidrine append_string(context, sp, "- ");
184b528cefcSMark Murray
185b528cefcSMark Murray /* --- max life */
1864137ff4cSJacques Vidrine if(ent->max_life)
1874137ff4cSJacques Vidrine append_string(context, sp, "%d ", *ent->max_life);
1884137ff4cSJacques Vidrine else
1894137ff4cSJacques Vidrine append_string(context, sp, "- ");
190b528cefcSMark Murray
191b528cefcSMark Murray /* --- max renewable life */
1924137ff4cSJacques Vidrine if(ent->max_renew)
1934137ff4cSJacques Vidrine append_string(context, sp, "%d ", *ent->max_renew);
1944137ff4cSJacques Vidrine else
1954137ff4cSJacques Vidrine append_string(context, sp, "- ");
196b528cefcSMark Murray
197b528cefcSMark Murray /* --- flags */
1984137ff4cSJacques Vidrine append_string(context, sp, "%d ", HDBFlags2int(ent->flags));
199b528cefcSMark Murray
2004137ff4cSJacques Vidrine /* --- generation number */
2014137ff4cSJacques Vidrine if(ent->generation) {
2024137ff4cSJacques Vidrine append_string(context, sp, "%s:%d:%d ", time2str(ent->generation->time),
2034137ff4cSJacques Vidrine ent->generation->usec,
2044137ff4cSJacques Vidrine ent->generation->gen);
2054137ff4cSJacques Vidrine } else
2064137ff4cSJacques Vidrine append_string(context, sp, "- ");
207b528cefcSMark Murray
208c19800e8SDoug Rabson /* --- extensions */
209c19800e8SDoug Rabson if(ent->extensions && ent->extensions->len > 0) {
210c19800e8SDoug Rabson for(i = 0; i < ent->extensions->len; i++) {
211c19800e8SDoug Rabson void *d;
212*ae771770SStanislav Sedov size_t size, sz = 0;
213c19800e8SDoug Rabson
214c19800e8SDoug Rabson ASN1_MALLOC_ENCODE(HDB_extension, d, size,
215c19800e8SDoug Rabson &ent->extensions->val[i], &sz, ret);
216c19800e8SDoug Rabson if (ret) {
217*ae771770SStanislav Sedov krb5_clear_error_message(context);
218c19800e8SDoug Rabson return ret;
219c19800e8SDoug Rabson }
220c19800e8SDoug Rabson if(size != sz)
221c19800e8SDoug Rabson krb5_abortx(context, "internal asn.1 encoder error");
222c19800e8SDoug Rabson
223c19800e8SDoug Rabson if (hex_encode(d, size, &p) < 0) {
224c19800e8SDoug Rabson free(d);
225*ae771770SStanislav Sedov krb5_set_error_message(context, ENOMEM, "malloc: out of memory");
226c19800e8SDoug Rabson return ENOMEM;
227c19800e8SDoug Rabson }
228c19800e8SDoug Rabson
229c19800e8SDoug Rabson free(d);
230c19800e8SDoug Rabson append_string(context, sp, "%s%s", p,
231c19800e8SDoug Rabson ent->extensions->len - 1 != i ? ":" : "");
232c19800e8SDoug Rabson free(p);
233c19800e8SDoug Rabson }
234c19800e8SDoug Rabson } else
235c19800e8SDoug Rabson append_string(context, sp, "-");
236c19800e8SDoug Rabson
237c19800e8SDoug Rabson
238b528cefcSMark Murray return 0;
239b528cefcSMark Murray }
240b528cefcSMark Murray
2414137ff4cSJacques Vidrine krb5_error_code
hdb_entry2string(krb5_context context,hdb_entry * ent,char ** str)2424137ff4cSJacques Vidrine hdb_entry2string (krb5_context context, hdb_entry *ent, char **str)
2434137ff4cSJacques Vidrine {
2444137ff4cSJacques Vidrine krb5_error_code ret;
2454137ff4cSJacques Vidrine krb5_data data;
2464137ff4cSJacques Vidrine krb5_storage *sp;
2474137ff4cSJacques Vidrine
2484137ff4cSJacques Vidrine sp = krb5_storage_emem();
2494137ff4cSJacques Vidrine if(sp == NULL) {
250*ae771770SStanislav Sedov krb5_set_error_message(context, ENOMEM, "malloc: out of memory");
2514137ff4cSJacques Vidrine return ENOMEM;
2524137ff4cSJacques Vidrine }
2534137ff4cSJacques Vidrine
2544137ff4cSJacques Vidrine ret = entry2string_int(context, sp, ent);
2554137ff4cSJacques Vidrine if(ret) {
2564137ff4cSJacques Vidrine krb5_storage_free(sp);
2574137ff4cSJacques Vidrine return ret;
2584137ff4cSJacques Vidrine }
2594137ff4cSJacques Vidrine
2608373020dSJacques Vidrine krb5_storage_write(sp, "\0", 1);
2614137ff4cSJacques Vidrine krb5_storage_to_data(sp, &data);
2624137ff4cSJacques Vidrine krb5_storage_free(sp);
2634137ff4cSJacques Vidrine *str = data.data;
2644137ff4cSJacques Vidrine return 0;
2654137ff4cSJacques Vidrine }
2664137ff4cSJacques Vidrine
267b528cefcSMark Murray /* print a hdb_entry to (FILE*)data; suitable for hdb_foreach */
268b528cefcSMark Murray
269b528cefcSMark Murray krb5_error_code
hdb_print_entry(krb5_context context,HDB * db,hdb_entry_ex * entry,void * data)270c19800e8SDoug Rabson hdb_print_entry(krb5_context context, HDB *db, hdb_entry_ex *entry, void *data)
271b528cefcSMark Murray {
2724137ff4cSJacques Vidrine krb5_error_code ret;
2734137ff4cSJacques Vidrine krb5_storage *sp;
2744137ff4cSJacques Vidrine
2754137ff4cSJacques Vidrine FILE *f = data;
2764137ff4cSJacques Vidrine
2774137ff4cSJacques Vidrine fflush(f);
2784137ff4cSJacques Vidrine sp = krb5_storage_from_fd(fileno(f));
2794137ff4cSJacques Vidrine if(sp == NULL) {
280*ae771770SStanislav Sedov krb5_set_error_message(context, ENOMEM, "malloc: out of memory");
2814137ff4cSJacques Vidrine return ENOMEM;
2824137ff4cSJacques Vidrine }
2834137ff4cSJacques Vidrine
284c19800e8SDoug Rabson ret = entry2string_int(context, sp, &entry->entry);
2854137ff4cSJacques Vidrine if(ret) {
2864137ff4cSJacques Vidrine krb5_storage_free(sp);
2874137ff4cSJacques Vidrine return ret;
2884137ff4cSJacques Vidrine }
2894137ff4cSJacques Vidrine
2908373020dSJacques Vidrine krb5_storage_write(sp, "\n", 1);
2914137ff4cSJacques Vidrine krb5_storage_free(sp);
292b528cefcSMark Murray return 0;
293b528cefcSMark Murray }
294