linux-btrfs.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Alex Elsayed <eternaleye@gmail.com>
To: linux-btrfs@vger.kernel.org
Subject: Re: [RFC] Preliminary BTRFS Encryption
Date: Mon, 19 Sep 2016 20:01:06 +0000 (UTC)	[thread overview]
Message-ID: <nrpg62$g72$2@blaine.gmane.org> (raw)
In-Reply-To: 20160919180805.GG21290@hungrycats.org

On Mon, 19 Sep 2016 14:08:06 -0400, Zygo Blaxell wrote:

> On Sat, Sep 17, 2016 at 06:37:16AM +0000, Alex Elsayed wrote:
>> > Encryption in ext4 is a per-directory-tree affair. One starts by
>> > setting an encryption policy (using an ioctl() call) for a given
>> > directory, which must be empty at the time; that policy includes a
>> > master key used for all files and directories stored below the target
>> > directory. Each individual file is encrypted with its own key, which
>> > is derived from the master key and a per-file random nonce value
>> > (which is stored in an extended attribute attached to the file's
>> > inode). File names and symbolic links are also encrypted.
> 
> Probably the simplest way to map this to btrfs is to move the nonce from
> the inode to the extent.

I agree. Mostly, I was making a point about how the ext4/VFS code (which 
_does_ put it on the inode) can't just be transported over to btrfs 
unchanged, which is what I read Dave Chinner as advocating.

> Inodes aren't unique within a btrfs filesystem, extents can be shared by
> multiple inodes, and a single extent can appear multiple times in the
> same inode at different offsets.  Attaching the nonce to the inode would
> not be sufficient to read the extent in all but the special case of a
> single reference at the original offset where it was written, and it
> also leads to the replay problems with duplicate inodes you pointed out.

Yup.

> Extents in a btrfs filesystem are unique and carry their own attributes
> (e.g. compression format, checksums) and reference count.  They can
> easily carry a reference to an encryption policy object and a nonce
> attribute.

Definitely agreed.

> Nonces within metadata are more complicated.  btrfs doesn't have
> directory files like ext4 does, so it doesn't get directory filename
> encryption for free with file encryption.  Encryption could be done
> per-item in the metadata trees, but in the special case of directories
> that happen to the the roots of subvols, it would be possible to encrypt
> entire pages of metadata at a time (with the caveat that a snapshot
> would require shared encryption policy between the origin and snapshot
> subvols).

Encrypting tree values per-item is actually one of the best arguments in 
_favor_ of nonce-misuse-resistant AEAD. Its security notion is very, very 
strong:

If a (key, nonce, associated data, message) tuple is repeated, the only 
data an attacker can discover is the fact that the two ciphertexts have 
the same value (a one-bit leak).

In other words, if you encrypt each value in the b-tree with some key, 
some nonce, use the b-tree key as the associated data, and use the value 
as the message, you get a _very_ secure system against a _very_ wide 
variety of attacks - essentially for free. And all _without_ sacrificing 
flexibility, as one could use distinct (crypto) keys for distinct (b-
tree) keys.

