From 3a26f8730c3dfdf203b7cae28bbaf44f482b52bb Mon Sep 17 00:00:00 2001 From: Jay Rauchenstein Date: Fri, 13 Aug 2021 17:57:55 -0700 Subject: [PATCH 1/4] util/log: add configuration option to set log file permissions Previously, all created log files were created with "644" permissions; readable by all, writable by the owner. This change adds a new "file-permissions" key to the file log sink config, defaulting to 644. Fixes #68799. Release note (cli change): Log file read and write permissions may now be set via the new "file-permissions" key in the --log flag or --log-config-file file. Release justification: This change is safe to release because it only adds new configurability which defaults to the existing behavior. --- docs/generated/logsinks.md | 1 + pkg/cli/log_flags_test.go | 56 ++++++++-- pkg/cli/testdata/logflags | 109 +++---------------- pkg/util/log/clog_test.go | 39 +++++++ pkg/util/log/file.go | 9 +- pkg/util/log/file_api.go | 1 + pkg/util/log/file_sync_buffer.go | 2 +- pkg/util/log/flags.go | 15 ++- pkg/util/log/logconfig/config.go | 48 +++++++++ pkg/util/log/logconfig/testdata/validate | 110 -------------------- pkg/util/log/logconfig/testdata/yaml | 51 +++++++++ pkg/util/log/logconfig/validate.go | 9 +- pkg/util/log/logconfig/validate_test.go | 66 +++++++++++- pkg/util/log/logpb/log.pb.go | 127 ++++++++++++++--------- pkg/util/log/logpb/log.proto | 1 + 15 files changed, 365 insertions(+), 279 deletions(-) diff --git a/docs/generated/logsinks.md b/docs/generated/logsinks.md index 5ff83bb851bc..810556af1b8c 100644 --- a/docs/generated/logsinks.md +++ b/docs/generated/logsinks.md @@ -72,6 +72,7 @@ Type-specific configuration options: | `dir` | specifies the output directory for files generated by this sink. Inherited from `file-defaults.dir` if not specified. | | `max-file-size` | the approximate maximum size of individual files generated by this sink. If zero, there is no maximum size. Inherited from `file-defaults.max-file-size` if not specified. | | `max-group-size` | the approximate maximum combined size of all files to be preserved for this sink. An asynchronous garbage collection removes files that cause the file set to grow beyond this specified size. If zero, old files are not removed. Inherited from `file-defaults.max-group-size` if not specified. | +| `file-permissions` | the "chmod-style" permissions the log files are created with as a 3-digit octal number. The executable bit must not be set. Defaults to 644 (readable by all, writable by owner). Inherited from `file-defaults.file-permissions` if not specified. | | `buffered-writes` | specifies whether to buffer log entries. Setting this to false flushes log writes upon every entry. Inherited from `file-defaults.buffered-writes` if not specified. | diff --git a/pkg/cli/log_flags_test.go b/pkg/cli/log_flags_test.go index d4a084adf619..37580e415a96 100644 --- a/pkg/cli/log_flags_test.go +++ b/pkg/cli/log_flags_test.go @@ -39,8 +39,7 @@ func TestSetupLogging(t *testing.T) { `filter: INFO, ` + `format: json-fluent-compact, ` + `redactable: true, ` + - `exit-on-error: false` + - `}` + `exit-on-error: false}` const defaultHTTPConfig = `http-defaults: {` + `method: POST, ` + `unsafe-tls: false, ` + @@ -51,18 +50,58 @@ func TestSetupLogging(t *testing.T) { `redactable: true, ` + `exit-on-error: false}` stdFileDefaultsRe := regexp.MustCompile( - `file-defaults: \{dir: (?P[^,]+), max-file-size: 10MiB, buffered-writes: true, filter: INFO, format: crdb-v2, redactable: true\}`) + `file-defaults: \{` + + `dir: (?P[^,]+), ` + + `max-file-size: 10MiB, ` + + `file-permissions: "0644", ` + + `buffered-writes: true, ` + + `filter: INFO, ` + + `format: crdb-v2, ` + + `redactable: true\}`) fileDefaultsNoMaxSizeRe := regexp.MustCompile( - `file-defaults: \{dir: (?P[^,]+), buffered-writes: true, filter: INFO, format: crdb-v2, redactable: true\}`) - const fileDefaultsNoDir = `file-defaults: {buffered-writes: true, filter: INFO, format: crdb-v2, redactable: true}` + `file-defaults: \{` + + `dir: (?P[^,]+), ` + + `file-permissions: "0644", ` + + `buffered-writes: true, ` + + `filter: INFO, ` + + `format: crdb-v2, ` + + `redactable: true\}`) + const fileDefaultsNoDir = `file-defaults: {` + + `file-permissions: "0644", ` + + `buffered-writes: true, ` + + `filter: INFO, ` + + `format: crdb-v2, ` + + `redactable: true}` const defaultLogDir = `PWD/cockroach-data/logs` stdCaptureFd2Re := regexp.MustCompile( - `capture-stray-errors: \{enable: true, dir: (?P[^}]+)\}`) + `capture-stray-errors: \{` + + `enable: true, ` + + `dir: (?P[^}]+)\}`) fileCfgRe := regexp.MustCompile( - `\{channels: (?Pall|\[[^]]*\]), dir: (?P[^,]+), max-file-size: 10MiB, buffered-writes: (?P[^,]+), filter: INFO, format: (?P[^,]+), redactable: true\}`) + `\{channels: (?Pall|\[[^]]*\]), ` + + `dir: (?P[^,]+), ` + + `max-file-size: 10MiB, ` + + `file-permissions: "0644", ` + + `buffered-writes: (?P[^,]+), ` + + `filter: INFO, ` + + `format: (?P[^,]+), ` + + `redactable: true\}`) + telemetryFileCfgRe := regexp.MustCompile( + `\{channels: \[TELEMETRY\], ` + + `dir: (?P[^,]+), ` + + `max-file-size: 100KiB, ` + + `max-group-size: 1.0MiB, ` + + `file-permissions: "0644", ` + + `buffered-writes: true, ` + + `filter: INFO, ` + + `format: crdb-v2, ` + + `redactable: true\}`) stderrCfgRe := regexp.MustCompile( - `stderr: {channels: all, filter: (?P[^,]+), format: crdb-v2-tty, redactable: (?P[^}]+)}`) + `stderr: {channels: all, ` + + `filter: (?P[^,]+), ` + + `format: crdb-v2-tty, ` + + `redactable: (?P[^}]+)}`) wd, err := os.Getwd() if err != nil { @@ -122,6 +161,7 @@ func TestSetupLogging(t *testing.T) { actual = strings.ReplaceAll(actual, fileDefaultsNoDir, "") actual = stdCaptureFd2Re.ReplaceAllString(actual, "") actual = fileCfgRe.ReplaceAllString(actual, "") + actual = telemetryFileCfgRe.ReplaceAllString(actual, "") actual = stderrCfgRe.ReplaceAllString(actual, "") actual = strings.ReplaceAll(actual, ``, ``) actual = strings.ReplaceAll(actual, ``, ``) diff --git a/pkg/cli/testdata/logflags b/pkg/cli/testdata/logflags index 25f8b285e0b4..c6bd26a25196 100644 --- a/pkg/cli/testdata/logflags +++ b/pkg/cli/testdata/logflags @@ -27,14 +27,7 @@ sql-auth: ,false,crdb-v2)>, sql-exec: ,true,crdb-v2)>, sql-slow: ,true,crdb-v2)>, sql-slow-internal-only: ,true,crdb-v2)>, -telemetry: {channels: [TELEMETRY], -dir: , -max-file-size: 100KiB, -max-group-size: 1.0MiB, -buffered-writes: true, -filter: INFO, -format: crdb-v2, -redactable: true}}, +telemetry: )>}, }, )>} @@ -57,14 +50,7 @@ sql-auth: ,false,crdb-v2)>, sql-exec: ,true,crdb-v2)>, sql-slow: ,true,crdb-v2)>, sql-slow-internal-only: ,true,crdb-v2)>, -telemetry: {channels: [TELEMETRY], -dir: , -max-file-size: 100KiB, -max-group-size: 1.0MiB, -buffered-writes: true, -filter: INFO, -format: crdb-v2, -redactable: true}}, +telemetry: )>}, }, )>} @@ -152,14 +138,7 @@ sql-auth: , sql-exec: , sql-slow: , sql-slow-internal-only: , -telemetry: {channels: [TELEMETRY], -dir: /pathA/logs, -max-file-size: 100KiB, -max-group-size: 1.0MiB, -buffered-writes: true, -filter: INFO, -format: crdb-v2, -redactable: true}}, +telemetry: }, }, } @@ -184,14 +163,7 @@ sql-auth: , sql-exec: , sql-slow: , sql-slow-internal-only: , -telemetry: {channels: [TELEMETRY], -dir: /mypath, -max-file-size: 100KiB, -max-group-size: 1.0MiB, -buffered-writes: true, -filter: INFO, -format: crdb-v2, -redactable: true}}, +telemetry: }, }, } @@ -217,14 +189,7 @@ sql-auth: , sql-exec: , sql-slow: , sql-slow-internal-only: , -telemetry: {channels: [TELEMETRY], -dir: /pathA/logs, -max-file-size: 100KiB, -max-group-size: 1.0MiB, -buffered-writes: true, -filter: INFO, -format: crdb-v2, -redactable: true}}, +telemetry: }, }, } @@ -255,14 +220,7 @@ sql-auth: , sql-exec: , sql-slow: , sql-slow-internal-only: , -telemetry: {channels: [TELEMETRY], -dir: /mypath, -max-file-size: 100KiB, -max-group-size: 1.0MiB, -buffered-writes: true, -filter: INFO, -format: crdb-v2, -redactable: true}}, +telemetry: }, }, } @@ -286,14 +244,7 @@ sql-auth: ,false,crdb-v2)>, sql-exec: ,true,crdb-v2)>, sql-slow: ,true,crdb-v2)>, sql-slow-internal-only: ,true,crdb-v2)>, -telemetry: {channels: [TELEMETRY], -dir: , -max-file-size: 100KiB, -max-group-size: 1.0MiB, -buffered-writes: true, -filter: INFO, -format: crdb-v2, -redactable: true}}, +telemetry: )>}, }, )>} @@ -318,14 +269,7 @@ sql-auth: ,false,crdb-v2)>, sql-exec: ,true,crdb-v2)>, sql-slow: ,true,crdb-v2)>, sql-slow-internal-only: ,true,crdb-v2)>, -telemetry: {channels: [TELEMETRY], -dir: , -max-file-size: 100KiB, -max-group-size: 1.0MiB, -buffered-writes: true, -filter: INFO, -format: crdb-v2, -redactable: true}}, +telemetry: )>}, }} # Logging to stderr without stderr capture causes an error in the default config. @@ -382,14 +326,7 @@ sql-auth: , sql-exec: , sql-slow: , sql-slow-internal-only: , -telemetry: {channels: [TELEMETRY], -dir: /mypath, -max-file-size: 100KiB, -max-group-size: 1.0MiB, -buffered-writes: true, -filter: INFO, -format: crdb-v2, -redactable: true}}, +telemetry: }, }, } @@ -415,14 +352,7 @@ sql-auth: , sql-exec: , sql-slow: , sql-slow-internal-only: , -telemetry: {channels: [TELEMETRY], -dir: /pathA, -max-file-size: 100KiB, -max-group-size: 1.0MiB, -buffered-writes: true, -filter: INFO, -format: crdb-v2, -redactable: true}}, +telemetry: }, }, } @@ -438,6 +368,7 @@ config: {, , sinks: {file-groups: {default: {channels: all, dir: /mypath, +file-permissions: "0644", buffered-writes: true, filter: INFO, format: crdb-v2, @@ -465,14 +396,7 @@ sql-auth: ,false,crdb-v2)>, sql-exec: ,true,crdb-v2)>, sql-slow: ,true,crdb-v2)>, sql-slow-internal-only: ,true,crdb-v2)>, -telemetry: {channels: [TELEMETRY], -dir: , -max-file-size: 100KiB, -max-group-size: 1.0MiB, -buffered-writes: true, -filter: INFO, -format: crdb-v2, -redactable: true}}, +telemetry: )>}, }, )>} @@ -496,14 +420,7 @@ sql-auth: ,false,crdb-v2)>, sql-exec: ,true,crdb-v2)>, sql-slow: ,true,crdb-v2)>, sql-slow-internal-only: ,true,crdb-v2)>, -telemetry: {channels: [TELEMETRY], -dir: , -max-file-size: 100KiB, -max-group-size: 1.0MiB, -buffered-writes: true, -filter: INFO, -format: crdb-v2, -redactable: true}}, +telemetry: )>}, }, )>} diff --git a/pkg/util/log/clog_test.go b/pkg/util/log/clog_test.go index dbcc3c520d42..2c89402c9521 100644 --- a/pkg/util/log/clog_test.go +++ b/pkg/util/log/clog_test.go @@ -310,6 +310,45 @@ func TestListLogFiles(t *testing.T) { } } +func TestFilePermissions(t *testing.T) { + defer leaktest.AfterTest(t)() + defer ScopeWithoutShowLogs(t).Close(t) + + fileMode := os.FileMode(0o400) // not the default 0o644 + + fs := debugLog.getFileSink() + defer func(p os.FileMode) { fs.filePermissions = p }(fs.filePermissions) + fs.filePermissions = fileMode + + Info(context.Background(), "x") + + sb, ok := debugLog.getFileSink().mu.file.(*syncBuffer) + if !ok { + t.Fatalf("buffer wasn't created") + } + + results, err := ListLogFiles() + if err != nil { + t.Fatalf("error in ListLogFiles: %v", err) + } + + expectedName := filepath.Base(sb.file.Name()) + foundExpected := false + for _, r := range results { + if r.Name != expectedName { + continue + } + foundExpected = true + if os.FileMode(r.FileMode) != fileMode { + t.Errorf("Logfile %v has file mode %v, expected %v", + expectedName, os.FileMode(r.FileMode), fileMode) + } + } + if !foundExpected { + t.Fatalf("unexpected results: %q", results) + } +} + func TestGetLogReader(t *testing.T) { defer leaktest.AfterTest(t)() defer ScopeWithoutShowLogs(t).Close(t) diff --git a/pkg/util/log/file.go b/pkg/util/log/file.go index 3bddcbab22b3..4bff86b70dd0 100644 --- a/pkg/util/log/file.go +++ b/pkg/util/log/file.go @@ -16,6 +16,7 @@ package log import ( "context" "fmt" + "io/fs" "math" "os" "os/user" @@ -87,6 +88,8 @@ type fileSink struct { // include at the start of a log file. getStartLines func(time.Time) []*buffer + filePermissions fs.FileMode + // mu protects the remaining elements of this structure and is // used to synchronize output to this file sink.. mu struct { @@ -131,6 +134,7 @@ func newFileSink( bufferedWrites bool, fileMaxSize, combinedMaxSize int64, getStartLines func(time.Time) []*buffer, + filePermissions fs.FileMode, ) *fileSink { prefix := program if fileNamePrefix != "" { @@ -143,6 +147,7 @@ func newFileSink( logFilesCombinedMaxSize: combinedMaxSize, gcNotify: make(chan struct{}, 1), getStartLines: getStartLines, + filePermissions: filePermissions, } f.mu.logDir = dir f.enabled.Set(dir != "") @@ -331,7 +336,7 @@ var errDirectoryNotSet = errors.New("log: log directory not set") // // It is invalid to call this with an unset output directory. func create( - dir, prefix string, t time.Time, lastRotation int64, + dir, prefix string, t time.Time, lastRotation int64, fileMode fs.FileMode, ) (f *os.File, updatedRotation int64, filename, symlink string, err error) { if dir == "" { return nil, lastRotation, "", "", errDirectoryNotSet @@ -352,7 +357,7 @@ func create( fname := filepath.Join(dir, name) // Open the file os.O_APPEND|os.O_CREATE rather than use os.Create. // Append is almost always more efficient than O_RDRW on most modern file systems. - f, err = os.OpenFile(fname, os.O_APPEND|os.O_CREATE|os.O_WRONLY, 0644) + f, err = os.OpenFile(fname, os.O_APPEND|os.O_CREATE|os.O_WRONLY, fileMode) return f, updatedRotation, fname, symlink, errors.Wrapf(err, "log: cannot create output file") } diff --git a/pkg/util/log/file_api.go b/pkg/util/log/file_api.go index a92f66b0e926..4edf86b9e91e 100644 --- a/pkg/util/log/file_api.go +++ b/pkg/util/log/file_api.go @@ -53,6 +53,7 @@ func MakeFileInfo(details logpb.FileDetails, info os.FileInfo) logpb.FileInfo { SizeBytes: info.Size(), ModTimeNanos: info.ModTime().UnixNano(), Details: details, + FileMode: uint32(info.Mode()), } } diff --git a/pkg/util/log/file_sync_buffer.go b/pkg/util/log/file_sync_buffer.go index 0c4024ce5df0..aa61f6c597ee 100644 --- a/pkg/util/log/file_sync_buffer.go +++ b/pkg/util/log/file_sync_buffer.go @@ -160,7 +160,7 @@ func (sb *syncBuffer) rotateFileLocked(now time.Time) (err error) { // continue using the previous file instead of breaking logging // altogether. newFile, newLastRotation, newFileName, symLinkName, err := create( - sb.fileSink.mu.logDir, sb.fileSink.prefix, now, sb.lastRotation) + sb.fileSink.mu.logDir, sb.fileSink.prefix, now, sb.lastRotation, sb.fileSink.filePermissions) if err != nil { return err } diff --git a/pkg/util/log/flags.go b/pkg/util/log/flags.go index 64df56ab4303..386a6045f44f 100644 --- a/pkg/util/log/flags.go +++ b/pkg/util/log/flags.go @@ -13,6 +13,7 @@ package log import ( "context" "fmt" + "io/fs" "math" "strings" @@ -145,6 +146,7 @@ func ApplyConfig(config logconfig.Config) (cleanupFn func(), err error) { bt, bf := true, false mf := logconfig.ByteSize(math.MaxInt64) f := logconfig.DefaultFileFormat + fm := logconfig.FilePermissions(0o644) fakeConfig := logconfig.FileSinkConfig{ FileDefaults: logconfig.FileDefaults{ CommonSinkConfig: logconfig.CommonSinkConfig{ @@ -158,10 +160,11 @@ func ApplyConfig(config logconfig.Config) (cleanupFn func(), err error) { // impression to the entry parser. Redactable: &bf, }, - Dir: config.CaptureFd2.Dir, - MaxGroupSize: config.CaptureFd2.MaxGroupSize, - MaxFileSize: &mf, - BufferedWrites: &bf, + Dir: config.CaptureFd2.Dir, + MaxGroupSize: config.CaptureFd2.MaxGroupSize, + MaxFileSize: &mf, + BufferedWrites: &bf, + FilePermissions: &fm, }, } fileSinkInfo, fileSink, err := newFileSinkInfo("stderr", fakeConfig) @@ -330,7 +333,9 @@ func newFileSinkInfo( *c.BufferedWrites, int64(*c.MaxFileSize), int64(*c.MaxGroupSize), - info.getStartLines) + info.getStartLines, + fs.FileMode(*c.FilePermissions), + ) info.sink = fileSink return info, fileSink, nil } diff --git a/pkg/util/log/logconfig/config.go b/pkg/util/log/logconfig/config.go index 8c9a99717fa2..d488bd67b06f 100644 --- a/pkg/util/log/logconfig/config.go +++ b/pkg/util/log/logconfig/config.go @@ -15,6 +15,7 @@ import ( "net/http" "reflect" "sort" + "strconv" "strings" "time" @@ -330,6 +331,11 @@ type FileDefaults struct { // size. If zero, old files are not removed. MaxGroupSize *ByteSize `yaml:"max-group-size,omitempty"` + // FilePermissions is the "chmod-style" permissions the log files are + // created with as a 3-digit octal number. The executable bit must not + // be set. Defaults to 644 (readable by all, writable by owner). + FilePermissions *FilePermissions `yaml:"file-permissions,omitempty"` + // BufferedWrites specifies whether to buffer log entries. // Setting this to false flushes log writes upon every entry. BufferedWrites *bool `yaml:"buffered-writes,omitempty"` @@ -737,6 +743,48 @@ func (x *ByteSize) UnmarshalYAML(fn func(interface{}) error) error { return nil } +// FilePermissions is a 9-bit number corresponding to the fs.FileMode +// a logfile is created with. It's written and read from the YAML as +// an octal string, regardless of leading zero or "0o" prefix. +type FilePermissions uint + +// IsZero implements the yaml.IsZeroer interface. +func (x FilePermissions) IsZero() bool { return x == 0 } + +// MarshalYAML implements the yaml.Marshaler interface. +func (x FilePermissions) MarshalYAML() (r interface{}, err error) { + return fmt.Sprintf("%04o", x), nil +} + +// UnmarshalYAML implements the yaml.Unmarshaler interface. +func (x *FilePermissions) UnmarshalYAML(fn func(interface{}) error) (err error) { + defer func() { + if err != nil { + err = errors.WithHint(err, "This value should consist of three even digits.") + } + }() + + var in string + if err = fn(&in); err != nil { + return err + } + + in = strings.TrimPrefix(in, "0o") + val, err := strconv.ParseInt(in, 8, 0) + if err != nil { + return errors.Errorf("file-permissions unparsable: %v", in) + } + if val > 0o777 || val < 0 { + return errors.Errorf("file-permissions out-of-range: %v", in) + } + if val&0o111 != 0 { + return errors.Errorf("file-permissions must not be executable: %v", in) + } + + *x = FilePermissions(val) + return nil +} + // String implements the fmt.Stringer interface. func (c *Config) String() string { b, err := yaml.Marshal(c) diff --git a/pkg/util/log/logconfig/testdata/validate b/pkg/util/log/logconfig/testdata/validate index 53c8efc3de31..47e87da8339a 100644 --- a/pkg/util/log/logconfig/testdata/validate +++ b/pkg/util/log/logconfig/testdata/validate @@ -5,22 +5,10 @@ sinks: file-groups: default: channels: all - dir: /default-dir - max-file-size: 10MiB - max-group-size: 100MiB - buffered-writes: true filter: INFO - format: crdb-v2 - redact: false - redactable: true - exit-on-error: true stderr: channels: all filter: NONE - format: crdb-v2-tty - redact: false - redactable: true - exit-on-error: true capture-stray-errors: enable: true dir: /default-dir @@ -37,22 +25,10 @@ sinks: file-groups: custom: channels: all - dir: /default-dir - max-file-size: 10MiB - max-group-size: 100MiB - buffered-writes: true filter: INFO - format: crdb-v2 - redact: false - redactable: true - exit-on-error: true stderr: channels: all filter: NONE - format: crdb-v2-tty - redact: false - redactable: true - exit-on-error: true capture-stray-errors: enable: true dir: /default-dir @@ -72,21 +48,10 @@ sinks: custom: channels: all dir: /custom - max-file-size: 10MiB - max-group-size: 100MiB - buffered-writes: true filter: INFO - format: crdb-v2 - redact: false - redactable: true - exit-on-error: true stderr: channels: all filter: NONE - format: crdb-v2-tty - redact: false - redactable: true - exit-on-error: true capture-stray-errors: enable: true dir: /custom @@ -106,22 +71,10 @@ sinks: file-groups: custom: channels: all - dir: /default-dir - max-file-size: 10MiB - max-group-size: 100MiB - buffered-writes: true filter: WARNING - format: crdb-v2 - redact: false - redactable: true - exit-on-error: true stderr: channels: all filter: NONE - format: crdb-v2-tty - redact: false - redactable: true - exit-on-error: true capture-stray-errors: enable: true dir: /default-dir @@ -139,15 +92,7 @@ sinks: file-groups: default: channels: all - dir: /default-dir - max-file-size: 10MiB - max-group-size: 100MiB - buffered-writes: true filter: INFO - format: crdb-v2 - redact: false - redactable: true - exit-on-error: true fluent-servers: custom: channels: [DEV] @@ -161,10 +106,6 @@ sinks: stderr: channels: all filter: NONE - format: crdb-v2-tty - redact: false - redactable: true - exit-on-error: true capture-stray-errors: enable: true dir: /default-dir @@ -181,22 +122,10 @@ sinks: file-groups: custom: channels: all - dir: /default-dir - max-file-size: 10MiB - max-group-size: 100MiB - buffered-writes: true filter: INFO - format: crdb-v2 - redact: false - redactable: true - exit-on-error: true stderr: channels: all filter: NONE - format: crdb-v2-tty - redact: false - redactable: true - exit-on-error: true capture-stray-errors: enable: true dir: /default-dir @@ -214,22 +143,11 @@ sinks: file-groups: custom: channels: all - dir: /default-dir - max-file-size: 10MiB - max-group-size: 100MiB buffered-writes: false filter: INFO - format: crdb-v2 - redact: false - redactable: true - exit-on-error: true stderr: channels: all filter: NONE - format: crdb-v2-tty - redact: false - redactable: true - exit-on-error: true capture-stray-errors: enable: true dir: /default-dir @@ -248,15 +166,7 @@ sinks: file-groups: default: channels: all - dir: /default-dir - max-file-size: 10MiB - max-group-size: 100MiB - buffered-writes: true filter: INFO - format: crdb-v2 - redact: false - redactable: true - exit-on-error: true fluent-servers: custom: channels: [DEV] @@ -270,10 +180,6 @@ sinks: stderr: channels: all filter: NONE - format: crdb-v2-tty - redact: false - redactable: true - exit-on-error: true capture-stray-errors: enable: true dir: /default-dir @@ -291,22 +197,10 @@ sinks: file-groups: default: channels: all - dir: /default-dir - max-file-size: 10MiB - max-group-size: 100MiB - buffered-writes: true filter: INFO - format: crdb-v2 - redact: false - redactable: true - exit-on-error: true stderr: channels: [DEV] filter: NONE - format: crdb-v2-tty - redact: false - redactable: true - exit-on-error: true capture-stray-errors: enable: true dir: /default-dir @@ -320,10 +214,6 @@ sinks: stderr: channels: all filter: NONE - format: crdb-v2-tty - redact: false - redactable: true - exit-on-error: true capture-stray-errors: enable: true dir: /default-dir diff --git a/pkg/util/log/logconfig/testdata/yaml b/pkg/util/log/logconfig/testdata/yaml index 366462e71eaf..49bd9ec85ac6 100644 --- a/pkg/util/log/logconfig/testdata/yaml +++ b/pkg/util/log/logconfig/testdata/yaml @@ -1,3 +1,5 @@ +### Used in pkg/util/log/logconfig/config_test.go + # Check how the empty config pretty-prints itself. yaml ---- @@ -191,3 +193,52 @@ sinks: channels: DEV,DEV ---- ERROR: duplicate channel name: "DEV" + +# Check that supported permission formats are accepted. +yaml +sinks: + file-groups: + decimal: + file-permissions: 222 + leadingzero: + file-permissions: 0222 + prefix: + file-permissions: 0o222 + quoted: + file-permissions: "0222" +---- +sinks: + file-groups: + decimal: + file-permissions: "0222" + leadingzero: + file-permissions: "0222" + prefix: + file-permissions: "0222" + quoted: + file-permissions: "0222" + +yaml +file-defaults: + file-permissions: foobar +---- +ERROR: file-permissions unparsable: foobar + +yaml +file-defaults: + file-permissions: 02222 +---- +ERROR: file-permissions out-of-range: 02222 + +yaml +file-defaults: + file-permissions: -222 +---- +ERROR: file-permissions out-of-range: -222 + +yaml +file-defaults: + file-permissions: 0454 +---- +ERROR: file-permissions must not be executable: 0454 + diff --git a/pkg/util/log/logconfig/validate.go b/pkg/util/log/logconfig/validate.go index 9721ddd5ebce..02b5a948f724 100644 --- a/pkg/util/log/logconfig/validate.go +++ b/pkg/util/log/logconfig/validate.go @@ -43,10 +43,11 @@ func (c *Config) Validate(defaultLogDir *string) (resErr error) { Criticality: &bf, } baseFileDefaults := FileDefaults{ - Dir: defaultLogDir, - BufferedWrites: &bt, - MaxFileSize: func() *ByteSize { s := ByteSize(0); return &s }(), - MaxGroupSize: func() *ByteSize { s := ByteSize(0); return &s }(), + Dir: defaultLogDir, + BufferedWrites: &bt, + MaxFileSize: func() *ByteSize { s := ByteSize(0); return &s }(), + MaxGroupSize: func() *ByteSize { s := ByteSize(0); return &s }(), + FilePermissions: func() *FilePermissions { s := FilePermissions(0o644); return &s }(), CommonSinkConfig: CommonSinkConfig{ Format: func() *string { s := DefaultFileFormat; return &s }(), Criticality: &bt, diff --git a/pkg/util/log/logconfig/validate_test.go b/pkg/util/log/logconfig/validate_test.go index 5d7c3c518ae2..d76e28fc892a 100644 --- a/pkg/util/log/logconfig/validate_test.go +++ b/pkg/util/log/logconfig/validate_test.go @@ -39,10 +39,7 @@ func TestValidate(t *testing.T) { if err := c.Validate(&defaultDir); err != nil { fmt.Fprintf(&buf, "ERROR: %v\n", err) } else { - // clear the default fields to reduce test over-specification - c.FileDefaults = FileDefaults{} - c.FluentDefaults = FluentDefaults{} - c.HTTPDefaults = HTTPDefaults{} + clearExpectedValues(&c) b, err := yaml.Marshal(&c) if err != nil { @@ -53,3 +50,64 @@ func TestValidate(t *testing.T) { return buf.String() }) } + +// clearExpectedValues clears the various "defaults" fields (because +// at this point we only care that the default values have been +// propagated) and nils out pointers that point to the expect value +// for their field, making the test more concise and future-proof +// without losing information (since if the field was already nil, +// we'd panic dereferencing it, failing the test). New fields with +// defaults can be added here to avoid having to update each test case. +func clearExpectedValues(c *Config) { + // clear the default fields to reduce test over-specification + c.FileDefaults = FileDefaults{} + c.FluentDefaults = FluentDefaults{} + c.HTTPDefaults = HTTPDefaults{} + + for _, f := range c.Sinks.FileGroups { + if *f.Dir == "/default-dir" { + f.Dir = nil + } + if *f.MaxFileSize == ByteSize(10<<20) { + f.MaxFileSize = nil + } + if *f.MaxGroupSize == ByteSize(100<<20) { + f.MaxGroupSize = nil + } + if *f.FilePermissions == FilePermissions(0644) { + f.FilePermissions = nil + } + if *f.BufferedWrites == true { + f.BufferedWrites = nil + } + if *f.Format == "crdb-v2" { + f.Format = nil + } + if *f.Redact == false { + f.Redact = nil + } + if *f.Redactable == true { + f.Redactable = nil + } + if *f.Criticality == true { + f.Criticality = nil + } + } + + // Clear stderr sink defaults + { + s := &c.Sinks.Stderr + if *s.Format == "crdb-v2-tty" { + s.Format = nil + } + if *s.Redact == false { + s.Redact = nil + } + if *s.Redactable == true { + s.Redactable = nil + } + if *s.Criticality == true { + s.Criticality = nil + } + } +} diff --git a/pkg/util/log/logpb/log.pb.go b/pkg/util/log/logpb/log.pb.go index d187db0d47a4..09084a51b7ca 100644 --- a/pkg/util/log/logpb/log.pb.go +++ b/pkg/util/log/logpb/log.pb.go @@ -389,6 +389,7 @@ type FileInfo struct { SizeBytes int64 `protobuf:"varint,2,opt,name=size_bytes,json=sizeBytes,proto3" json:"size_bytes,omitempty"` ModTimeNanos int64 `protobuf:"varint,3,opt,name=mod_time_nanos,json=modTimeNanos,proto3" json:"mod_time_nanos,omitempty"` Details FileDetails `protobuf:"bytes,4,opt,name=details,proto3" json:"details"` + FileMode uint32 `protobuf:"varint,5,opt,name=file_mode,json=fileMode,proto3" json:"file_mode,omitempty"` } func (m *FileInfo) Reset() { *m = FileInfo{} } @@ -431,55 +432,56 @@ func init() { func init() { proto.RegisterFile("util/log/logpb/log.proto", fileDescriptor_84e824ab4ae60f77) } var fileDescriptor_84e824ab4ae60f77 = []byte{ - // 765 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x6c, 0x94, 0xdf, 0x6e, 0xdb, 0x36, - 0x14, 0xc6, 0xad, 0x48, 0xb6, 0xa4, 0xe3, 0x24, 0x63, 0x89, 0x0e, 0xd0, 0xd6, 0x4e, 0x31, 0x82, - 0x0d, 0xf3, 0x72, 0xe1, 0x02, 0x1d, 0x06, 0xec, 0x6e, 0x50, 0x6c, 0x3a, 0xd1, 0xe6, 0xc8, 0x29, - 0xa9, 0xa4, 0xfb, 0x73, 0x21, 0x28, 0x32, 0xeb, 0x08, 0x91, 0xc5, 0x40, 0xa2, 0x07, 0x64, 0xef, - 0x30, 0x60, 0x0f, 0xb1, 0x87, 0xd8, 0x23, 0x04, 0xbb, 0xea, 0x65, 0xaf, 0x8a, 0xcd, 0x79, 0x91, - 0x81, 0xb4, 0xd5, 0x04, 0x58, 0x2e, 0x6c, 0x7c, 0xe7, 0xd3, 0x8f, 0x87, 0x3c, 0x3c, 0x07, 0x04, - 0x6f, 0x29, 0xf3, 0xe2, 0x45, 0x21, 0xe6, 0xea, 0x77, 0x7d, 0xa1, 0xfe, 0x07, 0xd7, 0x95, 0x90, - 0x02, 0xe3, 0x4c, 0x64, 0x57, 0x95, 0x48, 0xb3, 0xcb, 0x81, 0x62, 0x06, 0x85, 0x98, 0x7f, 0xfa, - 0x74, 0x2e, 0xe6, 0x42, 0x7f, 0x7e, 0xa1, 0xd4, 0x9a, 0xdc, 0xff, 0xcb, 0x84, 0x36, 0x29, 0x65, - 0x75, 0x83, 0xbf, 0x05, 0xa7, 0xe6, 0xbf, 0xf2, 0x2a, 0x97, 0x37, 0x9e, 0xd1, 0x33, 0xfa, 0xbb, - 0x2f, 0x9f, 0x0f, 0xfe, 0x9f, 0x66, 0xc0, 0x36, 0x0c, 0xfd, 0x40, 0x63, 0x0c, 0x96, 0xcc, 0x17, - 0xdc, 0xdb, 0xea, 0x19, 0x7d, 0x93, 0x6a, 0x8d, 0x9f, 0x83, 0x3b, 0x17, 0x95, 0x58, 0xca, 0xbc, - 0xe4, 0x5e, 0x47, 0x7f, 0xb8, 0x37, 0xd4, 0x8a, 0x37, 0x79, 0xc1, 0x3d, 0xb3, 0x67, 0xf4, 0x5d, - 0xaa, 0xb5, 0xf2, 0x0a, 0x05, 0x5b, 0xeb, 0x2c, 0x4a, 0x63, 0x0f, 0xec, 0x05, 0xaf, 0xeb, 0x74, - 0xce, 0xbd, 0xb6, 0x46, 0x9b, 0x50, 0xef, 0x99, 0xce, 0x6b, 0xcf, 0x5e, 0x67, 0x50, 0x5a, 0xd1, - 0x99, 0x58, 0x96, 0x92, 0x57, 0x9e, 0xd3, 0x33, 0xfa, 0x16, 0x6d, 0x42, 0xec, 0x03, 0x54, 0x7c, - 0x96, 0x66, 0x32, 0xbd, 0x28, 0xb8, 0xe7, 0xf6, 0x8c, 0xbe, 0x43, 0x1f, 0x38, 0xf8, 0x1b, 0xb0, - 0xb3, 0xcb, 0xb4, 0x2c, 0x79, 0xe1, 0x81, 0x2e, 0xfd, 0xd9, 0x63, 0xa5, 0x0f, 0xd7, 0x08, 0x6d, - 0x58, 0xfc, 0x05, 0xec, 0xd6, 0xb2, 0x5a, 0x66, 0x72, 0x59, 0xf1, 0x59, 0xc2, 0xcb, 0x99, 0xd7, - 0xed, 0x19, 0xfd, 0x1d, 0xba, 0x73, 0xef, 0x92, 0x72, 0x86, 0xbf, 0x02, 0xf4, 0x00, 0xab, 0x65, - 0x5a, 0x49, 0x6f, 0x5b, 0x83, 0x1f, 0xdd, 0xfb, 0x4c, 0xd9, 0xf8, 0x00, 0x9e, 0xd4, 0x32, 0xcd, - 0xae, 0x12, 0x59, 0xa5, 0x19, 0xdf, 0xb0, 0x3b, 0x0d, 0x9b, 0x66, 0x57, 0xb1, 0xf2, 0x35, 0xbb, - 0xff, 0xbb, 0x01, 0xdd, 0x71, 0x5e, 0xf0, 0x11, 0x97, 0x69, 0x5e, 0xe8, 0xf2, 0xaf, 0x2b, 0x31, - 0xaf, 0xd2, 0x85, 0xee, 0x9f, 0x4b, 0x9b, 0x50, 0x5d, 0xd6, 0xa5, 0xa8, 0xa5, 0x6e, 0x90, 0x4b, - 0xb5, 0xc6, 0xcf, 0xc0, 0x5d, 0xd6, 0xbc, 0x4a, 0xca, 0x74, 0xd1, 0xf4, 0xc1, 0x51, 0x46, 0x94, - 0x2e, 0xf8, 0x87, 0x8e, 0xb6, 0x1f, 0x74, 0xf4, 0x13, 0x30, 0xaf, 0xf3, 0xd9, 0xba, 0x97, 0x87, - 0xf6, 0xea, 0xfd, 0x9e, 0x79, 0x1a, 0x8e, 0xa8, 0xf2, 0xbe, 0xb7, 0x1c, 0x0b, 0xb5, 0xf7, 0xff, - 0x34, 0xc0, 0x51, 0xe7, 0x09, 0xcb, 0x37, 0x42, 0x65, 0xd0, 0x99, 0xd7, 0x27, 0xd1, 0x1a, 0x7f, - 0x06, 0x50, 0xe7, 0xbf, 0xf1, 0xe4, 0xe2, 0x46, 0xf2, 0x7a, 0x33, 0x2d, 0xae, 0x72, 0x0e, 0x95, - 0x81, 0x3f, 0x87, 0xdd, 0x85, 0x98, 0x25, 0x6a, 0xb3, 0xa4, 0x4c, 0x4b, 0x51, 0xeb, 0x63, 0x99, - 0x74, 0x7b, 0x21, 0x66, 0x71, 0xbe, 0xe0, 0x91, 0xf2, 0xf0, 0x77, 0x60, 0xcf, 0xd6, 0x05, 0xeb, - 0x49, 0xe9, 0xbe, 0xdc, 0x7b, 0xac, 0x55, 0x0f, 0xee, 0xe5, 0xd0, 0xba, 0x7d, 0xbf, 0xd7, 0xa2, - 0xcd, 0xaa, 0x83, 0x5f, 0xc0, 0x69, 0x66, 0x18, 0x77, 0xc1, 0x3e, 0x8b, 0x7e, 0x88, 0xa6, 0xaf, - 0x23, 0xd4, 0xc2, 0x0e, 0x58, 0x61, 0x34, 0x9e, 0x22, 0x43, 0xd9, 0xaf, 0x03, 0x1a, 0x85, 0xd1, - 0x11, 0xda, 0xc2, 0x2e, 0xb4, 0x09, 0xa5, 0x53, 0x8a, 0x4c, 0x25, 0xc7, 0x41, 0x1c, 0x4c, 0x90, - 0xa5, 0xe0, 0x68, 0x1a, 0x11, 0xd4, 0x56, 0xf0, 0x88, 0x8c, 0x83, 0xb3, 0x49, 0x8c, 0x3a, 0x07, - 0x7f, 0x1b, 0x60, 0x6f, 0xc6, 0x04, 0xdb, 0x60, 0x8e, 0xc8, 0x39, 0x6a, 0x29, 0x31, 0x3d, 0x65, - 0xc8, 0xc0, 0x00, 0x9d, 0x63, 0x12, 0x4c, 0xe2, 0x63, 0xb4, 0xa5, 0x96, 0xb1, 0x78, 0x4a, 0x83, - 0x23, 0x82, 0x4c, 0xbc, 0x0d, 0x0e, 0x23, 0x8c, 0x85, 0xd3, 0x88, 0x21, 0x0b, 0xef, 0x02, 0xb0, - 0x57, 0x93, 0x84, 0x0d, 0x8f, 0xc9, 0x49, 0x80, 0xda, 0x2a, 0x3e, 0x63, 0x84, 0x26, 0xc1, 0xe8, - 0x24, 0x8c, 0x50, 0x47, 0xc5, 0xa7, 0x34, 0x3c, 0x0f, 0x27, 0xe4, 0x88, 0x30, 0x64, 0xe3, 0xa7, - 0x80, 0x18, 0x89, 0x58, 0x18, 0x87, 0xe7, 0x24, 0x09, 0x86, 0x43, 0xc2, 0x18, 0x72, 0x74, 0xce, - 0x57, 0x93, 0x84, 0xfc, 0x48, 0x86, 0xc8, 0x6d, 0xa2, 0x53, 0x42, 0xc7, 0x08, 0xf0, 0xc7, 0xf0, - 0x44, 0x45, 0x61, 0x14, 0x13, 0x1a, 0x05, 0x1b, 0xbb, 0x8b, 0x77, 0xc0, 0x8d, 0xc9, 0x84, 0x9c, - 0x90, 0x98, 0xfe, 0x84, 0xb6, 0x0f, 0xbf, 0xbc, 0xfd, 0xd7, 0x6f, 0xdd, 0xae, 0x7c, 0xe3, 0xed, - 0xca, 0x37, 0xde, 0xad, 0x7c, 0xe3, 0x9f, 0x95, 0x6f, 0xfc, 0x71, 0xe7, 0xb7, 0xde, 0xde, 0xf9, - 0xad, 0x77, 0x77, 0x7e, 0xeb, 0xe7, 0xb6, 0x7e, 0x78, 0x2e, 0x3a, 0xfa, 0x2d, 0xf9, 0xfa, 0xbf, - 0x00, 0x00, 0x00, 0xff, 0xff, 0x8c, 0x9e, 0x4c, 0xb7, 0x91, 0x04, 0x00, 0x00, + // 779 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x6c, 0x94, 0xcf, 0x6f, 0xdb, 0x36, + 0x14, 0xc7, 0xad, 0x4a, 0xb6, 0xa4, 0xe7, 0x38, 0x63, 0x89, 0x0e, 0xd0, 0xd6, 0x4e, 0x31, 0x82, + 0x0d, 0xf3, 0x72, 0x70, 0x81, 0x0e, 0x03, 0x76, 0x1b, 0x14, 0x9b, 0x4e, 0xb4, 0x39, 0x72, 0x4a, + 0x29, 0xe9, 0x7e, 0x1c, 0x04, 0x45, 0x62, 0x1d, 0x21, 0x92, 0x18, 0x48, 0xf4, 0x80, 0xec, 0x7f, + 0x18, 0xb0, 0x3f, 0x67, 0xd7, 0xdd, 0x82, 0x9d, 0x7a, 0xec, 0xa9, 0xd8, 0x9c, 0x7f, 0x64, 0x20, + 0x6d, 0x35, 0x01, 0xd6, 0x83, 0x8d, 0xef, 0xfb, 0xea, 0xc3, 0x47, 0x3e, 0xbe, 0x07, 0x82, 0xb3, + 0x12, 0x79, 0xf1, 0xbc, 0xe0, 0x4b, 0xf9, 0xbb, 0xbe, 0x90, 0xff, 0xe3, 0xeb, 0x9a, 0x0b, 0x8e, + 0x71, 0xca, 0xd3, 0xab, 0x9a, 0x27, 0xe9, 0xe5, 0x58, 0x32, 0xe3, 0x82, 0x2f, 0x3f, 0x7d, 0xb2, + 0xe4, 0x4b, 0xae, 0x3e, 0x3f, 0x97, 0x6a, 0x43, 0xee, 0xff, 0xa9, 0x43, 0x97, 0x54, 0xa2, 0xbe, + 0xc1, 0xdf, 0x82, 0xd5, 0xb0, 0x5f, 0x59, 0x9d, 0x8b, 0x1b, 0x47, 0x1b, 0x6a, 0xa3, 0xdd, 0x17, + 0xcf, 0xc6, 0xff, 0x4f, 0x33, 0x0e, 0xb7, 0x0c, 0x7d, 0x4f, 0x63, 0x0c, 0x86, 0xc8, 0x4b, 0xe6, + 0x3c, 0x1a, 0x6a, 0x23, 0x9d, 0x2a, 0x8d, 0x9f, 0x81, 0xbd, 0xe4, 0x35, 0x5f, 0x89, 0xbc, 0x62, + 0x4e, 0x4f, 0x7d, 0xb8, 0x37, 0xe4, 0x8a, 0xd7, 0x79, 0xc1, 0x1c, 0x7d, 0xa8, 0x8d, 0x6c, 0xaa, + 0xb4, 0xf4, 0x0a, 0x09, 0x1b, 0x9b, 0x2c, 0x52, 0x63, 0x07, 0xcc, 0x92, 0x35, 0x4d, 0xb2, 0x64, + 0x4e, 0x57, 0xa1, 0x6d, 0xa8, 0xf6, 0x4c, 0x96, 0x8d, 0x63, 0x6e, 0x32, 0x48, 0x2d, 0xe9, 0x94, + 0xaf, 0x2a, 0xc1, 0x6a, 0xc7, 0x1a, 0x6a, 0x23, 0x83, 0xb6, 0x21, 0x76, 0x01, 0x6a, 0x96, 0x25, + 0xa9, 0x48, 0x2e, 0x0a, 0xe6, 0xd8, 0x43, 0x6d, 0x64, 0xd1, 0x07, 0x0e, 0xfe, 0x06, 0xcc, 0xf4, + 0x32, 0xa9, 0x2a, 0x56, 0x38, 0xa0, 0x4a, 0x7f, 0xfa, 0xa1, 0xd2, 0x27, 0x1b, 0x84, 0xb6, 0x2c, + 0xfe, 0x02, 0x76, 0x1b, 0x51, 0xaf, 0x52, 0xb1, 0xaa, 0x59, 0x16, 0xb3, 0x2a, 0x73, 0xfa, 0x43, + 0x6d, 0x34, 0xa0, 0x83, 0x7b, 0x97, 0x54, 0x19, 0xfe, 0x0a, 0xd0, 0x03, 0xac, 0x11, 0x49, 0x2d, + 0x9c, 0x1d, 0x05, 0x7e, 0x74, 0xef, 0x87, 0xd2, 0xc6, 0x07, 0xf0, 0xb8, 0x11, 0x49, 0x7a, 0x15, + 0x8b, 0x3a, 0x49, 0xd9, 0x96, 0x1d, 0xb4, 0x6c, 0x92, 0x5e, 0x45, 0xd2, 0x57, 0xec, 0xfe, 0xef, + 0x1a, 0xf4, 0x67, 0x79, 0xc1, 0xa6, 0x4c, 0x24, 0x79, 0xa1, 0xca, 0xbf, 0xae, 0xf9, 0xb2, 0x4e, + 0x4a, 0xd5, 0x3f, 0x9b, 0xb6, 0xa1, 0xbc, 0xac, 0x4b, 0xde, 0x08, 0xd5, 0x20, 0x9b, 0x2a, 0x8d, + 0x9f, 0x82, 0xbd, 0x6a, 0x58, 0x1d, 0x57, 0x49, 0xd9, 0xf6, 0xc1, 0x92, 0x46, 0x90, 0x94, 0xec, + 0x7d, 0x47, 0xbb, 0x0f, 0x3a, 0xfa, 0x09, 0xe8, 0xd7, 0x79, 0xb6, 0xe9, 0xe5, 0xa1, 0xb9, 0x7e, + 0xb7, 0xa7, 0x9f, 0xfa, 0x53, 0x2a, 0xbd, 0xef, 0x0d, 0xcb, 0x40, 0xdd, 0xfd, 0xbf, 0x34, 0xb0, + 0xe4, 0x79, 0xfc, 0xea, 0x35, 0x97, 0x19, 0x54, 0xe6, 0xcd, 0x49, 0x94, 0xc6, 0x9f, 0x01, 0x34, + 0xf9, 0x6f, 0x2c, 0xbe, 0xb8, 0x11, 0xac, 0xd9, 0x4e, 0x8b, 0x2d, 0x9d, 0x43, 0x69, 0xe0, 0xcf, + 0x61, 0xb7, 0xe4, 0x59, 0x2c, 0x37, 0x8b, 0xab, 0xa4, 0xe2, 0x8d, 0x3a, 0x96, 0x4e, 0x77, 0x4a, + 0x9e, 0x45, 0x79, 0xc9, 0x02, 0xe9, 0xe1, 0xef, 0xc0, 0xcc, 0x36, 0x05, 0xab, 0x49, 0xe9, 0xbf, + 0xd8, 0xfb, 0x50, 0xab, 0x1e, 0xdc, 0xcb, 0xa1, 0x71, 0xfb, 0x6e, 0xaf, 0x43, 0xdb, 0x55, 0xb2, + 0x70, 0x39, 0x6f, 0x71, 0xc9, 0xb3, 0x4d, 0x81, 0x03, 0x6a, 0x49, 0xe3, 0x84, 0x67, 0xec, 0xe0, + 0x17, 0xb0, 0xda, 0x01, 0xc7, 0x7d, 0x30, 0xcf, 0x82, 0x1f, 0x82, 0xc5, 0xab, 0x00, 0x75, 0xb0, + 0x05, 0x86, 0x1f, 0xcc, 0x16, 0x48, 0x93, 0xf6, 0x2b, 0x8f, 0x06, 0x7e, 0x70, 0x84, 0x1e, 0x61, + 0x1b, 0xba, 0x84, 0xd2, 0x05, 0x45, 0xba, 0x94, 0x33, 0x2f, 0xf2, 0xe6, 0xc8, 0x90, 0x70, 0xb0, + 0x08, 0x08, 0xea, 0x4a, 0x78, 0x4a, 0x66, 0xde, 0xd9, 0x3c, 0x42, 0xbd, 0x83, 0xbf, 0x35, 0x30, + 0xb7, 0x33, 0x84, 0x4d, 0xd0, 0xa7, 0xe4, 0x1c, 0x75, 0xa4, 0x58, 0x9c, 0x86, 0x48, 0xc3, 0x00, + 0xbd, 0x63, 0xe2, 0xcd, 0xa3, 0x63, 0xf4, 0x48, 0x2e, 0x0b, 0xa3, 0x05, 0xf5, 0x8e, 0x08, 0xd2, + 0xf1, 0x0e, 0x58, 0x21, 0x09, 0x43, 0x7f, 0x11, 0x84, 0xc8, 0xc0, 0xbb, 0x00, 0xe1, 0xcb, 0x79, + 0x1c, 0x4e, 0x8e, 0xc9, 0x89, 0x87, 0xba, 0x32, 0x3e, 0x0b, 0x09, 0x8d, 0xbd, 0xe9, 0x89, 0x1f, + 0xa0, 0x9e, 0x8c, 0x4f, 0xa9, 0x7f, 0xee, 0xcf, 0xc9, 0x11, 0x09, 0x91, 0x89, 0x9f, 0x00, 0x0a, + 0x49, 0x10, 0xfa, 0x91, 0x7f, 0x4e, 0x62, 0x6f, 0x32, 0x21, 0x61, 0x88, 0x2c, 0x95, 0xf3, 0xe5, + 0x3c, 0x26, 0x3f, 0x92, 0x09, 0xb2, 0xdb, 0xe8, 0x94, 0xd0, 0x19, 0x02, 0xfc, 0x31, 0x3c, 0x96, + 0x91, 0x1f, 0x44, 0x84, 0x06, 0xde, 0xd6, 0xee, 0xe3, 0x01, 0xd8, 0x11, 0x99, 0x93, 0x13, 0x12, + 0xd1, 0x9f, 0xd0, 0xce, 0xe1, 0x97, 0xb7, 0xff, 0xba, 0x9d, 0xdb, 0xb5, 0xab, 0xbd, 0x59, 0xbb, + 0xda, 0xdb, 0xb5, 0xab, 0xfd, 0xb3, 0x76, 0xb5, 0x3f, 0xee, 0xdc, 0xce, 0x9b, 0x3b, 0xb7, 0xf3, + 0xf6, 0xce, 0xed, 0xfc, 0xdc, 0x55, 0xaf, 0xd2, 0x45, 0x4f, 0x3d, 0x34, 0x5f, 0xff, 0x17, 0x00, + 0x00, 0xff, 0xff, 0x5e, 0x9b, 0x00, 0x53, 0xae, 0x04, 0x00, 0x00, } func (m *Entry) Marshal() (dAtA []byte, err error) { @@ -655,6 +657,11 @@ func (m *FileInfo) MarshalToSizedBuffer(dAtA []byte) (int, error) { _ = i var l int _ = l + if m.FileMode != 0 { + i = encodeVarintLog(dAtA, i, uint64(m.FileMode)) + i-- + dAtA[i] = 0x28 + } { size, err := m.Details.MarshalToSizedBuffer(dAtA[:i]) if err != nil { @@ -792,6 +799,9 @@ func (m *FileInfo) Size() (n int) { } l = m.Details.Size() n += 1 + l + sovLog(uint64(l)) + if m.FileMode != 0 { + n += 1 + sovLog(uint64(m.FileMode)) + } return n } @@ -1454,6 +1464,25 @@ func (m *FileInfo) Unmarshal(dAtA []byte) error { return err } iNdEx = postIndex + case 5: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field FileMode", wireType) + } + m.FileMode = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowLog + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.FileMode |= uint32(b&0x7F) << shift + if b < 0x80 { + break + } + } default: iNdEx = preIndex skippy, err := skipLog(dAtA[iNdEx:]) diff --git a/pkg/util/log/logpb/log.proto b/pkg/util/log/logpb/log.proto index a60dec7dcdff..6664d83a4dcf 100644 --- a/pkg/util/log/logpb/log.proto +++ b/pkg/util/log/logpb/log.proto @@ -270,4 +270,5 @@ message FileInfo { int64 size_bytes = 2; int64 mod_time_nanos = 3; FileDetails details = 4 [(gogoproto.nullable) = false]; + uint32 file_mode = 5; } From 1e3a9a6258576f17798ed638367dc5cd39f77a94 Mon Sep 17 00:00:00 2001 From: Tobias Grieger Date: Sat, 28 Aug 2021 17:25:09 +0200 Subject: [PATCH 2/4] roachtest: allow non-interactive roachstress.sh This allows using `roachstress.sh` for fully autonomous `git bisect runs`, such as ``` git bisect run /bin/bash -c \ 'TEST=splits/load/uniform/nodes=3 LOCAL=y COUNT=1 SHORT=y ./pkg/cmd/roachtest/roachstress.sh' ```` which was helpful in https://github.com/cockroachdb/cockroach/issues/69411. Release justification: testing only change Release note: None --- pkg/cmd/roachtest/roachstress.sh | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/pkg/cmd/roachtest/roachstress.sh b/pkg/cmd/roachtest/roachstress.sh index 0538caadaf4a..59725ea263a9 100755 --- a/pkg/cmd/roachtest/roachstress.sh +++ b/pkg/cmd/roachtest/roachstress.sh @@ -12,9 +12,9 @@ set -euo pipefail # Read user input. -read -r -e -i "${TEST-}" -p "Test regexp: " TEST -read -r -e -i "${COUNT-10}" -p "Count: " COUNT -read -r -e -i "${LOCAL-n}" -p "Local: " LOCAL +if [ -z "${TEST-}" ]; then read -r -e -p "Test regexp: " TEST; fi +if [ -z "${COUNT-}" ]; then read -r -e -i "10" -p "Count: " COUNT; fi +if [ -z "${LOCAL-}" ]; then read -r -e -i "n" -p "Local: " LOCAL; fi case $LOCAL in [Nn]* | false | "") LOCAL="";; *) LOCAL=".local";; @@ -50,8 +50,8 @@ a="${abase}/$(date '+%H%M%S')" short="short" if [ ! -f "${cr}" ]; then - yn="" - read -r -e -i "${SHORT-y}" -p "Build cockroach without the UI: " yn + yn="${SHORT-}" + if [ -z "${yn}" ]; then read -r -e -i "y" -p "Build cockroach without the UI: " yn; fi case $yn in [Nn]* | false | "") short="" esac From 37e36d42b5ae3382325bf8f3c8a7346d0eb91754 Mon Sep 17 00:00:00 2001 From: Tobias Grieger Date: Mon, 30 Aug 2021 14:50:30 +0200 Subject: [PATCH 3/4] roachtest: fix buglet in roachstress.sh If we switch between local and non-local mode, the workload binary may need to be rebuilt (unlike the roachtest binary, which is "always local"). We failed to do this properly since the caching was triggered by the existence of the `roachtest` binary. Release justification: testing-only change Release note: None --- pkg/cmd/roachtest/roachstress.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pkg/cmd/roachtest/roachstress.sh b/pkg/cmd/roachtest/roachstress.sh index 59725ea263a9..3f52d40ccae5 100755 --- a/pkg/cmd/roachtest/roachstress.sh +++ b/pkg/cmd/roachtest/roachstress.sh @@ -69,7 +69,7 @@ if [ ! -f "${cr}" ]; then fi fi -if [ ! -f "${rt}" ]; then +if [ ! -f "${wl}" ]; then if [ -z "${LOCAL}" ]; then ./build/builder.sh mkrelease amd64-linux-gnu bin/workload cp bin.docker_amd64/workload "${wl}" From 92016b959ce8a5528c9cb5dc538213e4588c30b8 Mon Sep 17 00:00:00 2001 From: Tobias Grieger Date: Mon, 30 Aug 2021 16:17:17 +0200 Subject: [PATCH 4/4] roachtest: use ! -v instead of -z in roachstress.sh As suggested by Erik. Release justification: testing-only change Release note: None --- pkg/cmd/roachtest/roachstress.sh | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/pkg/cmd/roachtest/roachstress.sh b/pkg/cmd/roachtest/roachstress.sh index 3f52d40ccae5..f113ce9a297b 100755 --- a/pkg/cmd/roachtest/roachstress.sh +++ b/pkg/cmd/roachtest/roachstress.sh @@ -12,9 +12,9 @@ set -euo pipefail # Read user input. -if [ -z "${TEST-}" ]; then read -r -e -p "Test regexp: " TEST; fi -if [ -z "${COUNT-}" ]; then read -r -e -i "10" -p "Count: " COUNT; fi -if [ -z "${LOCAL-}" ]; then read -r -e -i "n" -p "Local: " LOCAL; fi +if [ ! -v TEST ]; then read -r -e -p "Test regexp: " TEST; fi +if [ ! -v COUNT ]; then read -r -e -i "10" -p "Count: " COUNT; fi +if [ ! -v LOCAL ]; then read -r -e -i "n" -p "Local: " LOCAL; fi case $LOCAL in [Nn]* | false | "") LOCAL="";; *) LOCAL=".local";;