1 /*- 2 * SPDX-License-Identifier: BSD-2-Clause-FreeBSD 3 * 4 * Copyright (c) 2005-2011 Pawel Jakub Dawidek <pawel@dawidek.net> 5 * All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 1. Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * 2. Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in the 14 * documentation and/or other materials provided with the distribution. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE AUTHORS AND CONTRIBUTORS ``AS IS'' AND 17 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 19 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHORS OR CONTRIBUTORS BE LIABLE 20 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 21 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 22 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 23 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 24 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 25 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 26 * SUCH DAMAGE. 27 */ 28 29 #include <sys/cdefs.h> 30 __FBSDID("$FreeBSD$"); 31 32 #include <sys/param.h> 33 #include <sys/systm.h> 34 #include <sys/kernel.h> 35 #include <sys/module.h> 36 #include <sys/lock.h> 37 #include <sys/mutex.h> 38 #include <sys/bio.h> 39 #include <sys/sysctl.h> 40 #include <sys/malloc.h> 41 #include <sys/kthread.h> 42 #include <sys/proc.h> 43 #include <sys/sched.h> 44 #include <sys/uio.h> 45 46 #include <vm/uma.h> 47 48 #include <geom/geom.h> 49 #include <geom/geom_dbg.h> 50 #include <geom/eli/g_eli.h> 51 52 53 MALLOC_DECLARE(M_ELI); 54 55 56 static void 57 g_eli_ctl_attach(struct gctl_req *req, struct g_class *mp) 58 { 59 struct g_eli_metadata md; 60 struct g_provider *pp; 61 const char *name; 62 u_char *key, mkey[G_ELI_DATAIVKEYLEN]; 63 int *nargs, *detach, *readonly, *dryrunp; 64 int keysize, error, nkey, dryrun, dummy; 65 intmax_t *valp; 66 67 g_topology_assert(); 68 69 nargs = gctl_get_paraml(req, "nargs", sizeof(*nargs)); 70 if (nargs == NULL) { 71 gctl_error(req, "No '%s' argument.", "nargs"); 72 return; 73 } 74 if (*nargs != 1) { 75 gctl_error(req, "Invalid number of arguments."); 76 return; 77 } 78 79 detach = gctl_get_paraml(req, "detach", sizeof(*detach)); 80 if (detach == NULL) { 81 gctl_error(req, "No '%s' argument.", "detach"); 82 return; 83 } 84 85 /* "keyno" is optional for backward compatibility */ 86 nkey = -1; 87 valp = gctl_get_param(req, "keyno", &dummy); 88 if (valp != NULL) { 89 valp = gctl_get_paraml(req, "keyno", sizeof(*valp)); 90 if (valp != NULL) 91 nkey = *valp; 92 } 93 if (nkey < -1 || nkey >= G_ELI_MAXMKEYS) { 94 gctl_error(req, "Invalid '%s' argument.", "keyno"); 95 return; 96 } 97 98 readonly = gctl_get_paraml(req, "readonly", sizeof(*readonly)); 99 if (readonly == NULL) { 100 gctl_error(req, "No '%s' argument.", "readonly"); 101 return; 102 } 103 104 /* "dryrun" is optional for backward compatibility */ 105 dryrun = 0; 106 dryrunp = gctl_get_param(req, "dryrun", &dummy); 107 if (dryrunp != NULL) { 108 dryrunp = gctl_get_paraml(req, "dryrun", sizeof(*dryrunp)); 109 if (dryrunp != NULL) 110 dryrun = *dryrunp; 111 } 112 113 if (*detach && *readonly) { 114 gctl_error(req, "Options -d and -r are mutually exclusive."); 115 return; 116 } 117 118 name = gctl_get_asciiparam(req, "arg0"); 119 if (name == NULL) { 120 gctl_error(req, "No 'arg%u' argument.", 0); 121 return; 122 } 123 if (strncmp(name, "/dev/", strlen("/dev/")) == 0) 124 name += strlen("/dev/"); 125 pp = g_provider_by_name(name); 126 if (pp == NULL) { 127 gctl_error(req, "Provider %s is invalid.", name); 128 return; 129 } 130 error = g_eli_read_metadata(mp, pp, &md); 131 if (error != 0) { 132 gctl_error(req, "Cannot read metadata from %s (error=%d).", 133 name, error); 134 return; 135 } 136 if (md.md_keys == 0x00) { 137 explicit_bzero(&md, sizeof(md)); 138 gctl_error(req, "No valid keys on %s.", pp->name); 139 return; 140 } 141 if (!eli_metadata_crypto_supported(&md)) { 142 explicit_bzero(&md, sizeof(md)); 143 gctl_error(req, "Invalid or unsupported algorithms."); 144 return; 145 } 146 147 key = gctl_get_param(req, "key", &keysize); 148 if (key == NULL || keysize != G_ELI_USERKEYLEN) { 149 explicit_bzero(&md, sizeof(md)); 150 gctl_error(req, "No '%s' argument.", "key"); 151 return; 152 } 153 154 if (nkey == -1) 155 error = g_eli_mkey_decrypt_any(&md, key, mkey, &nkey); 156 else 157 error = g_eli_mkey_decrypt(&md, key, mkey, nkey); 158 explicit_bzero(key, keysize); 159 if (error == -1) { 160 explicit_bzero(&md, sizeof(md)); 161 gctl_error(req, "Wrong key for %s.", pp->name); 162 return; 163 } else if (error > 0) { 164 explicit_bzero(&md, sizeof(md)); 165 gctl_error(req, "Cannot decrypt Master Key for %s (error=%d).", 166 pp->name, error); 167 return; 168 } 169 G_ELI_DEBUG(1, "Using Master Key %u for %s.", nkey, pp->name); 170 171 if (*detach) 172 md.md_flags |= G_ELI_FLAG_WO_DETACH; 173 if (*readonly) 174 md.md_flags |= G_ELI_FLAG_RO; 175 if (!dryrun) 176 g_eli_create(req, mp, pp, &md, mkey, nkey); 177 explicit_bzero(mkey, sizeof(mkey)); 178 explicit_bzero(&md, sizeof(md)); 179 } 180 181 static struct g_eli_softc * 182 g_eli_find_device(struct g_class *mp, const char *prov) 183 { 184 struct g_eli_softc *sc; 185 struct g_geom *gp; 186 struct g_provider *pp; 187 struct g_consumer *cp; 188 189 if (strncmp(prov, "/dev/", strlen("/dev/")) == 0) 190 prov += strlen("/dev/"); 191 LIST_FOREACH(gp, &mp->geom, geom) { 192 sc = gp->softc; 193 if (sc == NULL) 194 continue; 195 pp = LIST_FIRST(&gp->provider); 196 if (pp != NULL && strcmp(pp->name, prov) == 0) 197 return (sc); 198 cp = LIST_FIRST(&gp->consumer); 199 if (cp != NULL && cp->provider != NULL && 200 strcmp(cp->provider->name, prov) == 0) { 201 return (sc); 202 } 203 } 204 return (NULL); 205 } 206 207 static void 208 g_eli_ctl_detach(struct gctl_req *req, struct g_class *mp) 209 { 210 struct g_eli_softc *sc; 211 int *force, *last, *nargs, error; 212 const char *prov; 213 char param[16]; 214 int i; 215 216 g_topology_assert(); 217 218 nargs = gctl_get_paraml(req, "nargs", sizeof(*nargs)); 219 if (nargs == NULL) { 220 gctl_error(req, "No '%s' argument.", "nargs"); 221 return; 222 } 223 if (*nargs <= 0) { 224 gctl_error(req, "Missing device(s)."); 225 return; 226 } 227 force = gctl_get_paraml(req, "force", sizeof(*force)); 228 if (force == NULL) { 229 gctl_error(req, "No '%s' argument.", "force"); 230 return; 231 } 232 last = gctl_get_paraml(req, "last", sizeof(*last)); 233 if (last == NULL) { 234 gctl_error(req, "No '%s' argument.", "last"); 235 return; 236 } 237 238 for (i = 0; i < *nargs; i++) { 239 snprintf(param, sizeof(param), "arg%d", i); 240 prov = gctl_get_asciiparam(req, param); 241 if (prov == NULL) { 242 gctl_error(req, "No 'arg%d' argument.", i); 243 return; 244 } 245 sc = g_eli_find_device(mp, prov); 246 if (sc == NULL) { 247 gctl_error(req, "No such device: %s.", prov); 248 return; 249 } 250 if (*last) { 251 sc->sc_flags |= G_ELI_FLAG_RW_DETACH; 252 sc->sc_geom->access = g_eli_access; 253 } else { 254 error = g_eli_destroy(sc, *force ? TRUE : FALSE); 255 if (error != 0) { 256 gctl_error(req, 257 "Cannot destroy device %s (error=%d).", 258 sc->sc_name, error); 259 return; 260 } 261 } 262 } 263 } 264 265 static void 266 g_eli_ctl_onetime(struct gctl_req *req, struct g_class *mp) 267 { 268 struct g_eli_metadata md; 269 struct g_provider *pp; 270 const char *name; 271 intmax_t *keylen, *sectorsize; 272 u_char mkey[G_ELI_DATAIVKEYLEN]; 273 int *nargs, *detach, *noautoresize, *notrim; 274 275 g_topology_assert(); 276 bzero(&md, sizeof(md)); 277 278 nargs = gctl_get_paraml(req, "nargs", sizeof(*nargs)); 279 if (nargs == NULL) { 280 gctl_error(req, "No '%s' argument.", "nargs"); 281 return; 282 } 283 if (*nargs != 1) { 284 gctl_error(req, "Invalid number of arguments."); 285 return; 286 } 287 288 strlcpy(md.md_magic, G_ELI_MAGIC, sizeof(md.md_magic)); 289 md.md_version = G_ELI_VERSION; 290 md.md_flags |= G_ELI_FLAG_ONETIME; 291 md.md_flags |= G_ELI_FLAG_AUTORESIZE; 292 293 detach = gctl_get_paraml(req, "detach", sizeof(*detach)); 294 if (detach != NULL && *detach) 295 md.md_flags |= G_ELI_FLAG_WO_DETACH; 296 noautoresize = gctl_get_paraml(req, "noautoresize", 297 sizeof(*noautoresize)); 298 if (noautoresize != NULL && *noautoresize) 299 md.md_flags &= ~G_ELI_FLAG_AUTORESIZE; 300 notrim = gctl_get_paraml(req, "notrim", sizeof(*notrim)); 301 if (notrim != NULL && *notrim) 302 md.md_flags |= G_ELI_FLAG_NODELETE; 303 304 md.md_ealgo = CRYPTO_ALGORITHM_MIN - 1; 305 name = gctl_get_asciiparam(req, "aalgo"); 306 if (name == NULL) { 307 gctl_error(req, "No '%s' argument.", "aalgo"); 308 return; 309 } 310 if (*name != '\0') { 311 md.md_aalgo = g_eli_str2aalgo(name); 312 if (md.md_aalgo >= CRYPTO_ALGORITHM_MIN && 313 md.md_aalgo <= CRYPTO_ALGORITHM_MAX) { 314 md.md_flags |= G_ELI_FLAG_AUTH; 315 } else { 316 /* 317 * For backward compatibility, check if the -a option 318 * was used to provide encryption algorithm. 319 */ 320 md.md_ealgo = g_eli_str2ealgo(name); 321 if (md.md_ealgo < CRYPTO_ALGORITHM_MIN || 322 md.md_ealgo > CRYPTO_ALGORITHM_MAX) { 323 gctl_error(req, 324 "Invalid authentication algorithm."); 325 return; 326 } else { 327 gctl_error(req, "warning: The -e option, not " 328 "the -a option is now used to specify " 329 "encryption algorithm to use."); 330 } 331 } 332 } 333 334 if (md.md_ealgo < CRYPTO_ALGORITHM_MIN || 335 md.md_ealgo > CRYPTO_ALGORITHM_MAX) { 336 name = gctl_get_asciiparam(req, "ealgo"); 337 if (name == NULL) { 338 gctl_error(req, "No '%s' argument.", "ealgo"); 339 return; 340 } 341 md.md_ealgo = g_eli_str2ealgo(name); 342 if (md.md_ealgo < CRYPTO_ALGORITHM_MIN || 343 md.md_ealgo > CRYPTO_ALGORITHM_MAX) { 344 gctl_error(req, "Invalid encryption algorithm."); 345 return; 346 } 347 } 348 349 keylen = gctl_get_paraml(req, "keylen", sizeof(*keylen)); 350 if (keylen == NULL) { 351 gctl_error(req, "No '%s' argument.", "keylen"); 352 return; 353 } 354 md.md_keylen = g_eli_keylen(md.md_ealgo, *keylen); 355 if (md.md_keylen == 0) { 356 gctl_error(req, "Invalid '%s' argument.", "keylen"); 357 return; 358 } 359 360 /* Not important here. */ 361 md.md_provsize = 0; 362 /* Not important here. */ 363 bzero(md.md_salt, sizeof(md.md_salt)); 364 365 md.md_keys = 0x01; 366 arc4rand(mkey, sizeof(mkey), 0); 367 368 /* Not important here. */ 369 bzero(md.md_hash, sizeof(md.md_hash)); 370 371 name = gctl_get_asciiparam(req, "arg0"); 372 if (name == NULL) { 373 gctl_error(req, "No 'arg%u' argument.", 0); 374 return; 375 } 376 if (strncmp(name, "/dev/", strlen("/dev/")) == 0) 377 name += strlen("/dev/"); 378 pp = g_provider_by_name(name); 379 if (pp == NULL) { 380 gctl_error(req, "Provider %s is invalid.", name); 381 return; 382 } 383 384 sectorsize = gctl_get_paraml(req, "sectorsize", sizeof(*sectorsize)); 385 if (sectorsize == NULL) { 386 gctl_error(req, "No '%s' argument.", "sectorsize"); 387 return; 388 } 389 if (*sectorsize == 0) 390 md.md_sectorsize = pp->sectorsize; 391 else { 392 if (*sectorsize < 0 || (*sectorsize % pp->sectorsize) != 0) { 393 gctl_error(req, "Invalid sector size."); 394 return; 395 } 396 if (*sectorsize > PAGE_SIZE) { 397 gctl_error(req, "warning: Using sectorsize bigger than " 398 "the page size!"); 399 } 400 md.md_sectorsize = *sectorsize; 401 } 402 403 g_eli_create(req, mp, pp, &md, mkey, -1); 404 explicit_bzero(mkey, sizeof(mkey)); 405 explicit_bzero(&md, sizeof(md)); 406 } 407 408 static void 409 g_eli_ctl_configure(struct gctl_req *req, struct g_class *mp) 410 { 411 struct g_eli_softc *sc; 412 struct g_eli_metadata md; 413 struct g_provider *pp; 414 struct g_consumer *cp; 415 char param[16]; 416 const char *prov; 417 u_char *sector; 418 int *nargs, *boot, *noboot, *trim, *notrim, *geliboot, *nogeliboot; 419 int *displaypass, *nodisplaypass, *autoresize, *noautoresize; 420 int zero, error, changed; 421 u_int i; 422 423 g_topology_assert(); 424 425 changed = 0; 426 zero = 0; 427 428 nargs = gctl_get_paraml(req, "nargs", sizeof(*nargs)); 429 if (nargs == NULL) { 430 gctl_error(req, "No '%s' argument.", "nargs"); 431 return; 432 } 433 if (*nargs <= 0) { 434 gctl_error(req, "Missing device(s)."); 435 return; 436 } 437 438 boot = gctl_get_paraml(req, "boot", sizeof(*boot)); 439 if (boot == NULL) 440 boot = &zero; 441 noboot = gctl_get_paraml(req, "noboot", sizeof(*noboot)); 442 if (noboot == NULL) 443 noboot = &zero; 444 if (*boot && *noboot) { 445 gctl_error(req, "Options -b and -B are mutually exclusive."); 446 return; 447 } 448 if (*boot || *noboot) 449 changed = 1; 450 451 trim = gctl_get_paraml(req, "trim", sizeof(*trim)); 452 if (trim == NULL) 453 trim = &zero; 454 notrim = gctl_get_paraml(req, "notrim", sizeof(*notrim)); 455 if (notrim == NULL) 456 notrim = &zero; 457 if (*trim && *notrim) { 458 gctl_error(req, "Options -t and -T are mutually exclusive."); 459 return; 460 } 461 if (*trim || *notrim) 462 changed = 1; 463 464 geliboot = gctl_get_paraml(req, "geliboot", sizeof(*geliboot)); 465 if (geliboot == NULL) 466 geliboot = &zero; 467 nogeliboot = gctl_get_paraml(req, "nogeliboot", sizeof(*nogeliboot)); 468 if (nogeliboot == NULL) 469 nogeliboot = &zero; 470 if (*geliboot && *nogeliboot) { 471 gctl_error(req, "Options -g and -G are mutually exclusive."); 472 return; 473 } 474 if (*geliboot || *nogeliboot) 475 changed = 1; 476 477 displaypass = gctl_get_paraml(req, "displaypass", sizeof(*displaypass)); 478 if (displaypass == NULL) 479 displaypass = &zero; 480 nodisplaypass = gctl_get_paraml(req, "nodisplaypass", sizeof(*nodisplaypass)); 481 if (nodisplaypass == NULL) 482 nodisplaypass = &zero; 483 if (*displaypass && *nodisplaypass) { 484 gctl_error(req, "Options -d and -D are mutually exclusive."); 485 return; 486 } 487 if (*displaypass || *nodisplaypass) 488 changed = 1; 489 490 autoresize = gctl_get_paraml(req, "autoresize", sizeof(*autoresize)); 491 if (autoresize == NULL) 492 autoresize = &zero; 493 noautoresize = gctl_get_paraml(req, "noautoresize", 494 sizeof(*noautoresize)); 495 if (noautoresize == NULL) 496 noautoresize = &zero; 497 if (*autoresize && *noautoresize) { 498 gctl_error(req, "Options -r and -R are mutually exclusive."); 499 return; 500 } 501 if (*autoresize || *noautoresize) 502 changed = 1; 503 504 if (!changed) { 505 gctl_error(req, "No option given."); 506 return; 507 } 508 509 for (i = 0; i < *nargs; i++) { 510 snprintf(param, sizeof(param), "arg%d", i); 511 prov = gctl_get_asciiparam(req, param); 512 if (prov == NULL) { 513 gctl_error(req, "No 'arg%d' argument.", i); 514 return; 515 } 516 sc = g_eli_find_device(mp, prov); 517 if (sc == NULL) { 518 /* 519 * We ignore not attached providers, userland part will 520 * take care of them. 521 */ 522 G_ELI_DEBUG(1, "Skipping configuration of not attached " 523 "provider %s.", prov); 524 continue; 525 } 526 if (sc->sc_flags & G_ELI_FLAG_RO) { 527 gctl_error(req, "Cannot change configuration of " 528 "read-only provider %s.", prov); 529 continue; 530 } 531 532 if (*boot && (sc->sc_flags & G_ELI_FLAG_BOOT)) { 533 G_ELI_DEBUG(1, "BOOT flag already configured for %s.", 534 prov); 535 continue; 536 } else if (*noboot && !(sc->sc_flags & G_ELI_FLAG_BOOT)) { 537 G_ELI_DEBUG(1, "BOOT flag not configured for %s.", 538 prov); 539 continue; 540 } 541 542 if (*notrim && (sc->sc_flags & G_ELI_FLAG_NODELETE)) { 543 G_ELI_DEBUG(1, "TRIM disable flag already configured for %s.", 544 prov); 545 continue; 546 } else if (*trim && !(sc->sc_flags & G_ELI_FLAG_NODELETE)) { 547 G_ELI_DEBUG(1, "TRIM disable flag not configured for %s.", 548 prov); 549 continue; 550 } 551 552 if (*geliboot && (sc->sc_flags & G_ELI_FLAG_GELIBOOT)) { 553 G_ELI_DEBUG(1, "GELIBOOT flag already configured for %s.", 554 prov); 555 continue; 556 } else if (*nogeliboot && !(sc->sc_flags & G_ELI_FLAG_GELIBOOT)) { 557 G_ELI_DEBUG(1, "GELIBOOT flag not configured for %s.", 558 prov); 559 continue; 560 } 561 562 if (*displaypass && (sc->sc_flags & G_ELI_FLAG_GELIDISPLAYPASS)) { 563 G_ELI_DEBUG(1, "GELIDISPLAYPASS flag already configured for %s.", 564 prov); 565 continue; 566 } else if (*nodisplaypass && 567 !(sc->sc_flags & G_ELI_FLAG_GELIDISPLAYPASS)) { 568 G_ELI_DEBUG(1, "GELIDISPLAYPASS flag not configured for %s.", 569 prov); 570 continue; 571 } 572 573 if (*autoresize && (sc->sc_flags & G_ELI_FLAG_AUTORESIZE)) { 574 G_ELI_DEBUG(1, "AUTORESIZE flag already configured for %s.", 575 prov); 576 continue; 577 } else if (*noautoresize && 578 !(sc->sc_flags & G_ELI_FLAG_AUTORESIZE)) { 579 G_ELI_DEBUG(1, "AUTORESIZE flag not configured for %s.", 580 prov); 581 continue; 582 } 583 584 if (!(sc->sc_flags & G_ELI_FLAG_ONETIME)) { 585 /* 586 * ONETIME providers don't write metadata to 587 * disk, so don't try reading it. This means 588 * we're bit-flipping uninitialized memory in md 589 * below, but that's OK; we don't do anything 590 * with it later. 591 */ 592 cp = LIST_FIRST(&sc->sc_geom->consumer); 593 pp = cp->provider; 594 error = g_eli_read_metadata(mp, pp, &md); 595 if (error != 0) { 596 gctl_error(req, 597 "Cannot read metadata from %s (error=%d).", 598 prov, error); 599 continue; 600 } 601 } 602 603 if (*boot) { 604 md.md_flags |= G_ELI_FLAG_BOOT; 605 sc->sc_flags |= G_ELI_FLAG_BOOT; 606 } else if (*noboot) { 607 md.md_flags &= ~G_ELI_FLAG_BOOT; 608 sc->sc_flags &= ~G_ELI_FLAG_BOOT; 609 } 610 611 if (*notrim) { 612 md.md_flags |= G_ELI_FLAG_NODELETE; 613 sc->sc_flags |= G_ELI_FLAG_NODELETE; 614 } else if (*trim) { 615 md.md_flags &= ~G_ELI_FLAG_NODELETE; 616 sc->sc_flags &= ~G_ELI_FLAG_NODELETE; 617 } 618 619 if (*geliboot) { 620 md.md_flags |= G_ELI_FLAG_GELIBOOT; 621 sc->sc_flags |= G_ELI_FLAG_GELIBOOT; 622 } else if (*nogeliboot) { 623 md.md_flags &= ~G_ELI_FLAG_GELIBOOT; 624 sc->sc_flags &= ~G_ELI_FLAG_GELIBOOT; 625 } 626 627 if (*displaypass) { 628 md.md_flags |= G_ELI_FLAG_GELIDISPLAYPASS; 629 sc->sc_flags |= G_ELI_FLAG_GELIDISPLAYPASS; 630 } else if (*nodisplaypass) { 631 md.md_flags &= ~G_ELI_FLAG_GELIDISPLAYPASS; 632 sc->sc_flags &= ~G_ELI_FLAG_GELIDISPLAYPASS; 633 } 634 635 if (*autoresize) { 636 md.md_flags |= G_ELI_FLAG_AUTORESIZE; 637 sc->sc_flags |= G_ELI_FLAG_AUTORESIZE; 638 } else if (*noautoresize) { 639 md.md_flags &= ~G_ELI_FLAG_AUTORESIZE; 640 sc->sc_flags &= ~G_ELI_FLAG_AUTORESIZE; 641 } 642 643 if (sc->sc_flags & G_ELI_FLAG_ONETIME) { 644 /* There's no metadata on disk so we are done here. */ 645 continue; 646 } 647 648 sector = malloc(pp->sectorsize, M_ELI, M_WAITOK | M_ZERO); 649 eli_metadata_encode(&md, sector); 650 error = g_write_data(cp, pp->mediasize - pp->sectorsize, sector, 651 pp->sectorsize); 652 if (error != 0) { 653 gctl_error(req, 654 "Cannot store metadata on %s (error=%d).", 655 prov, error); 656 } 657 explicit_bzero(&md, sizeof(md)); 658 explicit_bzero(sector, pp->sectorsize); 659 free(sector, M_ELI); 660 } 661 } 662 663 static void 664 g_eli_ctl_setkey(struct gctl_req *req, struct g_class *mp) 665 { 666 struct g_eli_softc *sc; 667 struct g_eli_metadata md; 668 struct g_provider *pp; 669 struct g_consumer *cp; 670 const char *name; 671 u_char *key, *mkeydst, *sector; 672 intmax_t *valp; 673 int keysize, nkey, error; 674 675 g_topology_assert(); 676 677 name = gctl_get_asciiparam(req, "arg0"); 678 if (name == NULL) { 679 gctl_error(req, "No 'arg%u' argument.", 0); 680 return; 681 } 682 key = gctl_get_param(req, "key", &keysize); 683 if (key == NULL || keysize != G_ELI_USERKEYLEN) { 684 gctl_error(req, "No '%s' argument.", "key"); 685 return; 686 } 687 sc = g_eli_find_device(mp, name); 688 if (sc == NULL) { 689 gctl_error(req, "Provider %s is invalid.", name); 690 return; 691 } 692 if (sc->sc_flags & G_ELI_FLAG_RO) { 693 gctl_error(req, "Cannot change keys for read-only provider."); 694 return; 695 } 696 cp = LIST_FIRST(&sc->sc_geom->consumer); 697 pp = cp->provider; 698 699 error = g_eli_read_metadata(mp, pp, &md); 700 if (error != 0) { 701 gctl_error(req, "Cannot read metadata from %s (error=%d).", 702 name, error); 703 return; 704 } 705 706 valp = gctl_get_paraml(req, "keyno", sizeof(*valp)); 707 if (valp == NULL) { 708 gctl_error(req, "No '%s' argument.", "keyno"); 709 return; 710 } 711 if (*valp != -1) 712 nkey = *valp; 713 else 714 nkey = sc->sc_nkey; 715 if (nkey < 0 || nkey >= G_ELI_MAXMKEYS) { 716 gctl_error(req, "Invalid '%s' argument.", "keyno"); 717 return; 718 } 719 720 valp = gctl_get_paraml(req, "iterations", sizeof(*valp)); 721 if (valp == NULL) { 722 gctl_error(req, "No '%s' argument.", "iterations"); 723 return; 724 } 725 /* Check if iterations number should and can be changed. */ 726 if (*valp != -1 && md.md_iterations == -1) { 727 md.md_iterations = *valp; 728 } else if (*valp != -1 && *valp != md.md_iterations) { 729 if (bitcount32(md.md_keys) != 1) { 730 gctl_error(req, "To be able to use '-i' option, only " 731 "one key can be defined."); 732 return; 733 } 734 if (md.md_keys != (1 << nkey)) { 735 gctl_error(req, "Only already defined key can be " 736 "changed when '-i' option is used."); 737 return; 738 } 739 md.md_iterations = *valp; 740 } 741 742 mkeydst = md.md_mkeys + nkey * G_ELI_MKEYLEN; 743 md.md_keys |= (1 << nkey); 744 745 bcopy(sc->sc_mkey, mkeydst, sizeof(sc->sc_mkey)); 746 747 /* Encrypt Master Key with the new key. */ 748 error = g_eli_mkey_encrypt(md.md_ealgo, key, md.md_keylen, mkeydst); 749 explicit_bzero(key, keysize); 750 if (error != 0) { 751 explicit_bzero(&md, sizeof(md)); 752 gctl_error(req, "Cannot encrypt Master Key (error=%d).", error); 753 return; 754 } 755 756 sector = malloc(pp->sectorsize, M_ELI, M_WAITOK | M_ZERO); 757 /* Store metadata with fresh key. */ 758 eli_metadata_encode(&md, sector); 759 explicit_bzero(&md, sizeof(md)); 760 error = g_write_data(cp, pp->mediasize - pp->sectorsize, sector, 761 pp->sectorsize); 762 explicit_bzero(sector, pp->sectorsize); 763 free(sector, M_ELI); 764 if (error != 0) { 765 gctl_error(req, "Cannot store metadata on %s (error=%d).", 766 pp->name, error); 767 return; 768 } 769 G_ELI_DEBUG(1, "Key %u changed on %s.", nkey, pp->name); 770 } 771 772 static void 773 g_eli_ctl_delkey(struct gctl_req *req, struct g_class *mp) 774 { 775 struct g_eli_softc *sc; 776 struct g_eli_metadata md; 777 struct g_provider *pp; 778 struct g_consumer *cp; 779 const char *name; 780 u_char *mkeydst, *sector; 781 intmax_t *valp; 782 size_t keysize; 783 int error, nkey, *all, *force; 784 u_int i; 785 786 g_topology_assert(); 787 788 nkey = 0; /* fixes causeless gcc warning */ 789 790 name = gctl_get_asciiparam(req, "arg0"); 791 if (name == NULL) { 792 gctl_error(req, "No 'arg%u' argument.", 0); 793 return; 794 } 795 sc = g_eli_find_device(mp, name); 796 if (sc == NULL) { 797 gctl_error(req, "Provider %s is invalid.", name); 798 return; 799 } 800 if (sc->sc_flags & G_ELI_FLAG_RO) { 801 gctl_error(req, "Cannot delete keys for read-only provider."); 802 return; 803 } 804 cp = LIST_FIRST(&sc->sc_geom->consumer); 805 pp = cp->provider; 806 807 error = g_eli_read_metadata(mp, pp, &md); 808 if (error != 0) { 809 gctl_error(req, "Cannot read metadata from %s (error=%d).", 810 name, error); 811 return; 812 } 813 814 all = gctl_get_paraml(req, "all", sizeof(*all)); 815 if (all == NULL) { 816 gctl_error(req, "No '%s' argument.", "all"); 817 return; 818 } 819 820 if (*all) { 821 mkeydst = md.md_mkeys; 822 keysize = sizeof(md.md_mkeys); 823 } else { 824 force = gctl_get_paraml(req, "force", sizeof(*force)); 825 if (force == NULL) { 826 gctl_error(req, "No '%s' argument.", "force"); 827 return; 828 } 829 830 valp = gctl_get_paraml(req, "keyno", sizeof(*valp)); 831 if (valp == NULL) { 832 gctl_error(req, "No '%s' argument.", "keyno"); 833 return; 834 } 835 if (*valp != -1) 836 nkey = *valp; 837 else 838 nkey = sc->sc_nkey; 839 if (nkey < 0 || nkey >= G_ELI_MAXMKEYS) { 840 gctl_error(req, "Invalid '%s' argument.", "keyno"); 841 return; 842 } 843 if (!(md.md_keys & (1 << nkey)) && !*force) { 844 gctl_error(req, "Master Key %u is not set.", nkey); 845 return; 846 } 847 md.md_keys &= ~(1 << nkey); 848 if (md.md_keys == 0 && !*force) { 849 gctl_error(req, "This is the last Master Key. Use '-f' " 850 "flag if you really want to remove it."); 851 return; 852 } 853 mkeydst = md.md_mkeys + nkey * G_ELI_MKEYLEN; 854 keysize = G_ELI_MKEYLEN; 855 } 856 857 sector = malloc(pp->sectorsize, M_ELI, M_WAITOK | M_ZERO); 858 for (i = 0; i <= g_eli_overwrites; i++) { 859 if (i == g_eli_overwrites) 860 explicit_bzero(mkeydst, keysize); 861 else 862 arc4rand(mkeydst, keysize, 0); 863 /* Store metadata with destroyed key. */ 864 eli_metadata_encode(&md, sector); 865 error = g_write_data(cp, pp->mediasize - pp->sectorsize, sector, 866 pp->sectorsize); 867 if (error != 0) { 868 G_ELI_DEBUG(0, "Cannot store metadata on %s " 869 "(error=%d).", pp->name, error); 870 } 871 /* 872 * Flush write cache so we don't overwrite data N times in cache 873 * and only once on disk. 874 */ 875 (void)g_io_flush(cp); 876 } 877 explicit_bzero(&md, sizeof(md)); 878 explicit_bzero(sector, pp->sectorsize); 879 free(sector, M_ELI); 880 if (*all) 881 G_ELI_DEBUG(1, "All keys removed from %s.", pp->name); 882 else 883 G_ELI_DEBUG(1, "Key %d removed from %s.", nkey, pp->name); 884 } 885 886 static void 887 g_eli_suspend_one(struct g_eli_softc *sc, struct gctl_req *req) 888 { 889 struct g_eli_worker *wr; 890 891 g_topology_assert(); 892 893 KASSERT(sc != NULL, ("NULL sc")); 894 895 if (sc->sc_flags & G_ELI_FLAG_ONETIME) { 896 gctl_error(req, 897 "Device %s is using one-time key, suspend not supported.", 898 sc->sc_name); 899 return; 900 } 901 902 mtx_lock(&sc->sc_queue_mtx); 903 if (sc->sc_flags & G_ELI_FLAG_SUSPEND) { 904 mtx_unlock(&sc->sc_queue_mtx); 905 gctl_error(req, "Device %s already suspended.", 906 sc->sc_name); 907 return; 908 } 909 sc->sc_flags |= G_ELI_FLAG_SUSPEND; 910 wakeup(sc); 911 for (;;) { 912 LIST_FOREACH(wr, &sc->sc_workers, w_next) { 913 if (wr->w_active) 914 break; 915 } 916 if (wr == NULL) 917 break; 918 /* Not all threads suspended. */ 919 msleep(&sc->sc_workers, &sc->sc_queue_mtx, PRIBIO, 920 "geli:suspend", 0); 921 } 922 /* 923 * Clear sensitive data on suspend, they will be recovered on resume. 924 */ 925 explicit_bzero(sc->sc_mkey, sizeof(sc->sc_mkey)); 926 g_eli_key_destroy(sc); 927 explicit_bzero(sc->sc_akey, sizeof(sc->sc_akey)); 928 explicit_bzero(&sc->sc_akeyctx, sizeof(sc->sc_akeyctx)); 929 explicit_bzero(sc->sc_ivkey, sizeof(sc->sc_ivkey)); 930 explicit_bzero(&sc->sc_ivctx, sizeof(sc->sc_ivctx)); 931 mtx_unlock(&sc->sc_queue_mtx); 932 G_ELI_DEBUG(0, "Device %s has been suspended.", sc->sc_name); 933 } 934 935 static void 936 g_eli_ctl_suspend(struct gctl_req *req, struct g_class *mp) 937 { 938 struct g_eli_softc *sc; 939 int *all, *nargs; 940 941 g_topology_assert(); 942 943 nargs = gctl_get_paraml(req, "nargs", sizeof(*nargs)); 944 if (nargs == NULL) { 945 gctl_error(req, "No '%s' argument.", "nargs"); 946 return; 947 } 948 all = gctl_get_paraml(req, "all", sizeof(*all)); 949 if (all == NULL) { 950 gctl_error(req, "No '%s' argument.", "all"); 951 return; 952 } 953 if (!*all && *nargs == 0) { 954 gctl_error(req, "Too few arguments."); 955 return; 956 } 957 958 if (*all) { 959 struct g_geom *gp, *gp2; 960 961 LIST_FOREACH_SAFE(gp, &mp->geom, geom, gp2) { 962 sc = gp->softc; 963 if (sc->sc_flags & G_ELI_FLAG_ONETIME) { 964 G_ELI_DEBUG(0, 965 "Device %s is using one-time key, suspend not supported, skipping.", 966 sc->sc_name); 967 continue; 968 } 969 g_eli_suspend_one(sc, req); 970 } 971 } else { 972 const char *prov; 973 char param[16]; 974 int i; 975 976 for (i = 0; i < *nargs; i++) { 977 snprintf(param, sizeof(param), "arg%d", i); 978 prov = gctl_get_asciiparam(req, param); 979 if (prov == NULL) { 980 G_ELI_DEBUG(0, "No 'arg%d' argument.", i); 981 continue; 982 } 983 984 sc = g_eli_find_device(mp, prov); 985 if (sc == NULL) { 986 G_ELI_DEBUG(0, "No such provider: %s.", prov); 987 continue; 988 } 989 g_eli_suspend_one(sc, req); 990 } 991 } 992 } 993 994 static void 995 g_eli_ctl_resume(struct gctl_req *req, struct g_class *mp) 996 { 997 struct g_eli_metadata md; 998 struct g_eli_softc *sc; 999 struct g_provider *pp; 1000 struct g_consumer *cp; 1001 const char *name; 1002 u_char *key, mkey[G_ELI_DATAIVKEYLEN]; 1003 int *nargs, keysize, error; 1004 u_int nkey; 1005 1006 g_topology_assert(); 1007 1008 nargs = gctl_get_paraml(req, "nargs", sizeof(*nargs)); 1009 if (nargs == NULL) { 1010 gctl_error(req, "No '%s' argument.", "nargs"); 1011 return; 1012 } 1013 if (*nargs != 1) { 1014 gctl_error(req, "Invalid number of arguments."); 1015 return; 1016 } 1017 1018 name = gctl_get_asciiparam(req, "arg0"); 1019 if (name == NULL) { 1020 gctl_error(req, "No 'arg%u' argument.", 0); 1021 return; 1022 } 1023 key = gctl_get_param(req, "key", &keysize); 1024 if (key == NULL || keysize != G_ELI_USERKEYLEN) { 1025 gctl_error(req, "No '%s' argument.", "key"); 1026 return; 1027 } 1028 sc = g_eli_find_device(mp, name); 1029 if (sc == NULL) { 1030 gctl_error(req, "Provider %s is invalid.", name); 1031 return; 1032 } 1033 cp = LIST_FIRST(&sc->sc_geom->consumer); 1034 pp = cp->provider; 1035 error = g_eli_read_metadata(mp, pp, &md); 1036 if (error != 0) { 1037 gctl_error(req, "Cannot read metadata from %s (error=%d).", 1038 name, error); 1039 return; 1040 } 1041 if (md.md_keys == 0x00) { 1042 explicit_bzero(&md, sizeof(md)); 1043 gctl_error(req, "No valid keys on %s.", pp->name); 1044 return; 1045 } 1046 1047 error = g_eli_mkey_decrypt_any(&md, key, mkey, &nkey); 1048 explicit_bzero(key, keysize); 1049 if (error == -1) { 1050 explicit_bzero(&md, sizeof(md)); 1051 gctl_error(req, "Wrong key for %s.", pp->name); 1052 return; 1053 } else if (error > 0) { 1054 explicit_bzero(&md, sizeof(md)); 1055 gctl_error(req, "Cannot decrypt Master Key for %s (error=%d).", 1056 pp->name, error); 1057 return; 1058 } 1059 G_ELI_DEBUG(1, "Using Master Key %u for %s.", nkey, pp->name); 1060 1061 mtx_lock(&sc->sc_queue_mtx); 1062 if (!(sc->sc_flags & G_ELI_FLAG_SUSPEND)) 1063 gctl_error(req, "Device %s is not suspended.", name); 1064 else { 1065 /* Restore sc_mkey, sc_ekeys, sc_akey and sc_ivkey. */ 1066 g_eli_mkey_propagate(sc, mkey); 1067 sc->sc_flags &= ~G_ELI_FLAG_SUSPEND; 1068 G_ELI_DEBUG(1, "Resumed %s.", pp->name); 1069 wakeup(sc); 1070 } 1071 mtx_unlock(&sc->sc_queue_mtx); 1072 explicit_bzero(mkey, sizeof(mkey)); 1073 explicit_bzero(&md, sizeof(md)); 1074 } 1075 1076 static int 1077 g_eli_kill_one(struct g_eli_softc *sc) 1078 { 1079 struct g_provider *pp; 1080 struct g_consumer *cp; 1081 int error = 0; 1082 1083 g_topology_assert(); 1084 1085 if (sc == NULL) 1086 return (ENOENT); 1087 1088 pp = LIST_FIRST(&sc->sc_geom->provider); 1089 g_error_provider(pp, ENXIO); 1090 1091 cp = LIST_FIRST(&sc->sc_geom->consumer); 1092 pp = cp->provider; 1093 1094 if (sc->sc_flags & G_ELI_FLAG_RO) { 1095 G_ELI_DEBUG(0, "WARNING: Metadata won't be erased on read-only " 1096 "provider: %s.", pp->name); 1097 } else { 1098 u_char *sector; 1099 u_int i; 1100 int err; 1101 1102 sector = malloc(pp->sectorsize, M_ELI, M_WAITOK); 1103 for (i = 0; i <= g_eli_overwrites; i++) { 1104 if (i == g_eli_overwrites) 1105 bzero(sector, pp->sectorsize); 1106 else 1107 arc4rand(sector, pp->sectorsize, 0); 1108 err = g_write_data(cp, pp->mediasize - pp->sectorsize, 1109 sector, pp->sectorsize); 1110 if (err != 0) { 1111 G_ELI_DEBUG(0, "Cannot erase metadata on %s " 1112 "(error=%d).", pp->name, err); 1113 if (error == 0) 1114 error = err; 1115 } 1116 /* 1117 * Flush write cache so we don't overwrite data N times 1118 * in cache and only once on disk. 1119 */ 1120 (void)g_io_flush(cp); 1121 } 1122 free(sector, M_ELI); 1123 } 1124 if (error == 0) 1125 G_ELI_DEBUG(0, "%s has been killed.", pp->name); 1126 g_eli_destroy(sc, TRUE); 1127 return (error); 1128 } 1129 1130 static void 1131 g_eli_ctl_kill(struct gctl_req *req, struct g_class *mp) 1132 { 1133 int *all, *nargs; 1134 int error; 1135 1136 g_topology_assert(); 1137 1138 nargs = gctl_get_paraml(req, "nargs", sizeof(*nargs)); 1139 if (nargs == NULL) { 1140 gctl_error(req, "No '%s' argument.", "nargs"); 1141 return; 1142 } 1143 all = gctl_get_paraml(req, "all", sizeof(*all)); 1144 if (all == NULL) { 1145 gctl_error(req, "No '%s' argument.", "all"); 1146 return; 1147 } 1148 if (!*all && *nargs == 0) { 1149 gctl_error(req, "Too few arguments."); 1150 return; 1151 } 1152 1153 if (*all) { 1154 struct g_geom *gp, *gp2; 1155 1156 LIST_FOREACH_SAFE(gp, &mp->geom, geom, gp2) { 1157 error = g_eli_kill_one(gp->softc); 1158 if (error != 0) 1159 gctl_error(req, "Not fully done."); 1160 } 1161 } else { 1162 struct g_eli_softc *sc; 1163 const char *prov; 1164 char param[16]; 1165 int i; 1166 1167 for (i = 0; i < *nargs; i++) { 1168 snprintf(param, sizeof(param), "arg%d", i); 1169 prov = gctl_get_asciiparam(req, param); 1170 if (prov == NULL) { 1171 G_ELI_DEBUG(0, "No 'arg%d' argument.", i); 1172 continue; 1173 } 1174 1175 sc = g_eli_find_device(mp, prov); 1176 if (sc == NULL) { 1177 G_ELI_DEBUG(0, "No such provider: %s.", prov); 1178 continue; 1179 } 1180 error = g_eli_kill_one(sc); 1181 if (error != 0) 1182 gctl_error(req, "Not fully done."); 1183 } 1184 } 1185 } 1186 1187 void 1188 g_eli_config(struct gctl_req *req, struct g_class *mp, const char *verb) 1189 { 1190 uint32_t *version; 1191 1192 g_topology_assert(); 1193 1194 version = gctl_get_paraml(req, "version", sizeof(*version)); 1195 if (version == NULL) { 1196 gctl_error(req, "No '%s' argument.", "version"); 1197 return; 1198 } 1199 while (*version != G_ELI_VERSION) { 1200 if (G_ELI_VERSION == G_ELI_VERSION_06 && 1201 *version == G_ELI_VERSION_05) { 1202 /* Compatible. */ 1203 break; 1204 } 1205 if (G_ELI_VERSION == G_ELI_VERSION_07 && 1206 (*version == G_ELI_VERSION_05 || 1207 *version == G_ELI_VERSION_06)) { 1208 /* Compatible. */ 1209 break; 1210 } 1211 gctl_error(req, "Userland and kernel parts are out of sync."); 1212 return; 1213 } 1214 1215 if (strcmp(verb, "attach") == 0) 1216 g_eli_ctl_attach(req, mp); 1217 else if (strcmp(verb, "detach") == 0 || strcmp(verb, "stop") == 0) 1218 g_eli_ctl_detach(req, mp); 1219 else if (strcmp(verb, "onetime") == 0) 1220 g_eli_ctl_onetime(req, mp); 1221 else if (strcmp(verb, "configure") == 0) 1222 g_eli_ctl_configure(req, mp); 1223 else if (strcmp(verb, "setkey") == 0) 1224 g_eli_ctl_setkey(req, mp); 1225 else if (strcmp(verb, "delkey") == 0) 1226 g_eli_ctl_delkey(req, mp); 1227 else if (strcmp(verb, "suspend") == 0) 1228 g_eli_ctl_suspend(req, mp); 1229 else if (strcmp(verb, "resume") == 0) 1230 g_eli_ctl_resume(req, mp); 1231 else if (strcmp(verb, "kill") == 0) 1232 g_eli_ctl_kill(req, mp); 1233 else 1234 gctl_error(req, "Unknown verb."); 1235 } 1236