Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add dev, opt, and srv linters #697

Merged
merged 1 commit into from
Sep 19, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
60 changes: 45 additions & 15 deletions pkg/build/linter.go
Original file line number Diff line number Diff line change
Expand Up @@ -36,36 +36,34 @@ type linter struct {
}

var linterMap = map[string]linter{
"dev": linter{devLinter, "If this package is creating /dev nodes, it should use udev instead; otherwise, remove any files in /dev"},
"opt": linter{optLinter, "This package should be a -compat package"},
"setuidgid": linter{isSetUidOrGidLinter, "Unset the setuid/setgid bit on the relevant files, or remove this linter"},
"srv": linter{srvLinter, "This package should be a -compat package"},
"tempdir": linter{tempDirLinter, "Remove any offending files in temporary dirs in the pipeline"},
"usrlocal": linter{usrLocalLinter, "This package should be a -compat package"},
"varempty": linter{varEmptyLinter, "Remove any offending files in /var/empty in the pipeline"},
}

var isDevRegex = regexp.MustCompile("^dev/")
var isOptRegex = regexp.MustCompile("^opt/")
var isSrvRegex = regexp.MustCompile("^srv/")
var isTempDirRegex = regexp.MustCompile("^(var/)?(tmp|run)/")
var isUsrLocalRegex = regexp.MustCompile("^usr/local/")
var isVarEmptyRegex = regexp.MustCompile("^var/empty/")
var isTempDirRegex = regexp.MustCompile("^(var/)?(tmp|run)/")
var isCompatPackage = regexp.MustCompile("-compat$")

