diff options
| author | Eric Biggers <ebiggers@google.com> | 2019-12-15 19:31:39 -0800 |
|---|---|---|
| committer | Eric Biggers <ebiggers@google.com> | 2020-01-05 10:02:13 -0800 |
| commit | 2b25de6d445faefc28629603dd754aec9f744e60 (patch) | |
| tree | c2e4dd53a2ed370be5b0699ede59538d508d347d /metadata/policy_test.go | |
| parent | d0ac36dcea341ff000aca983dd80e7bef9fc30ec (diff) | |
Metadata support for v2 encryption policies
Linux v5.4 and later supports v2 encryption policies. These have
several advantages over v1 encryption policies:
- Their encryption keys can be added/removed to/from the filesystem by
non-root users, thus gaining the benefits of the filesystem keyring
while also retaining support for non-root use.
- They use a more standard, secure, and flexible key derivation
function. Because of this, some future kernel-level fscrypt features
will be implemented for v2 policies only.
- They prevent a denial-of-service attack where a user could associate
the wrong key with another user's encrypted files.
Prepare the fscrypt tool to support v2 encryption policies by:
- Adding a policy_version field to the EncryptionOptions, i.e. to the
config file and to the policy metadata files.
- Using the kernel-specified algorithm to compute the key descriptor for
v2 policies.
- Handling setting and getting v2 policies.
Actually adding/removing the keys for v2 policies to/from the kernel is
left for the next patch.
Diffstat (limited to 'metadata/policy_test.go')
| -rw-r--r-- | metadata/policy_test.go | 63 |
1 files changed, 54 insertions, 9 deletions
diff --git a/metadata/policy_test.go b/metadata/policy_test.go index ad9dd80..3c0704a 100644 --- a/metadata/policy_test.go +++ b/metadata/policy_test.go @@ -26,17 +26,30 @@ import ( "testing" "github.com/golang/protobuf/proto" + "golang.org/x/sys/unix" "github.com/google/fscrypt/util" ) -const goodDescriptor = "0123456789abcdef" +const goodV1Descriptor = "0123456789abcdef" -var goodPolicy = &PolicyData{ - KeyDescriptor: goodDescriptor, +var goodV1Policy = &PolicyData{ + KeyDescriptor: goodV1Descriptor, Options: DefaultOptions, } +var goodV2EncryptionOptions = &EncryptionOptions{ + Padding: 32, + Contents: EncryptionOptions_AES_256_XTS, + Filenames: EncryptionOptions_AES_256_CTS, + PolicyVersion: 2, +} + +var goodV2Policy = &PolicyData{ + KeyDescriptor: "0123456789abcdef0123456789abcdef", + Options: goodV2EncryptionOptions, +} + // Creates a temporary directory for testing. func createTestDirectory(t *testing.T) (directory string, err error) { baseDirectory, err := util.TestRoot() @@ -83,7 +96,7 @@ func TestSetPolicyEmptyDirectory(t *testing.T) { } defer os.RemoveAll(directory) - if err = SetPolicy(directory, goodPolicy); err != nil { + if err = SetPolicy(directory, goodV1Policy); err != nil { t.Error(err) } } @@ -96,7 +109,7 @@ func TestSetPolicyNonemptyDirectory(t *testing.T) { } defer os.RemoveAll(directory) - if err = SetPolicy(directory, goodPolicy); err == nil { + if err = SetPolicy(directory, goodV1Policy); err == nil { t.Error("should have failed to set policy on a nonempty directory") } } @@ -109,7 +122,7 @@ func TestSetPolicyFile(t *testing.T) { } defer os.RemoveAll(directory) - if err = SetPolicy(file, goodPolicy); err == nil { + if err = SetPolicy(file, goodV1Policy); err == nil { t.Error("should have failed to set policy on a file") } } @@ -141,15 +154,15 @@ func TestGetPolicyEmptyDirectory(t *testing.T) { defer os.RemoveAll(directory) var actualPolicy *PolicyData - if err = SetPolicy(directory, goodPolicy); err != nil { + if err = SetPolicy(directory, goodV1Policy); err != nil { t.Fatal(err) } if actualPolicy, err = GetPolicy(directory); err != nil { t.Fatal(err) } - if !proto.Equal(actualPolicy, goodPolicy) { - t.Errorf("policy %+v does not equal expected policy %+v", actualPolicy, goodPolicy) + if !proto.Equal(actualPolicy, goodV1Policy) { + t.Errorf("policy %+v does not equal expected policy %+v", actualPolicy, goodV1Policy) } } @@ -165,3 +178,35 @@ func TestGetPolicyUnencrypted(t *testing.T) { t.Error("should have failed to set policy on a file") } } + +func requireV2PolicySupport(t *testing.T, directory string) { + file, err := os.Open(directory) + if err != nil { + t.Fatal(err) + } + defer file.Close() + + err = policyIoctl(file, unix.FS_IOC_GET_ENCRYPTION_POLICY_EX, nil) + if err == ErrEncryptionNotSupported { + t.Skip("No support for v2 encryption policies, skipping test") + } +} + +// Tests that a non-root user cannot set a v2 encryption policy unless the key +// has been added. +func TestSetV2PolicyNoKey(t *testing.T) { + if util.IsUserRoot() { + t.Skip("This test cannot be run as root") + } + directory, err := createTestDirectory(t) + if err != nil { + t.Fatal(err) + } + defer os.RemoveAll(directory) + requireV2PolicySupport(t, directory) + + err = SetPolicy(directory, goodV2Policy) + if err == nil { + t.Error("shouldn't have been able to set v2 policy without key added") + } +} |