From owner-svn-src-all@freebsd.org Fri Apr 8 01:25:26 2016 Return-Path: Delivered-To: svn-src-all@mailman.ysv.freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:1900:2254:206a::19:1]) by mailman.ysv.freebsd.org (Postfix) with ESMTP id ED353B082AB; Fri, 8 Apr 2016 01:25:26 +0000 (UTC) (envelope-from allanjude@FreeBSD.org) Received: from repo.freebsd.org (repo.freebsd.org [IPv6:2610:1c1:1:6068::e6a:0]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (Client did not present a certificate) by mx1.freebsd.org (Postfix) with ESMTPS id AFAB51EA4; Fri, 8 Apr 2016 01:25:26 +0000 (UTC) (envelope-from allanjude@FreeBSD.org) Received: from repo.freebsd.org ([127.0.1.37]) by repo.freebsd.org (8.15.2/8.15.2) with ESMTP id u381PPnP005930; Fri, 8 Apr 2016 01:25:25 GMT (envelope-from allanjude@FreeBSD.org) Received: (from allanjude@localhost) by repo.freebsd.org (8.15.2/8.15.2/Submit) id u381PPsx005925; Fri, 8 Apr 2016 01:25:25 GMT (envelope-from allanjude@FreeBSD.org) Message-Id: <201604080125.u381PPsx005925@repo.freebsd.org> X-Authentication-Warning: repo.freebsd.org: allanjude set sender to allanjude@FreeBSD.org using -f From: Allan Jude Date: Fri, 8 Apr 2016 01:25:25 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r297691 - in head: sbin/geom/class/eli sys/geom/eli X-SVN-Group: head MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-BeenThere: svn-src-all@freebsd.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: "SVN commit messages for the entire src tree \(except for " user" and " projects" \)" List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Fri, 08 Apr 2016 01:25:27 -0000 Author: allanjude Date: Fri Apr 8 01:25:25 2016 New Revision: 297691 URL: https://svnweb.freebsd.org/changeset/base/297691 Log: Create the GELIBOOT GEOM_ELI flag This flag indicates that the user wishes to use the GELIBOOT feature to boot from a fully encrypted root file system. Currently, GELIBOOT does not support key files, and in the future when it does, they will be loaded differently. Due to the design of GELI, and the desire for secrecy, the GELI metadata does not know if key files are used or not, it just adds the key material (if any) to the HMAC before the optional passphrase, so there is no way to tell if a GELI partition requires key files or not. Since the GELIBOOT code in boot2 and the loader does not support keys, they will now only attempt to attach if this flag is set. This will stop GELIBOOT from prompting for passwords to GELIs that it cannot decrypt, disrupting the boot process PR: 208251 Reviewed by: ed, oshogbo, wblock Sponsored by: ScaleEngine Inc. Differential Revision: https://reviews.freebsd.org/D5867 Modified: head/sbin/geom/class/eli/geli.8 head/sbin/geom/class/eli/geom_eli.c head/sys/geom/eli/g_eli.c head/sys/geom/eli/g_eli.h head/sys/geom/eli/g_eli_ctl.c Modified: head/sbin/geom/class/eli/geli.8 ============================================================================== --- head/sbin/geom/class/eli/geli.8 Fri Apr 8 00:24:21 2016 (r297690) +++ head/sbin/geom/class/eli/geli.8 Fri Apr 8 01:25:25 2016 (r297691) @@ -51,7 +51,7 @@ utility: .Pp .Nm .Cm init -.Op Fl bPTv +.Op Fl bgPTv .Op Fl a Ar aalgo .Op Fl B Ar backupfile .Op Fl e Ar ealgo @@ -88,7 +88,7 @@ utility: .Ar prov .Nm .Cm configure -.Op Fl bBtT +.Op Fl bBgGtT .Ar prov ... .Nm .Cm setkey @@ -293,6 +293,11 @@ The default and recommended algorithm is .Nm AES-XTS . .Nm NULL is unencrypted. +.It Fl g +Enable booting from this encrypted root filesystem. +The boot loader prompts for the passphrase and loads +.Xr loader 8 +from the encrypted partition. .It Fl i Ar iterations Number of iterations to use with PKCS#5v2 when processing User Key passphrase component. @@ -485,6 +490,13 @@ For more information, see the descriptio subcommand. .It Fl B Remove the BOOT flag from the given providers. +.It Fl g +Enable booting from this encrypted root filesystem. +The boot loader prompts for the passphrase and loads +.Xr loader 8 +from the encrypted partition. +.It Fl G +Deactivate booting from this encrypted root partition. .It Fl t Enable TRIM/UNMAP passthru. For more information, see the description of the Modified: head/sbin/geom/class/eli/geom_eli.c ============================================================================== --- head/sbin/geom/class/eli/geom_eli.c Fri Apr 8 00:24:21 2016 (r297690) +++ head/sbin/geom/class/eli/geom_eli.c Fri Apr 8 01:25:25 2016 (r297691) @@ -82,13 +82,13 @@ static int eli_backup_create(struct gctl /* * Available commands: * - * init [-bhPv] [-a aalgo] [-B backupfile] [-e ealgo] [-i iterations] [-l keylen] [-J newpassfile] [-K newkeyfile] [-V version] prov + * init [-bgPTv] [-a aalgo] [-B backupfile] [-e ealgo] [-i iterations] [-l keylen] [-J newpassfile] [-K newkeyfile] [-s sectorsize] [-V version] prov * label - alias for 'init' * attach [-dprv] [-j passfile] [-k keyfile] prov * detach [-fl] prov ... * stop - alias for 'detach' * onetime [-d] [-a aalgo] [-e ealgo] [-l keylen] prov - * configure [-bB] prov ... + * configure [-bBgGtT] prov ... * setkey [-pPv] [-n keyno] [-j passfile] [-J newpassfile] [-k keyfile] [-K newkeyfile] prov * delkey [-afv] [-n keyno] prov * suspend [-v] -a | prov ... @@ -108,6 +108,7 @@ struct g_command class_commands[] = { { 'b', "boot", NULL, G_TYPE_BOOL }, { 'B', "backupfile", "", G_TYPE_STRING }, { 'e', "ealgo", "", G_TYPE_STRING }, + { 'g', "geliboot", NULL, G_TYPE_BOOL }, { 'i', "iterations", "-1", G_TYPE_NUMBER }, { 'J', "newpassfile", G_VAL_OPTIONAL, G_TYPE_STRING | G_TYPE_MULTI }, { 'K', "newkeyfile", G_VAL_OPTIONAL, G_TYPE_STRING | G_TYPE_MULTI }, @@ -118,7 +119,7 @@ struct g_command class_commands[] = { { 'V', "mdversion", "-1", G_TYPE_NUMBER }, G_OPT_SENTINEL }, - "[-bPTv] [-a aalgo] [-B backupfile] [-e ealgo] [-i iterations] [-l keylen] [-J newpassfile] [-K newkeyfile] [-s sectorsize] [-V version] prov" + "[-bgPTv] [-a aalgo] [-B backupfile] [-e ealgo] [-i iterations] [-l keylen] [-J newpassfile] [-K newkeyfile] [-s sectorsize] [-V version] prov" }, { "label", G_FLAG_VERBOSE, eli_main, { @@ -126,6 +127,7 @@ struct g_command class_commands[] = { { 'b', "boot", NULL, G_TYPE_BOOL }, { 'B', "backupfile", "", G_TYPE_STRING }, { 'e', "ealgo", "", G_TYPE_STRING }, + { 'g', "geliboot", NULL, G_TYPE_BOOL }, { 'i', "iterations", "-1", G_TYPE_NUMBER }, { 'J', "newpassfile", G_VAL_OPTIONAL, G_TYPE_STRING | G_TYPE_MULTI }, { 'K', "newkeyfile", G_VAL_OPTIONAL, G_TYPE_STRING | G_TYPE_MULTI }, @@ -180,11 +182,13 @@ struct g_command class_commands[] = { { { 'b', "boot", NULL, G_TYPE_BOOL }, { 'B', "noboot", NULL, G_TYPE_BOOL }, + { 'g', "geliboot", NULL, G_TYPE_BOOL }, + { 'G', "nogeliboot", NULL, G_TYPE_BOOL }, { 't', "trim", NULL, G_TYPE_BOOL }, { 'T', "notrim", NULL, G_TYPE_BOOL }, G_OPT_SENTINEL }, - "[-bBtT] prov ..." + "[-bBgGtT] prov ..." }, { "setkey", G_FLAG_VERBOSE, eli_main, { @@ -702,6 +706,8 @@ eli_init(struct gctl_req *req) md.md_flags = 0; if (gctl_get_int(req, "boot")) md.md_flags |= G_ELI_FLAG_BOOT; + if (gctl_get_int(req, "geliboot")) + md.md_flags |= G_ELI_FLAG_GELIBOOT; if (gctl_get_int(req, "notrim")) md.md_flags |= G_ELI_FLAG_NODELETE; md.md_ealgo = CRYPTO_ALGORITHM_MIN - 1; @@ -906,7 +912,7 @@ eli_attach(struct gctl_req *req) static void eli_configure_detached(struct gctl_req *req, const char *prov, int boot, - int trim) + int geliboot, int trim) { struct g_eli_metadata md; bool changed = 0; @@ -928,6 +934,20 @@ eli_configure_detached(struct gctl_req * changed = 1; } + if (geliboot == 1 && (md.md_flags & G_ELI_FLAG_GELIBOOT)) { + if (verbose) + printf("GELIBOOT flag already configured for %s.\n", prov); + } else if (geliboot == 0 && !(md.md_flags & G_ELI_FLAG_GELIBOOT)) { + if (verbose) + printf("GELIBOOT flag not configured for %s.\n", prov); + } else if (geliboot >= 0) { + if (geliboot) + md.md_flags |= G_ELI_FLAG_GELIBOOT; + else + md.md_flags &= ~G_ELI_FLAG_GELIBOOT; + changed = 1; + } + if (trim == 0 && (md.md_flags & G_ELI_FLAG_NODELETE)) { if (verbose) printf("TRIM disable flag already configured for %s.\n", prov); @@ -951,8 +971,8 @@ static void eli_configure(struct gctl_req *req) { const char *prov; - bool boot, noboot, trim, notrim; - int doboot, dotrim; + bool boot, noboot, geliboot, nogeliboot, trim, notrim; + int doboot, dogeliboot, dotrim; int i, nargs; nargs = gctl_get_int(req, "nargs"); @@ -963,6 +983,8 @@ eli_configure(struct gctl_req *req) boot = gctl_get_int(req, "boot"); noboot = gctl_get_int(req, "noboot"); + geliboot = gctl_get_int(req, "geliboot"); + nogeliboot = gctl_get_int(req, "nogeliboot"); trim = gctl_get_int(req, "trim"); notrim = gctl_get_int(req, "notrim"); @@ -976,6 +998,16 @@ eli_configure(struct gctl_req *req) else if (noboot) doboot = 0; + dogeliboot = -1; + if (geliboot && nogeliboot) { + gctl_error(req, "Options -g and -G are mutually exclusive."); + return; + } + if (geliboot) + dogeliboot = 1; + else if (nogeliboot) + dogeliboot = 0; + dotrim = -1; if (trim && notrim) { gctl_error(req, "Options -t and -T are mutually exclusive."); @@ -986,7 +1018,7 @@ eli_configure(struct gctl_req *req) else if (notrim) dotrim = 0; - if (doboot == -1 && dotrim == -1) { + if (doboot == -1 && dogeliboot == -1 && dotrim == -1) { gctl_error(req, "No option given."); return; } @@ -997,7 +1029,7 @@ eli_configure(struct gctl_req *req) for (i = 0; i < nargs; i++) { prov = gctl_get_ascii(req, "arg%d", i); if (!eli_is_attached(prov)) - eli_configure_detached(req, prov, doboot, dotrim); + eli_configure_detached(req, prov, doboot, dogeliboot, dotrim); } } Modified: head/sys/geom/eli/g_eli.c ============================================================================== --- head/sys/geom/eli/g_eli.c Fri Apr 8 00:24:21 2016 (r297690) +++ head/sys/geom/eli/g_eli.c Fri Apr 8 01:25:25 2016 (r297691) @@ -1181,6 +1181,7 @@ g_eli_dumpconf(struct sbuf *sb, const ch ADD_FLAG(G_ELI_FLAG_DESTROY, "DESTROY"); ADD_FLAG(G_ELI_FLAG_RO, "READ-ONLY"); ADD_FLAG(G_ELI_FLAG_NODELETE, "NODELETE"); + ADD_FLAG(G_ELI_FLAG_GELIBOOT, "GELIBOOT"); #undef ADD_FLAG } sbuf_printf(sb, "\n"); Modified: head/sys/geom/eli/g_eli.h ============================================================================== --- head/sys/geom/eli/g_eli.h Fri Apr 8 00:24:21 2016 (r297690) +++ head/sys/geom/eli/g_eli.h Fri Apr 8 01:25:25 2016 (r297691) @@ -97,6 +97,8 @@ #define G_ELI_FLAG_RO 0x00000020 /* Don't pass through BIO_DELETE requests. */ #define G_ELI_FLAG_NODELETE 0x00000040 +/* This GELI supports GELIBoot */ +#define G_ELI_FLAG_GELIBOOT 0x00000080 /* RUNTIME FLAGS. */ /* Provider was open for writing. */ #define G_ELI_FLAG_WOPEN 0x00010000 Modified: head/sys/geom/eli/g_eli_ctl.c ============================================================================== --- head/sys/geom/eli/g_eli_ctl.c Fri Apr 8 00:24:21 2016 (r297690) +++ head/sys/geom/eli/g_eli_ctl.c Fri Apr 8 01:25:25 2016 (r297691) @@ -376,7 +376,7 @@ g_eli_ctl_configure(struct gctl_req *req char param[16]; const char *prov; u_char *sector; - int *nargs, *boot, *noboot, *trim, *notrim; + int *nargs, *boot, *noboot, *trim, *notrim, *geliboot, *nogeliboot; int zero, error, changed; u_int i; @@ -421,6 +421,19 @@ g_eli_ctl_configure(struct gctl_req *req if (*trim || *notrim) changed = 1; + geliboot = gctl_get_paraml(req, "geliboot", sizeof(*geliboot)); + if (geliboot == NULL) + geliboot = &zero; + nogeliboot = gctl_get_paraml(req, "nogeliboot", sizeof(*nogeliboot)); + if (nogeliboot == NULL) + nogeliboot = &zero; + if (*geliboot && *nogeliboot) { + gctl_error(req, "Options -g and -G are mutually exclusive."); + return; + } + if (*geliboot || *nogeliboot) + changed = 1; + if (!changed) { gctl_error(req, "No option given."); return; @@ -469,6 +482,16 @@ g_eli_ctl_configure(struct gctl_req *req continue; } + if (*geliboot && (sc->sc_flags & G_ELI_FLAG_GELIBOOT)) { + G_ELI_DEBUG(1, "GELIBOOT flag already configured for %s.", + prov); + continue; + } else if (*nogeliboot && !(sc->sc_flags & G_ELI_FLAG_GELIBOOT)) { + G_ELI_DEBUG(1, "GELIBOOT flag not configured for %s.", + prov); + continue; + } + if (!(sc->sc_flags & G_ELI_FLAG_ONETIME)) { /* * ONETIME providers don't write metadata to @@ -504,6 +527,14 @@ g_eli_ctl_configure(struct gctl_req *req sc->sc_flags &= ~G_ELI_FLAG_NODELETE; } + if (*geliboot) { + md.md_flags |= G_ELI_FLAG_GELIBOOT; + sc->sc_flags |= G_ELI_FLAG_GELIBOOT; + } else if (*nogeliboot) { + md.md_flags &= ~G_ELI_FLAG_GELIBOOT; + sc->sc_flags &= ~G_ELI_FLAG_GELIBOOT; + } + if (sc->sc_flags & G_ELI_FLAG_ONETIME) { /* There's no metadata on disk so we are done here. */ continue;