1 // SPDX-License-Identifier: GPL-2.0 2 /* 3 * This file is part of UBIFS. 4 * 5 * Copyright (C) 2018 Pengutronix, Sascha Hauer <s.hauer@pengutronix.de> 6 */ 7 8 /* 9 * This file implements various helper functions for UBIFS authentication support 10 */ 11 12 #include <linux/crypto.h> 13 #include <linux/verification.h> 14 #include <crypto/hash.h> 15 #include <crypto/sha.h> 16 #include <crypto/algapi.h> 17 #include <keys/user-type.h> 18 #include <keys/asymmetric-type.h> 19 20 #include "ubifs.h" 21 22 /** 23 * ubifs_node_calc_hash - calculate the hash of a UBIFS node 24 * @c: UBIFS file-system description object 25 * @node: the node to calculate a hash for 26 * @hash: the returned hash 27 * 28 * Returns 0 for success or a negative error code otherwise. 29 */ 30 int __ubifs_node_calc_hash(const struct ubifs_info *c, const void *node, 31 u8 *hash) 32 { 33 const struct ubifs_ch *ch = node; 34 SHASH_DESC_ON_STACK(shash, c->hash_tfm); 35 int err; 36 37 shash->tfm = c->hash_tfm; 38 39 err = crypto_shash_digest(shash, node, le32_to_cpu(ch->len), hash); 40 if (err < 0) 41 return err; 42 return 0; 43 } 44 45 /** 46 * ubifs_hash_calc_hmac - calculate a HMAC from a hash 47 * @c: UBIFS file-system description object 48 * @hash: the node to calculate a HMAC for 49 * @hmac: the returned HMAC 50 * 51 * Returns 0 for success or a negative error code otherwise. 52 */ 53 static int ubifs_hash_calc_hmac(const struct ubifs_info *c, const u8 *hash, 54 u8 *hmac) 55 { 56 SHASH_DESC_ON_STACK(shash, c->hmac_tfm); 57 int err; 58 59 shash->tfm = c->hmac_tfm; 60 61 err = crypto_shash_digest(shash, hash, c->hash_len, hmac); 62 if (err < 0) 63 return err; 64 return 0; 65 } 66 67 /** 68 * ubifs_prepare_auth_node - Prepare an authentication node 69 * @c: UBIFS file-system description object 70 * @node: the node to calculate a hash for 71 * @hash: input hash of previous nodes 72 * 73 * This function prepares an authentication node for writing onto flash. 74 * It creates a HMAC from the given input hash and writes it to the node. 75 * 76 * Returns 0 for success or a negative error code otherwise. 77 */ 78 int ubifs_prepare_auth_node(struct ubifs_info *c, void *node, 79 struct shash_desc *inhash) 80 { 81 struct ubifs_auth_node *auth = node; 82 u8 hash[UBIFS_HASH_ARR_SZ]; 83 int err; 84 85 { 86 SHASH_DESC_ON_STACK(hash_desc, c->hash_tfm); 87 88 hash_desc->tfm = c->hash_tfm; 89 ubifs_shash_copy_state(c, inhash, hash_desc); 90 91 err = crypto_shash_final(hash_desc, hash); 92 if (err) 93 return err; 94 } 95 96 err = ubifs_hash_calc_hmac(c, hash, auth->hmac); 97 if (err) 98 return err; 99 100 auth->ch.node_type = UBIFS_AUTH_NODE; 101 ubifs_prepare_node(c, auth, ubifs_auth_node_sz(c), 0); 102 return 0; 103 } 104 105 static struct shash_desc *ubifs_get_desc(const struct ubifs_info *c, 106 struct crypto_shash *tfm) 107 { 108 struct shash_desc *desc; 109 int err; 110 111 if (!ubifs_authenticated(c)) 112 return NULL; 113 114 desc = kmalloc(sizeof(*desc) + crypto_shash_descsize(tfm), GFP_KERNEL); 115 if (!desc) 116 return ERR_PTR(-ENOMEM); 117 118 desc->tfm = tfm; 119 120 err = crypto_shash_init(desc); 121 if (err) { 122 kfree(desc); 123 return ERR_PTR(err); 124 } 125 126 return desc; 127 } 128 129 /** 130 * __ubifs_hash_get_desc - get a descriptor suitable for hashing a node 131 * @c: UBIFS file-system description object 132 * 133 * This function returns a descriptor suitable for hashing a node. Free after use 134 * with kfree. 135 */ 136 struct shash_desc *__ubifs_hash_get_desc(const struct ubifs_info *c) 137 { 138 return ubifs_get_desc(c, c->hash_tfm); 139 } 140 141 /** 142 * ubifs_bad_hash - Report hash mismatches 143 * @c: UBIFS file-system description object 144 * @node: the node 145 * @hash: the expected hash 146 * @lnum: the LEB @node was read from 147 * @offs: offset in LEB @node was read from 148 * 149 * This function reports a hash mismatch when a node has a different hash than 150 * expected. 151 */ 152 void ubifs_bad_hash(const struct ubifs_info *c, const void *node, const u8 *hash, 153 int lnum, int offs) 154 { 155 int len = min(c->hash_len, 20); 156 int cropped = len != c->hash_len; 157 const char *cont = cropped ? "..." : ""; 158 159 u8 calc[UBIFS_HASH_ARR_SZ]; 160 161 __ubifs_node_calc_hash(c, node, calc); 162 163 ubifs_err(c, "hash mismatch on node at LEB %d:%d", lnum, offs); 164 ubifs_err(c, "hash expected: %*ph%s", len, hash, cont); 165 ubifs_err(c, "hash calculated: %*ph%s", len, calc, cont); 166 } 167 168 /** 169 * __ubifs_node_check_hash - check the hash of a node against given hash 170 * @c: UBIFS file-system description object 171 * @node: the node 172 * @expected: the expected hash 173 * 174 * This function calculates a hash over a node and compares it to the given hash. 175 * Returns 0 if both hashes are equal or authentication is disabled, otherwise a 176 * negative error code is returned. 177 */ 178 int __ubifs_node_check_hash(const struct ubifs_info *c, const void *node, 179 const u8 *expected) 180 { 181 u8 calc[UBIFS_HASH_ARR_SZ]; 182 int err; 183 184 err = __ubifs_node_calc_hash(c, node, calc); 185 if (err) 186 return err; 187 188 if (ubifs_check_hash(c, expected, calc)) 189 return -EPERM; 190 191 return 0; 192 } 193 194 /** 195 * ubifs_sb_verify_signature - verify the signature of a superblock 196 * @c: UBIFS file-system description object 197 * @sup: The superblock node 198 * 199 * To support offline signed images the superblock can be signed with a 200 * PKCS#7 signature. The signature is placed directly behind the superblock 201 * node in an ubifs_sig_node. 202 * 203 * Returns 0 when the signature can be successfully verified or a negative 204 * error code if not. 205 */ 206 int ubifs_sb_verify_signature(struct ubifs_info *c, 207 const struct ubifs_sb_node *sup) 208 { 209 int err; 210 struct ubifs_scan_leb *sleb; 211 struct ubifs_scan_node *snod; 212 const struct ubifs_sig_node *signode; 213 214 sleb = ubifs_scan(c, UBIFS_SB_LNUM, UBIFS_SB_NODE_SZ, c->sbuf, 0); 215 if (IS_ERR(sleb)) { 216 err = PTR_ERR(sleb); 217 return err; 218 } 219 220 if (sleb->nodes_cnt == 0) { 221 ubifs_err(c, "Unable to find signature node"); 222 err = -EINVAL; 223 goto out_destroy; 224 } 225 226 snod = list_first_entry(&sleb->nodes, struct ubifs_scan_node, list); 227 228 if (snod->type != UBIFS_SIG_NODE) { 229 ubifs_err(c, "Signature node is of wrong type"); 230 err = -EINVAL; 231 goto out_destroy; 232 } 233 234 signode = snod->node; 235 236 if (le32_to_cpu(signode->len) > snod->len + sizeof(struct ubifs_sig_node)) { 237 ubifs_err(c, "invalid signature len %d", le32_to_cpu(signode->len)); 238 err = -EINVAL; 239 goto out_destroy; 240 } 241 242 if (le32_to_cpu(signode->type) != UBIFS_SIGNATURE_TYPE_PKCS7) { 243 ubifs_err(c, "Signature type %d is not supported\n", 244 le32_to_cpu(signode->type)); 245 err = -EINVAL; 246 goto out_destroy; 247 } 248 249 err = verify_pkcs7_signature(sup, sizeof(struct ubifs_sb_node), 250 signode->sig, le32_to_cpu(signode->len), 251 NULL, VERIFYING_UNSPECIFIED_SIGNATURE, 252 NULL, NULL); 253 254 if (err) 255 ubifs_err(c, "Failed to verify signature"); 256 else 257 ubifs_msg(c, "Successfully verified super block signature"); 258 259 out_destroy: 260 ubifs_scan_destroy(sleb); 261 262 return err; 263 } 264 265 /** 266 * ubifs_init_authentication - initialize UBIFS authentication support 267 * @c: UBIFS file-system description object 268 * 269 * This function returns 0 for success or a negative error code otherwise. 270 */ 271 int ubifs_init_authentication(struct ubifs_info *c) 272 { 273 struct key *keyring_key; 274 const struct user_key_payload *ukp; 275 int err; 276 char hmac_name[CRYPTO_MAX_ALG_NAME]; 277 278 if (!c->auth_hash_name) { 279 ubifs_err(c, "authentication hash name needed with authentication"); 280 return -EINVAL; 281 } 282 283 c->auth_hash_algo = match_string(hash_algo_name, HASH_ALGO__LAST, 284 c->auth_hash_name); 285 if ((int)c->auth_hash_algo < 0) { 286 ubifs_err(c, "Unknown hash algo %s specified", 287 c->auth_hash_name); 288 return -EINVAL; 289 } 290 291 snprintf(hmac_name, CRYPTO_MAX_ALG_NAME, "hmac(%s)", 292 c->auth_hash_name); 293 294 keyring_key = request_key(&key_type_logon, c->auth_key_name, NULL); 295 296 if (IS_ERR(keyring_key)) { 297 ubifs_err(c, "Failed to request key: %ld", 298 PTR_ERR(keyring_key)); 299 return PTR_ERR(keyring_key); 300 } 301 302 down_read(&keyring_key->sem); 303 304 if (keyring_key->type != &key_type_logon) { 305 ubifs_err(c, "key type must be logon"); 306 err = -ENOKEY; 307 goto out; 308 } 309 310 ukp = user_key_payload_locked(keyring_key); 311 if (!ukp) { 312 /* key was revoked before we acquired its semaphore */ 313 err = -EKEYREVOKED; 314 goto out; 315 } 316 317 c->hash_tfm = crypto_alloc_shash(c->auth_hash_name, 0, 0); 318 if (IS_ERR(c->hash_tfm)) { 319 err = PTR_ERR(c->hash_tfm); 320 ubifs_err(c, "Can not allocate %s: %d", 321 c->auth_hash_name, err); 322 goto out; 323 } 324 325 c->hash_len = crypto_shash_digestsize(c->hash_tfm); 326 if (c->hash_len > UBIFS_HASH_ARR_SZ) { 327 ubifs_err(c, "hash %s is bigger than maximum allowed hash size (%d > %d)", 328 c->auth_hash_name, c->hash_len, UBIFS_HASH_ARR_SZ); 329 err = -EINVAL; 330 goto out_free_hash; 331 } 332 333 c->hmac_tfm = crypto_alloc_shash(hmac_name, 0, 0); 334 if (IS_ERR(c->hmac_tfm)) { 335 err = PTR_ERR(c->hmac_tfm); 336 ubifs_err(c, "Can not allocate %s: %d", hmac_name, err); 337 goto out_free_hash; 338 } 339 340 c->hmac_desc_len = crypto_shash_digestsize(c->hmac_tfm); 341 if (c->hmac_desc_len > UBIFS_HMAC_ARR_SZ) { 342 ubifs_err(c, "hmac %s is bigger than maximum allowed hmac size (%d > %d)", 343 hmac_name, c->hmac_desc_len, UBIFS_HMAC_ARR_SZ); 344 err = -EINVAL; 345 goto out_free_hash; 346 } 347 348 err = crypto_shash_setkey(c->hmac_tfm, ukp->data, ukp->datalen); 349 if (err) 350 goto out_free_hmac; 351 352 c->authenticated = true; 353 354 c->log_hash = ubifs_hash_get_desc(c); 355 if (IS_ERR(c->log_hash)) 356 goto out_free_hmac; 357 358 err = 0; 359 360 out_free_hmac: 361 if (err) 362 crypto_free_shash(c->hmac_tfm); 363 out_free_hash: 364 if (err) 365 crypto_free_shash(c->hash_tfm); 366 out: 367 up_read(&keyring_key->sem); 368 key_put(keyring_key); 369 370 return err; 371 } 372 373 /** 374 * __ubifs_exit_authentication - release resource 375 * @c: UBIFS file-system description object 376 * 377 * This function releases the authentication related resources. 378 */ 379 void __ubifs_exit_authentication(struct ubifs_info *c) 380 { 381 if (!ubifs_authenticated(c)) 382 return; 383 384 crypto_free_shash(c->hmac_tfm); 385 crypto_free_shash(c->hash_tfm); 386 kfree(c->log_hash); 387 } 388 389 /** 390 * ubifs_node_calc_hmac - calculate the HMAC of a UBIFS node 391 * @c: UBIFS file-system description object 392 * @node: the node to insert a HMAC into. 393 * @len: the length of the node 394 * @ofs_hmac: the offset in the node where the HMAC is inserted 395 * @hmac: returned HMAC 396 * 397 * This function calculates a HMAC of a UBIFS node. The HMAC is expected to be 398 * embedded into the node, so this area is not covered by the HMAC. Also not 399 * covered is the UBIFS_NODE_MAGIC and the CRC of the node. 400 */ 401 static int ubifs_node_calc_hmac(const struct ubifs_info *c, const void *node, 402 int len, int ofs_hmac, void *hmac) 403 { 404 SHASH_DESC_ON_STACK(shash, c->hmac_tfm); 405 int hmac_len = c->hmac_desc_len; 406 int err; 407 408 ubifs_assert(c, ofs_hmac > 8); 409 ubifs_assert(c, ofs_hmac + hmac_len < len); 410 411 shash->tfm = c->hmac_tfm; 412 413 err = crypto_shash_init(shash); 414 if (err) 415 return err; 416 417 /* behind common node header CRC up to HMAC begin */ 418 err = crypto_shash_update(shash, node + 8, ofs_hmac - 8); 419 if (err < 0) 420 return err; 421 422 /* behind HMAC, if any */ 423 if (len - ofs_hmac - hmac_len > 0) { 424 err = crypto_shash_update(shash, node + ofs_hmac + hmac_len, 425 len - ofs_hmac - hmac_len); 426 if (err < 0) 427 return err; 428 } 429 430 return crypto_shash_final(shash, hmac); 431 } 432 433 /** 434 * __ubifs_node_insert_hmac - insert a HMAC into a UBIFS node 435 * @c: UBIFS file-system description object 436 * @node: the node to insert a HMAC into. 437 * @len: the length of the node 438 * @ofs_hmac: the offset in the node where the HMAC is inserted 439 * 440 * This function inserts a HMAC at offset @ofs_hmac into the node given in 441 * @node. 442 * 443 * This function returns 0 for success or a negative error code otherwise. 444 */ 445 int __ubifs_node_insert_hmac(const struct ubifs_info *c, void *node, int len, 446 int ofs_hmac) 447 { 448 return ubifs_node_calc_hmac(c, node, len, ofs_hmac, node + ofs_hmac); 449 } 450 451 /** 452 * __ubifs_node_verify_hmac - verify the HMAC of UBIFS node 453 * @c: UBIFS file-system description object 454 * @node: the node to insert a HMAC into. 455 * @len: the length of the node 456 * @ofs_hmac: the offset in the node where the HMAC is inserted 457 * 458 * This function verifies the HMAC at offset @ofs_hmac of the node given in 459 * @node. Returns 0 if successful or a negative error code otherwise. 460 */ 461 int __ubifs_node_verify_hmac(const struct ubifs_info *c, const void *node, 462 int len, int ofs_hmac) 463 { 464 int hmac_len = c->hmac_desc_len; 465 u8 *hmac; 466 int err; 467 468 hmac = kmalloc(hmac_len, GFP_NOFS); 469 if (!hmac) 470 return -ENOMEM; 471 472 err = ubifs_node_calc_hmac(c, node, len, ofs_hmac, hmac); 473 if (err) { 474 kfree(hmac); 475 return err; 476 } 477 478 err = crypto_memneq(hmac, node + ofs_hmac, hmac_len); 479 480 kfree(hmac); 481 482 if (!err) 483 return 0; 484 485 return -EPERM; 486 } 487 488 int __ubifs_shash_copy_state(const struct ubifs_info *c, struct shash_desc *src, 489 struct shash_desc *target) 490 { 491 u8 *state; 492 int err; 493 494 state = kmalloc(crypto_shash_descsize(src->tfm), GFP_NOFS); 495 if (!state) 496 return -ENOMEM; 497 498 err = crypto_shash_export(src, state); 499 if (err) 500 goto out; 501 502 err = crypto_shash_import(target, state); 503 504 out: 505 kfree(state); 506 507 return err; 508 } 509 510 /** 511 * ubifs_hmac_wkm - Create a HMAC of the well known message 512 * @c: UBIFS file-system description object 513 * @hmac: The HMAC of the well known message 514 * 515 * This function creates a HMAC of a well known message. This is used 516 * to check if the provided key is suitable to authenticate a UBIFS 517 * image. This is only a convenience to the user to provide a better 518 * error message when the wrong key is provided. 519 * 520 * This function returns 0 for success or a negative error code otherwise. 521 */ 522 int ubifs_hmac_wkm(struct ubifs_info *c, u8 *hmac) 523 { 524 SHASH_DESC_ON_STACK(shash, c->hmac_tfm); 525 int err; 526 const char well_known_message[] = "UBIFS"; 527 528 if (!ubifs_authenticated(c)) 529 return 0; 530 531 shash->tfm = c->hmac_tfm; 532 533 err = crypto_shash_init(shash); 534 if (err) 535 return err; 536 537 err = crypto_shash_update(shash, well_known_message, 538 sizeof(well_known_message) - 1); 539 if (err < 0) 540 return err; 541 542 err = crypto_shash_final(shash, hmac); 543 if (err) 544 return err; 545 return 0; 546 } 547 548 /* 549 * ubifs_hmac_zero - test if a HMAC is zero 550 * @c: UBIFS file-system description object 551 * @hmac: the HMAC to test 552 * 553 * This function tests if a HMAC is zero and returns true if it is 554 * and false otherwise. 555 */ 556 bool ubifs_hmac_zero(struct ubifs_info *c, const u8 *hmac) 557 { 558 return !memchr_inv(hmac, 0, c->hmac_desc_len); 559 } 560