1 /*- 2 * Copyright (c) 2018, Juniper Networks, Inc. 3 * 4 * Redistribution and use in source and binary forms, with or without 5 * modification, are permitted provided that the following conditions 6 * are met: 7 * 1. Redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer. 9 * 2. Redistributions in binary form must reproduce the above copyright 10 * notice, this list of conditions and the following disclaimer in the 11 * documentation and/or other materials provided with the distribution. 12 * 13 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 14 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 15 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 16 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 17 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 18 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 19 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 20 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 21 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 22 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 23 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 24 */ 25 /* 26 * RCSid: 27 * from: signer.c,v 1.10 2018/03/23 01:14:30 sjg 28 * 29 * @(#) Copyright (c) 2012 Simon J. Gerraty 30 * 31 * This file is provided in the hope that it will 32 * be of use. There is absolutely NO WARRANTY. 33 * Permission to copy, redistribute or otherwise 34 * use this file is hereby granted provided that 35 * the above copyright notice and this notice are 36 * left intact. 37 * 38 * Please send copies of changes and bug-fixes to: 39 * sjg@crufty.net 40 */ 41 42 #include <sys/cdefs.h> 43 __FBSDID("$FreeBSD$"); 44 45 #include "../libsecureboot-priv.h" 46 #ifdef _STANDALONE 47 #define warnx printf 48 #else 49 50 #include <sys/param.h> 51 #include <sys/stat.h> 52 #include <unistd.h> 53 #include <stdio.h> 54 #include <fcntl.h> 55 #include <stdlib.h> 56 #include <string.h> 57 #include <err.h> 58 #endif 59 60 #include "decode.h" 61 #include "packet.h" 62 63 #ifdef USE_BEARSSL 64 65 #define get_error_string ve_error_get 66 67 void 68 initialize (void) 69 { 70 #ifdef _STANDALONE 71 ve_trust_init(); 72 #endif 73 } 74 75 #else 76 77 #include <openssl/err.h> 78 79 /** 80 * @brief intialize OpenSSL 81 */ 82 void 83 initialize(void) 84 { 85 static int once; 86 87 if (once) 88 return); 89 once = 1; 90 //CRYPTO_malloc_init(); 91 ERR_load_crypto_strings(); 92 OpenSSL_add_all_algorithms(); 93 } 94 95 /** 96 * @brief 97 * last error from OpenSSL as a string 98 */ 99 char * 100 get_error_string(void) 101 { 102 initialize(); 103 return (ERR_error_string(ERR_get_error(), NULL)); 104 } 105 #endif 106 107 /** 108 * @brief decode a signature packet 109 * 110 * We only support RSA 111 * 112 * @sa rfc4880:5.2 113 */ 114 ssize_t 115 decode_sig(int tag, unsigned char **pptr, size_t len, OpenPGP_sig *sig) 116 { 117 unsigned char *ptr; 118 unsigned char *pgpbytes; 119 unsigned char *sp; 120 int version; 121 int hcount = 0; 122 int ucount = 0; 123 int stag = 0; 124 int n; 125 126 n = tag; /* avoid unused */ 127 128 /* 129 * We need to keep a reference to the packet bytes 130 * as these form part of the signature data. 131 * 132 * @sa rfc4880:5.2.4 133 */ 134 pgpbytes = ptr = *pptr; 135 version = *ptr++; 136 if (version == 3) { 137 ptr++; 138 sig->pgpbytes = malloc(5); 139 if (!sig->pgpbytes) 140 return (-1); 141 memcpy(sig->pgpbytes, ptr, 5); 142 sig->pgpbytes_len = 5; 143 sig->sig_type = *ptr++; 144 ptr += 4; 145 sig->key_id = octets2hex(ptr, 8); 146 ptr += 8; 147 sig->sig_alg = *ptr++; 148 sig->hash_alg = *ptr++; 149 } else if (version == 4) { 150 sig->sig_type = *ptr++; 151 sig->sig_alg = *ptr++; 152 sig->hash_alg = *ptr++; 153 hcount = octets2i(ptr, 2); 154 ptr += 2; 155 sig->pgpbytes_len = (size_t)hcount + 6; 156 sig->pgpbytes = malloc(sig->pgpbytes_len + 6); 157 if (!sig->pgpbytes) 158 return (-1); 159 memcpy(sig->pgpbytes, pgpbytes, sig->pgpbytes_len); 160 sp = &sig->pgpbytes[sig->pgpbytes_len]; 161 *sp++ = 4; 162 *sp++ = 255; 163 memcpy(sp, i2octets(4, (int)sig->pgpbytes_len), 4); 164 sig->pgpbytes_len += 6; 165 166 while (hcount > 0) { 167 sp = decode_subpacket(&ptr, &stag, &n); 168 hcount -= n; 169 /* can check stag to see if we care */ 170 } 171 ucount = octets2i(ptr, 2); 172 ptr += 2; 173 while (ucount > 0) { 174 sp = decode_subpacket(&ptr, &stag, &n); 175 ucount -= n; 176 /* can check stag to see if we care */ 177 if (stag == 16) { 178 free(sig->key_id); 179 sig->key_id = octets2hex(sp, 8); 180 } 181 } 182 } else 183 return (-1); 184 ptr += 2; /* skip hash16 */ 185 if (sig->sig_alg == 1) { /* RSA */ 186 sig->sig = decode_mpi(&ptr, &sig->sig_len); 187 } 188 /* we are done */ 189 return ((ssize_t)len); 190 } 191 192 /** 193 * @brief map OpenPGP hash algorithm id's to name 194 * 195 * @sa rfc4880:9.4 196 */ 197 static struct hash_alg_map { 198 int halg; 199 const char *hname; 200 } hash_algs[] = { 201 {1, "md5"}, 202 {2, "sha1"}, 203 {8, "sha256"}, 204 {9, "sha384"}, 205 {10, "sha512"}, 206 {11, "sha224"}, 207 {0, NULL}, 208 }; 209 210 static const char * 211 get_hname(int hash_alg) 212 { 213 struct hash_alg_map *hmp; 214 215 for (hmp = hash_algs; hmp->halg > 0; hmp++) { 216 if (hmp->halg == hash_alg) 217 return (hmp->hname); 218 } 219 return (NULL); 220 } 221 222 /* lifted from signer.c */ 223 /** 224 * @brief verify a digest 225 * 226 * The public key, digest name, file and signature data. 227 * 228 * @return 1 on success 0 on failure, -1 on error 229 */ 230 #ifndef USE_BEARSSL 231 static int 232 verify_digest (EVP_PKEY *pkey, 233 const char *digest, 234 unsigned char *mdata, size_t mlen, 235 unsigned char *sdata, size_t slen) 236 { 237 EVP_MD_CTX ctx; 238 const EVP_MD *md = NULL; 239 EVP_PKEY_CTX *pctx = NULL; 240 int rc = 0; 241 int i = -1; 242 243 initialize(); 244 md = EVP_get_digestbyname(digest); 245 EVP_DigestInit(&ctx, md); 246 247 pctx = EVP_PKEY_CTX_new(pkey, NULL); 248 if (!pctx) 249 goto fail; 250 if (EVP_PKEY_verify_init(pctx) <= 0) 251 goto fail; 252 if (EVP_PKEY_CTX_set_signature_md(pctx, ctx.digest) <= 0) 253 goto fail; 254 i = EVP_PKEY_verify(pctx, sdata, slen, mdata, mlen); 255 if (i >= 0) 256 rc = i; 257 fail: 258 EVP_PKEY_CTX_free(pctx); 259 return (rc); 260 } 261 #endif 262 263 264 /** 265 * @brief verify OpenPGP signed file 266 * 267 * 268 * @param[in] filename 269 * used to determine the signature name 270 * 271 * @param[in] fdata 272 * content of filename 273 * 274 * @param[in] fbytes 275 * of fdata 276 * 277 * @param[in] sdata 278 * content of signature 279 * 280 * @param[in] sbytes 281 * of sdata 282 * 283 * @param[in] flags 284 * 285 * @return 0 on success 286 */ 287 int 288 openpgp_verify(const char *filename, 289 unsigned char *fdata, size_t fbytes, 290 unsigned char *sdata, size_t sbytes, 291 int flags) 292 { 293 OpenPGP_key *key; 294 OpenPGP_sig *sig; 295 #ifdef USE_BEARSSL 296 const br_hash_class *md; 297 br_hash_compat_context mctx; 298 const unsigned char *hash_oid; 299 #else 300 const EVP_MD *md = NULL; 301 EVP_MD_CTX mctx; 302 #endif 303 unsigned char mdata[64]; 304 unsigned char *ptr; 305 unsigned char *ddata = NULL; 306 const char *hname; 307 size_t mlen; 308 int rc = -1; 309 310 initialize(); 311 312 sig = NEW(OpenPGP_sig); 313 if (!sdata || !sig) { 314 warnx("cannot verify %s", filename); 315 goto oops; 316 } 317 if (!(sdata[0] & OPENPGP_TAG_ISTAG)) 318 sdata = ddata = dearmor((char *)sdata, sbytes, &sbytes); 319 ptr = sdata; 320 rc = decode_packet(2, &ptr, sbytes, (decoder_t)decode_sig, sig); 321 if (rc == 0 && sig->key_id) { 322 key = load_key_id(sig->key_id); 323 if (!key) { 324 warnx("cannot find key-id: %s", sig->key_id); 325 rc = -1; 326 } else if (!(hname = get_hname(sig->hash_alg))) { 327 warnx("unsupported hash algorithm: %d", sig->hash_alg); 328 rc = -1; 329 } else { 330 /* 331 * Hash fdata according to the OpenPGP recipe 332 * 333 * @sa rfc4880:5.2.4 334 */ 335 #ifdef USE_BEARSSL 336 switch (sig->hash_alg) { /* see hash_algs above */ 337 case 2: /* sha1 */ 338 md = &br_sha1_vtable; 339 mlen = br_sha1_SIZE; 340 hash_oid = BR_HASH_OID_SHA1; 341 break; 342 case 8: /* sha256 */ 343 md = &br_sha256_vtable; 344 mlen = br_sha256_SIZE; 345 hash_oid = BR_HASH_OID_SHA256; 346 break; 347 default: 348 warnx("unsupported hash algorithm: %s", hname); 349 goto oops; 350 } 351 md->init(&mctx.vtable); 352 md->update(&mctx.vtable, fdata, fbytes); 353 md->update(&mctx.vtable, sig->pgpbytes, 354 sig->pgpbytes_len); 355 md->out(&mctx.vtable, mdata); 356 357 rc = verify_rsa_digest(key->key, hash_oid, 358 mdata, mlen, sig->sig, sig->sig_len); 359 #else 360 md = EVP_get_digestbyname(hname); 361 EVP_DigestInit(&mctx, md); 362 EVP_DigestUpdate(&mctx, fdata, fbytes); 363 EVP_DigestUpdate(&mctx, sig->pgpbytes, 364 sig->pgpbytes_len); 365 mlen = sizeof(mdata); 366 EVP_DigestFinal(&mctx,mdata,(unsigned int *)&mlen); 367 368 rc = verify_digest(key->key, hname, mdata, mlen, 369 sig->sig, sig->sig_len); 370 #endif 371 372 if (rc > 0) { 373 if ((flags & 1)) 374 printf("Verified %s signed by %s\n", 375 filename, 376 key->user ? key->user->name : "someone"); 377 rc = 0; /* success */ 378 } else if (rc == 0) { 379 printf("Unverified %s: %s\n", 380 filename, get_error_string()); 381 rc = 1; 382 } else { 383 printf("Unverified %s\n", filename); 384 } 385 } 386 } else { 387 warnx("cannot decode signature for %s", filename); 388 rc = -1; 389 } 390 oops: 391 free(ddata); 392 free(sig); 393 return (rc); 394 } 395 396 #ifndef _STANDALONE 397 /** 398 * @brief list of extensions we handle 399 * 400 * ".asc" is preferred as it works seamlessly with openpgp 401 */ 402 static const char *sig_exts[] = { 403 ".asc", 404 ".pgp", 405 ".psig", 406 NULL, 407 }; 408 409 /** 410 * @brief verify OpenPGP signed file 411 * 412 * 413 * @param[in] filename 414 * used to determine the signature name 415 * 416 * @param[in] fdata 417 * content of filename 418 * 419 * @param[in] nbytes 420 * of fdata 421 * 422 * @return 423 */ 424 425 int 426 openpgp_verify_file(const char *filename, unsigned char *fdata, size_t nbytes) 427 { 428 char pbuf[MAXPATHLEN]; 429 unsigned char *sdata; 430 const char *sname = NULL; 431 const char **ep; 432 size_t sz; 433 int n; 434 435 for (ep = sig_exts; *ep; ep++) { 436 n = snprintf(pbuf, sizeof(pbuf), "%s%s", filename, *ep); 437 if (n >= (int)sizeof(pbuf)) { 438 warnx("cannot form signature name for %s", filename); 439 return (-1); 440 } 441 if (access(pbuf, R_OK) == 0) { 442 sname = pbuf; 443 break; 444 } 445 } 446 if (!sname) { 447 warnx("cannot find signature for %s", filename); 448 return (-1); 449 } 450 sdata = read_file(sname, &sz); 451 return (openpgp_verify(filename, fdata, nbytes, sdata, sz, 1)); 452 } 453 #endif 454 455 /** 456 * @brief verify OpenPGP signature 457 * 458 * @return content of signed file 459 */ 460 unsigned char * 461 verify_asc(const char *sigfile, int flags) 462 { 463 char pbuf[MAXPATHLEN]; 464 char *cp; 465 size_t n; 466 unsigned char *fdata, *sdata; 467 size_t fbytes, sbytes; 468 469 if ((sdata = read_file(sigfile, &sbytes))) { 470 n = strlcpy(pbuf, sigfile, sizeof(pbuf)); 471 if ((cp = strrchr(pbuf, '.'))) 472 *cp = '\0'; 473 if ((fdata = read_file(pbuf, &fbytes))) { 474 if (openpgp_verify(pbuf, fdata, fbytes, sdata, 475 sbytes, flags)) { 476 free(fdata); 477 fdata = NULL; 478 } 479 } 480 } else 481 fdata = NULL; 482 free(sdata); 483 return (fdata); 484 } 485