Line data Source code
1 : /* 2 : Unix SMB/CIFS implementation. 3 : 4 : Database Glue between Samba and the KDC 5 : 6 : Copyright (C) Guenther Deschner <gd@samba.org> 2014 7 : Copyright (C) Andreas Schneider <asn@samba.org> 2014 8 : 9 : This program is free software; you can redistribute it and/or modify 10 : it under the terms of the GNU General Public License as published by 11 : the Free Software Foundation; either version 3 of the License, or 12 : (at your option) any later version. 13 : 14 : This program is distributed in the hope that it will be useful, 15 : but WITHOUT ANY WARRANTY; without even the implied warranty of 16 : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 : GNU General Public License for more details. 18 : 19 : 20 : You should have received a copy of the GNU General Public License 21 : along with this program. If not, see <http://www.gnu.org/licenses/>. 22 : */ 23 : 24 : #include "includes.h" 25 : #include "system/kerberos.h" 26 : #include "sdb.h" 27 : #include "samba_kdc.h" 28 : #include "lib/krb5_wrap/krb5_samba.h" 29 : 30 : #undef DBGC_CLASS 31 : #define DBGC_CLASS DBGC_KERBEROS 32 : 33 363966 : void sdb_key_free(struct sdb_key *k) 34 : { 35 363966 : if (k == NULL) { 36 0 : return; 37 : } 38 : 39 : /* 40 : * Passing NULL as the Kerberos context is intentional here, as 41 : * both Heimdal and MIT libraries don't use the context when 42 : * clearing the keyblocks. 43 : */ 44 363966 : krb5_free_keyblock_contents(NULL, &k->key); 45 : 46 363966 : if (k->salt) { 47 262288 : smb_krb5_free_data_contents(NULL, &k->salt->salt); 48 262288 : SAFE_FREE(k->salt); 49 : } 50 : 51 363966 : ZERO_STRUCTP(k); 52 : } 53 : 54 680352 : void sdb_keys_free(struct sdb_keys *keys) 55 : { 56 : unsigned int i; 57 : 58 680352 : if (keys == NULL) { 59 0 : return; 60 : } 61 : 62 1044318 : for (i=0; i < keys->len; i++) { 63 363966 : sdb_key_free(&keys->val[i]); 64 : } 65 : 66 680352 : SAFE_FREE(keys->val); 67 680352 : ZERO_STRUCTP(keys); 68 : } 69 : 70 226784 : void sdb_entry_free(struct sdb_entry *s) 71 : { 72 226784 : if (s->skdc_entry != NULL) { 73 209053 : s->skdc_entry->db_entry = NULL; 74 209053 : TALLOC_FREE(s->skdc_entry); 75 : } 76 : 77 : /* 78 : * Passing NULL as the Kerberos context is intentional here, as both 79 : * Heimdal and MIT libraries don't use the context when clearing the 80 : * principals. 81 : */ 82 226784 : krb5_free_principal(NULL, s->principal); 83 : 84 226784 : sdb_keys_free(&s->keys); 85 226784 : sdb_keys_free(&s->old_keys); 86 226784 : sdb_keys_free(&s->older_keys); 87 226784 : krb5_free_principal(NULL, s->created_by.principal); 88 226784 : if (s->modified_by) { 89 53 : krb5_free_principal(NULL, s->modified_by->principal); 90 : } 91 226784 : SAFE_FREE(s->valid_start); 92 226784 : SAFE_FREE(s->valid_end); 93 226784 : SAFE_FREE(s->pw_end); 94 : 95 226784 : ZERO_STRUCTP(s); 96 226784 : } 97 : 98 210722 : struct SDBFlags int2SDBFlags(unsigned n) 99 : { 100 : struct SDBFlags flags; 101 : 102 210722 : memset(&flags, 0, sizeof(flags)); 103 : 104 210722 : flags.initial = (n >> 0) & 1; 105 210722 : flags.forwardable = (n >> 1) & 1; 106 210722 : flags.proxiable = (n >> 2) & 1; 107 210722 : flags.renewable = (n >> 3) & 1; 108 210722 : flags.postdate = (n >> 4) & 1; 109 210722 : flags.server = (n >> 5) & 1; 110 210722 : flags.client = (n >> 6) & 1; 111 210722 : flags.invalid = (n >> 7) & 1; 112 210722 : flags.require_preauth = (n >> 8) & 1; 113 210722 : flags.change_pw = (n >> 9) & 1; 114 210722 : flags.require_hwauth = (n >> 10) & 1; 115 210722 : flags.ok_as_delegate = (n >> 11) & 1; 116 210722 : flags.user_to_user = (n >> 12) & 1; 117 210722 : flags.immutable = (n >> 13) & 1; 118 210722 : flags.trusted_for_delegation = (n >> 14) & 1; 119 210722 : flags.allow_kerberos4 = (n >> 15) & 1; 120 210722 : flags.allow_digest = (n >> 16) & 1; 121 210722 : flags.locked_out = (n >> 17) & 1; 122 210722 : flags.do_not_store = (n >> 31) & 1; 123 210722 : return flags; 124 : } 125 : 126 : /* Set the etypes of an sdb_entry based on its available current keys. */ 127 210050 : krb5_error_code sdb_entry_set_etypes(struct sdb_entry *s) 128 : { 129 210050 : if (s->keys.val != NULL) { 130 : unsigned i; 131 : 132 210050 : s->etypes = malloc(sizeof(*s->etypes)); 133 210050 : if (s->etypes == NULL) { 134 0 : return ENOMEM; 135 : } 136 : 137 210050 : s->etypes->len = s->keys.len; 138 : 139 210050 : s->etypes->val = calloc(s->etypes->len, sizeof(*s->etypes->val)); 140 210050 : if (s->etypes->val == NULL) { 141 0 : return ENOMEM; 142 : } 143 : 144 786316 : for (i = 0; i < s->etypes->len; i++) { 145 576266 : const struct sdb_key *k = &s->keys.val[i]; 146 : 147 576266 : s->etypes->val[i] = KRB5_KEY_TYPE(&(k->key)); 148 : } 149 : } 150 : 151 210050 : return 0; 152 : } 153 : 154 : /* 155 : * Set the session etypes of a server sdb_entry based on its etypes, forcing in 156 : * strong etypes as desired. 157 : */ 158 155416 : krb5_error_code sdb_entry_set_session_etypes(struct sdb_entry *s, 159 : bool add_aes256, 160 : bool add_aes128, 161 : bool add_rc4) 162 : { 163 155416 : unsigned len = 0; 164 : 165 155416 : if (add_aes256) { 166 : /* Reserve space for AES256 */ 167 143209 : len += 1; 168 : } 169 : 170 155416 : if (add_aes128) { 171 : /* Reserve space for AES128 */ 172 142179 : len += 1; 173 : } 174 : 175 155416 : if (add_rc4) { 176 : /* Reserve space for RC4. */ 177 154363 : len += 1; 178 : } 179 : 180 155416 : if (len != 0) { 181 155416 : unsigned j = 0; 182 : 183 155416 : s->session_etypes = malloc(sizeof(*s->session_etypes)); 184 155416 : if (s->session_etypes == NULL) { 185 0 : return ENOMEM; 186 : } 187 : 188 : /* session_etypes must be sorted in order of strength, with preferred etype first. */ 189 : 190 155416 : s->session_etypes->val = calloc(len, sizeof(*s->session_etypes->val)); 191 155416 : if (s->session_etypes->val == NULL) { 192 0 : SAFE_FREE(s->session_etypes); 193 0 : return ENOMEM; 194 : } 195 : 196 155416 : if (add_aes256) { 197 : /* Add AES256 */ 198 143209 : s->session_etypes->val[j++] = ENCTYPE_AES256_CTS_HMAC_SHA1_96; 199 : } 200 : 201 155416 : if (add_aes128) { 202 : /* Add AES128. */ 203 142179 : s->session_etypes->val[j++] = ENCTYPE_AES128_CTS_HMAC_SHA1_96; 204 : } 205 : 206 155416 : if (add_rc4) { 207 : /* Add RC4. */ 208 154363 : s->session_etypes->val[j++] = ENCTYPE_ARCFOUR_HMAC; 209 : } 210 : 211 155416 : s->session_etypes->len = j; 212 : } 213 : 214 155416 : return 0; 215 : }