1/* $NetBSD: hdb.h,v 1.2 2017/01/28 21:31:48 christos Exp $ */
2
3/*
4 * Copyright (c) 1997 - 2007 Kungliga Tekniska Högskolan
5 * (Royal Institute of Technology, Stockholm, Sweden).
6 * All rights reserved.
7 *
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
10 * are met:
11 *
12 * 1. Redistributions of source code must retain the above copyright
13 * notice, this list of conditions and the following disclaimer.
14 *
15 * 2. Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in the
17 * documentation and/or other materials provided with the distribution.
18 *
19 * 3. Neither the name of the Institute nor the names of its contributors
20 * may be used to endorse or promote products derived from this software
21 * without specific prior written permission.
22 *
23 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND
24 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
25 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
26 * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
27 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
28 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
29 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
30 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
31 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
32 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
33 * SUCH DAMAGE.
34 */
35
36/* Id */
37
38#ifndef __HDB_H__
39#define __HDB_H__
40
41#include <stdio.h>
42
43#include <krb5/krb5.h>
44
45#include <krb5/hdb_err.h>
46
47#include <krb5/heim_asn1.h>
48#include <krb5/hdb_asn1.h>
49
50struct hdb_dbinfo;
51
52enum hdb_lockop{ HDB_RLOCK, HDB_WLOCK };
53
54/* flags for various functions */
55#define HDB_F_DECRYPT 1 /* decrypt keys */
56#define HDB_F_REPLACE 2 /* replace entry */
57#define HDB_F_GET_CLIENT 4 /* fetch client */
58#define HDB_F_GET_SERVER 8 /* fetch server */
59#define HDB_F_GET_KRBTGT 16 /* fetch krbtgt */
60#define HDB_F_GET_ANY 28 /* fetch any of client,server,krbtgt */
61#define HDB_F_CANON 32 /* want canonicalition */
62#define HDB_F_ADMIN_DATA 64 /* want data that kdc don't use */
63#define HDB_F_KVNO_SPECIFIED 128 /* we want a particular KVNO */
64#define HDB_F_CURRENT_KVNO 256 /* we want the current KVNO */
65#define HDB_F_LIVE_CLNT_KVNOS 512 /* we want all live keys for pre-auth */
66#define HDB_F_LIVE_SVC_KVNOS 1024 /* we want all live keys for tix */
67#define HDB_F_ALL_KVNOS 2048 /* we want all the keys, live or not */
68#define HDB_F_FOR_AS_REQ 4096 /* fetch is for a AS REQ */
69#define HDB_F_FOR_TGS_REQ 8192 /* fetch is for a TGS REQ */
70#define HDB_F_PRECHECK 16384 /* check that the operation would succeed */
71
72/* hdb_capability_flags */
73#define HDB_CAP_F_HANDLE_ENTERPRISE_PRINCIPAL 1
74#define HDB_CAP_F_HANDLE_PASSWORDS 2
75#define HDB_CAP_F_PASSWORD_UPDATE_KEYS 4
76#define HDB_CAP_F_SHARED_DIRECTORY 8
77
78/* auth status values */
79#define HDB_AUTH_SUCCESS 0
80#define HDB_AUTH_WRONG_PASSWORD 1
81#define HDB_AUTH_INVALID_SIGNATURE 2
82
83/* key usage for master key */
84#define HDB_KU_MKEY 0x484442
85
86typedef struct hdb_master_key_data *hdb_master_key;
87
88/**
89 * hdb_entry_ex is a wrapper structure around the hdb_entry structure
90 * that allows backends to keep a pointer to the backing store, ie in
91 * ->hdb_fetch_kvno(), so that we the kadmin/kpasswd backend gets around to
92 * ->hdb_store(), the backend doesn't need to lookup the entry again.
93 */
94
95typedef struct hdb_entry_ex {
96 void *ctx;
97 hdb_entry entry;
98 void (*free_entry)(krb5_context, struct hdb_entry_ex *);
99} hdb_entry_ex;
100
101
102/**
103 * HDB backend function pointer structure
104 *
105 * The HDB structure is what the KDC and kadmind framework uses to
106 * query the backend database when talking about principals.
107 */
108
109typedef struct HDB {
110 void *hdb_db;
111 void *hdb_dbc; /** don't use, only for DB3 */
112 char *hdb_name;
113 int hdb_master_key_set;
114 hdb_master_key hdb_master_key;
115 int hdb_openp;
116 int hdb_capability_flags;
117 int lock_count;
118 int lock_type;
119 /**
120 * Open (or create) the a Kerberos database.
121 *
122 * Open (or create) the a Kerberos database that was resolved with
123 * hdb_create(). The third and fourth flag to the function are the
124 * same as open(), thus passing O_CREAT will create the data base
125 * if it doesn't exists.
126 *
127 * Then done the caller should call hdb_close(), and to release
128 * all resources hdb_destroy().
129 */
130 krb5_error_code (*hdb_open)(krb5_context, struct HDB*, int, mode_t);
131 /**
132 * Close the database for transaction
133 *
134 * Closes the database for further transactions, wont release any
135 * permanant resources. the database can be ->hdb_open-ed again.
136 */
137 krb5_error_code (*hdb_close)(krb5_context, struct HDB*);
138 /**
139 * Free an entry after use.
140 */
141 void (*hdb_free)(krb5_context, struct HDB*, hdb_entry_ex*);
142 /**
143 * Fetch an entry from the backend
144 *
145 * Fetch an entry from the backend, flags are what type of entry
146 * should be fetch: client, server, krbtgt.
147 * knvo (if specified and flags HDB_F_KVNO_SPECIFIED set) is the kvno to get
148 */
149 krb5_error_code (*hdb_fetch_kvno)(krb5_context, struct HDB*,
150 krb5_const_principal, unsigned, krb5_kvno,
151 hdb_entry_ex*);
152 /**
153 * Store an entry to database
154 */
155 krb5_error_code (*hdb_store)(krb5_context, struct HDB*,
156 unsigned, hdb_entry_ex*);
157 /**
158 * Remove an entry from the database.
159 */
160 krb5_error_code (*hdb_remove)(krb5_context, struct HDB*,
161 unsigned, krb5_const_principal);
162 /**
163 * As part of iteration, fetch one entry
164 */
165 krb5_error_code (*hdb_firstkey)(krb5_context, struct HDB*,
166 unsigned, hdb_entry_ex*);
167 /**
168 * As part of iteration, fetch next entry
169 */
170 krb5_error_code (*hdb_nextkey)(krb5_context, struct HDB*,
171 unsigned, hdb_entry_ex*);
172 /**
173 * Lock database
174 *
175 * A lock can only be held by one consumers. Transaction can still
176 * happen on the database while the lock is held, so the entry is
177 * only useful for syncroning creation of the database and renaming of the database.
178 */
179 krb5_error_code (*hdb_lock)(krb5_context, struct HDB*, int);
180 /**
181 * Unlock database
182 */
183 krb5_error_code (*hdb_unlock)(krb5_context, struct HDB*);
184 /**
185 * Rename the data base.
186 *
187 * Assume that the database is not hdb_open'ed and not locked.
188 */
189 krb5_error_code (*hdb_rename)(krb5_context, struct HDB*, const char*);
190 /**
191 * Get an hdb_entry from a classical DB backend
192 *
193 * This function takes a principal key (krb5_data) and returns all
194 * data related to principal in the return krb5_data. The returned
195 * encoded entry is of type hdb_entry or hdb_entry_alias.
196 */
197 krb5_error_code (*hdb__get)(krb5_context, struct HDB*,
198 krb5_data, krb5_data*);
199 /**
200 * Store an hdb_entry from a classical DB backend
201 *
202 * This function takes a principal key (krb5_data) and encoded
203 * hdb_entry or hdb_entry_alias as the data to store.
204 *
205 * For a file-based DB, this must synchronize to disk when done.
206 * This is sub-optimal for kadm5_s_rename_principal(), and for
207 * kadm5_s_modify_principal() when using principal aliases; to
208 * improve this so that only one fsync() need be done
209 * per-transaction will require HDB API extensions.
210 */
211 krb5_error_code (*hdb__put)(krb5_context, struct HDB*, int,
212 krb5_data, krb5_data);
213 /**
214 * Delete and hdb_entry from a classical DB backend
215 *
216 * This function takes a principal key (krb5_data) naming the record
217 * to delete.
218 *
219 * Same discussion as in @ref HDB::hdb__put
220 */
221 krb5_error_code (*hdb__del)(krb5_context, struct HDB*, krb5_data);
222 /**
223 * Destroy the handle to the database.
224 *
225 * Destroy the handle to the database, deallocate all memory and
226 * related resources. Does not remove any permanent data. Its the
227 * logical reverse of hdb_create() function that is the entry
228 * point for the module.
229 */
230 krb5_error_code (*hdb_destroy)(krb5_context, struct HDB*);
231 /**
232 * Get the list of realms this backend handles.
233 * This call is optional to support. The returned realms are used
234 * for announcing the realms over bonjour. Free returned array
235 * with krb5_free_host_realm().
236 */
237 krb5_error_code (*hdb_get_realms)(krb5_context, struct HDB *, krb5_realm **);
238 /**
239 * Change password.
240 *
241 * Will update keys for the entry when given password. The new
242 * keys must be written into the entry and will then later be
243 * ->hdb_store() into the database. The backend will still perform
244 * all other operations, increasing the kvno, and update
245 * modification timestamp.
246 *
247 * The backend needs to call _kadm5_set_keys() and perform password
248 * quality checks.
249 */
250 krb5_error_code (*hdb_password)(krb5_context, struct HDB*, hdb_entry_ex*, const char *, int);
251
252 /**
253 * Auth feedback
254 *
255 * This is a feedback call that allows backends that provides
256 * lockout functionality to register failure and/or successes.
257 *
258 * In case the entry is locked out, the backend should set the
259 * hdb_entry.flags.locked-out flag.
260 */
261 krb5_error_code (*hdb_auth_status)(krb5_context, struct HDB *, hdb_entry_ex *, int);
262 /**
263 * Check if delegation is allowed.
264 */
265 krb5_error_code (*hdb_check_constrained_delegation)(krb5_context, struct HDB *, hdb_entry_ex *, krb5_const_principal);
266
267 /**
268 * Check if this name is an alias for the supplied client for PKINIT userPrinicpalName logins
269 */
270 krb5_error_code (*hdb_check_pkinit_ms_upn_match)(krb5_context, struct HDB *, hdb_entry_ex *, krb5_const_principal);
271
272 /**
273 * Check if s4u2self is allowed from this client to this server
274 */
275 krb5_error_code (*hdb_check_s4u2self)(krb5_context, struct HDB *, hdb_entry_ex *, krb5_const_principal);
276}HDB;
277
278#define HDB_INTERFACE_VERSION 9
279
280struct hdb_method {
281 int version;
282 krb5_error_code (*init)(krb5_context, void **);
283 void (*fini)(void *);
284 const char *prefix;
285 krb5_error_code (*create)(krb5_context, HDB **, const char *filename);
286};
287
288/* dump entry format, for hdb_print_entry() */
289typedef enum hdb_dump_format {
290 HDB_DUMP_HEIMDAL = 0,
291 HDB_DUMP_MIT = 1,
292} hdb_dump_format_t;
293
294struct hdb_print_entry_arg {
295 FILE *out;
296 hdb_dump_format_t fmt;
297};
298
299typedef krb5_error_code (*hdb_foreach_func_t)(krb5_context, HDB*,
300 hdb_entry_ex*, void*);
301extern krb5_kt_ops hdb_kt_ops;
302extern krb5_kt_ops hdb_get_kt_ops;
303
304extern const int hdb_interface_version;
305
306#include <krb5/hdb-protos.h>
307
308#endif /* __HDB_H__ */
309