(You still need something for protecting the _structure_ of the B-tree, 
but that's a different issue).

> This is what makes keys at the subvol root level so attractive.

Pretty much.

>> So there isn't quite a "subvol key" in the VFS approach - each
>> directory has a key, and there are derived keys for the entries below
>> it. (I'll note that this framing does not address shared extents _at
>> all_, and would love to have clarification on that).
> 
> Files are modified by creating new extents (using parameters inherited
> from the inode to fill in the extent attributes) and updating the inode
> to refer to the new extent instead of the old one at the modified
> offset. Cloned extents are references to existing extents associated
> with a different inode or at a different place within the same inode (if
> the extent is not compatible with the destination inode, clone fails
> with an error).  A snapshot is an efficient way to clone an entire
> subvol tree at once, including all inodes and attributes.

There is the caveat of chattr +C, which would need hard-disabled for 
extent-level encryption (vs block level).

> Inode attributes and extent attributes can sometimes conflict,
> especially during a clone operation.  Encryption attributes could become
> one of these cases (i.e. to prevent an extent from one encryption policy
> from being cloned to an inode under a different encryption policy).

That is a good approach.

>> > I don't see how snapshots could work, writable or otherwise, without
>> > separating the key identity from the subvol identity and having a
>> > many-to-one relationship between subvols and keys.  The extents in
>> > each subvol would be shared, and they'd be encrypted with a single
>> > secret, so there's not really another way to do this.
>> 
>> That's not the issue. The issue is that, assuming the key stays the
>> same,
>> then a user could quite possibly create a snapshot, write into both the
>> original and the snapshot, causing encryption to occur twice with the
>> same key, same nonce, and different data.
> 
> If the extents have nonces (and inodes do not) then this doesn't happen.
> A write to either snapshot necessarily creates new extents in all cases
> (the nodatacow feature, the only way to modify a data extent in-place,
> is disabled when the extent is shared).

As above, note that if encryption is applied to extents rather than 
blocks, nodatacow becomes a data loss vector (partial write -> AEAD 
verify failure).


  reply	other threads:[~2016-09-19 20:01 UTC|newest]

Thread overview: 66+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2016-09-13 13:39 [RFC] Preliminary BTRFS Encryption Anand Jain
2016-09-13 13:39 ` [PATCH] btrfs: Encryption: Add btrfs encryption support Anand Jain
2016-09-13 14:12   ` kbuild test robot
2016-09-13 14:24   ` kbuild test robot
2016-09-13 16:10   ` kbuild test robot
2016-09-13 13:39 ` [PATCH 1/2] btrfs-progs: make wait_for_commit non static Anand Jain
2016-09-13 13:39 ` [PATCH 2/2] btrfs-progs: add encryption support Anand Jain
2016-09-13 13:39 ` [PATCH] fstests: btrfs: support encryption Anand Jain
2016-09-13 16:42 ` [RFC] Preliminary BTRFS Encryption Wilson Meier
2016-09-14  7:02   ` Anand Jain
2016-09-14 18:26     ` Wilson Meier
2016-09-15  4:53 ` Alex Elsayed
2016-09-15 11:33   ` Anand Jain
2016-09-15 11:47     ` Alex Elsayed
2016-09-16 11:35       ` Anand Jain
2016-09-15  5:38 ` Chris Murphy
2016-09-15 11:32   ` Anand Jain
2016-09-15 11:37 ` Austin S. Hemmelgarn
2016-09-15 14:06   ` Anand Jain
2016-09-15 14:24     ` Austin S. Hemmelgarn
2016-09-16  8:58       ` David Sterba
2016-09-17  2:18       ` Zygo Blaxell
2016-09-16  1:12 ` Dave Chinner
2016-09-16  5:47   ` Roman Mamedov
2016-09-16  6:49   ` Alex Elsayed
2016-09-17  4:38     ` Zygo Blaxell
2016-09-17  6:37       ` Alex Elsayed
2016-09-19 18:08         ` Zygo Blaxell
2016-09-19 20:01           ` Alex Elsayed [this message]
2016-09-19 22:22             ` Zygo Blaxell
2016-09-19 22:25             ` Chris Murphy
2016-09-19 22:31               ` Zygo Blaxell
2016-09-20  1:10                 ` Zygo Blaxell
2016-09-17 18:45       ` David Sterba
2016-09-20 14:26         ` Anand Jain
2016-09-16 10:45   ` Brendan Hide
2016-09-16 11:46   ` Anand Jain
2016-09-16  8:49 ` David Sterba
2016-09-16 11:56   ` Anand Jain
2016-09-17 20:35     ` David Sterba
2016-09-18  8:34       ` RAID1 availability issue[2], Hot-spare and auto-replace Anand Jain
2016-09-18 17:28         ` Chris Murphy
2016-09-18 17:34           ` Chris Murphy
2016-09-19  2:25           ` Anand Jain
2016-09-19 12:07             ` Austin S. Hemmelgarn
2016-09-19 12:25           ` Austin S. Hemmelgarn
2016-09-18  9:54       ` [RFC] Preliminary BTRFS Encryption Anand Jain
2016-09-20  0:12   ` Chris Mason
2016-09-20  0:55     ` Anand Jain
2016-09-17  6:58 ` Eric Biggers
2016-09-17  7:13   ` Alex Elsayed
2016-09-19 18:57     ` Zygo Blaxell
2016-09-19 19:50       ` Alex Elsayed
2016-09-19 22:12         ` Zygo Blaxell
2016-09-17 16:12   ` Anand Jain
2016-09-17 18:57     ` Chris Murphy
2016-09-19 15:15 ` Experimental btrfs encryption Theodore Ts'o
2016-09-19 20:58   ` Alex Elsayed
2016-09-20  0:32     ` Chris Mason
2016-09-20  2:47       ` Alex Elsayed
2016-09-20  2:50       ` Theodore Ts'o
2016-09-20  3:05         ` Alex Elsayed
2016-09-20  4:09         ` Zygo Blaxell
2016-09-20 15:44         ` Chris Mason
2016-09-21 13:52           ` Anand Jain
2016-09-20  4:05   ` Anand Jain

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to='nrpg62$g72$2@blaine.gmane.org' \
    --to=eternaleye@gmail.com \
    --cc=linux-btrfs@vger.kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).