diff options
| author | Eric Biggers <ebiggers@google.com> | 2022-02-23 12:35:04 -0800 |
|---|---|---|
| committer | Eric Biggers <ebiggers@google.com> | 2022-02-23 12:35:04 -0800 |
| commit | bd380777d68816b55da85a42d4cdf7fb262b4ba2 (patch) | |
| tree | a53418f4b71b351193fc0a24e2b9cd039b6424df | |
| parent | 1ab74f59b52ec244fee003effa8415c6c4038a54 (diff) | |
Make the output of 'fscrypt status' unambiguous
Following the example of /proc/self/mountinfo, replace the space,
newline, tab, and backslash characters with octal escape sequences so
that the output can be parsed unambiguously.
| -rw-r--r-- | cmd/fscrypt/status.go | 7 | ||||
| -rw-r--r-- | filesystem/mountpoint.go | 15 | ||||
| -rw-r--r-- | filesystem/mountpoint_test.go | 15 |
3 files changed, 35 insertions, 2 deletions
diff --git a/cmd/fscrypt/status.go b/cmd/fscrypt/status.go index 255bb2b..d10dfd8 100644 --- a/cmd/fscrypt/status.go +++ b/cmd/fscrypt/status.go @@ -114,8 +114,11 @@ func writeGlobalStatus(w io.Writer) error { continue } - fmt.Fprintf(t, "%s\t%s\t%s\t%s\t%s\n", mount.Path, mount.Device, - mount.FilesystemType, supportString, yesNoString(usingFscrypt)) + fmt.Fprintf(t, "%s\t%s\t%s\t%s\t%s\n", + filesystem.EscapeString(mount.Path), + filesystem.EscapeString(mount.Device), + filesystem.EscapeString(mount.FilesystemType), + supportString, yesNoString(usingFscrypt)) if supportErr == nil { supportCount++ diff --git a/filesystem/mountpoint.go b/filesystem/mountpoint.go index 182cafa..0b0693b 100644 --- a/filesystem/mountpoint.go +++ b/filesystem/mountpoint.go @@ -77,6 +77,21 @@ func unescapeString(str string) string { return sb.String() } +// EscapeString is the reverse of unescapeString. Use this to avoid injecting +// spaces or newlines into output that uses these characters as separators. +func EscapeString(str string) string { + var sb strings.Builder + for _, b := range []byte(str) { + switch b { + case ' ', '\t', '\n', '\\': + sb.WriteString(fmt.Sprintf("\\%03o", b)) + default: + sb.WriteByte(b) + } + } + return sb.String() +} + // We get the device name via the device number rather than use the mount source // field directly. This is necessary to handle a rootfs that was mounted via // the kernel command line, since mountinfo always shows /dev/root for that. diff --git a/filesystem/mountpoint_test.go b/filesystem/mountpoint_test.go index 749e5e3..99d4b55 100644 --- a/filesystem/mountpoint_test.go +++ b/filesystem/mountpoint_test.go @@ -179,6 +179,21 @@ func TestLoadMountWithSpecialCharacters(t *testing.T) { } } +// Tests the EscapeString() and unescapeString() functions. +func TestStringEscaping(t *testing.T) { + charsNeedEscaping := " \t\n\\" + charsDontNeedEscaping := "ABCDEF\u2603\xff\xff\v" + + orig := charsNeedEscaping + charsDontNeedEscaping + escaped := `\040\011\012\134` + charsDontNeedEscaping + if EscapeString(orig) != escaped { + t.Fatal("EscapeString gave wrong result") + } + if unescapeString(escaped) != orig { + t.Fatal("unescapeString gave wrong result") + } +} + // Test parsing some invalid mountinfo lines. func TestLoadBadMountInfo(t *testing.T) { mountinfos := []string{"a", |