cephfs: upgrade fscrypt version to fix concurrency issue

In older versions of fscrypt there is a race condition
when multiple encrypted cephfs instances are deployed
simultaneously.

Signed-off-by: NymanRobin <robin.nyman@est.tech>
(cherry picked from commit 3073409695)
This commit is contained in:
NymanRobin
2024-05-08 12:58:38 +03:00
committed by mergify[bot]
parent 3805bea505
commit ca713945ad
13 changed files with 94 additions and 54 deletions

View File

@ -22,10 +22,10 @@
// All of the actions include a significant amount of logging, so that good
// output can be provided for cmd/fscrypt's verbose mode.
// The top-level actions currently include:
// - Creating a new config file
// - Creating a context on which to perform actions
// - Creating, unlocking, and modifying Protectors
// - Creating, unlocking, and modifying Policies
// - Creating a new config file
// - Creating a context on which to perform actions
// - Creating, unlocking, and modifying Protectors
// - Creating, unlocking, and modifying Policies
package actions
import (

View File

@ -24,6 +24,7 @@ import (
"log"
"os"
"os/user"
"reflect"
"github.com/pkg/errors"
"google.golang.org/protobuf/proto"
@ -452,7 +453,7 @@ func (policy *Policy) AddProtector(protector *Protector) error {
// If the protector is on a different filesystem, we need to add a link
// to it on the policy's filesystem.
if policy.Context.Mount != protector.Context.Mount {
if !reflect.DeepEqual(policy.Context.Mount, protector.Context.Mount) {
log.Printf("policy on %s\n protector on %s\n", policy.Context.Mount, protector.Context.Mount)
ownerIfCreating, err := getOwnerOfMetadataForProtector(protector)
if err != nil {
@ -525,7 +526,7 @@ func (policy *Policy) RemoveProtector(protectorDescriptor string) error {
func (policy *Policy) Apply(path string) error {
if pathMount, err := filesystem.FindMount(path); err != nil {
return err
} else if pathMount != policy.Context.Mount {
} else if !reflect.DeepEqual(pathMount, policy.Context.Mount) {
return &ErrDifferentFilesystem{policy.Context.Mount, pathMount}
}

View File

@ -18,17 +18,17 @@
*/
// Package crypto manages all the cryptography for fscrypt. This includes:
// - Key management (key.go)
// - Securely holding keys in memory
// - Making recovery keys
// - Randomness (rand.go)
// - Cryptographic algorithms (crypto.go)
// - encryption (AES256-CTR)
// - authentication (SHA256-based HMAC)
// - key stretching (SHA256-based HKDF)
// - key wrapping/unwrapping (Encrypt then MAC)
// - passphrase-based key derivation (Argon2id)
// - key descriptor computation (double SHA512, or HKDF-SHA512)
// 1. Key management (key.go)
// - Securely holding keys in memory
// - Making recovery keys
// 2. Randomness (rand.go)
// 3. Cryptographic algorithms (crypto.go)
// - encryption (AES256-CTR)
// - authentication (SHA256-based HMAC)
// - key stretching (SHA256-based HKDF)
// - key wrapping/unwrapping (Encrypt then MAC)
// - passphrase-based key derivation (Argon2id)
// - key descriptor computation (double SHA512, or HKDF-SHA512)
package crypto
import (

View File

@ -30,7 +30,8 @@ import (
// the operating system has insufficient randomness, the buffer creation will
// fail. This is an improvement over Go's built-in crypto/rand which will still
// return bytes if the system has insufficiency entropy.
// See: https://github.com/golang/go/issues/19274
//
// See: https://github.com/golang/go/issues/19274
//
// While this syscall was only introduced in Kernel v3.17, it predates the
// introduction of filesystem encryption, so it introduces no additional

View File

@ -21,15 +21,15 @@
// Package filesystem deals with the structure of the files on disk used to
// store the metadata for fscrypt. Specifically, this package includes:
// - mountpoint management (mountpoint.go)
// - querying existing mounted filesystems
// - getting filesystems from a UUID
// - finding the filesystem for a specific path
// - metadata organization (filesystem.go)
// - setting up a mounted filesystem for use with fscrypt
// - adding/querying/deleting metadata
// - making links to other filesystems' metadata
// - following links to get data from other filesystems
// 1. mountpoint management (mountpoint.go)
// - querying existing mounted filesystems
// - getting filesystems from a UUID
// - finding the filesystem for a specific path
// 2. metadata organization (filesystem.go)
// - setting up a mounted filesystem for use with fscrypt
// - adding/querying/deleting metadata
// - making links to other filesystems' metadata
// - following links to get data from other filesystems
package filesystem
import (
@ -195,6 +195,7 @@ func (err *ErrProtectorNotFound) Error() string {
var SortDescriptorsByLastMtime = false
// Mount contains information for a specific mounted filesystem.
//
// Path - Absolute path where the directory is mounted
// FilesystemType - Type of the mounted filesystem, e.g. "ext4"
// Device - Device for filesystem (empty string if we cannot find one)
@ -210,8 +211,9 @@ var SortDescriptorsByLastMtime = false
// setup first. Specifically, the directories created look like:
// <mountpoint>
// └── .fscrypt
// ├── policies
// └── protectors
//
// ├── policies
// └── protectors
//
// These "policies" and "protectors" directories will contain files that are
// the corresponding metadata structures for policies and protectors. The public
@ -723,13 +725,13 @@ func (m *Mount) addMetadata(path string, md metadata.Metadata, owner *user.User)
// considering that it could be a malicious file created to cause a
// denial-of-service. Specifically, the following checks are done:
//
// - It must be a regular file, not another type of file like a symlink or FIFO.
// (Symlinks aren't bad by themselves, but given that a malicious user could
// point one to absolutely anywhere, and there is no known use case for the
// metadata files themselves being symlinks, it seems best to disallow them.)
// - It must have a reasonable size (<= maxMetadataFileSize).
// - If trustedUser is non-nil, then the file must be owned by the given user
// or by root.
// - It must be a regular file, not another type of file like a symlink or FIFO.
// (Symlinks aren't bad by themselves, but given that a malicious user could
// point one to absolutely anywhere, and there is no known use case for the
// metadata files themselves being symlinks, it seems best to disallow them.)
// - It must have a reasonable size (<= maxMetadataFileSize).
// - If trustedUser is non-nil, then the file must be owned by the given user
// or by root.
//
// Take care to avoid TOCTOU (time-of-check-time-of-use) bugs when doing these
// tests. Notably, we must open the file before checking the file type, as the

View File

@ -106,6 +106,7 @@ func getDeviceName(num DeviceNumber) string {
// Parse one line of /proc/self/mountinfo.
//
// The line contains the following space-separated fields:
//
// [0] mount ID
// [1] parent ID
// [2] major:minor
@ -184,11 +185,11 @@ func addUncontainedSubtreesRecursive(dst map[string]bool,
// preferably a read-write mount. However, that doesn't work in containers
// where the "/" subtree might not be mounted. Here's a real-world example:
//
// mnt.Subtree mnt.Path
// ----------- --------
// /var/lib/lxc/base/rootfs /
// /var/cache/pacman/pkg /var/cache/pacman/pkg
// /srv/repo/x86_64 /srv/http/x86_64
// mnt.Subtree mnt.Path
// ----------- --------
// /var/lib/lxc/base/rootfs /
// /var/cache/pacman/pkg /var/cache/pacman/pkg
// /srv/repo/x86_64 /srv/http/x86_64
//
// In this case, all mnt.Subtree are independent. To handle this case, we must
// choose the Mount whose mnt.Path contains the others, i.e. the first one.
@ -199,10 +200,10 @@ func addUncontainedSubtreesRecursive(dst map[string]bool,
// needed to correctly handle bind mounts. For example, in the following case,
// the first Mount should be chosen:
//
// mnt.Subtree mnt.Path
// ----------- --------
// /foo /foo
// /foo/dir /dir
// mnt.Subtree mnt.Path
// ----------- --------
// /foo /foo
// /foo/dir /dir
//
// To solve this, we divide the mounts into non-overlapping trees of mnt.Path.
// Then, we choose one of these trees which contains (exactly or via path

View File

@ -21,9 +21,9 @@
// Package metadata contains all of the on disk structures.
// These structures are defined in metadata.proto. The package also
// contains functions for manipulating these structures, specifically:
// * Reading and Writing the Config file to disk
// * Getting and Setting Policies for directories
// * Reasonable defaults for a Policy's EncryptionOptions
// - Reading and Writing the Config file to disk
// - Getting and Setting Policies for directories
// - Reasonable defaults for a Policy's EncryptionOptions
package metadata
import (

View File

@ -23,7 +23,7 @@
// Code generated by protoc-gen-go. DO NOT EDIT.
// versions:
// protoc-gen-go v1.28.0
// protoc-gen-go v1.33.0
// protoc v3.6.1
// source: metadata/metadata.proto

View File

@ -28,6 +28,7 @@ import (
"os"
"os/user"
"strconv"
"syscall"
"unsafe"
"github.com/pkg/errors"
@ -85,6 +86,15 @@ func (err *ErrDirectoryNotOwned) Error() string {
write access to the directory.`, err.Path, owner)
}
// ErrLockedRegularFile indicates that the path is a locked regular file.
type ErrLockedRegularFile struct {
Path string
}
func (err *ErrLockedRegularFile) Error() string {
return fmt.Sprintf("cannot operate on locked regular file %q", err.Path)
}
// ErrNotEncrypted indicates that the path is not encrypted.
type ErrNotEncrypted struct {
Path string
@ -164,6 +174,9 @@ func buildV2PolicyData(policy *unix.FscryptPolicyV2) *PolicyData {
func GetPolicy(path string) (*PolicyData, error) {
file, err := os.Open(path)
if err != nil {
if err.(*os.PathError).Err == syscall.ENOKEY {
return nil, &ErrLockedRegularFile{path}
}
return nil, err
}
defer file.Close()

View File

@ -18,8 +18,8 @@
*/
// Package security manages:
// - Cache clearing (cache.go)
// - Privilege manipulation (privileges.go)
// - Cache clearing (cache.go)
// - Privilege manipulation (privileges.go)
package security
// Use the libc versions of setreuid, setregid, and setgroups instead of the

12
vendor/modules.txt vendored
View File

@ -62,6 +62,8 @@ github.com/AzureAD/microsoft-authentication-library-for-go/apps/internal/options
github.com/AzureAD/microsoft-authentication-library-for-go/apps/internal/shared
github.com/AzureAD/microsoft-authentication-library-for-go/apps/internal/version
github.com/AzureAD/microsoft-authentication-library-for-go/apps/public
# github.com/BurntSushi/toml v1.3.2
## explicit; go 1.16
# github.com/IBM/keyprotect-go-client v0.12.2
## explicit; go 1.15
github.com/IBM/keyprotect-go-client
@ -224,6 +226,8 @@ github.com/ceph/go-ceph/rbd/admin
# github.com/cespare/xxhash/v2 v2.2.0
## explicit; go 1.11
github.com/cespare/xxhash/v2
# github.com/client9/misspell v0.3.4
## explicit
# github.com/container-storage-interface/spec v1.9.0
## explicit; go 1.18
github.com/container-storage-interface/spec/lib/go/csi
@ -347,8 +351,8 @@ github.com/google/cel-go/interpreter
github.com/google/cel-go/interpreter/functions
github.com/google/cel-go/parser
github.com/google/cel-go/parser/gen
# github.com/google/fscrypt v0.3.4
## explicit; go 1.16
# github.com/google/fscrypt v0.3.6-0.20240502174735-068b9f8f5dec
## explicit; go 1.18
github.com/google/fscrypt/actions
github.com/google/fscrypt/crypto
github.com/google/fscrypt/filesystem
@ -617,6 +621,8 @@ github.com/stoewer/go-strcase
## explicit; go 1.17
github.com/stretchr/testify/assert
github.com/stretchr/testify/require
# github.com/wadey/gocovmerge v0.0.0-20160331181800-b5bfa59ec0ad
## explicit
# go.etcd.io/etcd/api/v3 v3.5.10
## explicit; go 1.20
go.etcd.io/etcd/api/v3/authpb
@ -942,6 +948,8 @@ gopkg.in/yaml.v2
# gopkg.in/yaml.v3 v3.0.1
## explicit
gopkg.in/yaml.v3
# honnef.co/go/tools v0.4.5
## explicit; go 1.19
# k8s.io/api v0.29.3 => k8s.io/api v0.29.3
## explicit; go 1.21
k8s.io/api/admission/v1