Home | History | Annotate | Line # | Download | only in kdc
      1 /*	$NetBSD: default_config.c,v 1.3 2023/06/19 21:41:41 christos Exp $	*/
      2 
      3 /*
      4  * Copyright (c) 1997-2007 Kungliga Tekniska Hgskolan
      5  * (Royal Institute of Technology, Stockholm, Sweden).
      6  * All rights reserved.
      7  *
      8  * Portions Copyright (c) 2009 Apple Inc. All rights reserved.
      9  *
     10  * Redistribution and use in source and binary forms, with or without
     11  * modification, are permitted provided that the following conditions
     12  * are met:
     13  *
     14  * 1. Redistributions of source code must retain the above copyright
     15  *    notice, this list of conditions and the following disclaimer.
     16  *
     17  * 2. Redistributions in binary form must reproduce the above copyright
     18  *    notice, this list of conditions and the following disclaimer in the
     19  *    documentation and/or other materials provided with the distribution.
     20  *
     21  * 3. Neither the name of the Institute nor the names of its contributors
     22  *    may be used to endorse or promote products derived from this software
     23  *    without specific prior written permission.
     24  *
     25  * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND
     26  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
     27  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
     28  * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
     29  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
     30  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
     31  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
     32  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
     33  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
     34  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
     35  * SUCH DAMAGE.
     36  */
     37 
     38 #include "kdc_locl.h"
     39 #include <krb5/getarg.h>
     40 #include <krb5/parse_bytes.h>
     41 
     42 krb5_error_code
     43 krb5_kdc_get_config(krb5_context context, krb5_kdc_configuration **config)
     44 {
     45     krb5_kdc_configuration *c;
     46 
     47     c = calloc(1, sizeof(*c));
     48     if (c == NULL) {
     49 	krb5_set_error_message(context, ENOMEM, "malloc: out of memory");
     50 	return ENOMEM;
     51     }
     52 
     53     c->num_kdc_processes = -1;
     54     c->require_preauth = TRUE;
     55     c->kdc_warn_pwexpire = 0;
     56     c->encode_as_rep_as_tgs_rep = FALSE;
     57     c->tgt_use_strongest_session_key = FALSE;
     58     c->preauth_use_strongest_session_key = FALSE;
     59     c->svc_use_strongest_session_key = FALSE;
     60     c->use_strongest_server_key = TRUE;
     61     c->check_ticket_addresses = TRUE;
     62     c->allow_null_ticket_addresses = TRUE;
     63     c->allow_anonymous = FALSE;
     64     c->historical_anon_realm = FALSE;
     65     c->strict_nametypes = FALSE;
     66     c->trpolicy = TRPOLICY_ALWAYS_CHECK;
     67     c->enable_pkinit = FALSE;
     68     c->pkinit_princ_in_cert = TRUE;
     69     c->pkinit_require_binding = TRUE;
     70     c->db = NULL;
     71     c->num_db = 0;
     72     c->logf = NULL;
     73 
     74     c->num_kdc_processes =
     75         krb5_config_get_int_default(context, NULL, c->num_kdc_processes,
     76 				    "kdc", "num-kdc-processes", NULL);
     77 
     78     c->require_preauth =
     79 	krb5_config_get_bool_default(context, NULL,
     80 				     c->require_preauth,
     81 				     "kdc", "require-preauth", NULL);
     82 #ifdef DIGEST
     83     c->enable_digest =
     84 	krb5_config_get_bool_default(context, NULL,
     85 				     FALSE,
     86 				     "kdc", "enable-digest", NULL);
     87 
     88     {
     89 	const char *digests;
     90 
     91 	digests = krb5_config_get_string(context, NULL,
     92 					 "kdc",
     93 					 "digests_allowed", NULL);
     94 	if (digests == NULL)
     95 	    digests = "ntlm-v2";
     96 	c->digests_allowed = parse_flags(digests,_kdc_digestunits, 0);
     97 	if (c->digests_allowed == -1) {
     98 	    kdc_log(context, c, 0,
     99 		    "unparsable digest units (%s), turning off digest",
    100 		    digests);
    101 	    c->enable_digest = 0;
    102 	} else if (c->digests_allowed == 0) {
    103 	    kdc_log(context, c, 0,
    104 		    "no digest enable, turning digest off",
    105 		    digests);
    106 	    c->enable_digest = 0;
    107 	}
    108     }
    109 #endif
    110 
    111 #ifdef KX509
    112     c->enable_kx509 =
    113 	krb5_config_get_bool_default(context, NULL,
    114 				     FALSE,
    115 				     "kdc", "enable-kx509", NULL);
    116 
    117     if (c->enable_kx509) {
    118 	c->kx509_template =
    119 	    krb5_config_get_string(context, NULL,
    120 				   "kdc", "kx509_template", NULL);
    121 	c->kx509_ca =
    122 	    krb5_config_get_string(context, NULL,
    123 				   "kdc", "kx509_ca", NULL);
    124 	if (c->kx509_ca == NULL || c->kx509_template == NULL) {
    125 	    kdc_log(context, c, 0,
    126 		    "missing kx509 configuration, turning off");
    127 	    c->enable_kx509 = FALSE;
    128 	}
    129     }
    130 #endif
    131 
    132     c->tgt_use_strongest_session_key =
    133 	krb5_config_get_bool_default(context, NULL,
    134 				     c->tgt_use_strongest_session_key,
    135 				     "kdc",
    136 				     "tgt-use-strongest-session-key", NULL);
    137     c->preauth_use_strongest_session_key =
    138 	krb5_config_get_bool_default(context, NULL,
    139 				     c->preauth_use_strongest_session_key,
    140 				     "kdc",
    141 				     "preauth-use-strongest-session-key", NULL);
    142     c->svc_use_strongest_session_key =
    143 	krb5_config_get_bool_default(context, NULL,
    144 				     c->svc_use_strongest_session_key,
    145 				     "kdc",
    146 				     "svc-use-strongest-session-key", NULL);
    147     c->use_strongest_server_key =
    148 	krb5_config_get_bool_default(context, NULL,
    149 				     c->use_strongest_server_key,
    150 				     "kdc",
    151 				     "use-strongest-server-key", NULL);
    152 
    153     c->check_ticket_addresses =
    154 	krb5_config_get_bool_default(context, NULL,
    155 				     c->check_ticket_addresses,
    156 				     "kdc",
    157 				     "check-ticket-addresses", NULL);
    158     c->allow_null_ticket_addresses =
    159 	krb5_config_get_bool_default(context, NULL,
    160 				     c->allow_null_ticket_addresses,
    161 				     "kdc",
    162 				     "allow-null-ticket-addresses", NULL);
    163 
    164     c->allow_anonymous =
    165 	krb5_config_get_bool_default(context, NULL,
    166 				     c->allow_anonymous,
    167 				     "kdc",
    168 				     "allow-anonymous", NULL);
    169 
    170     c->historical_anon_realm =
    171 	krb5_config_get_bool_default(context, NULL,
    172 				     c->historical_anon_realm,
    173 				     "kdc",
    174 				     "historical_anon_realm", NULL);
    175 
    176     c->strict_nametypes =
    177 	krb5_config_get_bool_default(context, NULL,
    178 				     c->strict_nametypes,
    179 				     "kdc",
    180 				     "strict-nametypes", NULL);
    181 
    182     c->max_datagram_reply_length =
    183 	krb5_config_get_int_default(context,
    184 				    NULL,
    185 				    1400,
    186 				    "kdc",
    187 				    "max-kdc-datagram-reply-length",
    188 				    NULL);
    189 
    190     {
    191 	const char *trpolicy_str;
    192 
    193 	trpolicy_str =
    194 	    krb5_config_get_string_default(context, NULL, "DEFAULT", "kdc",
    195 					   "transited-policy", NULL);
    196 	if(strcasecmp(trpolicy_str, "always-check") == 0) {
    197 	    c->trpolicy = TRPOLICY_ALWAYS_CHECK;
    198 	} else if(strcasecmp(trpolicy_str, "allow-per-principal") == 0) {
    199 	    c->trpolicy = TRPOLICY_ALLOW_PER_PRINCIPAL;
    200 	} else if(strcasecmp(trpolicy_str, "always-honour-request") == 0) {
    201 	    c->trpolicy = TRPOLICY_ALWAYS_HONOUR_REQUEST;
    202 	} else if(strcasecmp(trpolicy_str, "DEFAULT") == 0) {
    203 	    /* default */
    204 	} else {
    205 	    kdc_log(context, c, 0,
    206 		    "unknown transited-policy: %s, "
    207 		    "reverting to default (always-check)",
    208 		    trpolicy_str);
    209 	}
    210     }
    211 
    212     c->encode_as_rep_as_tgs_rep =
    213 	krb5_config_get_bool_default(context, NULL,
    214 				     c->encode_as_rep_as_tgs_rep,
    215 				     "kdc",
    216 				     "encode_as_rep_as_tgs_rep", NULL);
    217 
    218     c->kdc_warn_pwexpire =
    219 	krb5_config_get_time_default (context, NULL,
    220 				      c->kdc_warn_pwexpire,
    221 				      "kdc", "kdc_warn_pwexpire", NULL);
    222 
    223 
    224     c->enable_pkinit =
    225 	krb5_config_get_bool_default(context,
    226 				     NULL,
    227 				     c->enable_pkinit,
    228 				     "kdc",
    229 				     "enable-pkinit",
    230 				     NULL);
    231 
    232 
    233     c->pkinit_kdc_identity =
    234 	krb5_config_get_string(context, NULL,
    235 			       "kdc", "pkinit_identity", NULL);
    236     c->pkinit_kdc_anchors =
    237 	krb5_config_get_string(context, NULL,
    238 			       "kdc", "pkinit_anchors", NULL);
    239     c->pkinit_kdc_cert_pool =
    240 	krb5_config_get_strings(context, NULL,
    241 				"kdc", "pkinit_pool", NULL);
    242     c->pkinit_kdc_revoke =
    243 	krb5_config_get_strings(context, NULL,
    244 				"kdc", "pkinit_revoke", NULL);
    245     c->pkinit_kdc_ocsp_file =
    246 	krb5_config_get_string(context, NULL,
    247 			       "kdc", "pkinit_kdc_ocsp", NULL);
    248     c->pkinit_kdc_friendly_name =
    249 	krb5_config_get_string(context, NULL,
    250 			       "kdc", "pkinit_kdc_friendly_name", NULL);
    251     c->pkinit_princ_in_cert =
    252 	krb5_config_get_bool_default(context, NULL,
    253 				     c->pkinit_princ_in_cert,
    254 				     "kdc",
    255 				     "pkinit_principal_in_certificate",
    256 				     NULL);
    257     c->pkinit_require_binding =
    258 	krb5_config_get_bool_default(context, NULL,
    259 				     c->pkinit_require_binding,
    260 				     "kdc",
    261 				     "pkinit_win2k_require_binding",
    262 				     NULL);
    263     c->pkinit_dh_min_bits =
    264 	krb5_config_get_int_default(context, NULL,
    265 				    0,
    266 				    "kdc", "pkinit_dh_min_bits", NULL);
    267 
    268     *config = c;
    269 
    270     return 0;
    271 }
    272 
    273 krb5_error_code
    274 krb5_kdc_pkinit_config(krb5_context context, krb5_kdc_configuration *config)
    275 {
    276 #ifdef PKINIT
    277 #ifdef __APPLE__
    278     config->enable_pkinit = 1;
    279 
    280     if (config->pkinit_kdc_identity == NULL) {
    281 	if (config->pkinit_kdc_friendly_name == NULL)
    282 	    config->pkinit_kdc_friendly_name =
    283 		strdup("O=System Identity,CN=com.apple.kerberos.kdc");
    284 	config->pkinit_kdc_identity = strdup("KEYCHAIN:");
    285     }
    286     if (config->pkinit_kdc_anchors == NULL)
    287 	config->pkinit_kdc_anchors = strdup("KEYCHAIN:");
    288 
    289 #endif /* __APPLE__ */
    290 
    291     if (config->enable_pkinit) {
    292 	if (config->pkinit_kdc_identity == NULL)
    293 	    krb5_errx(context, 1, "pkinit enabled but no identity");
    294 
    295 	if (config->pkinit_kdc_anchors == NULL)
    296 	    krb5_errx(context, 1, "pkinit enabled but no X509 anchors");
    297 
    298 	krb5_kdc_pk_initialize(context, config,
    299 			       config->pkinit_kdc_identity,
    300 			       config->pkinit_kdc_anchors,
    301 			       config->pkinit_kdc_cert_pool,
    302 			       config->pkinit_kdc_revoke);
    303 
    304     }
    305 
    306     return 0;
    307 #endif /* PKINIT */
    308 }
    309