Message ID | 87wpzrmfp6.fsf@openvz.org |
---|---|
State | Rejected, archived |
Headers | show |
Dmitry Monakhov <dmonlist@gmail.com> writes: > Theodore Ts'o <tytso@mit.edu> writes: > >> On Wed, May 27, 2015 at 01:06:06PM -0400, Theodore Ts'o wrote: >>> >>> That's not true. If the attacker finds the encryption key for an >>> inode, and they have the nonce which is stored in file's extended >>> attribute, what the attacker has is a single plaintext/ciphertext >>> pair. That doesn't imply that they can get the master key; they would >>> still need to do a brute force search on the keyspace try to find the >>> master key. >> >> So an update, after conferring with Michael Halcrow, who set me >> straight. I was wrong, because I mixed up which was the deriving key >> and which was the source key. You're correct; if an attacker could >> get ahold of the per-file key, they could use the nonce to decrypt it >> and obtain the master key. >> >> However, there are only two ways to determine the per-file key. The >> first is a ring 0 compromise, in which case it's likely they could get >> access to the master key, and the second is if there is a practical >> known-plaintext attack on AES, and the attacker has access to the >> block device --- and possibly a chosen-plaintext attack if the >> attacker can control what data is written to the file. But either >> way, if there is such a crypto-analytic attack on AES, then this is >> going to be least of the whole world's problems. :-) > Ohh. My knowledge in cryptography is very weak, but imagine same > practical scenarios where attacker can find dozens of files with > known content by using knowledge of inode attributes and environment. > Let's consider user encrypted his encrypted chroot-environment, so > attacker may try to compare file attributes (permission, size and > directory nesting level) with files from distro repositories (rpm/deb) > > For example let's comare two directories encrypted one and my /bin/ > kvm-xfstests:~# ls -l /vdc/X/4BbchaihxJLF5D+gErB0DC/ | sort -k 5 > -n | tail - > -rwxr-xr-x 1 root root 202936 May 29 17:09 l51q60ZbBvtGnUl8a3y3yA > -rwxr-xr-x 1 root root 219392 May 29 17:09 5NluBcuHcBAb6J6ByLUtBC > -rwxr-xr-x 1 root root 235768 May 29 17:09 lrFAT0jlaLHwenJ2PqwiEA > -rwxr-xr-x 1 root root 290816 May 29 17:09 P7A5KsxbBO4Dyv8ofxedhA > -rwxr-xr-x 1 root root 309488 May 29 17:09 PeOSBWm54qDpEMCov6TqSC > -rwxr-xr-x 1 root root 313584 May 29 17:09 TEGrdRgB2KxMFqysRtg6LB > -rwxr-xr-x 1 root root 314560 May 29 17:09 e6waVwHbgdmx97A,CncgxD > -rwxr-xr-x 1 root root 358072 May 29 17:09 Zz51PHoSv91wjUjn9sCypB > -rwxr-xr-x 1 root root 538904 May 29 17:09 ulVnXayZZW0SdYp3fJe83B > root@kvm-xfstests:~# ls -l /bin | sort -k 5 -n | tail -n10 > -rwxr-xr-x 1 root root 202936 Oct 3 2014 grep > -rwxr-xr-x 1 root root 219392 Dec 5 09:13 journalctl > -rwxr-xr-x 1 root root 235768 Dec 5 09:13 systemd-inhibit > -rwxr-xr-x 1 root root 280816 Dec 5 09:13 machinectl > -rwxr-xr-x 1 root root 309488 Dec 5 09:13 loginctl > -rwxr-xr-x 1 root root 313584 Dec 5 09:13 udevadm > -rwxr-xr-x 1 root root 314560 Sep 5 2014 ip > -rwxr-xr-x 1 root root 358072 Nov 8 2014 tar > -rwxr-xr-x 1 root root 538904 Dec 5 09:13 systemctl > -rwxr-xr-x 1 root root 1029624 Nov 12 2014 bash > > This gives me as an attacker very good guess that > l51q60ZbBvtGnUl8a3y3yA == grep and so on, So I have can try brute force > attack on first block (But AFAIU it is not practical for AES-256) > May be we can prevent this my tweak inode size if key is not > available. For example allign i_size to fsblock which makes distro-based > attack impractical. See patch attached. > >> >> There are alternatives, such as either using the master to encrypt the >> nonce and none+1: (AES-256-ENCRYPT(nonce) || AES-256-ENCRYPT >> (nonce+1)). But this will be 40% slower than what we are currently >> doing, which is to use AES-256 to encrypt the master key. >> > At least it would be reasonable to provide this as an mkfs/tune2fs > option. I'll try to prepare patches. >> Or we could use an HMAC, which would be even slower yet, especially >> since many chips have AES acceleration, but few have SHA hardware >> acceleration. >> >> So ultimately, the question is whether we want to make a change (with >> all of the versioning work we would need for backwards compatibility) >> that decreases performance, which will be especially noticeable for >> small files, to protect against a partial Ring 0 compromise when other >> Ring 0 compromise would make us be toast anyway. >> >> - Ted > > diff --git a/fs/ext4/inode.c b/fs/ext4/inode.c > index 0554b0b..e45cec4 100644 > --- a/fs/ext4/inode.c > +++ b/fs/ext4/inode.c > @@ -4790,6 +4790,10 @@ int ext4_getattr(struct vfsmount *mnt, struct dentry *dentry, > inode = d_inode(dentry); > generic_fillattr(inode, stat); > > + /* Tweak inode size for encrypted inodes */ > + if (unlikely(ext4_encrypted_inode(inode) && ext4_get_encryption_info(inode) == -ENOKEY)) > + stat->size = (stat->size + stat->blksize - 1 ) & ~(stat->blksize - 1); > + Hm. I've just realized that this patch is useless because once attacker has access to FS he likely also has access to block device so i_size is known for each inode because it is stored on disk unencrypted. > /* > * If there is inline data in the inode, the inode will normally not > * have data blocks allocated (it may have an external xattr block). -- To unsubscribe from this list: send the line "unsubscribe linux-ext4" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
On Fri, May 29, 2015 at 08:55:17PM +0300, Dmitry Monakhov wrote: > This gives me as an attacker very good guess that > l51q60ZbBvtGnUl8a3y3yA == grep and so on, So I have can try brute force > attack on first block (But AFAIU it is not practical for AES-256) > May be we can prevent this my tweak inode size if key is not > available. For example allign i_size to fsblock which makes distro-based > attack impractical. See patch attached. It's not practical for AES-128, let alone AES-256: If you assume: * Every person on the planet owns 10 computers. * There are 7 billion people on the planet. * Each of these computers can test 1 billion key combinations per second. * On average, you can crack the key after testing 50% of the possibilities. Then the earth's population can crack one AES-128 encryption key in 77,000,000,000,000,000,000,000,000 years![1] AES-256 is 10^19 times harder. So take the 77,000,000,000,000,000,000,000,000 years and add another 19 zero's. :-) The bottom line is trying to deny the attacker plaintext/ciphertext pairs really isn't worth the effort. It's assumed the attacker can do this, and it really doesn't bother me. After all, the the per-inode key is a completely random 256 bit key. The much more concerning attack is one where the attacker tries to attack the user's passphrase by trying brute force the user's password. We're using a pbkdf2_sha512 with an iteration count of 65535, to try and slow down the brute force attack, but if the user is using the typically horrendous user-chosen password, it's still going to be the weakest link. So the attacker will simply use a password link, try all lower-case passwords, all lower case passwords with a single digit, etc., etc., turn that into a master key, try to use the master key and the nonce to create the per-inode key, and then see if the resulting file or filename looks plausible. The fact that it will take 65535 iterations of SHA-512 per passphrase tried will slow the attacker down somewhat, but if the user uses a birthday, or their girlfriend's name, etc., it's not going to help enough. > At least it would be reasonable to provide this as an mkfs/tune2fs > option. I'd really rather not support adding extra complexity unless it's very clear what is the specific threat that we are protecting about, and we're clear that it is a valid threat in the context of the overall system. Otherwise we may be strengthening the titanium/steel door while ignoring the paper maiche walls that it is set in. (Or see the image on slide #4 of: http://kernsec.org/files/lss2014/Halcrow_EXT4_Encryption.pdf :-) - Ted [1] http://www.eetimes.com/document.asp?doc_id=1279619 -- To unsubscribe from this list: send the line "unsubscribe linux-ext4" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
diff --git a/fs/ext4/inode.c b/fs/ext4/inode.c index 0554b0b..e45cec4 100644 --- a/fs/ext4/inode.c +++ b/fs/ext4/inode.c @@ -4790,6 +4790,10 @@ int ext4_getattr(struct vfsmount *mnt, struct dentry *dentry, inode = d_inode(dentry); generic_fillattr(inode, stat); + /* Tweak inode size for encrypted inodes */ + if (unlikely(ext4_encrypted_inode(inode) && ext4_get_encryption_info(inode) == -ENOKEY)) + stat->size = (stat->size + stat->blksize - 1 ) & ~(stat->blksize - 1); + /* * If there is inline data in the inode, the inode will normally not * have data blocks allocated (it may have an external xattr block).