diff options
-rw-r--r-- | sys/geom/eli/g_eli.c | 2 | ||||
-rw-r--r-- | sys/geom/eli/g_eli.h | 17 | ||||
-rw-r--r-- | sys/geom/eli/g_eli_ctl.c | 6 | ||||
-rw-r--r-- | sys/geom/eli/g_eli_key_cache.c | 8 |
4 files changed, 27 insertions, 6 deletions
diff --git a/sys/geom/eli/g_eli.c b/sys/geom/eli/g_eli.c index 72f93f4..6819fcc 100644 --- a/sys/geom/eli/g_eli.c +++ b/sys/geom/eli/g_eli.c @@ -726,6 +726,8 @@ g_eli_create(struct gctl_req *req, struct g_class *mp, struct g_provider *bpp, (sc->sc_flags & G_ELI_FLAG_AUTH) != 0) { sc->sc_flags |= G_ELI_FLAG_FIRST_KEY; } + if (md->md_version < G_ELI_VERSION_07) + sc->sc_flags |= G_ELI_FLAG_ENC_IVKEY; sc->sc_ealgo = md->md_ealgo; sc->sc_nkey = nkey; diff --git a/sys/geom/eli/g_eli.h b/sys/geom/eli/g_eli.h index a5aad8f..835a1b3 100644 --- a/sys/geom/eli/g_eli.h +++ b/sys/geom/eli/g_eli.h @@ -68,6 +68,8 @@ * 5 - Added multiple encrypton keys and AES-XTS support. * 6 - Fixed usage of multiple keys for authenticated providers (the * G_ELI_FLAG_FIRST_KEY flag will be set for older versions). + * 7 - Encryption keys are now generated from the Data Key and not from the + * IV Key (the G_ELI_FLAG_ENC_IVKEY flag will be set for older versions). */ #define G_ELI_VERSION_00 0 #define G_ELI_VERSION_01 1 @@ -76,7 +78,8 @@ #define G_ELI_VERSION_04 4 #define G_ELI_VERSION_05 5 #define G_ELI_VERSION_06 6 -#define G_ELI_VERSION G_ELI_VERSION_06 +#define G_ELI_VERSION_07 7 +#define G_ELI_VERSION G_ELI_VERSION_07 /* ON DISK FLAGS. */ /* Use random, onetime keys. */ @@ -104,6 +107,8 @@ #define G_ELI_FLAG_SUSPEND 0x00100000 /* Provider uses first encryption key. */ #define G_ELI_FLAG_FIRST_KEY 0x00200000 +/* Provider uses IV-Key for encryption key generation. */ +#define G_ELI_FLAG_ENC_IVKEY 0x00400000 #define G_ELI_NEW_BIO 255 @@ -237,7 +242,7 @@ eli_metadata_encode_v0(struct g_eli_metadata *md, u_char **datap) *datap = p; } static __inline void -eli_metadata_encode_v1v2v3v4v5v6(struct g_eli_metadata *md, u_char **datap) +eli_metadata_encode_v1v2v3v4v5v6v7(struct g_eli_metadata *md, u_char **datap) { u_char *p; @@ -275,7 +280,8 @@ eli_metadata_encode(struct g_eli_metadata *md, u_char *data) case G_ELI_VERSION_04: case G_ELI_VERSION_05: case G_ELI_VERSION_06: - eli_metadata_encode_v1v2v3v4v5v6(md, &p); + case G_ELI_VERSION_07: + eli_metadata_encode_v1v2v3v4v5v6v7(md, &p); break; default: #ifdef _KERNEL @@ -315,7 +321,7 @@ eli_metadata_decode_v0(const u_char *data, struct g_eli_metadata *md) } static __inline int -eli_metadata_decode_v1v2v3v4v5v6(const u_char *data, struct g_eli_metadata *md) +eli_metadata_decode_v1v2v3v4v5v6v7(const u_char *data, struct g_eli_metadata *md) { MD5_CTX ctx; const u_char *p; @@ -357,7 +363,8 @@ eli_metadata_decode(const u_char *data, struct g_eli_metadata *md) case G_ELI_VERSION_04: case G_ELI_VERSION_05: case G_ELI_VERSION_06: - error = eli_metadata_decode_v1v2v3v4v5v6(data, md); + case G_ELI_VERSION_07: + error = eli_metadata_decode_v1v2v3v4v5v6v7(data, md); break; default: error = EOPNOTSUPP; diff --git a/sys/geom/eli/g_eli_ctl.c b/sys/geom/eli/g_eli_ctl.c index 65672d5..520d237 100644 --- a/sys/geom/eli/g_eli_ctl.c +++ b/sys/geom/eli/g_eli_ctl.c @@ -1020,6 +1020,12 @@ g_eli_config(struct gctl_req *req, struct g_class *mp, const char *verb) /* Compatible. */ break; } + if (G_ELI_VERSION == G_ELI_VERSION_07 && + (*version == G_ELI_VERSION_05 || + *version == G_ELI_VERSION_06)) { + /* Compatible. */ + break; + } gctl_error(req, "Userland and kernel parts are out of sync."); return; } diff --git a/sys/geom/eli/g_eli_key_cache.c b/sys/geom/eli/g_eli_key_cache.c index 33a2ca9..d7158e4 100644 --- a/sys/geom/eli/g_eli_key_cache.c +++ b/sys/geom/eli/g_eli_key_cache.c @@ -91,14 +91,20 @@ RB_GENERATE(g_eli_key_tree, g_eli_key, gek_link, g_eli_key_cmp); static void g_eli_key_fill(struct g_eli_softc *sc, struct g_eli_key *key, uint64_t keyno) { + const uint8_t *ekey; struct { char magic[4]; uint8_t keyno[8]; } __packed hmacdata; + if ((sc->sc_flags & G_ELI_FLAG_ENC_IVKEY) != 0) + ekey = sc->sc_mkey; + else + ekey = sc->sc_ekey; + bcopy("ekey", hmacdata.magic, 4); le64enc(hmacdata.keyno, keyno); - g_eli_crypto_hmac(sc->sc_mkey, G_ELI_MAXKEYLEN, (uint8_t *)&hmacdata, + g_eli_crypto_hmac(ekey, G_ELI_MAXKEYLEN, (uint8_t *)&hmacdata, sizeof(hmacdata), key->gek_key, 0); key->gek_keyno = keyno; key->gek_count = 0; |