func usrLocalLinter(_ LinterContext, path string, _ fs.DirEntry) error {
if isUsrLocalRegex.MatchString(path) {
return fmt.Errorf("/usr/local path found in non-compat package")
func devLinter(_ LinterContext, path string, _ fs.DirEntry) error {
if isDevRegex.MatchString(path) {
return fmt.Errorf("Package writes to /dev")
}

return nil
}

func varEmptyLinter(_ LinterContext, path string, _ fs.DirEntry) error {
if isVarEmptyRegex.MatchString(path) {
return fmt.Errorf("Package writes to /var/empty")
}

return nil
}

func tempDirLinter(_ LinterContext, path string, _ fs.DirEntry) error {
if isTempDirRegex.MatchString(path) {
return fmt.Errorf("Package writes to a temp dir")
func optLinter(_ LinterContext, path string, _ fs.DirEntry) error {
if isOptRegex.MatchString(path) {
return fmt.Errorf("Package writes to /opt")
}

return nil
Expand All @@ -87,6 +85,38 @@ func isSetUidOrGidLinter(_ LinterContext, _ string, d fs.DirEntry) error {
return nil
}

func srvLinter(_ LinterContext, path string, _ fs.DirEntry) error {
if isSrvRegex.MatchString(path) {
return fmt.Errorf("Package writes to /srv")
}

return nil
}

func tempDirLinter(_ LinterContext, path string, _ fs.DirEntry) error {
if isTempDirRegex.MatchString(path) {
return fmt.Errorf("Package writes to a temp dir")
}

return nil
}

func usrLocalLinter(_ LinterContext, path string, _ fs.DirEntry) error {
if isUsrLocalRegex.MatchString(path) {
return fmt.Errorf("/usr/local path found in non-compat package")
}

return nil
}

func varEmptyLinter(_ LinterContext, path string, _ fs.DirEntry) error {
if isVarEmptyRegex.MatchString(path) {
return fmt.Errorf("Package writes to /var/empty")
}

return nil
}

func lintPackageFs(lctx LinterContext, fsys fs.FS, linters []string) error {
// If this is a compat package, do nothing.
if isCompatPackage.MatchString(lctx.pkgname) {
Expand Down
98 changes: 94 additions & 4 deletions pkg/build/linter_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ func Test_usrLocalLinter(t *testing.T) {
Epoch: 0,
Checks: config.Checks{
Enabled: []string{"usrlocal"},
Disabled: []string{"setuidgid", "tempdir", "varempty"},
Disabled: []string{"dev", "opt", "setuidgid", "srv", "tempdir", "varempty"},
},
},
}
Expand Down Expand Up @@ -66,7 +66,7 @@ func Test_varEmptyLinter(t *testing.T) {
Epoch: 0,
Checks: config.Checks{
Enabled: []string{"varempty"},
Disabled: []string{"setuidgid", "tempdir", "usrlocal"},
Disabled: []string{"dev", "opt", "setuidgid", "srv", "tempdir", "usrlocal"},
},
},
}
Expand All @@ -84,6 +84,96 @@ func Test_varEmptyLinter(t *testing.T) {
assert.Error(t, lintPackageFs(lctx, fsys, linters))
}

func Test_devLinter(t *testing.T) {
dir, err := os.MkdirTemp("", "melange.XXXXX")
defer os.RemoveAll(dir)
assert.NoError(t, err)

cfg := config.Configuration{
Package: config.Package{
Name: "test",
Version: "4.2.0",
Epoch: 0,
Checks: config.Checks{
Enabled: []string{"dev"},
Disabled: []string{"opt", "setuidgid", "srv", "tempdir", "usrlocal", "varempty"},
},
},
}

pathdir := filepath.Join(dir, "dev")
err = os.MkdirAll(pathdir, 0700)
assert.NoError(t, err)
_, err = os.Create(filepath.Join(pathdir, "test.txt"))
assert.NoError(t, err)

linters := cfg.Package.Checks.GetLinters()
assert.Equal(t, linters, []string{"dev"})
fsys := os.DirFS(dir)
lctx := LinterContext{cfg.Package.Name, &cfg, &cfg.Package.Checks}
assert.Error(t, lintPackageFs(lctx, fsys, linters))
}

func Test_optLinter(t *testing.T) {
dir, err := os.MkdirTemp("", "melange.XXXXX")
defer os.RemoveAll(dir)
assert.NoError(t, err)

cfg := config.Configuration{
Package: config.Package{
Name: "test",
Version: "4.2.0",
Epoch: 0,
Checks: config.Checks{
Enabled: []string{"opt"},
Disabled: []string{"dev", "setuidgid", "srv", "tempdir", "usrlocal", "varempty"},
},
},
}

pathdir := filepath.Join(dir, "opt")
err = os.MkdirAll(pathdir, 0700)
assert.NoError(t, err)
_, err = os.Create(filepath.Join(pathdir, "test.txt"))
assert.NoError(t, err)

linters := cfg.Package.Checks.GetLinters()
assert.Equal(t, linters, []string{"opt"})
fsys := os.DirFS(dir)
lctx := LinterContext{cfg.Package.Name, &cfg, &cfg.Package.Checks}
assert.Error(t, lintPackageFs(lctx, fsys, linters))
}

func Test_srvLinter(t *testing.T) {
dir, err := os.MkdirTemp("", "melange.XXXXX")
defer os.RemoveAll(dir)
assert.NoError(t, err)

cfg := config.Configuration{
Package: config.Package{
Name: "test",
Version: "4.2.0",
Epoch: 0,
Checks: config.Checks{
Enabled: []string{"srv"},
Disabled: []string{"dev", "opt", "setuidgid", "tempdir", "usrlocal", "varempty"},
},
},
}

pathdir := filepath.Join(dir, "srv")
err = os.MkdirAll(pathdir, 0700)
assert.NoError(t, err)
_, err = os.Create(filepath.Join(pathdir, "test.txt"))
assert.NoError(t, err)

linters := cfg.Package.Checks.GetLinters()
assert.Equal(t, linters, []string{"srv"})
fsys := os.DirFS(dir)
lctx := LinterContext{cfg.Package.Name, &cfg, &cfg.Package.Checks}
assert.Error(t, lintPackageFs(lctx, fsys, linters))
}

func Test_tempDirLinter(t *testing.T) {
dir, err := os.MkdirTemp("", "melange.XXXXX")
defer os.RemoveAll(dir)
Expand All @@ -96,7 +186,7 @@ func Test_tempDirLinter(t *testing.T) {
Epoch: 0,
Checks: config.Checks{
Enabled: []string{"tempdir"},
Disabled: []string{"setuidgid", "usrlocal", "varempty"},
Disabled: []string{"dev", "opt", "setuidgid", "srv", "usrlocal", "varempty"},
},
},
}
Expand Down Expand Up @@ -157,7 +247,7 @@ func Test_setUidGidLinter(t *testing.T) {
Epoch: 0,
Checks: config.Checks{
Enabled: []string{"setuidgid"},
Disabled: []string{"tempdir", "usrlocal", "varempty"},
Disabled: []string{"dev", "opt", "srv", "tempdir", "usrlocal", "varempty"},
},
},
}
Expand Down
3 changes: 3 additions & 0 deletions pkg/config/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -338,6 +338,9 @@ func (cfg Configuration) Name() string {
}

var defaultLinters = []string{
"dev",
"opt",
"srv",
"setuidgid",
"tempdir",
"usrlocal",
Expand Down
Loading